Move to refcounted implementation of collators.

This commit is contained in:
Andrei Zmievski 2006-04-20 21:56:43 +00:00
parent 54ff84d3d5
commit 16c55fb25a
8 changed files with 76 additions and 23 deletions

View File

@ -1227,15 +1227,17 @@ ZEND_API char *get_zend_version()
ZEND_API void zend_reset_locale_deps(TSRMLS_D)
{
UCollator *coll;
UErrorCode status = U_ZERO_ERROR;
if (UG(default_collator)) {
ucol_close(UG(default_collator));
zend_collator_destroy(UG(default_collator));
}
UG(default_collator) = ucol_open(UG(default_locale), &status);
coll = ucol_open(UG(default_locale), &status);
if (U_FAILURE(status)) {
zend_error(E_ERROR, "Could not open collator for locale %s", UG(default_locale));
}
UG(default_collator) = zend_collator_create(coll);
}
static void init_unicode_request_globals(TSRMLS_D)
@ -1248,7 +1250,7 @@ static void init_unicode_request_globals(TSRMLS_D)
static void shutdown_unicode_request_globals(TSRMLS_D)
{
ucol_close(UG(default_collator));
zend_collator_destroy(UG(default_collator));
efree(UG(default_locale));
}

View File

@ -307,9 +307,9 @@ struct _zend_unicode_globals {
uint16_t to_error_mode;
char *default_locale;
UCollator *default_collator;
zend_collator *default_collator;
HashTable flex_compatible;
HashTable flex_compatible; /* table of flex-compatible encodings */
};
#endif /* ZEND_GLOBALS_H */

View File

@ -1443,7 +1443,7 @@ ZEND_API int string_locale_compare_function(zval *result, zval *op1, zval *op2 T
op2 = &op2_copy;
}
Z_LVAL_P(result) = ucol_strcoll(UG(default_collator), Z_USTRVAL_P(op1), Z_USTRLEN_P(op1), Z_USTRVAL_P(op2), Z_USTRLEN_P(op2));
Z_LVAL_P(result) = ucol_strcoll(UG(default_collator)->coll, Z_USTRVAL_P(op1), Z_USTRLEN_P(op1), Z_USTRVAL_P(op2), Z_USTRLEN_P(op2));
Z_TYPE_P(result) = IS_LONG;
if (use_copy1) {

View File

@ -677,6 +677,27 @@ void zend_register_unicode_exceptions(TSRMLS_D)
}
/* }}} */
zend_collator* zend_collator_create(UCollator *coll)
{
zend_collator *zcoll = NULL;
zcoll = emalloc(sizeof(zend_collator));
zcoll->coll = coll;
zcoll->refcount = 1;
return zcoll;
}
void zend_collator_destroy(zend_collator *zcoll)
{
zcoll->refcount--;
if (zcoll->refcount == 0) {
ucol_close(zcoll->coll);
efree(zcoll);
}
}
/*
* Local variables:
* tab-width: 4

View File

@ -48,6 +48,12 @@ typedef enum {
} zend_conv_direction;
typedef struct _zend_collator {
UCollator *coll;
int refcount;
} zend_collator;
extern ZEND_API zend_class_entry *unicodeConversionException;
@ -58,6 +64,8 @@ void zend_set_converter_error_mode(UConverter *conv, zend_conv_direction dir, ui
void zend_set_converter_subst_char(UConverter *conv, UChar *subst_char);
void zend_register_unicode_exceptions(TSRMLS_D);
void zend_update_converters_error_behavior(TSRMLS_D);
zend_collator* zend_collator_create(UCollator *coll);
void zend_collator_destroy(zend_collator *zcoll);
/* API functions */

View File

@ -42,8 +42,8 @@ static zend_object_handlers unicode_object_handlers_collator;
typedef struct _php_collator_obj php_collator_obj;
struct _php_collator_obj {
zend_object std;
UCollator *col;
zend_object std;
zend_collator *zcoll;
};
#define COLLATOR_SET_CONTEXT \
@ -140,8 +140,8 @@ static void collator_object_free_storage(void *object TSRMLS_DC)
{
php_collator_obj *intern = (php_collator_obj *)object;
if (intern->col) {
ucol_close(intern->col);
if (intern->zcoll) {
zend_collator_destroy(intern->zcoll);
}
if (intern->std.properties) {
@ -178,10 +178,11 @@ PHP_METHOD(collator, __construct)
PHP_FUNCTION(collator_create)
{
php_collator_obj *collatorobj;
UErrorCode error;
UErrorCode status = U_ZERO_ERROR;
char *collator_name;
int collator_name_len;
zval *object;
UCollator *ucoll;
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &collator_name, &collator_name_len) == FAILURE) {
RETURN_FALSE;
@ -192,8 +193,13 @@ PHP_FUNCTION(collator_create)
}
collator_instantiate(unicode_ce_collator, object TSRMLS_CC);
collatorobj = (php_collator_obj *) zend_object_store_get_object(object TSRMLS_CC);
error = U_ZERO_ERROR;
collatorobj->col = ucol_open(collator_name, &error);
ucoll = ucol_open(collator_name, &status);
if (U_FAILURE(status)) {
/* UTODO handle error case properly */
zend_error(E_ERROR, "Could not open collator for locale %s", UG(default_locale));
return;
}
collatorobj->zcoll = zend_collator_create(ucoll);
}
PHP_FUNCTION(collator_compare)
@ -207,7 +213,7 @@ PHP_FUNCTION(collator_compare)
RETURN_FALSE;
}
collatorobj = (php_collator_obj *) zend_object_store_get_object(object TSRMLS_CC);
RETURN_LONG(ucol_strcoll(collatorobj->col, string1, string1_len, string2, string2_len));
RETURN_LONG(ucol_strcoll(collatorobj->zcoll->coll, string1, string1_len, string2, string2_len));
}
PHP_FUNCTION(collator_sort)
@ -216,7 +222,7 @@ PHP_FUNCTION(collator_sort)
php_collator_obj *collatorobj;
zval *array;
HashTable *target_hash;
UCollator *orig_collator;
zend_collator *orig_collator;
if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Oa/", &object, unicode_ce_collator, &array) == FAILURE) {
RETURN_FALSE;
@ -226,7 +232,7 @@ PHP_FUNCTION(collator_sort)
target_hash = HASH_OF(array);
php_set_compare_func(SORT_LOCALE_STRING TSRMLS_CC);
orig_collator = UG(default_collator);
UG(default_collator) = collatorobj->col;
UG(default_collator) = collatorobj->zcoll;
if (zend_hash_sort(target_hash, zend_qsort, php_array_data_compare, 1 TSRMLS_CC) == FAILURE) {
RETVAL_FALSE;
} else {
@ -245,7 +251,7 @@ PHP_FUNCTION(collator_set_strength)
RETURN_FALSE;
}
collatorobj = (php_collator_obj *) zend_object_store_get_object(object TSRMLS_CC);
ucol_setStrength(collatorobj->col, strength);
ucol_setStrength(collatorobj->zcoll->coll, strength);
}
PHP_FUNCTION(collator_get_strength)
@ -257,7 +263,7 @@ PHP_FUNCTION(collator_get_strength)
RETURN_FALSE;
}
collatorobj = (php_collator_obj *) zend_object_store_get_object(object TSRMLS_CC);
RETURN_LONG(ucol_getStrength(collatorobj->col));
RETURN_LONG(ucol_getStrength(collatorobj->zcoll->coll));
}
PHP_FUNCTION(collator_set_attribute)
@ -272,7 +278,7 @@ PHP_FUNCTION(collator_set_attribute)
}
collatorobj = (php_collator_obj *) zend_object_store_get_object(object TSRMLS_CC);
error = U_ZERO_ERROR;
ucol_setAttribute(collatorobj->col, attribute, value, &error);
ucol_setAttribute(collatorobj->zcoll->coll, attribute, value, &error);
RETURN_BOOL(error == U_ZERO_ERROR ? 1 : 0);
}
@ -288,9 +294,26 @@ PHP_FUNCTION(collator_get_attribute)
}
collatorobj = (php_collator_obj *) zend_object_store_get_object(object TSRMLS_CC);
error = U_ZERO_ERROR;
value = ucol_getAttribute(collatorobj->col, attribute, &error);
value = ucol_getAttribute(collatorobj->zcoll->coll, attribute, &error);
if (error != U_ZERO_ERROR) {
RETURN_FALSE;
}
RETURN_LONG(value);
}
PHP_FUNCTION(i18n_coll_get_default)
{
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "") == FAILURE) {
return;
}
}
/*
* Local variables:
* tab-width: 4
* c-basic-offset: 4
* End:
* vim600: noet sw=4 ts=4 fdm=marker
* vim<600: noet sw=4 ts=4
*/

View File

@ -57,6 +57,7 @@ PHP_MINFO_FUNCTION(unicode);
PHP_FUNCTION(i18n_loc_get_default);
PHP_FUNCTION(i18n_loc_set_default);
PHP_FUNCTION(i18n_coll_get_default);
PHP_FUNCTION(collator_create);
PHP_FUNCTION(collator_compare);
PHP_FUNCTION(collator_sort);

View File

@ -18,7 +18,6 @@
/* $Id$ */
#include "php_unicode.h"
#if HAVE_UNICODE
#include "zend_unicode.h"
void php_register_unicode_iterators(TSRMLS_D);
@ -236,6 +235,7 @@ PHP_FUNCTION(unicode_get_subst_char)
zend_function_entry unicode_functions[] = {
PHP_FE(i18n_loc_get_default, NULL)
PHP_FE(i18n_loc_set_default, NULL)
PHP_FE(i18n_coll_get_default, NULL)
PHP_FE(unicode_decode, NULL)
PHP_FE(unicode_semantics, NULL)
PHP_FE(unicode_encode, NULL)
@ -318,8 +318,6 @@ PHP_MINFO_FUNCTION(unicode)
/* }}} */
#endif /* HAVE_UNICODE */
/*
* Local variables: