mirror of
https://github.com/php/php-src.git
synced 2024-09-22 10:27:25 +00:00
Merge remote branch 'upstream/master' into hash_password
Conflicts: ext/standard/crypt.c
This commit is contained in:
commit
9e18e578f0
2
NEWS
2
NEWS
@ -12,6 +12,8 @@ PHP NEWS
|
||||
(Nikita Popov)
|
||||
|
||||
- Core:
|
||||
. Fixed bug #62443 (Crypt SHA256/512 Segfaults With Malformed
|
||||
Salt). (Anthony Ferrara)
|
||||
. Added boolval(). (Jille Timmermans).
|
||||
. Fixed bug #61681 (Malformed grammar). (Nikita Popov, Etienne, Laruence).
|
||||
. Fixed bug #61038 (unpack("a5", "str\0\0") does not work as expected).
|
||||
|
@ -188,6 +188,9 @@ PHP X.Y UPGRADE NOTES
|
||||
- IntlCalendar
|
||||
- IntlGregorianCalendar
|
||||
- IntlTimeZone
|
||||
- IntlBreakIterator
|
||||
- IntlRuleBasedBreakIterator
|
||||
- IntlCodePointBreakIterator
|
||||
|
||||
========================================
|
||||
7. Removed Extensions
|
||||
|
@ -1206,7 +1206,7 @@ static YYSIZE_T zend_yytnamerr(char *yyres, const char *yystr)
|
||||
|
||||
if (LANG_SCNG(yy_text)[0] == 0 &&
|
||||
LANG_SCNG(yy_leng) == 1 &&
|
||||
memcmp(yystr, ZEND_STRL("\"end of file\"")) == 0) {
|
||||
memcmp(yystr, "\"end of file\"", sizeof("\"end of file\"") - 1) == 0) {
|
||||
yystpcpy(yyres, "end of file");
|
||||
return sizeof("end of file")-1;
|
||||
}
|
||||
|
397
ext/intl/breakiterator/breakiterator_class.cpp
Normal file
397
ext/intl/breakiterator/breakiterator_class.cpp
Normal file
@ -0,0 +1,397 @@
|
||||
/*
|
||||
+----------------------------------------------------------------------+
|
||||
| PHP Version 5 |
|
||||
+----------------------------------------------------------------------+
|
||||
| This source file is subject to version 3.01 of the PHP license, |
|
||||
| that is bundled with this package in the file LICENSE, and is |
|
||||
| available through the world-wide-web at the following url: |
|
||||
| http://www.php.net/license/3_01.txt |
|
||||
| If you did not receive a copy of the PHP license and are unable to |
|
||||
| obtain it through the world-wide-web, please send a note to |
|
||||
| license@php.net so we can mail you a copy immediately. |
|
||||
+----------------------------------------------------------------------+
|
||||
| Authors: Gustavo Lopes <cataphract@php.net> |
|
||||
+----------------------------------------------------------------------+
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
#include "config.h"
|
||||
#endif
|
||||
|
||||
#include <unicode/brkiter.h>
|
||||
#include <unicode/rbbi.h>
|
||||
#include "codepointiterator_internal.h"
|
||||
|
||||
#include "breakiterator_iterators.h"
|
||||
|
||||
#include <typeinfo>
|
||||
|
||||
extern "C" {
|
||||
#define USE_BREAKITERATOR_POINTER 1
|
||||
#include "breakiterator_class.h"
|
||||
#include "breakiterator_methods.h"
|
||||
#include "rulebasedbreakiterator_methods.h"
|
||||
#include "codepointiterator_methods.h"
|
||||
#include <zend_exceptions.h>
|
||||
#include <zend_interfaces.h>
|
||||
#include <assert.h>
|
||||
}
|
||||
|
||||
using PHP::CodePointBreakIterator;
|
||||
|
||||
/* {{{ Global variables */
|
||||
zend_class_entry *BreakIterator_ce_ptr;
|
||||
zend_class_entry *RuleBasedBreakIterator_ce_ptr;
|
||||
zend_class_entry *CodePointBreakIterator_ce_ptr;
|
||||
zend_object_handlers BreakIterator_handlers;
|
||||
/* }}} */
|
||||
|
||||
U_CFUNC void breakiterator_object_create(zval *object,
|
||||
BreakIterator *biter TSRMLS_DC)
|
||||
{
|
||||
UClassID classId = biter->getDynamicClassID();
|
||||
zend_class_entry *ce;
|
||||
|
||||
if (classId == RuleBasedBreakIterator::getStaticClassID()) {
|
||||
ce = RuleBasedBreakIterator_ce_ptr;
|
||||
} else if (classId == CodePointBreakIterator::getStaticClassID()) {
|
||||
ce = CodePointBreakIterator_ce_ptr;
|
||||
} else {
|
||||
ce = BreakIterator_ce_ptr;
|
||||
}
|
||||
|
||||
object_init_ex(object, ce);
|
||||
breakiterator_object_construct(object, biter TSRMLS_CC);
|
||||
}
|
||||
|
||||
U_CFUNC void breakiterator_object_construct(zval *object,
|
||||
BreakIterator *biter TSRMLS_DC)
|
||||
{
|
||||
BreakIterator_object *bio;
|
||||
|
||||
BREAKITER_METHOD_FETCH_OBJECT_NO_CHECK; //populate to from object
|
||||
assert(bio->biter == NULL);
|
||||
bio->biter = biter;
|
||||
}
|
||||
|
||||
/* {{{ compare handler for BreakIterator */
|
||||
static int BreakIterator_compare_objects(zval *object1,
|
||||
zval *object2 TSRMLS_DC)
|
||||
{
|
||||
BreakIterator_object *bio1,
|
||||
*bio2;
|
||||
|
||||
bio1 = (BreakIterator_object*)zend_object_store_get_object(object1 TSRMLS_CC);
|
||||
bio2 = (BreakIterator_object*)zend_object_store_get_object(object2 TSRMLS_CC);
|
||||
|
||||
if (bio1->biter == NULL || bio2->biter == NULL) {
|
||||
return bio1->biter == bio2->biter ? 0 : 1;
|
||||
}
|
||||
|
||||
return *bio1->biter == *bio2->biter ? 0 : 1;
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
/* {{{ clone handler for BreakIterator */
|
||||
static zend_object_value BreakIterator_clone_obj(zval *object TSRMLS_DC)
|
||||
{
|
||||
BreakIterator_object *bio_orig,
|
||||
*bio_new;
|
||||
zend_object_value ret_val;
|
||||
|
||||
bio_orig = (BreakIterator_object*)zend_object_store_get_object(object TSRMLS_CC);
|
||||
intl_errors_reset(INTL_DATA_ERROR_P(bio_orig) TSRMLS_CC);
|
||||
|
||||
ret_val = BreakIterator_ce_ptr->create_object(Z_OBJCE_P(object) TSRMLS_CC);
|
||||
bio_new = (BreakIterator_object*)zend_object_store_get_object_by_handle(
|
||||
ret_val.handle TSRMLS_CC);
|
||||
|
||||
zend_objects_clone_members(&bio_new->zo, ret_val,
|
||||
&bio_orig->zo, Z_OBJ_HANDLE_P(object) TSRMLS_CC);
|
||||
|
||||
if (bio_orig->biter != NULL) {
|
||||
BreakIterator *new_biter;
|
||||
|
||||
new_biter = bio_orig->biter->clone();
|
||||
if (!new_biter) {
|
||||
char *err_msg;
|
||||
intl_errors_set_code(BREAKITER_ERROR_P(bio_orig),
|
||||
U_MEMORY_ALLOCATION_ERROR TSRMLS_CC);
|
||||
intl_errors_set_custom_msg(BREAKITER_ERROR_P(bio_orig),
|
||||
"Could not clone BreakIterator", 0 TSRMLS_CC);
|
||||
err_msg = intl_error_get_message(BREAKITER_ERROR_P(bio_orig) TSRMLS_CC);
|
||||
zend_throw_exception(NULL, err_msg, 0 TSRMLS_CC);
|
||||
efree(err_msg);
|
||||
} else {
|
||||
bio_new->biter = new_biter;
|
||||
bio_new->text = bio_orig->text;
|
||||
if (bio_new->text) {
|
||||
zval_add_ref(&bio_new->text);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
zend_throw_exception(NULL, "Cannot clone unconstructed BreakIterator", 0 TSRMLS_CC);
|
||||
}
|
||||
|
||||
return ret_val;
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
/* {{{ get_debug_info handler for BreakIterator */
|
||||
static HashTable *BreakIterator_get_debug_info(zval *object, int *is_temp TSRMLS_DC)
|
||||
{
|
||||
zval zv = zval_used_for_init;
|
||||
BreakIterator_object *bio;
|
||||
const BreakIterator *biter;
|
||||
|
||||
*is_temp = 1;
|
||||
|
||||
array_init_size(&zv, 8);
|
||||
|
||||
bio = (BreakIterator_object*)zend_object_store_get_object(object TSRMLS_CC);
|
||||
biter = bio->biter;
|
||||
|
||||
if (biter == NULL) {
|
||||
add_assoc_bool_ex(&zv, "valid", sizeof("valid"), 0);
|
||||
return Z_ARRVAL(zv);
|
||||
}
|
||||
add_assoc_bool_ex(&zv, "valid", sizeof("valid"), 1);
|
||||
|
||||
if (bio->text == NULL) {
|
||||
add_assoc_null_ex(&zv, "text", sizeof("text"));
|
||||
} else {
|
||||
zval_add_ref(&bio->text);
|
||||
add_assoc_zval_ex(&zv, "text", sizeof("text"), bio->text);
|
||||
}
|
||||
|
||||
add_assoc_string_ex(&zv, "type", sizeof("type"),
|
||||
const_cast<char*>(typeid(*biter).name()), 1);
|
||||
|
||||
return Z_ARRVAL(zv);
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
/* {{{ void breakiterator_object_init(BreakIterator_object* to)
|
||||
* Initialize internals of BreakIterator_object not specific to zend standard objects.
|
||||
*/
|
||||
static void breakiterator_object_init(BreakIterator_object *bio TSRMLS_DC)
|
||||
{
|
||||
intl_error_init(BREAKITER_ERROR_P(bio) TSRMLS_CC);
|
||||
bio->biter = NULL;
|
||||
bio->text = NULL;
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
/* {{{ BreakIterator_objects_dtor */
|
||||
static void BreakIterator_objects_dtor(void *object,
|
||||
zend_object_handle handle TSRMLS_DC)
|
||||
{
|
||||
zend_objects_destroy_object((zend_object*)object, handle TSRMLS_CC);
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
/* {{{ BreakIterator_objects_free */
|
||||
static void BreakIterator_objects_free(zend_object *object TSRMLS_DC)
|
||||
{
|
||||
BreakIterator_object* bio = (BreakIterator_object*) object;
|
||||
|
||||
if (bio->text) {
|
||||
zval_ptr_dtor(&bio->text);
|
||||
}
|
||||
if (bio->biter) {
|
||||
delete bio->biter;
|
||||
bio->biter = NULL;
|
||||
}
|
||||
intl_error_reset(BREAKITER_ERROR_P(bio) TSRMLS_CC);
|
||||
|
||||
zend_object_std_dtor(&bio->zo TSRMLS_CC);
|
||||
|
||||
efree(bio);
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
/* {{{ BreakIterator_object_create */
|
||||
static zend_object_value BreakIterator_object_create(zend_class_entry *ce TSRMLS_DC)
|
||||
{
|
||||
zend_object_value retval;
|
||||
BreakIterator_object* intern;
|
||||
|
||||
intern = (BreakIterator_object*)ecalloc(1, sizeof(BreakIterator_object));
|
||||
|
||||
zend_object_std_init(&intern->zo, ce TSRMLS_CC);
|
||||
#if PHP_VERSION_ID < 50399
|
||||
zend_hash_copy(intern->zo.properties, &(ce->default_properties),
|
||||
(copy_ctor_func_t) zval_add_ref, NULL, sizeof(zval*));
|
||||
#else
|
||||
object_properties_init((zend_object*) intern, ce);
|
||||
#endif
|
||||
breakiterator_object_init(intern TSRMLS_CC);
|
||||
|
||||
retval.handle = zend_objects_store_put(
|
||||
intern,
|
||||
BreakIterator_objects_dtor,
|
||||
(zend_objects_free_object_storage_t) BreakIterator_objects_free,
|
||||
NULL TSRMLS_CC);
|
||||
|
||||
retval.handlers = &BreakIterator_handlers;
|
||||
|
||||
return retval;
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
/* {{{ BreakIterator/RuleBasedBreakIterator methods arguments info */
|
||||
|
||||
ZEND_BEGIN_ARG_INFO_EX(ainfo_biter_void, 0, 0, 0)
|
||||
ZEND_END_ARG_INFO()
|
||||
|
||||
ZEND_BEGIN_ARG_INFO_EX(ainfo_biter_locale, 0, 0, 0)
|
||||
ZEND_ARG_INFO(0, "locale")
|
||||
ZEND_END_ARG_INFO()
|
||||
|
||||
ZEND_BEGIN_ARG_INFO_EX(ainfo_biter_setText, 0, 0, 1)
|
||||
ZEND_ARG_INFO(0, "text")
|
||||
ZEND_END_ARG_INFO()
|
||||
|
||||
ZEND_BEGIN_ARG_INFO_EX(ainfo_biter_next, 0, 0, 0)
|
||||
ZEND_ARG_INFO(0, "offset")
|
||||
ZEND_END_ARG_INFO()
|
||||
|
||||
ZEND_BEGIN_ARG_INFO_EX(ainfo_biter_offset, 0, 0, 1)
|
||||
ZEND_ARG_INFO(0, "offset")
|
||||
ZEND_END_ARG_INFO()
|
||||
|
||||
ZEND_BEGIN_ARG_INFO_EX(ainfo_biter_get_locale, 0, 0, 1)
|
||||
ZEND_ARG_INFO(0, "locale_type")
|
||||
ZEND_END_ARG_INFO()
|
||||
|
||||
ZEND_BEGIN_ARG_INFO_EX(ainfo_biter_getPartsIterator, 0, 0, 0)
|
||||
ZEND_ARG_INFO(0, "key_type")
|
||||
ZEND_END_ARG_INFO()
|
||||
|
||||
ZEND_BEGIN_ARG_INFO_EX(ainfo_rbbi___construct, 0, 0, 1)
|
||||
ZEND_ARG_INFO(0, "rules")
|
||||
ZEND_ARG_INFO(0, "areCompiled")
|
||||
ZEND_END_ARG_INFO()
|
||||
|
||||
/* }}} */
|
||||
|
||||
/* {{{ BreakIterator_class_functions
|
||||
* Every 'BreakIterator' class method has an entry in this table
|
||||
*/
|
||||
static const zend_function_entry BreakIterator_class_functions[] = {
|
||||
PHP_ME(BreakIterator, __construct, ainfo_biter_void, ZEND_ACC_PRIVATE)
|
||||
PHP_ME_MAPPING(createWordInstance, breakiter_create_word_instance, ainfo_biter_locale, ZEND_ACC_STATIC | ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(createLineInstance, breakiter_create_line_instance, ainfo_biter_locale, ZEND_ACC_STATIC | ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(createCharacterInstance, breakiter_create_character_instance, ainfo_biter_locale, ZEND_ACC_STATIC | ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(createSentenceInstance, breakiter_create_sentence_instance, ainfo_biter_locale, ZEND_ACC_STATIC | ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(createTitleInstance, breakiter_create_title_instance, ainfo_biter_locale, ZEND_ACC_STATIC | ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(createCodePointInstance, breakiter_create_code_point_instance, ainfo_biter_void, ZEND_ACC_STATIC | ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(getText, breakiter_get_text, ainfo_biter_void, ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(setText, breakiter_set_text, ainfo_biter_setText, ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(first, breakiter_first, ainfo_biter_void, ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(last, breakiter_last, ainfo_biter_void, ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(previous, breakiter_previous, ainfo_biter_void, ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(next, breakiter_next, ainfo_biter_next, ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(current, breakiter_current, ainfo_biter_void, ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(following, breakiter_following, ainfo_biter_offset, ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(preceding, breakiter_preceding, ainfo_biter_offset, ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(isBoundary, breakiter_is_boundary, ainfo_biter_offset, ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(getLocale, breakiter_get_locale, ainfo_biter_void, ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(getPartsIterator, breakiter_get_parts_iterator, ainfo_biter_getPartsIterator, ZEND_ACC_PUBLIC)
|
||||
|
||||
PHP_ME_MAPPING(getErrorCode, breakiter_get_error_code, ainfo_biter_void, ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(getErrorMessage, breakiter_get_error_message, ainfo_biter_void, ZEND_ACC_PUBLIC)
|
||||
PHP_FE_END
|
||||
};
|
||||
/* }}} */
|
||||
|
||||
/* {{{ RuleBasedBreakIterator_class_functions
|
||||
*/
|
||||
static const zend_function_entry RuleBasedBreakIterator_class_functions[] = {
|
||||
PHP_ME(IntlRuleBasedBreakIterator, __construct, ainfo_rbbi___construct, ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(getRules, rbbi_get_rules, ainfo_biter_void, ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(getRuleStatus, rbbi_get_rule_status, ainfo_biter_void, ZEND_ACC_PUBLIC)
|
||||
PHP_ME_MAPPING(getRuleStatusVec, rbbi_get_rule_status_vec, ainfo_biter_void, ZEND_ACC_PUBLIC)
|
||||
#if U_ICU_VERSION_MAJOR_NUM * 10 + U_ICU_VERSION_MINOR_NUM >= 48
|
||||
PHP_ME_MAPPING(getBinaryRules, rbbi_get_binary_rules, ainfo_biter_void, ZEND_ACC_PUBLIC)
|
||||
#endif
|
||||
PHP_FE_END
|
||||
};
|
||||
/* }}} */
|
||||
|
||||
/* {{{ CodePointBreakIterator_class_functions
|
||||
*/
|
||||
static const zend_function_entry CodePointBreakIterator_class_functions[] = {
|
||||
PHP_ME_MAPPING(getLastCodePoint, cpbi_get_last_code_point, ainfo_biter_void, ZEND_ACC_PUBLIC)
|
||||
PHP_FE_END
|
||||
};
|
||||
/* }}} */
|
||||
|
||||
|
||||
/* {{{ breakiterator_register_BreakIterator_class
|
||||
* Initialize 'BreakIterator' class
|
||||
*/
|
||||
U_CFUNC void breakiterator_register_BreakIterator_class(TSRMLS_D)
|
||||
{
|
||||
zend_class_entry ce;
|
||||
|
||||
/* Create and register 'BreakIterator' class. */
|
||||
INIT_CLASS_ENTRY(ce, "IntlBreakIterator", BreakIterator_class_functions);
|
||||
ce.create_object = BreakIterator_object_create;
|
||||
ce.get_iterator = _breakiterator_get_iterator;
|
||||
BreakIterator_ce_ptr = zend_register_internal_class(&ce TSRMLS_CC);
|
||||
|
||||
memcpy(&BreakIterator_handlers, zend_get_std_object_handlers(),
|
||||
sizeof BreakIterator_handlers);
|
||||
BreakIterator_handlers.compare_objects = BreakIterator_compare_objects;
|
||||
BreakIterator_handlers.clone_obj = BreakIterator_clone_obj;
|
||||
BreakIterator_handlers.get_debug_info = BreakIterator_get_debug_info;
|
||||
|
||||
zend_class_implements(BreakIterator_ce_ptr TSRMLS_CC, 1,
|
||||
zend_ce_traversable);
|
||||
|
||||
zend_declare_class_constant_long(BreakIterator_ce_ptr,
|
||||
"DONE", sizeof("DONE") - 1, BreakIterator::DONE TSRMLS_CC );
|
||||
|
||||
/* Declare constants that are defined in the C header */
|
||||
#define BREAKITER_DECL_LONG_CONST(name) \
|
||||
zend_declare_class_constant_long(BreakIterator_ce_ptr, #name, \
|
||||
sizeof(#name) - 1, UBRK_ ## name TSRMLS_CC)
|
||||
|
||||
BREAKITER_DECL_LONG_CONST(WORD_NONE);
|
||||
BREAKITER_DECL_LONG_CONST(WORD_NONE_LIMIT);
|
||||
BREAKITER_DECL_LONG_CONST(WORD_NUMBER);
|
||||
BREAKITER_DECL_LONG_CONST(WORD_NUMBER_LIMIT);
|
||||
BREAKITER_DECL_LONG_CONST(WORD_LETTER);
|
||||
BREAKITER_DECL_LONG_CONST(WORD_LETTER_LIMIT);
|
||||
BREAKITER_DECL_LONG_CONST(WORD_KANA);
|
||||
BREAKITER_DECL_LONG_CONST(WORD_KANA_LIMIT);
|
||||
BREAKITER_DECL_LONG_CONST(WORD_IDEO);
|
||||
BREAKITER_DECL_LONG_CONST(WORD_IDEO_LIMIT);
|
||||
|
||||
BREAKITER_DECL_LONG_CONST(LINE_SOFT);
|
||||
BREAKITER_DECL_LONG_CONST(LINE_SOFT_LIMIT);
|
||||
BREAKITER_DECL_LONG_CONST(LINE_HARD);
|
||||
BREAKITER_DECL_LONG_CONST(LINE_HARD_LIMIT);
|
||||
|
||||
BREAKITER_DECL_LONG_CONST(SENTENCE_TERM);
|
||||
BREAKITER_DECL_LONG_CONST(SENTENCE_TERM_LIMIT);
|
||||
BREAKITER_DECL_LONG_CONST(SENTENCE_SEP);
|
||||
BREAKITER_DECL_LONG_CONST(SENTENCE_SEP_LIMIT);
|
||||
|
||||
#undef BREAKITER_DECL_LONG_CONST
|
||||
|
||||
|
||||
/* Create and register 'RuleBasedBreakIterator' class. */
|
||||
INIT_CLASS_ENTRY(ce, "IntlRuleBasedBreakIterator",
|
||||
RuleBasedBreakIterator_class_functions);
|
||||
RuleBasedBreakIterator_ce_ptr = zend_register_internal_class_ex(&ce,
|
||||
BreakIterator_ce_ptr, NULL TSRMLS_CC);
|
||||
|
||||
/* Create and register 'CodePointBreakIterator' class. */
|
||||
INIT_CLASS_ENTRY(ce, "IntlCodePointBreakIterator",
|
||||
CodePointBreakIterator_class_functions);
|
||||
CodePointBreakIterator_ce_ptr = zend_register_internal_class_ex(&ce,
|
||||
BreakIterator_ce_ptr, NULL TSRMLS_CC);
|
||||
}
|
||||
/* }}} */
|
71
ext/intl/breakiterator/breakiterator_class.h
Normal file
71
ext/intl/breakiterator/breakiterator_class.h
Normal file
@ -0,0 +1,71 @@
|
||||
/*
|
||||
+----------------------------------------------------------------------+
|
||||
| PHP Version 5 |
|
||||
+----------------------------------------------------------------------+
|
||||
| This source file is subject to version 3.01 of the PHP license, |
|
||||
| that is bundled with this package in the file LICENSE, and is |
|
||||
| available through the world-wide-web at the following url: |
|
||||
| http://www.php.net/license/3_01.txt |
|
||||
| If you did not receive a copy of the PHP license and are unable to |
|
||||
| obtain it through the world-wide-web, please send a note to |
|
||||
| license@php.net so we can mail you a copy immediately. |
|
||||
+----------------------------------------------------------------------+
|
||||
| Authors: Gustavo Lopes <cataphract@php.net> |
|
||||
+----------------------------------------------------------------------+
|
||||
*/
|
||||
|
||||
#ifndef BREAKITERATOR_CLASS_H
|
||||
#define BREAKITERATOR_CLASS_H
|
||||
|
||||
//redefinition of inline in PHP headers causes problems, so include this before
|
||||
#include <math.h>
|
||||
|
||||
#include <php.h>
|
||||
#include "../intl_error.h"
|
||||
#include "../intl_data.h"
|
||||
|
||||
#ifndef USE_BREAKITERATOR_POINTER
|
||||
typedef void BreakIterator;
|
||||
#endif
|
||||
|
||||
typedef struct {
|
||||
zend_object zo;
|
||||
|
||||
// error handling
|
||||
intl_error err;
|
||||
|
||||
// ICU break iterator
|
||||
BreakIterator* biter;
|
||||
|
||||
// current text
|
||||
zval *text;
|
||||
} BreakIterator_object;
|
||||
|
||||
#define BREAKITER_ERROR(bio) (bio)->err
|
||||
#define BREAKITER_ERROR_P(bio) &(BREAKITER_ERROR(bio))
|
||||
|
||||
#define BREAKITER_ERROR_CODE(bio) INTL_ERROR_CODE(BREAKITER_ERROR(bio))
|
||||
#define BREAKITER_ERROR_CODE_P(bio) &(INTL_ERROR_CODE(BREAKITER_ERROR(bio)))
|
||||
|
||||
#define BREAKITER_METHOD_INIT_VARS INTL_METHOD_INIT_VARS(BreakIterator, bio)
|
||||
#define BREAKITER_METHOD_FETCH_OBJECT_NO_CHECK INTL_METHOD_FETCH_OBJECT(BreakIterator, bio)
|
||||
#define BREAKITER_METHOD_FETCH_OBJECT \
|
||||
BREAKITER_METHOD_FETCH_OBJECT_NO_CHECK; \
|
||||
if (bio->biter == NULL) \
|
||||
{ \
|
||||
intl_errors_set(&bio->err, U_ILLEGAL_ARGUMENT_ERROR, "Found unconstructed BreakIterator", 0 TSRMLS_CC); \
|
||||
RETURN_FALSE; \
|
||||
}
|
||||
|
||||
void breakiterator_object_create(zval *object, BreakIterator *break_iter TSRMLS_DC);
|
||||
|
||||
void breakiterator_object_construct(zval *object, BreakIterator *break_iter TSRMLS_DC);
|
||||
|
||||
void breakiterator_register_BreakIterator_class(TSRMLS_D);
|
||||
|
||||
extern zend_class_entry *BreakIterator_ce_ptr,
|
||||
*RuleBasedBreakIterator_ce_ptr;
|
||||
|
||||
extern zend_object_handlers BreakIterator_handlers;
|
||||
|
||||
#endif /* #ifndef BREAKITERATOR_CLASS_H */
|
346
ext/intl/breakiterator/breakiterator_iterators.cpp
Normal file
346
ext/intl/breakiterator/breakiterator_iterators.cpp
Normal file
@ -0,0 +1,346 @@
|
||||
/*
|
||||
+----------------------------------------------------------------------+
|
||||
| PHP Version 5 |
|
||||
+----------------------------------------------------------------------+
|
||||
| This source file is subject to version 3.01 of the PHP license, |
|
||||
| that is bundled with this package in the file LICENSE, and is |
|
||||
| available through the world-wide-web at the following url: |
|
||||
| http://www.php.net/license/3_01.txt |
|
||||
| If you did not receive a copy of the PHP license and are unable to |
|
||||
| obtain it through the world-wide-web, please send a note to |
|
||||
| license@php.net so we can mail you a copy immediately. |
|
||||
+----------------------------------------------------------------------+
|
||||
| Authors: Gustavo Lopes <cataphract@php.net> |
|
||||
+----------------------------------------------------------------------+
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
#include "config.h"
|
||||
#endif
|
||||
|
||||
#include <unicode/brkiter.h>
|
||||
|
||||
#include "breakiterator_iterators.h"
|
||||
#include "../common/common_enum.h"
|
||||
|
||||
extern "C" {
|
||||
#define USE_BREAKITERATOR_POINTER
|
||||
#include "breakiterator_class.h"
|
||||
#include "../intl_convert.h"
|
||||
#include "../locale/locale.h"
|
||||
#include <zend_exceptions.h>
|
||||
}
|
||||
|
||||
static zend_class_entry *IntlPartsIterator_ce_ptr;
|
||||
static zend_object_handlers IntlPartsIterator_handlers;
|
||||
|
||||
/* BreakIterator's iterator */
|
||||
|
||||
inline BreakIterator *_breakiter_prolog(zend_object_iterator *iter TSRMLS_DC)
|
||||
{
|
||||
BreakIterator_object *bio;
|
||||
bio = (BreakIterator_object*)zend_object_store_get_object(
|
||||
(const zval*)iter->data TSRMLS_CC);
|
||||
intl_errors_reset(BREAKITER_ERROR_P(bio) TSRMLS_CC);
|
||||
if (bio->biter == NULL) {
|
||||
intl_errors_set(BREAKITER_ERROR_P(bio), U_INVALID_STATE_ERROR,
|
||||
"The BreakIterator object backing the PHP iterator is not "
|
||||
"properly constructed", 0 TSRMLS_CC);
|
||||
}
|
||||
return bio->biter;
|
||||
}
|
||||
|
||||
static void _breakiterator_destroy_it(zend_object_iterator *iter TSRMLS_DC)
|
||||
{
|
||||
zval_ptr_dtor((zval**)&iter->data);
|
||||
}
|
||||
|
||||
static void _breakiterator_move_forward(zend_object_iterator *iter TSRMLS_DC)
|
||||
{
|
||||
BreakIterator *biter = _breakiter_prolog(iter TSRMLS_CC);
|
||||
zoi_with_current *zoi_iter = (zoi_with_current*)iter;
|
||||
|
||||
iter->funcs->invalidate_current(iter TSRMLS_CC);
|
||||
|
||||
if (biter == NULL) {
|
||||
return;
|
||||
}
|
||||
|
||||
int32_t pos = biter->next();
|
||||
if (pos != BreakIterator::DONE) {
|
||||
MAKE_STD_ZVAL(zoi_iter->current);
|
||||
ZVAL_LONG(zoi_iter->current, (long)pos);
|
||||
} //else we've reached the end of the enum, nothing more is required
|
||||
}
|
||||
|
||||
static void _breakiterator_rewind(zend_object_iterator *iter TSRMLS_DC)
|
||||
{
|
||||
BreakIterator *biter = _breakiter_prolog(iter TSRMLS_CC);
|
||||
zoi_with_current *zoi_iter = (zoi_with_current*)iter;
|
||||
|
||||
int32_t pos = biter->first();
|
||||
MAKE_STD_ZVAL(zoi_iter->current);
|
||||
ZVAL_LONG(zoi_iter->current, (long)pos);
|
||||
}
|
||||
|
||||
static zend_object_iterator_funcs breakiterator_iterator_funcs = {
|
||||
zoi_with_current_dtor,
|
||||
zoi_with_current_valid,
|
||||
zoi_with_current_get_current_data,
|
||||
NULL,
|
||||
_breakiterator_move_forward,
|
||||
_breakiterator_rewind,
|
||||
zoi_with_current_invalidate_current
|
||||
};
|
||||
|
||||
U_CFUNC zend_object_iterator *_breakiterator_get_iterator(
|
||||
zend_class_entry *ce, zval *object, int by_ref TSRMLS_DC)
|
||||
{
|
||||
BreakIterator_object *bio;
|
||||
if (by_ref) {
|
||||
zend_throw_exception(NULL,
|
||||
"Iteration by reference is not supported", 0 TSRMLS_CC);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
bio = (BreakIterator_object*)zend_object_store_get_object(object TSRMLS_CC);
|
||||
BreakIterator *biter = bio->biter;
|
||||
|
||||
if (biter == NULL) {
|
||||
zend_throw_exception(NULL,
|
||||
"The BreakIterator is not properly constructed", 0 TSRMLS_CC);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
zoi_with_current *zoi_iter =
|
||||
static_cast<zoi_with_current*>(emalloc(sizeof *zoi_iter));
|
||||
zoi_iter->zoi.data = static_cast<void*>(object);
|
||||
zoi_iter->zoi.funcs = &breakiterator_iterator_funcs;
|
||||
zoi_iter->zoi.index = 0;
|
||||
zoi_iter->destroy_it = _breakiterator_destroy_it;
|
||||
zoi_iter->wrapping_obj = NULL; /* not used; object is in zoi.data */
|
||||
zoi_iter->current = NULL;
|
||||
|
||||
zval_add_ref(&object);
|
||||
|
||||
return reinterpret_cast<zend_object_iterator *>(zoi_iter);
|
||||
}
|
||||
|
||||
/* BreakIterator parts iterator */
|
||||
|
||||
typedef struct zoi_break_iter_parts {
|
||||
zoi_with_current zoi_cur;
|
||||
parts_iter_key_type key_type;
|
||||
BreakIterator_object *bio; /* so we don't have to fetch it all the time */
|
||||
} zoi_break_iter_parts;
|
||||
|
||||
static void _breakiterator_parts_destroy_it(zend_object_iterator *iter TSRMLS_DC)
|
||||
{
|
||||
zval_ptr_dtor(reinterpret_cast<zval**>(&iter->data));
|
||||
}
|
||||
|
||||
static int _breakiterator_parts_get_current_key(zend_object_iterator *iter,
|
||||
char **str_key,
|
||||
uint *str_key_len,
|
||||
ulong *int_key TSRMLS_DC)
|
||||
{
|
||||
/* the actual work is done in move_forward and rewind */
|
||||
*int_key = iter->index;
|
||||
return HASH_KEY_IS_LONG;
|
||||
}
|
||||
|
||||
static void _breakiterator_parts_move_forward(zend_object_iterator *iter TSRMLS_DC)
|
||||
{
|
||||
zoi_break_iter_parts *zoi_bit = (zoi_break_iter_parts*)iter;
|
||||
BreakIterator_object *bio = zoi_bit->bio;
|
||||
|
||||
iter->funcs->invalidate_current(iter TSRMLS_CC);
|
||||
|
||||
int32_t cur,
|
||||
next;
|
||||
|
||||
cur = bio->biter->current();
|
||||
if (cur == BreakIterator::DONE) {
|
||||
return;
|
||||
}
|
||||
next = bio->biter->next();
|
||||
if (next == BreakIterator::DONE) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (zoi_bit->key_type == PARTS_ITERATOR_KEY_LEFT) {
|
||||
iter->index = cur;
|
||||
} else if (zoi_bit->key_type == PARTS_ITERATOR_KEY_RIGHT) {
|
||||
iter->index = next;
|
||||
}
|
||||
/* else zoi_bit->key_type == PARTS_ITERATOR_KEY_SEQUENTIAL
|
||||
* No need to do anything, the engine increments ->index */
|
||||
|
||||
const char *s = Z_STRVAL_P(bio->text);
|
||||
int32_t slen = Z_STRLEN_P(bio->text),
|
||||
len;
|
||||
char *res;
|
||||
|
||||
if (next == BreakIterator::DONE) {
|
||||
next = slen;
|
||||
}
|
||||
assert(next <= slen && next >= cur);
|
||||
len = next - cur;
|
||||
res = static_cast<char*>(emalloc(len + 1));
|
||||
|
||||
memcpy(res, &s[cur], len);
|
||||
res[len] = '\0';
|
||||
|
||||
MAKE_STD_ZVAL(zoi_bit->zoi_cur.current);
|
||||
ZVAL_STRINGL(zoi_bit->zoi_cur.current, res, len, 0);
|
||||
}
|
||||
|
||||
static void _breakiterator_parts_rewind(zend_object_iterator *iter TSRMLS_DC)
|
||||
{
|
||||
zoi_break_iter_parts *zoi_bit = (zoi_break_iter_parts*)iter;
|
||||
BreakIterator_object *bio = zoi_bit->bio;
|
||||
|
||||
if (zoi_bit->zoi_cur.current) {
|
||||
iter->funcs->invalidate_current(iter TSRMLS_CC);
|
||||
}
|
||||
|
||||
bio->biter->first();
|
||||
|
||||
iter->funcs->move_forward(iter TSRMLS_CC);
|
||||
}
|
||||
|
||||
static zend_object_iterator_funcs breakiterator_parts_it_funcs = {
|
||||
zoi_with_current_dtor,
|
||||
zoi_with_current_valid,
|
||||
zoi_with_current_get_current_data,
|
||||
_breakiterator_parts_get_current_key,
|
||||
_breakiterator_parts_move_forward,
|
||||
_breakiterator_parts_rewind,
|
||||
zoi_with_current_invalidate_current
|
||||
};
|
||||
|
||||
void IntlIterator_from_BreakIterator_parts(zval *break_iter_zv,
|
||||
zval *object,
|
||||
parts_iter_key_type key_type TSRMLS_DC)
|
||||
{
|
||||
IntlIterator_object *ii;
|
||||
|
||||
zval_add_ref(&break_iter_zv);
|
||||
|
||||
object_init_ex(object, IntlPartsIterator_ce_ptr);
|
||||
ii = (IntlIterator_object*)zend_object_store_get_object(object TSRMLS_CC);
|
||||
|
||||
ii->iterator = (zend_object_iterator*)emalloc(sizeof(zoi_break_iter_parts));
|
||||
ii->iterator->data = break_iter_zv;
|
||||
ii->iterator->funcs = &breakiterator_parts_it_funcs;
|
||||
ii->iterator->index = 0;
|
||||
((zoi_with_current*)ii->iterator)->destroy_it = _breakiterator_parts_destroy_it;
|
||||
((zoi_with_current*)ii->iterator)->wrapping_obj = object;
|
||||
((zoi_with_current*)ii->iterator)->current = NULL;
|
||||
|
||||
((zoi_break_iter_parts*)ii->iterator)->bio = (BreakIterator_object*)
|
||||
zend_object_store_get_object(break_iter_zv TSRMLS_CC);
|
||||
assert(((zoi_break_iter_parts*)ii->iterator)->bio->biter != NULL);
|
||||
((zoi_break_iter_parts*)ii->iterator)->key_type = key_type;
|
||||
}
|
||||
|
||||
U_CFUNC zend_object_value IntlPartsIterator_object_create(zend_class_entry *ce TSRMLS_DC)
|
||||
{
|
||||
zend_object_value retval;
|
||||
|
||||
retval = IntlIterator_ce_ptr->create_object(ce TSRMLS_CC);
|
||||
retval.handlers = &IntlPartsIterator_handlers;
|
||||
|
||||
return retval;
|
||||
}
|
||||
|
||||
U_CFUNC zend_function *IntlPartsIterator_get_method(zval **object_ptr,
|
||||
char *method, int method_len, const zend_literal *key TSRMLS_DC)
|
||||
{
|
||||
zend_literal local_literal = {0};
|
||||
zend_function *ret;
|
||||
ALLOCA_FLAG(use_heap)
|
||||
|
||||
if (key == NULL) {
|
||||
Z_STRVAL(local_literal.constant) = static_cast<char*>(
|
||||
do_alloca(method_len + 1, use_heap));
|
||||
zend_str_tolower_copy(Z_STRVAL(local_literal.constant),
|
||||
method, method_len);
|
||||
local_literal.hash_value = zend_hash_func(
|
||||
Z_STRVAL(local_literal.constant), method_len + 1);
|
||||
key = &local_literal;
|
||||
}
|
||||
|
||||
if ((key->hash_value & 0xFFFFFFFF) == 0xA2B486A1 /* hash of getrulestatus\0 */
|
||||
&& method_len == sizeof("getrulestatus") - 1
|
||||
&& memcmp("getrulestatus", Z_STRVAL(key->constant), method_len) == 0) {
|
||||
IntlIterator_object *obj = (IntlIterator_object*)
|
||||
zend_object_store_get_object(*object_ptr TSRMLS_CC);
|
||||
if (obj->iterator && obj->iterator->data) {
|
||||
zval *break_iter_zv = static_cast<zval*>(obj->iterator->data);
|
||||
*object_ptr = break_iter_zv;
|
||||
ret = Z_OBJ_HANDLER_P(break_iter_zv, get_method)(object_ptr,
|
||||
method, method_len, key TSRMLS_CC);
|
||||
goto end;
|
||||
}
|
||||
}
|
||||
|
||||
ret = std_object_handlers.get_method(object_ptr,
|
||||
method, method_len, key TSRMLS_CC);
|
||||
|
||||
end:
|
||||
if (key == &local_literal) {
|
||||
free_alloca(Z_STRVAL(local_literal.constant), use_heap);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
U_CFUNC PHP_METHOD(IntlPartsIterator, getBreakIterator)
|
||||
{
|
||||
INTLITERATOR_METHOD_INIT_VARS;
|
||||
|
||||
if (zend_parse_parameters_none() == FAILURE) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"IntlPartsIterator::getBreakIterator: bad arguments", 0 TSRMLS_CC);
|
||||
return;
|
||||
}
|
||||
|
||||
INTLITERATOR_METHOD_FETCH_OBJECT;
|
||||
|
||||
zval *biter_zval = static_cast<zval*>(ii->iterator->data);
|
||||
RETURN_ZVAL(biter_zval, 1, 0);
|
||||
}
|
||||
|
||||
ZEND_BEGIN_ARG_INFO_EX(ainfo_parts_it_void, 0, 0, 0)
|
||||
ZEND_END_ARG_INFO()
|
||||
|
||||
static const zend_function_entry IntlPartsIterator_class_functions[] = {
|
||||
PHP_ME(IntlPartsIterator, getBreakIterator, ainfo_parts_it_void, ZEND_ACC_PUBLIC)
|
||||
PHP_FE_END
|
||||
};
|
||||
|
||||
U_CFUNC void breakiterator_register_IntlPartsIterator_class(TSRMLS_D)
|
||||
{
|
||||
zend_class_entry ce;
|
||||
|
||||
/* Create and register 'BreakIterator' class. */
|
||||
INIT_CLASS_ENTRY(ce, "IntlPartsIterator", IntlPartsIterator_class_functions);
|
||||
IntlPartsIterator_ce_ptr = zend_register_internal_class_ex(&ce,
|
||||
IntlIterator_ce_ptr, NULL TSRMLS_CC);
|
||||
IntlPartsIterator_ce_ptr->create_object = IntlPartsIterator_object_create;
|
||||
|
||||
memcpy(&IntlPartsIterator_handlers, &IntlIterator_handlers,
|
||||
sizeof IntlPartsIterator_handlers);
|
||||
IntlPartsIterator_handlers.get_method = IntlPartsIterator_get_method;
|
||||
|
||||
#define PARTSITER_DECL_LONG_CONST(name) \
|
||||
zend_declare_class_constant_long(IntlPartsIterator_ce_ptr, #name, \
|
||||
sizeof(#name) - 1, PARTS_ITERATOR_ ## name TSRMLS_CC)
|
||||
|
||||
PARTSITER_DECL_LONG_CONST(KEY_SEQUENTIAL);
|
||||
PARTSITER_DECL_LONG_CONST(KEY_LEFT);
|
||||
PARTSITER_DECL_LONG_CONST(KEY_RIGHT);
|
||||
|
||||
#undef PARTSITER_DECL_LONG_CONST
|
||||
}
|
42
ext/intl/breakiterator/breakiterator_iterators.h
Normal file
42
ext/intl/breakiterator/breakiterator_iterators.h
Normal file
@ -0,0 +1,42 @@
|
||||
/*
|
||||
+----------------------------------------------------------------------+
|
||||
| PHP Version 5 |
|
||||
+----------------------------------------------------------------------+
|
||||
| This source file is subject to version 3.01 of the PHP license, |
|
||||
| that is bundled with this package in the file LICENSE, and is |
|
||||
| available through the world-wide-web at the following url: |
|
||||
| http://www.php.net/license/3_01.txt |
|
||||
| If you did not receive a copy of the PHP license and are unable to |
|
||||
| obtain it through the world-wide-web, please send a note to |
|
||||
| license@php.net so we can mail you a copy immediately. |
|
||||
+----------------------------------------------------------------------+
|
||||
| Authors: Gustavo Lopes <cataphract@php.net> |
|
||||
+----------------------------------------------------------------------+
|
||||
*/
|
||||
#ifndef INTL_BREAKITERATOR_ITERATORS_H
|
||||
#define INTL_BREAKITERATOR_ITERATORS_H
|
||||
|
||||
#include <unicode/umachine.h>
|
||||
|
||||
U_CDECL_BEGIN
|
||||
#include <math.h>
|
||||
#include <php.h>
|
||||
U_CDECL_END
|
||||
|
||||
typedef enum {
|
||||
PARTS_ITERATOR_KEY_SEQUENTIAL,
|
||||
PARTS_ITERATOR_KEY_LEFT,
|
||||
PARTS_ITERATOR_KEY_RIGHT,
|
||||
} parts_iter_key_type;
|
||||
|
||||
#ifdef __cplusplus
|
||||
void IntlIterator_from_BreakIterator_parts(zval *break_iter_zv,
|
||||
zval *object,
|
||||
parts_iter_key_type key_type TSRMLS_DC);
|
||||
#endif
|
||||
|
||||
U_CFUNC zend_object_iterator *_breakiterator_get_iterator(
|
||||
zend_class_entry *ce, zval *object, int by_ref TSRMLS_DC);
|
||||
U_CFUNC void breakiterator_register_IntlPartsIterator_class(TSRMLS_D);
|
||||
|
||||
#endif
|
452
ext/intl/breakiterator/breakiterator_methods.cpp
Normal file
452
ext/intl/breakiterator/breakiterator_methods.cpp
Normal file
@ -0,0 +1,452 @@
|
||||
/*
|
||||
+----------------------------------------------------------------------+
|
||||
| PHP Version 5 |
|
||||
+----------------------------------------------------------------------+
|
||||
| This source file is subject to version 3.01 of the PHP license, |
|
||||
| that is bundled with this package in the file LICENSE, and is |
|
||||
| available through the world-wide-web at the following url: |
|
||||
| http://www.php.net/license/3_01.txt |
|
||||
| If you did not receive a copy of the PHP license and are unable to |
|
||||
| obtain it through the world-wide-web, please send a note to |
|
||||
| license@php.net so we can mail you a copy immediately. |
|
||||
+----------------------------------------------------------------------+
|
||||
| Authors: Gustavo Lopes <cataphract@php.net> |
|
||||
+----------------------------------------------------------------------+
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
#include "config.h"
|
||||
#endif
|
||||
|
||||
#include <unicode/brkiter.h>
|
||||
#include "codepointiterator_internal.h"
|
||||
|
||||
#include "breakiterator_iterators.h"
|
||||
|
||||
extern "C" {
|
||||
#include "../php_intl.h"
|
||||
#define USE_BREAKITERATOR_POINTER 1
|
||||
#include "breakiterator_class.h"
|
||||
#include "../locale/locale.h"
|
||||
#include <zend_exceptions.h>
|
||||
}
|
||||
|
||||
using PHP::CodePointBreakIterator;
|
||||
|
||||
U_CFUNC PHP_METHOD(BreakIterator, __construct)
|
||||
{
|
||||
zend_throw_exception( NULL,
|
||||
"An object of this type cannot be created with the new operator",
|
||||
0 TSRMLS_CC );
|
||||
}
|
||||
|
||||
static void _breakiter_factory(const char *func_name,
|
||||
BreakIterator *(*func)(const Locale&, UErrorCode&),
|
||||
INTERNAL_FUNCTION_PARAMETERS)
|
||||
{
|
||||
BreakIterator *biter;
|
||||
const char *locale_str = NULL;
|
||||
int dummy;
|
||||
char *msg;
|
||||
UErrorCode status = UErrorCode();
|
||||
intl_error_reset(NULL TSRMLS_CC);
|
||||
|
||||
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s!",
|
||||
&locale_str, &dummy) == FAILURE) {
|
||||
spprintf(&msg, NULL, "%s: bad arguments", func_name);
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, msg, 1 TSRMLS_CC);
|
||||
efree(msg);
|
||||
RETURN_NULL();
|
||||
}
|
||||
|
||||
if (locale_str == NULL) {
|
||||
locale_str = intl_locale_get_default(TSRMLS_C);
|
||||
}
|
||||
|
||||
biter = func(Locale::createFromName(locale_str), status);
|
||||
intl_error_set_code(NULL, status TSRMLS_CC);
|
||||
if (U_FAILURE(status)) {
|
||||
spprintf(&msg, NULL, "%s: error creating BreakIterator",
|
||||
func_name);
|
||||
intl_error_set_custom_msg(NULL, msg, 1 TSRMLS_CC);
|
||||
efree(msg);
|
||||
RETURN_NULL();
|
||||
}
|
||||
|
||||
breakiterator_object_create(return_value, biter TSRMLS_CC);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_create_word_instance)
|
||||
{
|
||||
_breakiter_factory("breakiter_create_word_instance",
|
||||
&BreakIterator::createWordInstance,
|
||||
INTERNAL_FUNCTION_PARAM_PASSTHRU);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_create_line_instance)
|
||||
{
|
||||
_breakiter_factory("breakiter_create_line_instance",
|
||||
&BreakIterator::createLineInstance,
|
||||
INTERNAL_FUNCTION_PARAM_PASSTHRU);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_create_character_instance)
|
||||
{
|
||||
_breakiter_factory("breakiter_create_character_instance",
|
||||
&BreakIterator::createCharacterInstance,
|
||||
INTERNAL_FUNCTION_PARAM_PASSTHRU);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_create_sentence_instance)
|
||||
{
|
||||
_breakiter_factory("breakiter_create_sentence_instance",
|
||||
&BreakIterator::createSentenceInstance,
|
||||
INTERNAL_FUNCTION_PARAM_PASSTHRU);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_create_title_instance)
|
||||
{
|
||||
_breakiter_factory("breakiter_create_title_instance",
|
||||
&BreakIterator::createTitleInstance,
|
||||
INTERNAL_FUNCTION_PARAM_PASSTHRU);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_create_code_point_instance)
|
||||
{
|
||||
UErrorCode status = UErrorCode();
|
||||
intl_error_reset(NULL TSRMLS_CC);
|
||||
|
||||
if (zend_parse_parameters_none() == FAILURE) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"breakiter_create_code_point_instance: bad arguments", 0 TSRMLS_CC);
|
||||
RETURN_NULL();
|
||||
}
|
||||
|
||||
CodePointBreakIterator *cpbi = new CodePointBreakIterator();
|
||||
breakiterator_object_create(return_value, cpbi TSRMLS_CC);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_get_text)
|
||||
{
|
||||
BREAKITER_METHOD_INIT_VARS;
|
||||
object = getThis();
|
||||
|
||||
if (zend_parse_parameters_none() == FAILURE) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"breakiter_get_text: bad arguments", 0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
BREAKITER_METHOD_FETCH_OBJECT;
|
||||
|
||||
if (bio->text == NULL) {
|
||||
RETURN_NULL();
|
||||
} else {
|
||||
RETURN_ZVAL(bio->text, 1, 0);
|
||||
}
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_set_text)
|
||||
{
|
||||
char *text;
|
||||
int text_len;
|
||||
UText *ut = NULL;
|
||||
zval **textzv;
|
||||
BREAKITER_METHOD_INIT_VARS;
|
||||
object = getThis();
|
||||
|
||||
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s",
|
||||
&text, &text_len) == FAILURE) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"breakiter_set_text: bad arguments", 0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
int res = zend_get_parameters_ex(1, &textzv);
|
||||
assert(res == SUCCESS);
|
||||
|
||||
BREAKITER_METHOD_FETCH_OBJECT;
|
||||
|
||||
/* assert it's safe to use text and text_len because zpp changes the
|
||||
* arguments in the stack */
|
||||
assert(text == Z_STRVAL_PP(textzv));
|
||||
|
||||
ut = utext_openUTF8(ut, text, text_len, BREAKITER_ERROR_CODE_P(bio));
|
||||
INTL_CTOR_CHECK_STATUS(bio, "breakiter_set_text: error opening UText");
|
||||
|
||||
bio->biter->setText(ut, BREAKITER_ERROR_CODE(bio));
|
||||
utext_close(ut); /* ICU shallow clones the UText */
|
||||
INTL_CTOR_CHECK_STATUS(bio, "breakiter_set_text: error calling "
|
||||
"BreakIterator::setText()");
|
||||
|
||||
/* When ICU clones the UText, it does not copy the buffer, so we have to
|
||||
* keep the string buffer around by holding a reference to its zval. This
|
||||
* also allows a faste implementation of getText() */
|
||||
if (bio->text != NULL) {
|
||||
zval_ptr_dtor(&bio->text);
|
||||
}
|
||||
bio->text = *textzv;
|
||||
zval_add_ref(&bio->text);
|
||||
|
||||
RETURN_TRUE;
|
||||
}
|
||||
|
||||
static void _breakiter_no_args_ret_int32(
|
||||
const char *func_name,
|
||||
int32_t (BreakIterator::*func)(),
|
||||
INTERNAL_FUNCTION_PARAMETERS)
|
||||
{
|
||||
char *msg;
|
||||
BREAKITER_METHOD_INIT_VARS;
|
||||
object = getThis();
|
||||
|
||||
if (zend_parse_parameters_none() == FAILURE) {
|
||||
spprintf(&msg, NULL, "%s: bad arguments", func_name);
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, msg, 1 TSRMLS_CC);
|
||||
efree(msg);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
BREAKITER_METHOD_FETCH_OBJECT;
|
||||
|
||||
int32_t res = (bio->biter->*func)();
|
||||
|
||||
RETURN_LONG((long)res);
|
||||
}
|
||||
|
||||
static void _breakiter_int32_ret_int32(
|
||||
const char *func_name,
|
||||
int32_t (BreakIterator::*func)(int32_t),
|
||||
INTERNAL_FUNCTION_PARAMETERS)
|
||||
{
|
||||
char *msg;
|
||||
long arg;
|
||||
BREAKITER_METHOD_INIT_VARS;
|
||||
object = getThis();
|
||||
|
||||
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "l", &arg) == FAILURE) {
|
||||
spprintf(&msg, NULL, "%s: bad arguments", func_name);
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, msg, 1 TSRMLS_CC);
|
||||
efree(msg);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
BREAKITER_METHOD_FETCH_OBJECT;
|
||||
|
||||
if (arg < INT32_MIN || arg > INT32_MAX) {
|
||||
spprintf(&msg, NULL, "%s: offset argument is outside bounds of "
|
||||
"a 32-bit wide integer", func_name);
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, msg, 1 TSRMLS_CC);
|
||||
efree(msg);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
int32_t res = (bio->biter->*func)((int32_t)arg);
|
||||
|
||||
RETURN_LONG((long)res);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_first)
|
||||
{
|
||||
_breakiter_no_args_ret_int32("breakiter_first",
|
||||
&BreakIterator::first,
|
||||
INTERNAL_FUNCTION_PARAM_PASSTHRU);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_last)
|
||||
{
|
||||
_breakiter_no_args_ret_int32("breakiter_last",
|
||||
&BreakIterator::last,
|
||||
INTERNAL_FUNCTION_PARAM_PASSTHRU);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_previous)
|
||||
{
|
||||
_breakiter_no_args_ret_int32("breakiter_previous",
|
||||
&BreakIterator::previous,
|
||||
INTERNAL_FUNCTION_PARAM_PASSTHRU);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_next)
|
||||
{
|
||||
bool no_arg_version = false;
|
||||
|
||||
if (ZEND_NUM_ARGS() == 0) {
|
||||
no_arg_version = true;
|
||||
} else if (ZEND_NUM_ARGS() == 1) {
|
||||
zval **arg;
|
||||
int res = zend_get_parameters_ex(1, &arg);
|
||||
assert(res == SUCCESS);
|
||||
if (Z_TYPE_PP(arg) == IS_NULL) {
|
||||
no_arg_version = true;
|
||||
ht = 0; /* pretend we don't have any argument */
|
||||
} else {
|
||||
no_arg_version = false;
|
||||
}
|
||||
}
|
||||
|
||||
if (no_arg_version) {
|
||||
_breakiter_no_args_ret_int32("breakiter_next",
|
||||
&BreakIterator::next,
|
||||
INTERNAL_FUNCTION_PARAM_PASSTHRU);
|
||||
} else {
|
||||
_breakiter_int32_ret_int32("breakiter_next",
|
||||
&BreakIterator::next,
|
||||
INTERNAL_FUNCTION_PARAM_PASSTHRU);
|
||||
}
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_current)
|
||||
{
|
||||
BREAKITER_METHOD_INIT_VARS;
|
||||
object = getThis();
|
||||
|
||||
if (zend_parse_parameters_none() == FAILURE) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"breakiter_current: bad arguments", 0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
BREAKITER_METHOD_FETCH_OBJECT;
|
||||
|
||||
int32_t res = bio->biter->current();
|
||||
|
||||
RETURN_LONG((long)res);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_following)
|
||||
{
|
||||
_breakiter_int32_ret_int32("breakiter_following",
|
||||
&BreakIterator::following,
|
||||
INTERNAL_FUNCTION_PARAM_PASSTHRU);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_preceding)
|
||||
{
|
||||
_breakiter_int32_ret_int32("breakiter_preceding",
|
||||
&BreakIterator::preceding,
|
||||
INTERNAL_FUNCTION_PARAM_PASSTHRU);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_is_boundary)
|
||||
{
|
||||
long offset;
|
||||
BREAKITER_METHOD_INIT_VARS;
|
||||
object = getThis();
|
||||
|
||||
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "l",
|
||||
&offset) == FAILURE) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"breakiter_is_boundary: bad arguments", 0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
if (offset < INT32_MIN || offset > INT32_MAX) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"breakiter_is_boundary: offset argument is outside bounds of "
|
||||
"a 32-bit wide integer", 0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
BREAKITER_METHOD_FETCH_OBJECT;
|
||||
|
||||
UBool res = bio->biter->isBoundary((int32_t)offset);
|
||||
|
||||
RETURN_BOOL((long)res);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_get_locale)
|
||||
{
|
||||
long locale_type;
|
||||
BREAKITER_METHOD_INIT_VARS;
|
||||
object = getThis();
|
||||
|
||||
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "l", &locale_type) == FAILURE) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"breakiter_get_locale: bad arguments", 0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
if (locale_type != ULOC_ACTUAL_LOCALE && locale_type != ULOC_VALID_LOCALE) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"breakiter_get_locale: invalid locale type", 0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
BREAKITER_METHOD_FETCH_OBJECT;
|
||||
|
||||
Locale locale = bio->biter->getLocale((ULocDataLocaleType)locale_type,
|
||||
BREAKITER_ERROR_CODE(bio));
|
||||
INTL_METHOD_CHECK_STATUS(bio,
|
||||
"breakiter_get_locale: Call to ICU method has failed");
|
||||
|
||||
RETURN_STRING(locale.getName(), 1);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_get_parts_iterator)
|
||||
{
|
||||
long key_type = 0;
|
||||
BREAKITER_METHOD_INIT_VARS;
|
||||
object = getThis();
|
||||
|
||||
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "|l", &key_type) == FAILURE) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"breakiter_get_parts_iterator: bad arguments", 0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
if (key_type != PARTS_ITERATOR_KEY_SEQUENTIAL
|
||||
&& key_type != PARTS_ITERATOR_KEY_LEFT
|
||||
&& key_type != PARTS_ITERATOR_KEY_RIGHT) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"breakiter_get_parts_iterator: bad key type", 0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
BREAKITER_METHOD_FETCH_OBJECT;
|
||||
|
||||
IntlIterator_from_BreakIterator_parts(
|
||||
object, return_value, (parts_iter_key_type)key_type TSRMLS_CC);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_get_error_code)
|
||||
{
|
||||
BREAKITER_METHOD_INIT_VARS;
|
||||
object = getThis();
|
||||
|
||||
if (zend_parse_parameters_none() == FAILURE) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"breakiter_get_error_code: bad arguments", 0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
/* Fetch the object (without resetting its last error code ). */
|
||||
bio = (BreakIterator_object*)zend_object_store_get_object(object TSRMLS_CC);
|
||||
if (bio == NULL)
|
||||
RETURN_FALSE;
|
||||
|
||||
RETURN_LONG((long)BREAKITER_ERROR_CODE(bio));
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(breakiter_get_error_message)
|
||||
{
|
||||
const char* message = NULL;
|
||||
BREAKITER_METHOD_INIT_VARS;
|
||||
object = getThis();
|
||||
|
||||
if (zend_parse_parameters_none() == FAILURE) {
|
||||
intl_error_set( NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"breakiter_get_error_message: bad arguments", 0 TSRMLS_CC );
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
|
||||
/* Fetch the object (without resetting its last error code ). */
|
||||
bio = (BreakIterator_object*)zend_object_store_get_object(object TSRMLS_CC);
|
||||
if (bio == NULL)
|
||||
RETURN_FALSE;
|
||||
|
||||
/* Return last error message. */
|
||||
message = intl_error_get_message(BREAKITER_ERROR_P(bio) TSRMLS_CC);
|
||||
RETURN_STRING(message, 0);
|
||||
}
|
64
ext/intl/breakiterator/breakiterator_methods.h
Normal file
64
ext/intl/breakiterator/breakiterator_methods.h
Normal file
@ -0,0 +1,64 @@
|
||||
/*
|
||||
+----------------------------------------------------------------------+
|
||||
| PHP Version 5 |
|
||||
+----------------------------------------------------------------------+
|
||||
| This source file is subject to version 3.01 of the PHP license, |
|
||||
| that is bundled with this package in the file LICENSE, and is |
|
||||
| available through the world-wide-web at the following url: |
|
||||
| http://www.php.net/license/3_01.txt |
|
||||
| If you did not receive a copy of the PHP license and are unable to |
|
||||
| obtain it through the world-wide-web, please send a note to |
|
||||
| license@php.net so we can mail you a copy immediately. |
|
||||
+----------------------------------------------------------------------+
|
||||
| Authors: Gustavo Lopes <cataphract@php.net> |
|
||||
+----------------------------------------------------------------------+
|
||||
*/
|
||||
|
||||
#ifndef BREAKITERATOR_METHODS_H
|
||||
#define BREAKITERATOR_METHODS_H
|
||||
|
||||
#include <php.h>
|
||||
|
||||
PHP_METHOD(BreakIterator, __construct);
|
||||
|
||||
PHP_FUNCTION(breakiter_create_word_instance);
|
||||
|
||||
PHP_FUNCTION(breakiter_create_line_instance);
|
||||
|
||||
PHP_FUNCTION(breakiter_create_character_instance);
|
||||
|
||||
PHP_FUNCTION(breakiter_create_sentence_instance);
|
||||
|
||||
PHP_FUNCTION(breakiter_create_title_instance);
|
||||
|
||||
PHP_FUNCTION(breakiter_create_code_point_instance);
|
||||
|
||||
PHP_FUNCTION(breakiter_get_text);
|
||||
|
||||
PHP_FUNCTION(breakiter_set_text);
|
||||
|
||||
PHP_FUNCTION(breakiter_first);
|
||||
|
||||
PHP_FUNCTION(breakiter_last);
|
||||
|
||||
PHP_FUNCTION(breakiter_previous);
|
||||
|
||||
PHP_FUNCTION(breakiter_next);
|
||||
|
||||
PHP_FUNCTION(breakiter_current);
|
||||
|
||||
PHP_FUNCTION(breakiter_following);
|
||||
|
||||
PHP_FUNCTION(breakiter_preceding);
|
||||
|
||||
PHP_FUNCTION(breakiter_is_boundary);
|
||||
|
||||
PHP_FUNCTION(breakiter_get_locale);
|
||||
|
||||
PHP_FUNCTION(breakiter_get_parts_iterator);
|
||||
|
||||
PHP_FUNCTION(breakiter_get_error_code);
|
||||
|
||||
PHP_FUNCTION(breakiter_get_error_message);
|
||||
|
||||
#endif
|
291
ext/intl/breakiterator/codepointiterator_internal.cpp
Normal file
291
ext/intl/breakiterator/codepointiterator_internal.cpp
Normal file
@ -0,0 +1,291 @@
|
||||
/*
|
||||
+----------------------------------------------------------------------+
|
||||
| PHP Version 5 |
|
||||
+----------------------------------------------------------------------+
|
||||
| This source file is subject to version 3.01 of the PHP license, |
|
||||
| that is bundled with this package in the file LICENSE, and is |
|
||||
| available through the world-wide-web at the following url: |
|
||||
| http://www.php.net/license/3_01.txt |
|
||||
| If you did not receive a copy of the PHP license and are unable to |
|
||||
| obtain it through the world-wide-web, please send a note to |
|
||||
| license@php.net so we can mail you a copy immediately. |
|
||||
+----------------------------------------------------------------------+
|
||||
| Authors: Gustavo Lopes <cataphract@php.net> |
|
||||
+----------------------------------------------------------------------+
|
||||
*/
|
||||
|
||||
#include "codepointiterator_internal.h"
|
||||
#include <unicode/uchriter.h>
|
||||
#include <typeinfo>
|
||||
|
||||
//copied from cmemory.h, which is not public
|
||||
typedef union {
|
||||
long t1;
|
||||
double t2;
|
||||
void *t3;
|
||||
} UAlignedMemory;
|
||||
|
||||
#define U_POINTER_MASK_LSB(ptr, mask) (((ptrdiff_t)(char *)(ptr)) & (mask))
|
||||
#define U_ALIGNMENT_OFFSET(ptr) U_POINTER_MASK_LSB(ptr, sizeof(UAlignedMemory) - 1)
|
||||
#define U_ALIGNMENT_OFFSET_UP(ptr) (sizeof(UAlignedMemory) - U_ALIGNMENT_OFFSET(ptr))
|
||||
|
||||
using namespace PHP;
|
||||
|
||||
UOBJECT_DEFINE_RTTI_IMPLEMENTATION(CodePointBreakIterator);
|
||||
|
||||
CodePointBreakIterator::CodePointBreakIterator()
|
||||
: BreakIterator(), fCharIter(NULL), lastCodePoint(U_SENTINEL)
|
||||
{
|
||||
UErrorCode uec = UErrorCode();
|
||||
this->fText = utext_openUChars(NULL, NULL, 0, &uec);
|
||||
}
|
||||
|
||||
CodePointBreakIterator::CodePointBreakIterator(const PHP::CodePointBreakIterator &other)
|
||||
: BreakIterator(other), fText(NULL), fCharIter(NULL), lastCodePoint(U_SENTINEL)
|
||||
{
|
||||
*this = other;
|
||||
}
|
||||
|
||||
CodePointBreakIterator& CodePointBreakIterator::operator=(const CodePointBreakIterator& that)
|
||||
{
|
||||
UErrorCode uec = UErrorCode();
|
||||
UText *ut_clone = NULL;
|
||||
|
||||
if (this == &that) {
|
||||
return *this;
|
||||
}
|
||||
|
||||
this->fText = utext_clone(this->fText, that.fText, FALSE, TRUE, &uec);
|
||||
|
||||
//don't bother copying the character iterator, getText() is deprecated
|
||||
clearCurrentCharIter();
|
||||
|
||||
this->lastCodePoint = that.lastCodePoint;
|
||||
return *this;
|
||||
}
|
||||
|
||||
CodePointBreakIterator::~CodePointBreakIterator()
|
||||
{
|
||||
if (this->fText) {
|
||||
utext_close(this->fText);
|
||||
}
|
||||
clearCurrentCharIter();
|
||||
}
|
||||
|
||||
UBool CodePointBreakIterator::operator==(const BreakIterator& that) const
|
||||
{
|
||||
if (typeid(*this) != typeid(that)) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
const CodePointBreakIterator& that2 =
|
||||
static_cast<const CodePointBreakIterator&>(that);
|
||||
|
||||
if (!utext_equals(this->fText, that2.fText)) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
CodePointBreakIterator* CodePointBreakIterator::clone(void) const
|
||||
{
|
||||
return new CodePointBreakIterator(*this);
|
||||
}
|
||||
|
||||
CharacterIterator& CodePointBreakIterator::getText(void) const
|
||||
{
|
||||
if (this->fCharIter == NULL) {
|
||||
//this method is deprecated anyway; setup bogus iterator
|
||||
static const UChar c = 0;
|
||||
this->fCharIter = new UCharCharacterIterator(&c, 0);
|
||||
}
|
||||
|
||||
return *this->fCharIter;
|
||||
}
|
||||
|
||||
UText *CodePointBreakIterator::getUText(UText *fillIn, UErrorCode &status) const
|
||||
{
|
||||
return utext_clone(fillIn, this->fText, FALSE, TRUE, &status);
|
||||
}
|
||||
|
||||
void CodePointBreakIterator::setText(const UnicodeString &text)
|
||||
{
|
||||
UErrorCode uec = UErrorCode();
|
||||
|
||||
//this closes the previous utext, if any
|
||||
this->fText = utext_openConstUnicodeString(this->fText, &text, &uec);
|
||||
|
||||
clearCurrentCharIter();
|
||||
}
|
||||
|
||||
void CodePointBreakIterator::setText(UText *text, UErrorCode &status)
|
||||
{
|
||||
if (U_FAILURE(status)) {
|
||||
return;
|
||||
}
|
||||
|
||||
this->fText = utext_clone(this->fText, text, FALSE, TRUE, &status);
|
||||
|
||||
clearCurrentCharIter();
|
||||
}
|
||||
|
||||
void CodePointBreakIterator::adoptText(CharacterIterator* it)
|
||||
{
|
||||
UErrorCode uec = UErrorCode();
|
||||
clearCurrentCharIter();
|
||||
|
||||
this->fCharIter = it;
|
||||
this->fText = utext_openCharacterIterator(this->fText, it, &uec);
|
||||
}
|
||||
|
||||
int32_t CodePointBreakIterator::first(void)
|
||||
{
|
||||
UTEXT_SETNATIVEINDEX(this->fText, 0);
|
||||
this->lastCodePoint = U_SENTINEL;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int32_t CodePointBreakIterator::last(void)
|
||||
{
|
||||
int32_t pos = (int32_t)utext_nativeLength(this->fText);
|
||||
UTEXT_SETNATIVEINDEX(this->fText, pos);
|
||||
this->lastCodePoint = U_SENTINEL;
|
||||
|
||||
return pos;
|
||||
}
|
||||
|
||||
int32_t CodePointBreakIterator::previous(void)
|
||||
{
|
||||
this->lastCodePoint = UTEXT_PREVIOUS32(this->fText);
|
||||
if (this->lastCodePoint == U_SENTINEL) {
|
||||
return BreakIterator::DONE;
|
||||
}
|
||||
|
||||
return (int32_t)UTEXT_GETNATIVEINDEX(this->fText);
|
||||
}
|
||||
|
||||
int32_t CodePointBreakIterator::next(void)
|
||||
{
|
||||
this->lastCodePoint = UTEXT_NEXT32(this->fText);
|
||||
if (this->lastCodePoint == U_SENTINEL) {
|
||||
return BreakIterator::DONE;
|
||||
}
|
||||
|
||||
return (int32_t)UTEXT_GETNATIVEINDEX(this->fText);
|
||||
}
|
||||
|
||||
int32_t CodePointBreakIterator::current(void) const
|
||||
{
|
||||
return (int32_t)UTEXT_GETNATIVEINDEX(this->fText);
|
||||
}
|
||||
|
||||
int32_t CodePointBreakIterator::following(int32_t offset)
|
||||
{
|
||||
this->lastCodePoint = utext_next32From(this->fText, offset);
|
||||
if (this->lastCodePoint == U_SENTINEL) {
|
||||
return BreakIterator::DONE;
|
||||
}
|
||||
|
||||
return (int32_t)UTEXT_GETNATIVEINDEX(this->fText);
|
||||
}
|
||||
|
||||
int32_t CodePointBreakIterator::preceding(int32_t offset)
|
||||
{
|
||||
this->lastCodePoint = utext_previous32From(this->fText, offset);
|
||||
if (this->lastCodePoint == U_SENTINEL) {
|
||||
return BreakIterator::DONE;
|
||||
}
|
||||
|
||||
return (int32_t)UTEXT_GETNATIVEINDEX(this->fText);
|
||||
}
|
||||
|
||||
UBool CodePointBreakIterator::isBoundary(int32_t offset)
|
||||
{
|
||||
//this function has side effects, and it's supposed to
|
||||
utext_setNativeIndex(this->fText, offset);
|
||||
return (offset == utext_getNativeIndex(this->fText));
|
||||
}
|
||||
|
||||
int32_t CodePointBreakIterator::next(int32_t n)
|
||||
{
|
||||
UBool res = utext_moveIndex32(this->fText, n);
|
||||
|
||||
#ifndef UTEXT_CURRENT32
|
||||
#define UTEXT_CURRENT32 utext_current32
|
||||
#endif
|
||||
|
||||
if (res) {
|
||||
this->lastCodePoint = UTEXT_CURRENT32(this->fText);
|
||||
return (int32_t)UTEXT_GETNATIVEINDEX(this->fText);
|
||||
} else {
|
||||
this->lastCodePoint = U_SENTINEL;
|
||||
return BreakIterator::DONE;
|
||||
}
|
||||
}
|
||||
|
||||
CodePointBreakIterator *CodePointBreakIterator::createBufferClone(
|
||||
void *stackBuffer, int32_t &bufferSize, UErrorCode &status)
|
||||
{
|
||||
//see implementation of RuleBasedBreakIterator::createBufferClone()
|
||||
if (U_FAILURE(status)) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (bufferSize <= 0) {
|
||||
bufferSize = sizeof(CodePointBreakIterator) + U_ALIGNMENT_OFFSET_UP(0);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
char *buf = (char*)stackBuffer;
|
||||
uint32_t s = bufferSize;
|
||||
|
||||
if (stackBuffer == NULL) {
|
||||
s = 0;
|
||||
}
|
||||
|
||||
if (U_ALIGNMENT_OFFSET(stackBuffer) != 0) {
|
||||
uint32_t offsetUp = (uint32_t)U_ALIGNMENT_OFFSET_UP(buf);
|
||||
s -= offsetUp;
|
||||
buf += offsetUp;
|
||||
}
|
||||
|
||||
if (s < sizeof(CodePointBreakIterator)) {
|
||||
CodePointBreakIterator *clonedBI = new CodePointBreakIterator(*this);
|
||||
if (clonedBI == NULL) {
|
||||
status = U_MEMORY_ALLOCATION_ERROR;
|
||||
} else {
|
||||
status = U_SAFECLONE_ALLOCATED_WARNING;
|
||||
}
|
||||
|
||||
return clonedBI;
|
||||
}
|
||||
|
||||
return new(buf) CodePointBreakIterator(*this);
|
||||
}
|
||||
|
||||
CodePointBreakIterator &CodePointBreakIterator::refreshInputText(UText *input, UErrorCode &status)
|
||||
{
|
||||
//see implementation of RuleBasedBreakIterator::createBufferClone()
|
||||
if (U_FAILURE(status)) {
|
||||
return *this;
|
||||
}
|
||||
if (input == NULL) {
|
||||
status = U_ILLEGAL_ARGUMENT_ERROR;
|
||||
return *this;
|
||||
}
|
||||
|
||||
int64_t pos = utext_getNativeIndex(this->fText);
|
||||
this->fText = utext_clone(this->fText, input, FALSE, TRUE, &status);
|
||||
if (U_FAILURE(status)) {
|
||||
return *this;
|
||||
}
|
||||
|
||||
utext_setNativeIndex(this->fText, pos);
|
||||
if (utext_getNativeIndex(fText) != pos) {
|
||||
status = U_ILLEGAL_ARGUMENT_ERROR;
|
||||
}
|
||||
|
||||
return *this;
|
||||
}
|
98
ext/intl/breakiterator/codepointiterator_internal.h
Normal file
98
ext/intl/breakiterator/codepointiterator_internal.h
Normal file
@ -0,0 +1,98 @@
|
||||
/*
|
||||
+----------------------------------------------------------------------+
|
||||
| PHP Version 5 |
|
||||
+----------------------------------------------------------------------+
|
||||
| This source file is subject to version 3.01 of the PHP license, |
|
||||
| that is bundled with this package in the file LICENSE, and is |
|
||||
| available through the world-wide-web at the following url: |
|
||||
| http://www.php.net/license/3_01.txt |
|
||||
| If you did not receive a copy of the PHP license and are unable to |
|
||||
| obtain it through the world-wide-web, please send a note to |
|
||||
| license@php.net so we can mail you a copy immediately. |
|
||||
+----------------------------------------------------------------------+
|
||||
| Authors: Gustavo Lopes <cataphract@php.net> |
|
||||
+----------------------------------------------------------------------+
|
||||
*/
|
||||
|
||||
#ifndef CODEPOINTITERATOR_INTERNAL_H
|
||||
#define CODEPOINTITERATOR_INTERNAL_H
|
||||
|
||||
#include <unicode/brkiter.h>
|
||||
|
||||
using U_ICU_NAMESPACE::BreakIterator;
|
||||
|
||||
namespace PHP {
|
||||
|
||||
class CodePointBreakIterator : public BreakIterator {
|
||||
|
||||
public:
|
||||
static UClassID getStaticClassID();
|
||||
|
||||
CodePointBreakIterator();
|
||||
|
||||
CodePointBreakIterator(const CodePointBreakIterator &other);
|
||||
|
||||
CodePointBreakIterator& operator=(const CodePointBreakIterator& that);
|
||||
|
||||
virtual ~CodePointBreakIterator();
|
||||
|
||||
virtual UBool operator==(const BreakIterator& that) const;
|
||||
|
||||
virtual CodePointBreakIterator* clone(void) const;
|
||||
|
||||
virtual UClassID getDynamicClassID(void) const;
|
||||
|
||||
virtual CharacterIterator& getText(void) const;
|
||||
|
||||
virtual UText *getUText(UText *fillIn, UErrorCode &status) const;
|
||||
|
||||
virtual void setText(const UnicodeString &text);
|
||||
|
||||
virtual void setText(UText *text, UErrorCode &status);
|
||||
|
||||
virtual void adoptText(CharacterIterator* it);
|
||||
|
||||
virtual int32_t first(void);
|
||||
|
||||
virtual int32_t last(void);
|
||||
|
||||
virtual int32_t previous(void);
|
||||
|
||||
virtual int32_t next(void);
|
||||
|
||||
virtual int32_t current(void) const;
|
||||
|
||||
virtual int32_t following(int32_t offset);
|
||||
|
||||
virtual int32_t preceding(int32_t offset);
|
||||
|
||||
virtual UBool isBoundary(int32_t offset);
|
||||
|
||||
virtual int32_t next(int32_t n);
|
||||
|
||||
virtual CodePointBreakIterator *createBufferClone(void *stackBuffer,
|
||||
int32_t &BufferSize,
|
||||
UErrorCode &status);
|
||||
|
||||
virtual CodePointBreakIterator &refreshInputText(UText *input, UErrorCode &status);
|
||||
|
||||
inline UChar32 getLastCodePoint()
|
||||
{
|
||||
return this->lastCodePoint;
|
||||
}
|
||||
|
||||
private:
|
||||
UText *fText;
|
||||
UChar32 lastCodePoint;
|
||||
mutable CharacterIterator *fCharIter;
|
||||
|
||||
inline void clearCurrentCharIter()
|
||||
{
|
||||
delete this->fCharIter;
|
||||
this->fCharIter = NULL;
|
||||
this->lastCodePoint = U_SENTINEL;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
#endif
|
44
ext/intl/breakiterator/codepointiterator_methods.cpp
Normal file
44
ext/intl/breakiterator/codepointiterator_methods.cpp
Normal file
@ -0,0 +1,44 @@
|
||||
/*
|
||||
+----------------------------------------------------------------------+
|
||||
| PHP Version 5 |
|
||||
+----------------------------------------------------------------------+
|
||||
| This source file is subject to version 3.01 of the PHP license, |
|
||||
| that is bundled with this package in the file LICENSE, and is |
|
||||
| available through the world-wide-web at the following url: |
|
||||
| http://www.php.net/license/3_01.txt |
|
||||
| If you did not receive a copy of the PHP license and are unable to |
|
||||
| obtain it through the world-wide-web, please send a note to |
|
||||
| license@php.net so we can mail you a copy immediately. |
|
||||
+----------------------------------------------------------------------+
|
||||
| Authors: Gustavo Lopes <cataphract@php.net> |
|
||||
+----------------------------------------------------------------------+
|
||||
*/
|
||||
|
||||
#include "codepointiterator_internal.h"
|
||||
|
||||
extern "C" {
|
||||
#define USE_BREAKITERATOR_POINTER 1
|
||||
#include "breakiterator_class.h"
|
||||
}
|
||||
|
||||
using PHP::CodePointBreakIterator;
|
||||
|
||||
static inline CodePointBreakIterator *fetch_cpbi(BreakIterator_object *bio) {
|
||||
return (CodePointBreakIterator*)bio->biter;
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(cpbi_get_last_code_point)
|
||||
{
|
||||
BREAKITER_METHOD_INIT_VARS;
|
||||
object = getThis();
|
||||
|
||||
if (zend_parse_parameters_none() == FAILURE) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"cpbi_get_last_code_point: bad arguments", 0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
BREAKITER_METHOD_FETCH_OBJECT;
|
||||
|
||||
RETURN_LONG(fetch_cpbi(bio)->getLastCodePoint());
|
||||
}
|
24
ext/intl/breakiterator/codepointiterator_methods.h
Normal file
24
ext/intl/breakiterator/codepointiterator_methods.h
Normal file
@ -0,0 +1,24 @@
|
||||
/*
|
||||
+----------------------------------------------------------------------+
|
||||
| PHP Version 5 |
|
||||
+----------------------------------------------------------------------+
|
||||
| This source file is subject to version 3.01 of the PHP license, |
|
||||
| that is bundled with this package in the file LICENSE, and is |
|
||||
| available through the world-wide-web at the following url: |
|
||||
| http://www.php.net/license/3_01.txt |
|
||||
| If you did not receive a copy of the PHP license and are unable to |
|
||||
| obtain it through the world-wide-web, please send a note to |
|
||||
| license@php.net so we can mail you a copy immediately. |
|
||||
+----------------------------------------------------------------------+
|
||||
| Authors: Gustavo Lopes <cataphract@php.net> |
|
||||
+----------------------------------------------------------------------+
|
||||
*/
|
||||
|
||||
#ifndef CODEPOINTITERATOR_METHODS_H
|
||||
#define CODEPOINTITERATOR_METHODS_H
|
||||
|
||||
#include <php.h>
|
||||
|
||||
PHP_FUNCTION(cpbi_get_last_code_point);
|
||||
|
||||
#endif
|
219
ext/intl/breakiterator/rulebasedbreakiterator_methods.cpp
Normal file
219
ext/intl/breakiterator/rulebasedbreakiterator_methods.cpp
Normal file
@ -0,0 +1,219 @@
|
||||
/*
|
||||
+----------------------------------------------------------------------+
|
||||
| PHP Version 5 |
|
||||
+----------------------------------------------------------------------+
|
||||
| This source file is subject to version 3.01 of the PHP license, |
|
||||
| that is bundled with this package in the file LICENSE, and is |
|
||||
| available through the world-wide-web at the following url: |
|
||||
| http://www.php.net/license/3_01.txt |
|
||||
| If you did not receive a copy of the PHP license and are unable to |
|
||||
| obtain it through the world-wide-web, please send a note to |
|
||||
| license@php.net so we can mail you a copy immediately. |
|
||||
+----------------------------------------------------------------------+
|
||||
| Authors: Gustavo Lopes <cataphract@php.net> |
|
||||
+----------------------------------------------------------------------+
|
||||
*/
|
||||
|
||||
#include <unicode/rbbi.h>
|
||||
|
||||
extern "C" {
|
||||
#define USE_BREAKITERATOR_POINTER 1
|
||||
#include "breakiterator_class.h"
|
||||
#include <zend_exceptions.h>
|
||||
#include <limits.h>
|
||||
}
|
||||
|
||||
#include "../intl_convertcpp.h"
|
||||
|
||||
static inline RuleBasedBreakIterator *fetch_rbbi(BreakIterator_object *bio) {
|
||||
return (RuleBasedBreakIterator*)bio->biter;
|
||||
}
|
||||
|
||||
static void _php_intlgregcal_constructor_body(INTERNAL_FUNCTION_PARAMETERS)
|
||||
{
|
||||
zval *object = getThis();
|
||||
char *rules;
|
||||
int rules_len;
|
||||
zend_bool compiled = 0;
|
||||
UErrorCode status = U_ZERO_ERROR;
|
||||
intl_error_reset(NULL TSRMLS_CC);
|
||||
|
||||
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s|b",
|
||||
&rules, &rules_len, &compiled) == FAILURE) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"rbbi_create_instance: bad arguments", 0 TSRMLS_CC);
|
||||
RETURN_NULL();
|
||||
}
|
||||
|
||||
// instantiation of ICU object
|
||||
RuleBasedBreakIterator *rbbi;
|
||||
|
||||
if (!compiled) {
|
||||
UnicodeString rulesStr;
|
||||
UParseError parseError = UParseError();
|
||||
if (intl_stringFromChar(rulesStr, rules, rules_len, &status)
|
||||
== FAILURE) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"rbbi_create_instance: rules were not a valid UTF-8 string",
|
||||
0 TSRMLS_CC);
|
||||
RETURN_NULL();
|
||||
}
|
||||
|
||||
rbbi = new RuleBasedBreakIterator(rulesStr, parseError, status);
|
||||
intl_error_set_code(NULL, status TSRMLS_CC);
|
||||
if (U_FAILURE(status)) {
|
||||
char *msg;
|
||||
smart_str parse_error_str;
|
||||
parse_error_str = intl_parse_error_to_string(&parseError);
|
||||
spprintf(&msg, 0, "rbbi_create_instance: unable to create "
|
||||
"RuleBasedBreakIterator from rules (%s)", parse_error_str.c);
|
||||
smart_str_free(&parse_error_str);
|
||||
intl_error_set_custom_msg(NULL, msg, 1 TSRMLS_CC);
|
||||
efree(msg);
|
||||
RETURN_NULL();
|
||||
}
|
||||
} else { // compiled
|
||||
#if U_ICU_VERSION_MAJOR_NUM * 10 + U_ICU_VERSION_MINOR_NUM >= 48
|
||||
rbbi = new RuleBasedBreakIterator((uint8_t*)rules, rules_len, status);
|
||||
if (U_FAILURE(status)) {
|
||||
intl_error_set(NULL, status, "rbbi_create_instance: unable to "
|
||||
"create instance from compiled rules", 0 TSRMLS_CC);
|
||||
RETURN_NULL();
|
||||
}
|
||||
#else
|
||||
intl_error_set(NULL, U_UNSUPPORTED_ERROR, "rbbi_create_instance: "
|
||||
"compiled rules require ICU >= 4.8", 0 TSRMLS_CC);
|
||||
RETURN_NULL();
|
||||
#endif
|
||||
}
|
||||
|
||||
breakiterator_object_create(return_value, rbbi TSRMLS_CC);
|
||||
}
|
||||
|
||||
U_CFUNC PHP_METHOD(IntlRuleBasedBreakIterator, __construct)
|
||||
{
|
||||
zval orig_this = *getThis();
|
||||
|
||||
return_value = getThis();
|
||||
//changes this to IS_NULL (without first destroying) if there's an error
|
||||
_php_intlgregcal_constructor_body(INTERNAL_FUNCTION_PARAM_PASSTHRU);
|
||||
|
||||
if (Z_TYPE_P(return_value) == IS_NULL) {
|
||||
zend_object_store_ctor_failed(&orig_this TSRMLS_CC);
|
||||
zval_dtor(&orig_this);
|
||||
}
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(rbbi_get_rules)
|
||||
{
|
||||
BREAKITER_METHOD_INIT_VARS;
|
||||
object = getThis();
|
||||
|
||||
if (zend_parse_parameters_none() == FAILURE) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"rbbi_get_rules: bad arguments", 0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
BREAKITER_METHOD_FETCH_OBJECT;
|
||||
|
||||
const UnicodeString rules = fetch_rbbi(bio)->getRules();
|
||||
|
||||
Z_TYPE_P(return_value) = IS_STRING;
|
||||
if (intl_charFromString(rules, &Z_STRVAL_P(return_value),
|
||||
&Z_STRLEN_P(return_value), BREAKITER_ERROR_CODE_P(bio)) == FAILURE)
|
||||
{
|
||||
intl_errors_set(BREAKITER_ERROR_P(bio), BREAKITER_ERROR_CODE(bio),
|
||||
"rbbi_hash_code: Error converting result to UTF-8 string",
|
||||
0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(rbbi_get_rule_status)
|
||||
{
|
||||
BREAKITER_METHOD_INIT_VARS;
|
||||
object = getThis();
|
||||
|
||||
if (zend_parse_parameters_none() == FAILURE) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"rbbi_get_rule_status: bad arguments", 0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
BREAKITER_METHOD_FETCH_OBJECT;
|
||||
|
||||
RETURN_LONG(fetch_rbbi(bio)->getRuleStatus());
|
||||
}
|
||||
|
||||
U_CFUNC PHP_FUNCTION(rbbi_get_rule_status_vec)
|
||||
{
|
||||
BREAKITER_METHOD_INIT_VARS;
|
||||
object = getThis();
|
||||
|
||||
if (zend_parse_parameters_none() == FAILURE) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"rbbi_get_rule_status_vec: bad arguments", 0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
BREAKITER_METHOD_FETCH_OBJECT;
|
||||
|
||||
int32_t num_rules = fetch_rbbi(bio)->getRuleStatusVec(NULL, 0,
|
||||
BREAKITER_ERROR_CODE(bio));
|
||||
if (BREAKITER_ERROR_CODE(bio) == U_BUFFER_OVERFLOW_ERROR) {
|
||||
BREAKITER_ERROR_CODE(bio) = U_ZERO_ERROR;
|
||||
} else {
|
||||
// should not happen
|
||||
INTL_METHOD_CHECK_STATUS(bio, "rbbi_get_rule_status_vec: failed "
|
||||
" determining the number of status values");
|
||||
}
|
||||
int32_t *rules = new int32_t[num_rules];
|
||||
num_rules = fetch_rbbi(bio)->getRuleStatusVec(rules, num_rules,
|
||||
BREAKITER_ERROR_CODE(bio));
|
||||
if (U_FAILURE(BREAKITER_ERROR_CODE(bio))) {
|
||||
delete[] rules;
|
||||
intl_errors_set(BREAKITER_ERROR_P(bio), BREAKITER_ERROR_CODE(bio),
|
||||
"rbbi_get_rule_status_vec: failed obtaining the status values",
|
||||
0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
array_init_size(return_value, num_rules);
|
||||
for (int32_t i = 0; i < num_rules; i++) {
|
||||
add_next_index_long(return_value, rules[i]);
|
||||
}
|
||||
delete[] rules;
|
||||
}
|
||||
|
||||
#if U_ICU_VERSION_MAJOR_NUM * 10 + U_ICU_VERSION_MINOR_NUM >= 48
|
||||
U_CFUNC PHP_FUNCTION(rbbi_get_binary_rules)
|
||||
{
|
||||
BREAKITER_METHOD_INIT_VARS;
|
||||
object = getThis();
|
||||
|
||||
if (zend_parse_parameters_none() == FAILURE) {
|
||||
intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR,
|
||||
"rbbi_get_binary_rules: bad arguments", 0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
BREAKITER_METHOD_FETCH_OBJECT;
|
||||
|
||||
uint32_t rules_len;
|
||||
const uint8_t *rules = fetch_rbbi(bio)->getBinaryRules(rules_len);
|
||||
|
||||
if (rules_len > INT_MAX - 1) {
|
||||
intl_errors_set(BREAKITER_ERROR_P(bio), BREAKITER_ERROR_CODE(bio),
|
||||
"rbbi_get_binary_rules: the rules are too large",
|
||||
0 TSRMLS_CC);
|
||||
RETURN_FALSE;
|
||||
}
|
||||
|
||||
char *ret_rules = static_cast<char*>(emalloc(rules_len + 1));
|
||||
memcpy(ret_rules, rules, rules_len);
|
||||
ret_rules[rules_len] = '\0';
|
||||
|
||||
RETURN_STRINGL(ret_rules, rules_len, 0);
|
||||
}
|
||||
#endif
|
32
ext/intl/breakiterator/rulebasedbreakiterator_methods.h
Normal file
32
ext/intl/breakiterator/rulebasedbreakiterator_methods.h
Normal file
@ -0,0 +1,32 @@
|
||||
/*
|
||||
+----------------------------------------------------------------------+
|
||||
| PHP Version 5 |
|
||||
+----------------------------------------------------------------------+
|
||||
| This source file is subject to version 3.01 of the PHP license, |
|
||||
| that is bundled with this package in the file LICENSE, and is |
|
||||
| available through the world-wide-web at the following url: |
|
||||
| http://www.php.net/license/3_01.txt |
|
||||
| If you did not receive a copy of the PHP license and are unable to |
|
||||
| obtain it through the world-wide-web, please send a note to |
|
||||
| license@php.net so we can mail you a copy immediately. |
|
||||
+----------------------------------------------------------------------+
|
||||
| Authors: Gustavo Lopes <cataphract@php.net> |
|
||||
+----------------------------------------------------------------------+
|
||||
*/
|
||||
|
||||
#ifndef RULEBASEDBREAKITERATOR_METHODS_H
|
||||
#define RULEBASEDBREAKITERATOR_METHODS_H
|
||||
|
||||
#include <php.h>
|
||||
|
||||
PHP_METHOD(IntlRuleBasedBreakIterator, __construct);
|
||||
|
||||
PHP_FUNCTION(rbbi_get_rules);
|
||||
|
||||
PHP_FUNCTION(rbbi_get_rule_status);
|
||||
|
||||
PHP_FUNCTION(rbbi_get_rule_status_vec);
|
||||
|
||||
PHP_FUNCTION(rbbi_get_binary_rules);
|
||||
|
||||
#endif
|
@ -25,12 +25,12 @@
|
||||
#include <unicode/ustring.h>
|
||||
#include "../intl_convertcpp.h"
|
||||
extern "C" {
|
||||
#include "../php_intl.h"
|
||||
#define USE_TIMEZONE_POINTER 1
|
||||
#include "../timezone/timezone_class.h"
|
||||
#define USE_CALENDAR_POINTER 1
|
||||
#include "calendar_class.h"
|
||||
#include "../intl_convert.h"
|
||||
#include "../locale/locale.h"
|
||||
#include <zend_exceptions.h>
|
||||
#include <zend_interfaces.h>
|
||||
#include <ext/date/php_date.h>
|
||||
|
@ -24,11 +24,11 @@
|
||||
#include <unicode/calendar.h>
|
||||
#include <unicode/gregocal.h>
|
||||
extern "C" {
|
||||
#include "../php_intl.h"
|
||||
#define USE_TIMEZONE_POINTER 1
|
||||
#include "../timezone/timezone_class.h"
|
||||
#define USE_CALENDAR_POINTER 1
|
||||
#include "calendar_class.h"
|
||||
#include "../locale/locale.h"
|
||||
#include <ext/date/php_date.h>
|
||||
}
|
||||
|
||||
|
@ -26,45 +26,14 @@
|
||||
#include "common_enum.h"
|
||||
|
||||
extern "C" {
|
||||
#include "intl_error.h"
|
||||
#include "intl_data.h"
|
||||
#include <zend_interfaces.h>
|
||||
#include <zend_exceptions.h>
|
||||
}
|
||||
|
||||
static zend_class_entry *IntlIterator_ce_ptr;
|
||||
static zend_object_handlers IntlIterator_handlers;
|
||||
zend_class_entry *IntlIterator_ce_ptr;
|
||||
zend_object_handlers IntlIterator_handlers;
|
||||
|
||||
typedef struct {
|
||||
zend_object zo;
|
||||
intl_error err;
|
||||
zend_object_iterator *iterator;
|
||||
} IntlIterator_object;
|
||||
|
||||
#define INTLITERATOR_ERROR(ii) (ii)->err
|
||||
#define INTLITERATOR_ERROR_P(ii) &(INTLITERATOR_ERROR(ii))
|
||||
|
||||
#define INTLITERATOR_ERROR_CODE(ii) INTL_ERROR_CODE(INTLITERATOR_ERROR(ii))
|
||||
#define INTLITERATOR_ERROR_CODE_P(ii) &(INTL_ERROR_CODE(INTLITERATOR_ERROR(ii)))
|
||||
|
||||
#define INTLITERATOR_METHOD_INIT_VARS INTL_METHOD_INIT_VARS(IntlIterator, ii)
|
||||
#define INTLITERATOR_METHOD_FETCH_OBJECT_NO_CHECK INTL_METHOD_FETCH_OBJECT(IntlIterator, ii)
|
||||
#define INTLITERATOR_METHOD_FETCH_OBJECT\
|
||||
object = getThis(); \
|
||||
INTLITERATOR_METHOD_FETCH_OBJECT_NO_CHECK; \
|
||||
if (ii->iterator == NULL) { \
|
||||
intl_errors_set(&ii->err, U_ILLEGAL_ARGUMENT_ERROR, "Found unconstructed IntlIterator", 0 TSRMLS_CC); \
|
||||
RETURN_FALSE; \
|
||||
}
|
||||
|
||||
typedef struct {
|
||||
zend_object_iterator zoi;
|
||||
zval *current;
|
||||
zval *wrapping_obj;
|
||||
void (*destroy_free_it)(zend_object_iterator *iterator TSRMLS_DC);
|
||||
} zoi_with_current;
|
||||
|
||||
static void zoi_with_current_dtor(zend_object_iterator *iter TSRMLS_DC)
|
||||
void zoi_with_current_dtor(zend_object_iterator *iter TSRMLS_DC)
|
||||
{
|
||||
zoi_with_current *zoiwc = (zoi_with_current*)iter;
|
||||
|
||||
@ -84,22 +53,22 @@ static void zoi_with_current_dtor(zend_object_iterator *iter TSRMLS_DC)
|
||||
* function being called by the iterator wrapper destructor function and
|
||||
* not finding the memory of this iterator allocated anymore. */
|
||||
iter->funcs->invalidate_current(iter TSRMLS_CC);
|
||||
zoiwc->destroy_free_it(iter TSRMLS_CC);
|
||||
zoiwc->destroy_it(iter TSRMLS_CC);
|
||||
efree(iter);
|
||||
}
|
||||
}
|
||||
|
||||
static int zoi_with_current_valid(zend_object_iterator *iter TSRMLS_DC)
|
||||
U_CFUNC int zoi_with_current_valid(zend_object_iterator *iter TSRMLS_DC)
|
||||
{
|
||||
return ((zoi_with_current*)iter)->current != NULL ? SUCCESS : FAILURE;
|
||||
}
|
||||
|
||||
static void zoi_with_current_get_current_data(zend_object_iterator *iter, zval ***data TSRMLS_DC)
|
||||
U_CFUNC void zoi_with_current_get_current_data(zend_object_iterator *iter, zval ***data TSRMLS_DC)
|
||||
{
|
||||
*data = &((zoi_with_current*)iter)->current;
|
||||
}
|
||||
|
||||
static void zoi_with_current_invalidate_current(zend_object_iterator *iter TSRMLS_DC)
|
||||
U_CFUNC void zoi_with_current_invalidate_current(zend_object_iterator *iter TSRMLS_DC)
|
||||
{
|
||||
zoi_with_current *zoi_iter = (zoi_with_current*)iter;
|
||||
if (zoi_iter->current) {
|
||||
@ -155,7 +124,7 @@ static void string_enum_rewind(zend_object_iterator *iter TSRMLS_DC)
|
||||
}
|
||||
}
|
||||
|
||||
static void string_enum_destroy_free_it(zend_object_iterator *iter TSRMLS_DC)
|
||||
static void string_enum_destroy_it(zend_object_iterator *iter TSRMLS_DC)
|
||||
{
|
||||
delete (StringEnumeration*)iter->data;
|
||||
}
|
||||
@ -179,7 +148,7 @@ U_CFUNC void IntlIterator_from_StringEnumeration(StringEnumeration *se, zval *ob
|
||||
ii->iterator->data = (void*)se;
|
||||
ii->iterator->funcs = &string_enum_object_iterator_funcs;
|
||||
ii->iterator->index = 0;
|
||||
((zoi_with_current*)ii->iterator)->destroy_free_it = string_enum_destroy_free_it;
|
||||
((zoi_with_current*)ii->iterator)->destroy_it = string_enum_destroy_it;
|
||||
((zoi_with_current*)ii->iterator)->wrapping_obj = object;
|
||||
((zoi_with_current*)ii->iterator)->current = NULL;
|
||||
}
|
||||
@ -331,7 +300,7 @@ static PHP_METHOD(IntlIterator, rewind)
|
||||
if (ii->iterator->funcs->rewind) {
|
||||
ii->iterator->funcs->rewind(ii->iterator TSRMLS_CC);
|
||||
} else {
|
||||
intl_error_set(NULL, U_UNSUPPORTED_ERROR,
|
||||
intl_errors_set(INTLITERATOR_ERROR_P(ii), U_UNSUPPORTED_ERROR,
|
||||
"IntlIterator::rewind: rewind not supported", 0 TSRMLS_CC);
|
||||
}
|
||||
}
|
||||
|
@ -25,10 +25,49 @@ extern "C" {
|
||||
#include <math.h>
|
||||
#endif
|
||||
#include <php.h>
|
||||
#include "../intl_error.h"
|
||||
#include "../intl_data.h"
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#define INTLITERATOR_ERROR(ii) (ii)->err
|
||||
#define INTLITERATOR_ERROR_P(ii) &(INTLITERATOR_ERROR(ii))
|
||||
|
||||
#define INTLITERATOR_ERROR_CODE(ii) INTL_ERROR_CODE(INTLITERATOR_ERROR(ii))
|
||||
#define INTLITERATOR_ERROR_CODE_P(ii) &(INTL_ERROR_CODE(INTLITERATOR_ERROR(ii)))
|
||||
|
||||
#define INTLITERATOR_METHOD_INIT_VARS INTL_METHOD_INIT_VARS(IntlIterator, ii)
|
||||
#define INTLITERATOR_METHOD_FETCH_OBJECT_NO_CHECK INTL_METHOD_FETCH_OBJECT(IntlIterator, ii)
|
||||
#define INTLITERATOR_METHOD_FETCH_OBJECT\
|
||||
object = getThis(); \
|
||||
INTLITERATOR_METHOD_FETCH_OBJECT_NO_CHECK; \
|
||||
if (ii->iterator == NULL) { \
|
||||
intl_errors_set(&ii->err, U_ILLEGAL_ARGUMENT_ERROR, "Found unconstructed IntlIterator", 0 TSRMLS_CC); \
|
||||
RETURN_FALSE; \
|
||||
}
|
||||
|
||||
typedef struct {
|
||||
zend_object zo;
|
||||
intl_error err;
|
||||
zend_object_iterator *iterator;
|
||||
} IntlIterator_object;
|
||||
|
||||
typedef struct {
|
||||
zend_object_iterator zoi;
|
||||
zval *current;
|
||||
zval *wrapping_obj;
|
||||
void (*destroy_it)(zend_object_iterator *iterator TSRMLS_DC);
|
||||
} zoi_with_current;
|
||||
|
||||
extern zend_class_entry *IntlIterator_ce_ptr;
|
||||
extern zend_object_handlers IntlIterator_handlers;
|
||||
|
||||
U_CFUNC void zoi_with_current_dtor(zend_object_iterator *iter TSRMLS_DC);
|
||||
U_CFUNC int zoi_with_current_valid(zend_object_iterator *iter TSRMLS_DC);
|
||||
U_CFUNC void zoi_with_current_get_current_data(zend_object_iterator *iter, zval ***data TSRMLS_DC);
|
||||
U_CFUNC void zoi_with_current_invalidate_current(zend_object_iterator *iter TSRMLS_DC);
|
||||
|
||||
#ifdef __cplusplus
|
||||
U_CFUNC void IntlIterator_from_StringEnumeration(StringEnumeration *se, zval *object TSRMLS_DC);
|
||||
#endif
|
||||
|
@ -75,6 +75,12 @@ if test "$PHP_INTL" != "no"; then
|
||||
calendar/calendar_class.cpp \
|
||||
calendar/calendar_methods.cpp \
|
||||
calendar/gregoriancalendar_methods.cpp \
|
||||
breakiterator/breakiterator_class.cpp \
|
||||
breakiterator/breakiterator_iterators.cpp \
|
||||
breakiterator/breakiterator_methods.cpp \
|
||||
breakiterator/rulebasedbreakiterator_methods.cpp \
|
||||
breakiterator/codepointiterator_internal.cpp \
|
||||
breakiterator/codepointiterator_methods.cpp \
|
||||
idn/idn.c \
|
||||
$icu_spoof_src, $ext_shared,,$ICU_INCS -Wno-write-strings)
|
||||
PHP_ADD_BUILD_DIR($ext_builddir/collator)
|
||||
@ -91,4 +97,5 @@ if test "$PHP_INTL" != "no"; then
|
||||
PHP_ADD_BUILD_DIR($ext_builddir/calendar)
|
||||
PHP_ADD_BUILD_DIR($ext_builddir/idn)
|
||||
PHP_ADD_BUILD_DIR($ext_builddir/spoofchecker)
|
||||
PHP_ADD_BUILD_DIR($ext_builddir/breakiterator)
|
||||
fi
|
||||
|
@ -102,6 +102,15 @@ if (PHP_INTL != "no") {
|
||||
gregoriancalendar_methods.cpp \
|
||||
calendar_class.cpp",
|
||||
"intl");
|
||||
|
||||
ADD_SOURCES(configure_module_dirname + "/breakiterator", "\
|
||||
breakiterator_class.cpp \
|
||||
breakiterator_methods.cpp \
|
||||
breakiterator_iterators.cpp \
|
||||
rulebasedbreakiterator_methods.cpp \
|
||||
codepointiterator_internal.cpp \
|
||||
codepointiterator_methods.cpp ",
|
||||
"intl");
|
||||
|
||||
ADD_FLAG("LIBS_INTL", "icudt.lib icuin.lib icuio.lib icule.lib iculx.lib");
|
||||
AC_DEFINE("HAVE_INTL", 1, "Internationalization support enabled");
|
||||
|
@ -25,6 +25,7 @@
|
||||
|
||||
#include "php_intl.h"
|
||||
#include "intl_error.h"
|
||||
#include "intl_convert.h"
|
||||
|
||||
ZEND_EXTERN_MODULE_GLOBALS( intl )
|
||||
|
||||
@ -242,7 +243,82 @@ void intl_register_IntlException_class( TSRMLS_D )
|
||||
default_exception_ce, NULL TSRMLS_CC );
|
||||
IntlException_ce_ptr->create_object = default_exception_ce->create_object;
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
smart_str intl_parse_error_to_string( UParseError* pe )
|
||||
{
|
||||
smart_str ret = {0};
|
||||
char *buf;
|
||||
int u8len;
|
||||
UErrorCode status;
|
||||
int any = 0;
|
||||
|
||||
assert( pe != NULL );
|
||||
|
||||
smart_str_appends( &ret, "parse error " );
|
||||
if( pe->line > 0 )
|
||||
{
|
||||
smart_str_appends( &ret, "on line " );
|
||||
smart_str_append_long( &ret, (long ) pe->line );
|
||||
any = 1;
|
||||
}
|
||||
if( pe->offset >= 0 ) {
|
||||
if( any )
|
||||
smart_str_appends( &ret, ", " );
|
||||
else
|
||||
smart_str_appends( &ret, "at " );
|
||||
|
||||
smart_str_appends( &ret, "offset " );
|
||||
smart_str_append_long( &ret, (long ) pe->offset );
|
||||
any = 1;
|
||||
}
|
||||
|
||||
if (pe->preContext[0] != 0 ) {
|
||||
if( any )
|
||||
smart_str_appends( &ret, ", " );
|
||||
|
||||
smart_str_appends( &ret, "after \"" );
|
||||
intl_convert_utf16_to_utf8( &buf, &u8len, pe->preContext, -1, &status );
|
||||
if( U_FAILURE( status ) )
|
||||
{
|
||||
smart_str_appends( &ret, "(could not convert parser error pre-context to UTF-8)" );
|
||||
}
|
||||
else {
|
||||
smart_str_appendl( &ret, buf, u8len );
|
||||
efree( buf );
|
||||
}
|
||||
smart_str_appends( &ret, "\"" );
|
||||
any = 1;
|
||||
}
|
||||
|
||||
if( pe->postContext[0] != 0 )
|
||||
{
|
||||
if( any )
|
||||
smart_str_appends( &ret, ", " );
|
||||
|
||||
smart_str_appends( &ret, "before or at \"" );
|
||||
intl_convert_utf16_to_utf8( &buf, &u8len, pe->postContext, -1, &status );
|
||||
if( U_FAILURE( status ) )
|
||||
{
|
||||
smart_str_appends( &ret, "(could not convert parser error post-context to UTF-8)" );
|
||||
}
|
||||
else
|
||||
{
|
||||
smart_str_appendl( &ret, buf, u8len );
|
||||
efree( buf );
|
||||
}
|
||||
smart_str_appends( &ret, "\"" );
|
||||
any = 1;
|
||||
}
|
||||
|
||||
if( !any )
|
||||
{
|
||||
smart_str_free( &ret );
|
||||
smart_str_appends( &ret, "no parse error" );
|
||||
}
|
||||
|
||||
smart_str_0( &ret );
|
||||
return ret;
|
||||
}
|
||||
|
||||
/*
|
||||
* Local variables:
|
||||
|
@ -20,6 +20,8 @@
|
||||
#define INTL_ERROR_H
|
||||
|
||||
#include <unicode/utypes.h>
|
||||
#include <unicode/parseerr.h>
|
||||
#include <ext/standard/php_smart_str.h>
|
||||
|
||||
#define INTL_ERROR_CODE(e) (e).code
|
||||
|
||||
@ -44,6 +46,9 @@ void intl_errors_set_custom_msg( intl_error* err, char* msg, int copyMsg
|
||||
void intl_errors_set_code( intl_error* err, UErrorCode err_code TSRMLS_DC );
|
||||
void intl_errors_set( intl_error* err, UErrorCode code, char* msg, int copyMsg TSRMLS_DC );
|
||||
|
||||
// Other error helpers
|
||||
smart_str intl_parse_error_to_string( UParseError* pe );
|
||||
|
||||
// exported to be called on extension MINIT
|
||||
void intl_register_IntlException_class( TSRMLS_D );
|
||||
|
||||
|
@ -22,8 +22,6 @@
|
||||
#include <php.h>
|
||||
|
||||
void locale_register_constants( INIT_FUNC_ARGS );
|
||||
|
||||
const char *intl_locale_get_default( TSRMLS_D );
|
||||
|
||||
#define OPTION_DEFAULT NULL
|
||||
#define LOC_LANG_TAG "language"
|
||||
|
@ -201,14 +201,6 @@ static int getSingletonPos(char* str)
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
const char *intl_locale_get_default( TSRMLS_D )
|
||||
{
|
||||
if( INTL_G(default_locale) == NULL ) {
|
||||
return uloc_getDefault();
|
||||
}
|
||||
return INTL_G(default_locale);
|
||||
}
|
||||
|
||||
/* {{{ proto static string Locale::getDefault( )
|
||||
Get default locale */
|
||||
/* }}} */
|
||||
|
@ -78,6 +78,9 @@
|
||||
#include "calendar/calendar_methods.h"
|
||||
#include "calendar/gregoriancalendar_methods.h"
|
||||
|
||||
#include "breakiterator/breakiterator_class.h"
|
||||
#include "breakiterator/breakiterator_iterators.h"
|
||||
|
||||
#include "idn/idn.h"
|
||||
|
||||
#if U_ICU_VERSION_MAJOR_NUM > 3 && U_ICU_VERSION_MINOR_NUM >=2
|
||||
@ -109,6 +112,14 @@
|
||||
|
||||
ZEND_DECLARE_MODULE_GLOBALS( intl )
|
||||
|
||||
const char *intl_locale_get_default( TSRMLS_D )
|
||||
{
|
||||
if( INTL_G(default_locale) == NULL ) {
|
||||
return uloc_getDefault();
|
||||
}
|
||||
return INTL_G(default_locale);
|
||||
}
|
||||
|
||||
/* {{{ Arguments info */
|
||||
ZEND_BEGIN_ARG_INFO_EX(collator_static_0_args, 0, 0, 0)
|
||||
ZEND_END_ARG_INFO()
|
||||
@ -958,6 +969,12 @@ PHP_MINIT_FUNCTION( intl )
|
||||
/* Register 'IntlIterator' PHP class */
|
||||
intl_register_IntlIterator_class( TSRMLS_C );
|
||||
|
||||
/* Register 'BreakIterator' class */
|
||||
breakiterator_register_BreakIterator_class( TSRMLS_C );
|
||||
|
||||
/* Register 'IntlPartsIterator' class */
|
||||
breakiterator_register_IntlPartsIterator_class( TSRMLS_C );
|
||||
|
||||
/* Global error handling. */
|
||||
intl_error_init( NULL TSRMLS_CC );
|
||||
|
||||
|
@ -69,6 +69,8 @@ PHP_RINIT_FUNCTION(intl);
|
||||
PHP_RSHUTDOWN_FUNCTION(intl);
|
||||
PHP_MINFO_FUNCTION(intl);
|
||||
|
||||
const char *intl_locale_get_default( TSRMLS_D );
|
||||
|
||||
#define PHP_INTL_VERSION "1.1.0"
|
||||
|
||||
#endif /* PHP_INTL_H */
|
||||
|
@ -78,13 +78,11 @@ static zend_object_value ResourceBundle_object_create( zend_class_entry *ce TSRM
|
||||
/* {{{ ResourceBundle_ctor */
|
||||
static void resourcebundle_ctor(INTERNAL_FUNCTION_PARAMETERS)
|
||||
{
|
||||
char * bundlename;
|
||||
int bundlename_len = 0;
|
||||
char * locale;
|
||||
int locale_len = 0;
|
||||
zend_bool fallback = 1;
|
||||
|
||||
char * pbuf;
|
||||
const char *bundlename;
|
||||
int bundlename_len = 0;
|
||||
const char *locale;
|
||||
int locale_len = 0;
|
||||
zend_bool fallback = 1;
|
||||
|
||||
zval *object = return_value;
|
||||
ResourceBundle_object *rb = (ResourceBundle_object *) zend_object_store_get_object( object TSRMLS_CC);
|
||||
@ -116,6 +114,7 @@ static void resourcebundle_ctor(INTERNAL_FUNCTION_PARAMETERS)
|
||||
|
||||
if (!fallback && (INTL_DATA_ERROR_CODE(rb) == U_USING_FALLBACK_WARNING ||
|
||||
INTL_DATA_ERROR_CODE(rb) == U_USING_DEFAULT_WARNING)) {
|
||||
char *pbuf;
|
||||
intl_errors_set_code(NULL, INTL_DATA_ERROR_CODE(rb) TSRMLS_CC);
|
||||
spprintf(&pbuf, 0, "resourcebundle_ctor: Cannot load libICU resource "
|
||||
"'%s' without fallback from %s to %s",
|
||||
|
13
ext/intl/tests/breakiter___construct.phpt
Normal file
13
ext/intl/tests/breakiter___construct.phpt
Normal file
@ -0,0 +1,13 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::__construct() should not be callable
|
||||
--SKIPIF--
|
||||
if (!extension_loaded('intl'))
|
||||
die('skip intl extension not enabled');
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
|
||||
new IntlBreakIterator();
|
||||
--EXPECTF--
|
||||
|
||||
Fatal error: Call to private IntlBreakIterator::__construct() from invalid context in %s on line %d
|
38
ext/intl/tests/breakiter___construct_error.phpt
Normal file
38
ext/intl/tests/breakiter___construct_error.phpt
Normal file
@ -0,0 +1,38 @@
|
||||
--TEST--
|
||||
IntlRuleBasedBreakIterator::__construct(): arg errors
|
||||
--SKIPIF--
|
||||
<?php if( !extension_loaded( 'intl' ) ) print 'skip'; ?>
|
||||
<?php if(version_compare(INTL_ICU_VERSION, '4.8') < 0) print 'skip ICU >= 4.8 only'; ?>
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
|
||||
//missing ; at the end:
|
||||
var_dump(new IntlRuleBasedBreakIterator('[\p{Letter}\uFFFD]+;[:number:]+'));
|
||||
var_dump(new IntlRuleBasedBreakIterator());
|
||||
var_dump(new IntlRuleBasedBreakIterator(1,2,3));
|
||||
var_dump(new IntlRuleBasedBreakIterator('[\p{Letter}\uFFFD]+;[:number:]+;', array()));
|
||||
var_dump(new IntlRuleBasedBreakIterator('[\p{Letter}\uFFFD]+;[:number:]+;', true));
|
||||
|
||||
--EXPECTF--
|
||||
|
||||
Warning: IntlRuleBasedBreakIterator::__construct(): rbbi_create_instance: unable to create RuleBasedBreakIterator from rules (parse error on line 1, offset 31) in %s on line %d
|
||||
NULL
|
||||
|
||||
Warning: IntlRuleBasedBreakIterator::__construct() expects at least 1 parameter, 0 given in %s on line %d
|
||||
|
||||
Warning: IntlRuleBasedBreakIterator::__construct(): rbbi_create_instance: bad arguments in %s on line %d
|
||||
NULL
|
||||
|
||||
Warning: IntlRuleBasedBreakIterator::__construct() expects at most 2 parameters, 3 given in %s on line %d
|
||||
|
||||
Warning: IntlRuleBasedBreakIterator::__construct(): rbbi_create_instance: bad arguments in %s on line %d
|
||||
NULL
|
||||
|
||||
Warning: IntlRuleBasedBreakIterator::__construct() expects parameter 2 to be boolean, array given in %s on line %d
|
||||
|
||||
Warning: IntlRuleBasedBreakIterator::__construct(): rbbi_create_instance: bad arguments in %s on line %d
|
||||
NULL
|
||||
|
||||
Warning: IntlRuleBasedBreakIterator::__construct(): rbbi_create_instance: unable to create instance from compiled rules in %s on line %d
|
||||
NULL
|
23
ext/intl/tests/breakiter_clone_basic.phpt
Normal file
23
ext/intl/tests/breakiter_clone_basic.phpt
Normal file
@ -0,0 +1,23 @@
|
||||
--TEST--
|
||||
IntlBreakIterator: clone handler
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
|
||||
$bi = new IntlRuleBasedBreakIterator('[\p{Letter}\uFFFD]+;[:number:]+;');
|
||||
$bi_clone = clone $bi;
|
||||
var_dump(get_class($bi), get_class($bi_clone));
|
||||
var_dump($bi == $bi_clone);
|
||||
|
||||
$bi->setText('foobar');
|
||||
$bi_clone = clone $bi;
|
||||
var_dump(get_class($bi), get_class($bi_clone));
|
||||
var_dump($bi == $bi_clone);
|
||||
|
||||
--EXPECT--
|
||||
string(26) "IntlRuleBasedBreakIterator"
|
||||
string(26) "IntlRuleBasedBreakIterator"
|
||||
bool(true)
|
||||
string(26) "IntlRuleBasedBreakIterator"
|
||||
string(26) "IntlRuleBasedBreakIterator"
|
||||
bool(true)
|
43
ext/intl/tests/breakiter_createCodePointInstance_basic.phpt
Normal file
43
ext/intl/tests/breakiter_createCodePointInstance_basic.phpt
Normal file
@ -0,0 +1,43 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::createCodePointInstance(): basic test
|
||||
--SKIPIF--
|
||||
<?php
|
||||
if (!extension_loaded('intl'))
|
||||
die('skip intl extension not enabled');
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$text = 'ตัวอย่างข้อความ';
|
||||
|
||||
$codepoint_it = IntlBreakIterator::createCodePointInstance();
|
||||
var_dump(get_class($codepoint_it));
|
||||
$codepoint_it->setText($text);
|
||||
|
||||
print_r(iterator_to_array($codepoint_it));
|
||||
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
string(26) "IntlCodePointBreakIterator"
|
||||
Array
|
||||
(
|
||||
[0] => 0
|
||||
[1] => 3
|
||||
[2] => 6
|
||||
[3] => 9
|
||||
[4] => 12
|
||||
[5] => 15
|
||||
[6] => 18
|
||||
[7] => 21
|
||||
[8] => 24
|
||||
[9] => 27
|
||||
[10] => 30
|
||||
[11] => 33
|
||||
[12] => 36
|
||||
[13] => 39
|
||||
[14] => 42
|
||||
[15] => 45
|
||||
)
|
||||
==DONE==
|
18
ext/intl/tests/breakiter_createCodePointInstance_error.phpt
Normal file
18
ext/intl/tests/breakiter_createCodePointInstance_error.phpt
Normal file
@ -0,0 +1,18 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::createCodePointInstance(): bad arguments
|
||||
--SKIPIF--
|
||||
<?php
|
||||
if (!extension_loaded('intl'))
|
||||
die('skip intl extension not enabled');
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
|
||||
var_dump(IntlBreakIterator::createCodePointInstance(array()));
|
||||
--EXPECTF--
|
||||
|
||||
Warning: IntlBreakIterator::createCodePointInstance() expects exactly 0 parameters, 1 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::createCodePointInstance(): breakiter_create_code_point_instance: bad arguments in %s on line %d
|
||||
NULL
|
||||
|
24
ext/intl/tests/breakiter_current_basic.phpt
Normal file
24
ext/intl/tests/breakiter_current_basic.phpt
Normal file
@ -0,0 +1,24 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::current(): basic test
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$bi = IntlBreakIterator::createWordInstance('pt');
|
||||
var_dump($bi->current());
|
||||
$bi->setText('foo bar trans zoo bee');
|
||||
|
||||
var_dump($bi->first());
|
||||
var_dump($bi->current());
|
||||
var_dump($bi->next());
|
||||
var_dump($bi->current());
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
int(0)
|
||||
int(0)
|
||||
int(0)
|
||||
int(3)
|
||||
int(3)
|
||||
==DONE==
|
45
ext/intl/tests/breakiter_factories_basic.phpt
Normal file
45
ext/intl/tests/breakiter_factories_basic.phpt
Normal file
@ -0,0 +1,45 @@
|
||||
--TEST--
|
||||
IntlBreakIterator factories: basic tests
|
||||
--SKIPIF--
|
||||
if (!extension_loaded('intl'))
|
||||
die('skip intl extension not enabled');
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "ja");
|
||||
|
||||
$m = array('createWordInstance', 'createLineInstance', 'createCharacterInstance',
|
||||
'createSentenceInstance', 'createTitleInstance');
|
||||
|
||||
$t = 'Frase 1... Frase 2'.
|
||||
|
||||
$o1 = $o2 = null;
|
||||
foreach ($m as $method) {
|
||||
echo "===== $method =====\n";
|
||||
$o1 = call_user_func(array('IntlBreakIterator', $method), 'ja');
|
||||
var_dump($o1 == $o2);
|
||||
$o2 = call_user_func(array('IntlBreakIterator', $method), NULL);
|
||||
var_dump($o1 == $o2);
|
||||
echo "\n";
|
||||
}
|
||||
--EXPECT--
|
||||
===== createWordInstance =====
|
||||
bool(false)
|
||||
bool(true)
|
||||
|
||||
===== createLineInstance =====
|
||||
bool(false)
|
||||
bool(true)
|
||||
|
||||
===== createCharacterInstance =====
|
||||
bool(false)
|
||||
bool(true)
|
||||
|
||||
===== createSentenceInstance =====
|
||||
bool(false)
|
||||
bool(true)
|
||||
|
||||
===== createTitleInstance =====
|
||||
bool(false)
|
||||
bool(true)
|
||||
|
39
ext/intl/tests/breakiter_factories_error.phpt
Normal file
39
ext/intl/tests/breakiter_factories_error.phpt
Normal file
@ -0,0 +1,39 @@
|
||||
--TEST--
|
||||
IntlBreakIterator factory methods: argument errors
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
|
||||
var_dump(IntlBreakIterator::createWordInstance(array()));
|
||||
var_dump(IntlBreakIterator::createSentenceInstance(NULL, 2));
|
||||
var_dump(IntlBreakIterator::createCharacterInstance(NULL, 2));
|
||||
var_dump(IntlBreakIterator::createTitleInstance(NULL, 2));
|
||||
var_dump(IntlBreakIterator::createLineInstance(NULL, 2));
|
||||
|
||||
|
||||
--EXPECTF--
|
||||
|
||||
Warning: IntlBreakIterator::createWordInstance() expects parameter 1 to be string, array given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::createWordInstance(): breakiter_create_word_instance: bad arguments in %s on line %d
|
||||
NULL
|
||||
|
||||
Warning: IntlBreakIterator::createSentenceInstance() expects exactly 1 parameter, 2 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::createSentenceInstance(): breakiter_create_sentence_instance: bad arguments in %s on line %d
|
||||
NULL
|
||||
|
||||
Warning: IntlBreakIterator::createCharacterInstance() expects exactly 1 parameter, 2 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::createCharacterInstance(): breakiter_create_character_instance: bad arguments in %s on line %d
|
||||
NULL
|
||||
|
||||
Warning: IntlBreakIterator::createTitleInstance() expects exactly 1 parameter, 2 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::createTitleInstance(): breakiter_create_title_instance: bad arguments in %s on line %d
|
||||
NULL
|
||||
|
||||
Warning: IntlBreakIterator::createLineInstance() expects exactly 1 parameter, 2 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::createLineInstance(): breakiter_create_line_instance: bad arguments in %s on line %d
|
||||
NULL
|
21
ext/intl/tests/breakiter_first_basic.phpt
Normal file
21
ext/intl/tests/breakiter_first_basic.phpt
Normal file
@ -0,0 +1,21 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::first(): basic test
|
||||
--SKIPIF--
|
||||
if (!extension_loaded('intl'))
|
||||
die('skip intl extension not enabled');
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
|
||||
$bi = IntlBreakIterator::createWordInstance('pt');
|
||||
$bi->setText('foo bar trans');
|
||||
|
||||
var_dump($bi->current());
|
||||
var_dump($bi->next());
|
||||
var_dump($bi->first());
|
||||
var_dump($bi->current());
|
||||
--EXPECT--
|
||||
int(0)
|
||||
int(3)
|
||||
int(0)
|
||||
int(0)
|
@ -0,0 +1,35 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::first()/last()/previous()/current(): arg errors
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
|
||||
$bi = new IntlRuleBasedBreakIterator('[\p{Letter}\uFFFD]+;[:number:]+;');
|
||||
$bi->setText("\x80sdfé\x90d888 dfsa9");
|
||||
|
||||
var_dump($bi->first(1));
|
||||
var_dump($bi->last(1));
|
||||
var_dump($bi->previous(1));
|
||||
var_dump($bi->current(1));
|
||||
|
||||
--EXPECTF--
|
||||
|
||||
Warning: IntlBreakIterator::first() expects exactly 0 parameters, 1 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::first(): breakiter_first: bad arguments in %s on line %d
|
||||
bool(false)
|
||||
|
||||
Warning: IntlBreakIterator::last() expects exactly 0 parameters, 1 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::last(): breakiter_last: bad arguments in %s on line %d
|
||||
bool(false)
|
||||
|
||||
Warning: IntlBreakIterator::previous() expects exactly 0 parameters, 1 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::previous(): breakiter_previous: bad arguments in %s on line %d
|
||||
bool(false)
|
||||
|
||||
Warning: IntlBreakIterator::current() expects exactly 0 parameters, 1 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::current(): breakiter_current: bad arguments in %s on line %d
|
||||
bool(false)
|
20
ext/intl/tests/breakiter_following_basic.phpt
Normal file
20
ext/intl/tests/breakiter_following_basic.phpt
Normal file
@ -0,0 +1,20 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::following(): basic test
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$bi = IntlBreakIterator::createWordInstance('pt');
|
||||
$bi->setText('foo bar trans zoo bee');
|
||||
|
||||
var_dump($bi->following(5));
|
||||
var_dump($bi->following(50));
|
||||
var_dump($bi->following(-1));
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
int(7)
|
||||
int(-1)
|
||||
int(0)
|
||||
==DONE==
|
@ -0,0 +1,47 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::following()/preceding()/isBoundary(): arg errors
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
|
||||
$bi = new IntlRuleBasedBreakIterator('[\p{Letter}\uFFFD]+;[:number:]+;');
|
||||
$bi->setText("\x80sdfé\x90d888 dfsa9");
|
||||
|
||||
var_dump($bi->following(1, 2));
|
||||
var_dump($bi->following(array()));
|
||||
var_dump($bi->preceding(1, 2));
|
||||
var_dump($bi->preceding(array()));
|
||||
var_dump($bi->isBoundary(1, 2));
|
||||
var_dump($bi->isBoundary(array()));
|
||||
|
||||
--EXPECTF--
|
||||
|
||||
Warning: IntlBreakIterator::following() expects exactly 1 parameter, 2 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::following(): breakiter_following: bad arguments in %s on line %d
|
||||
bool(false)
|
||||
|
||||
Warning: IntlBreakIterator::following() expects parameter 1 to be long, array given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::following(): breakiter_following: bad arguments in %s on line %d
|
||||
bool(false)
|
||||
|
||||
Warning: IntlBreakIterator::preceding() expects exactly 1 parameter, 2 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::preceding(): breakiter_preceding: bad arguments in %s on line %d
|
||||
bool(false)
|
||||
|
||||
Warning: IntlBreakIterator::preceding() expects parameter 1 to be long, array given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::preceding(): breakiter_preceding: bad arguments in %s on line %d
|
||||
bool(false)
|
||||
|
||||
Warning: IntlBreakIterator::isBoundary() expects exactly 1 parameter, 2 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::isBoundary(): breakiter_is_boundary: bad arguments in %s on line %d
|
||||
bool(false)
|
||||
|
||||
Warning: IntlBreakIterator::isBoundary() expects parameter 1 to be long, array given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::isBoundary(): breakiter_is_boundary: bad arguments in %s on line %d
|
||||
bool(false)
|
17
ext/intl/tests/breakiter_getLocale_basic.phpt
Normal file
17
ext/intl/tests/breakiter_getLocale_basic.phpt
Normal file
@ -0,0 +1,17 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::getLocale(): basic test
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$bi = IntlBreakIterator::createSentenceInstance('pt');
|
||||
|
||||
var_dump($bi->getLocale(0));
|
||||
var_dump($bi->getLocale(1));
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
string(4) "root"
|
||||
string(4) "root"
|
||||
==DONE==
|
29
ext/intl/tests/breakiter_getLocale_error.phpt
Normal file
29
ext/intl/tests/breakiter_getLocale_error.phpt
Normal file
@ -0,0 +1,29 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::getLocale(): arg errors
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
|
||||
$bi = new IntlRuleBasedBreakIterator('[\p{Letter}\uFFFD]+;[:number:]+;');
|
||||
$bi->setText("\x80sdfé\x90d888 dfsa9");
|
||||
|
||||
var_dump($bi->getLocale(1, 2));
|
||||
var_dump($bi->getLocale(array()));
|
||||
var_dump($bi->getLocale());
|
||||
|
||||
--EXPECTF--
|
||||
|
||||
Warning: IntlBreakIterator::getLocale() expects exactly 1 parameter, 2 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::getLocale(): breakiter_get_locale: bad arguments in %s on line %d
|
||||
bool(false)
|
||||
|
||||
Warning: IntlBreakIterator::getLocale() expects parameter 1 to be long, array given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::getLocale(): breakiter_get_locale: bad arguments in %s on line %d
|
||||
bool(false)
|
||||
|
||||
Warning: IntlBreakIterator::getLocale() expects exactly 1 parameter, 0 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::getLocale(): breakiter_get_locale: bad arguments in %s on line %d
|
||||
bool(false)
|
33
ext/intl/tests/breakiter_getPartsIterator_basic.phpt
Normal file
33
ext/intl/tests/breakiter_getPartsIterator_basic.phpt
Normal file
@ -0,0 +1,33 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::getPartsIterator(): basic test
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$bi = IntlBreakIterator::createWordInstance('pt');
|
||||
$pi = $bi->getPartsIterator();
|
||||
var_dump(get_class($pi));
|
||||
print_r(iterator_to_array($pi));
|
||||
|
||||
$bi->setText("foo bar");
|
||||
$pi = $bi->getPartsIterator();
|
||||
var_dump(get_class($pi->getBreakIterator()));
|
||||
print_r(iterator_to_array($pi));
|
||||
var_dump($pi->getRuleStatus());
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
string(17) "IntlPartsIterator"
|
||||
Array
|
||||
(
|
||||
)
|
||||
string(26) "IntlRuleBasedBreakIterator"
|
||||
Array
|
||||
(
|
||||
[0] => foo
|
||||
[1] =>
|
||||
[2] => bar
|
||||
)
|
||||
int(0)
|
||||
==DONE==
|
33
ext/intl/tests/breakiter_getPartsIterator_error.phpt
Normal file
33
ext/intl/tests/breakiter_getPartsIterator_error.phpt
Normal file
@ -0,0 +1,33 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::getPartsIterator(): bad args
|
||||
--SKIPIF--
|
||||
<?php
|
||||
if (!extension_loaded('intl'))
|
||||
die('skip intl extension not enabled');
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$it = IntlBreakIterator::createWordInstance(NULL);
|
||||
var_dump($it->getPartsIterator(array()));
|
||||
var_dump($it->getPartsIterator(1, 2));
|
||||
var_dump($it->getPartsIterator(-1));
|
||||
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECTF--
|
||||
|
||||
Warning: IntlBreakIterator::getPartsIterator() expects parameter 1 to be long, array given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::getPartsIterator(): breakiter_get_parts_iterator: bad arguments in %s on line %d
|
||||
bool(false)
|
||||
|
||||
Warning: IntlBreakIterator::getPartsIterator() expects at most 1 parameter, 2 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::getPartsIterator(): breakiter_get_parts_iterator: bad arguments in %s on line %d
|
||||
bool(false)
|
||||
|
||||
Warning: IntlBreakIterator::getPartsIterator(): breakiter_get_parts_iterator: bad key type in %s on line %d
|
||||
bool(false)
|
||||
==DONE==
|
60
ext/intl/tests/breakiter_getPartsIterator_var1.phpt
Normal file
60
ext/intl/tests/breakiter_getPartsIterator_var1.phpt
Normal file
@ -0,0 +1,60 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::getPartsIterator(): argument variations
|
||||
--SKIPIF--
|
||||
<?php
|
||||
if (!extension_loaded('intl'))
|
||||
die('skip intl extension not enabled');
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$text = 'foo bar tao';
|
||||
|
||||
$it = IntlBreakIterator::createWordInstance(NULL);
|
||||
$it->setText($text);
|
||||
|
||||
var_dump(iterator_to_array($it->getPartsIterator(IntlPartsIterator::KEY_SEQUENTIAL)));
|
||||
var_dump(iterator_to_array($it->getPartsIterator(IntlPartsIterator::KEY_LEFT)));
|
||||
var_dump(iterator_to_array($it->getPartsIterator(IntlPartsIterator::KEY_RIGHT)));
|
||||
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
array(5) {
|
||||
[0]=>
|
||||
string(3) "foo"
|
||||
[1]=>
|
||||
string(1) " "
|
||||
[2]=>
|
||||
string(3) "bar"
|
||||
[3]=>
|
||||
string(1) " "
|
||||
[4]=>
|
||||
string(3) "tao"
|
||||
}
|
||||
array(5) {
|
||||
[0]=>
|
||||
string(3) "foo"
|
||||
[4]=>
|
||||
string(1) " "
|
||||
[5]=>
|
||||
string(3) "bar"
|
||||
[8]=>
|
||||
string(1) " "
|
||||
[9]=>
|
||||
string(3) "tao"
|
||||
}
|
||||
array(5) {
|
||||
[3]=>
|
||||
string(3) "foo"
|
||||
[5]=>
|
||||
string(1) " "
|
||||
[8]=>
|
||||
string(3) "bar"
|
||||
[9]=>
|
||||
string(1) " "
|
||||
[12]=>
|
||||
string(3) "tao"
|
||||
}
|
||||
==DONE==
|
16
ext/intl/tests/breakiter_getText_basic.phpt
Normal file
16
ext/intl/tests/breakiter_getText_basic.phpt
Normal file
@ -0,0 +1,16 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::getText(): basic test
|
||||
--SKIPIF--
|
||||
if (!extension_loaded('intl'))
|
||||
die('skip intl extension not enabled');
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
|
||||
$bi = IntlBreakIterator::createWordInstance('pt');
|
||||
var_dump($bi->getText());
|
||||
$bi->setText('foo bar');
|
||||
var_dump($bi->getText());
|
||||
--EXPECTF--
|
||||
NULL
|
||||
string(7) "foo bar"
|
15
ext/intl/tests/breakiter_getText_error.phpt
Normal file
15
ext/intl/tests/breakiter_getText_error.phpt
Normal file
@ -0,0 +1,15 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::getText(): arg errors
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
|
||||
$bi = new IntlRuleBasedBreakIterator('[\p{Letter}]+;');
|
||||
var_dump($bi->getText(array()));
|
||||
|
||||
--EXPECTF--
|
||||
|
||||
Warning: IntlBreakIterator::getText() expects exactly 0 parameters, 1 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::getText(): breakiter_get_text: bad arguments in %s on line %d
|
||||
bool(false)
|
24
ext/intl/tests/breakiter_isBoundary_basic.phpt
Normal file
24
ext/intl/tests/breakiter_isBoundary_basic.phpt
Normal file
@ -0,0 +1,24 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::isBoundary(): basic test
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$bi = IntlBreakIterator::createWordInstance('pt');
|
||||
$bi->setText('foo bar trans zoo bee');
|
||||
|
||||
var_dump($bi->isBoundary(0));
|
||||
var_dump($bi->isBoundary(7));
|
||||
var_dump($bi->isBoundary(-1));
|
||||
var_dump($bi->isBoundary(1));
|
||||
var_dump($bi->isBoundary(50));
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
bool(true)
|
||||
bool(true)
|
||||
bool(false)
|
||||
bool(false)
|
||||
bool(false)
|
||||
==DONE==
|
19
ext/intl/tests/breakiter_last_basic.phpt
Normal file
19
ext/intl/tests/breakiter_last_basic.phpt
Normal file
@ -0,0 +1,19 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::last(): basic test
|
||||
--SKIPIF--
|
||||
if (!extension_loaded('intl'))
|
||||
die('skip intl extension not enabled');
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
|
||||
$bi = IntlBreakIterator::createWordInstance('pt');
|
||||
$bi->setText('foo bar trans');
|
||||
|
||||
var_dump($bi->current());
|
||||
var_dump($bi->last());
|
||||
var_dump($bi->current());
|
||||
--EXPECTF--
|
||||
int(0)
|
||||
int(13)
|
||||
int(13)
|
26
ext/intl/tests/breakiter_next_basic.phpt
Normal file
26
ext/intl/tests/breakiter_next_basic.phpt
Normal file
@ -0,0 +1,26 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::next(): basic test
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$bi = IntlBreakIterator::createWordInstance('pt');
|
||||
$bi->setText('foo bar trans zoo bee');
|
||||
|
||||
var_dump($bi->first());
|
||||
var_dump($bi->next());
|
||||
var_dump($bi->next(2));
|
||||
var_dump($bi->next(-1));
|
||||
var_dump($bi->next(0));
|
||||
var_dump($bi->next(NULL));
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
int(0)
|
||||
int(3)
|
||||
int(7)
|
||||
int(4)
|
||||
int(4)
|
||||
int(7)
|
||||
==DONE==
|
23
ext/intl/tests/breakiter_next_error.phpt
Normal file
23
ext/intl/tests/breakiter_next_error.phpt
Normal file
@ -0,0 +1,23 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::next(): arg errors
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
|
||||
$bi = new IntlRuleBasedBreakIterator('[\p{Letter}\uFFFD]+;[:number:]+;');
|
||||
$bi->setText("\x80sdfé\x90d888 dfsa9");
|
||||
|
||||
var_dump($bi->next(1, 2));
|
||||
var_dump($bi->next(array()));
|
||||
|
||||
--EXPECTF--
|
||||
|
||||
Warning: IntlBreakIterator::next() expects exactly 1 parameter, 2 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::next(): breakiter_next: bad arguments in %s on line %d
|
||||
bool(false)
|
||||
|
||||
Warning: IntlBreakIterator::next() expects parameter 1 to be long, array given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::next(): breakiter_next: bad arguments in %s on line %d
|
||||
bool(false)
|
20
ext/intl/tests/breakiter_preceding_basic.phpt
Normal file
20
ext/intl/tests/breakiter_preceding_basic.phpt
Normal file
@ -0,0 +1,20 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::preceding(): basic test
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$bi = IntlBreakIterator::createWordInstance('pt');
|
||||
$bi->setText('foo bar trans zoo bee');
|
||||
|
||||
var_dump($bi->preceding(5));
|
||||
var_dump($bi->preceding(50));
|
||||
var_dump($bi->preceding(-1));
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
int(4)
|
||||
int(21)
|
||||
int(0)
|
||||
==DONE==
|
18
ext/intl/tests/breakiter_previous_basic.phpt
Normal file
18
ext/intl/tests/breakiter_previous_basic.phpt
Normal file
@ -0,0 +1,18 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::previous(): basic test
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$bi = IntlBreakIterator::createWordInstance('pt');
|
||||
$bi->setText('foo bar trans');
|
||||
|
||||
var_dump($bi->last());
|
||||
var_dump($bi->previous());
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
int(13)
|
||||
int(8)
|
||||
==DONE==
|
35
ext/intl/tests/breakiter_setText_basic.phpt
Normal file
35
ext/intl/tests/breakiter_setText_basic.phpt
Normal file
@ -0,0 +1,35 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::setText(): basic test
|
||||
--SKIPIF--
|
||||
if (!extension_loaded('intl'))
|
||||
die('skip intl extension not enabled');
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
|
||||
class A {
|
||||
function __tostring() { return 'aaa'; }
|
||||
}
|
||||
|
||||
$bi = IntlBreakIterator::createWordInstance('pt');
|
||||
var_dump($bi->setText('foo bar'));
|
||||
var_dump($bi->getText());
|
||||
var_dump($bi->setText(1));
|
||||
var_dump($bi->getText());
|
||||
var_dump($bi->setText(new A));
|
||||
var_dump($bi->getText());
|
||||
|
||||
/* setText resets the pointer */
|
||||
var_dump($bi->next());
|
||||
var_dump($bi->setText('foo bar'));
|
||||
var_dump($bi->current());
|
||||
--EXPECT--
|
||||
bool(true)
|
||||
string(7) "foo bar"
|
||||
bool(true)
|
||||
string(1) "1"
|
||||
bool(true)
|
||||
string(3) "aaa"
|
||||
int(3)
|
||||
bool(true)
|
||||
int(0)
|
40
ext/intl/tests/breakiter_setText_error.phpt
Normal file
40
ext/intl/tests/breakiter_setText_error.phpt
Normal file
@ -0,0 +1,40 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::setText(): arg errors
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
|
||||
$bi = new IntlRuleBasedBreakIterator('[\p{Letter}]+;');
|
||||
var_dump($bi->setText());
|
||||
var_dump($bi->setText(array()));
|
||||
var_dump($bi->setText(1,2));
|
||||
|
||||
class A {
|
||||
function __destruct() { var_dump('destructed'); throw new Exception('e'); }
|
||||
function __tostring() { return 'foo'; }
|
||||
}
|
||||
|
||||
try {
|
||||
var_dump($bi->setText(new A));
|
||||
} catch (Exception $e) {
|
||||
var_dump($e->getMessage());
|
||||
}
|
||||
|
||||
--EXPECTF--
|
||||
|
||||
Warning: IntlBreakIterator::setText() expects exactly 1 parameter, 0 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::setText(): breakiter_set_text: bad arguments in %s on line %d
|
||||
bool(false)
|
||||
|
||||
Warning: IntlBreakIterator::setText() expects parameter 1 to be string, array given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::setText(): breakiter_set_text: bad arguments in %s on line %d
|
||||
bool(false)
|
||||
|
||||
Warning: IntlBreakIterator::setText() expects exactly 1 parameter, 2 given in %s on line %d
|
||||
|
||||
Warning: IntlBreakIterator::setText(): breakiter_set_text: bad arguments in %s on line %d
|
||||
bool(false)
|
||||
string(10) "destructed"
|
||||
string(1) "e"
|
33
ext/intl/tests/cpbi_clone_equality.phpt
Normal file
33
ext/intl/tests/cpbi_clone_equality.phpt
Normal file
@ -0,0 +1,33 @@
|
||||
--TEST--
|
||||
IntlCodePointBreakIterator: clone and equality
|
||||
--SKIPIF--
|
||||
<?php
|
||||
if (!extension_loaded('intl'))
|
||||
die('skip intl extension not enabled');
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$text = 'ตัวอย่างข้อความ';
|
||||
$text2 = 'foo';
|
||||
|
||||
$it = IntlBreakIterator::createCodePointInstance();
|
||||
$it->setText($text);
|
||||
|
||||
$it_clone = clone $it;
|
||||
var_dump($it == $it_clone);
|
||||
|
||||
$it->setText($text2 );
|
||||
var_dump($it == $it_clone);
|
||||
|
||||
$it_clone->setText($text2);
|
||||
var_dump($it == $it_clone);
|
||||
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
bool(true)
|
||||
bool(false)
|
||||
bool(true)
|
||||
==DONE==
|
82
ext/intl/tests/cpbi_getLastCodePoint_basic.phpt
Normal file
82
ext/intl/tests/cpbi_getLastCodePoint_basic.phpt
Normal file
@ -0,0 +1,82 @@
|
||||
--TEST--
|
||||
IntlCodepointBreakIterator::getLastCodePoint(): basic test
|
||||
--SKIPIF--
|
||||
<?php
|
||||
if (!extension_loaded('intl'))
|
||||
die('skip intl extension not enabled');
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$text = 'ตัวอย่างข้อความ';
|
||||
|
||||
$codepoint_it = IntlBreakIterator::createCodePointInstance();
|
||||
$codepoint_it->setText($text);
|
||||
|
||||
var_dump($codepoint_it->getLastCodePoint());
|
||||
//first() and last() don't read codepoint and set the last code point var to -1
|
||||
//The pointer is after the last read codepoint if moving forward and
|
||||
//before the last read codepoint is moving backwards
|
||||
$p = $codepoint_it->first();
|
||||
while ($p != IntlBreakIterator::DONE) {
|
||||
$c = $codepoint_it->getLastCodePoint();
|
||||
if ($c > 0)
|
||||
var_dump(sprintf('U+%04X', $codepoint_it->getLastCodePoint()));
|
||||
else
|
||||
var_dump($c);
|
||||
//it's a post-increment operation as to the codepoint, i.e., it gives the codepoint
|
||||
//starting at the initial position and only then moves the pointer forward
|
||||
$p = $codepoint_it->next();
|
||||
}
|
||||
|
||||
echo "Now backwards\n";
|
||||
$p = $codepoint_it->last();
|
||||
while ($p != IntlBreakIterator::DONE) {
|
||||
$c = $codepoint_it->getLastCodePoint();
|
||||
if ($c > 0)
|
||||
var_dump(sprintf('U+%04X', $codepoint_it->getLastCodePoint()));
|
||||
else
|
||||
var_dump($c);
|
||||
$p = $codepoint_it->previous();
|
||||
}
|
||||
|
||||
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
int(-1)
|
||||
int(-1)
|
||||
string(6) "U+0E15"
|
||||
string(6) "U+0E31"
|
||||
string(6) "U+0E27"
|
||||
string(6) "U+0E2D"
|
||||
string(6) "U+0E22"
|
||||
string(6) "U+0E48"
|
||||
string(6) "U+0E32"
|
||||
string(6) "U+0E07"
|
||||
string(6) "U+0E02"
|
||||
string(6) "U+0E49"
|
||||
string(6) "U+0E2D"
|
||||
string(6) "U+0E04"
|
||||
string(6) "U+0E27"
|
||||
string(6) "U+0E32"
|
||||
string(6) "U+0E21"
|
||||
Now backwards
|
||||
int(-1)
|
||||
string(6) "U+0E21"
|
||||
string(6) "U+0E32"
|
||||
string(6) "U+0E27"
|
||||
string(6) "U+0E04"
|
||||
string(6) "U+0E2D"
|
||||
string(6) "U+0E49"
|
||||
string(6) "U+0E02"
|
||||
string(6) "U+0E07"
|
||||
string(6) "U+0E32"
|
||||
string(6) "U+0E48"
|
||||
string(6) "U+0E22"
|
||||
string(6) "U+0E2D"
|
||||
string(6) "U+0E27"
|
||||
string(6) "U+0E31"
|
||||
string(6) "U+0E15"
|
||||
==DONE==
|
19
ext/intl/tests/cpbi_getLastCodePoint_error.phpt
Normal file
19
ext/intl/tests/cpbi_getLastCodePoint_error.phpt
Normal file
@ -0,0 +1,19 @@
|
||||
--TEST--
|
||||
IntlBreakIterator::getLastCodePoint(): bad args
|
||||
--SKIPIF--
|
||||
<?php
|
||||
if (!extension_loaded('intl'))
|
||||
die('skip intl extension not enabled');
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
|
||||
$it = IntlBreakIterator::createCodePointInstance();
|
||||
var_dump($it->getLastCodePoint(array()));
|
||||
--EXPECTF--
|
||||
|
||||
Warning: IntlCodePointBreakIterator::getLastCodePoint() expects exactly 0 parameters, 1 given in %s on line %d
|
||||
|
||||
Warning: IntlCodePointBreakIterator::getLastCodePoint(): cpbi_get_last_code_point: bad arguments in %s on line %d
|
||||
bool(false)
|
||||
|
40
ext/intl/tests/cpbi_parts_iterator.phpt
Normal file
40
ext/intl/tests/cpbi_parts_iterator.phpt
Normal file
@ -0,0 +1,40 @@
|
||||
--TEST--
|
||||
IntlCodepointBreakIterator's part iterator
|
||||
--SKIPIF--
|
||||
<?php
|
||||
if (!extension_loaded('intl'))
|
||||
die('skip intl extension not enabled');
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$text = 'ตัวอย่างข้อความ';
|
||||
|
||||
$it = IntlBreakIterator::createCodePointInstance()->getPartsIterator();
|
||||
$it->getBreakIterator()->setText($text);
|
||||
|
||||
foreach ($it as $k => $v) {
|
||||
echo "$k. $v (" . sprintf("U+%04X", $it->getBreakIterator()->getLastCodePoint()) .
|
||||
") at {$it->getBreakIterator()->current()}\r\n";
|
||||
}
|
||||
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
0. ต (U+0E15) at 3
|
||||
1. ั (U+0E31) at 6
|
||||
2. ว (U+0E27) at 9
|
||||
3. อ (U+0E2D) at 12
|
||||
4. ย (U+0E22) at 15
|
||||
5. ่ (U+0E48) at 18
|
||||
6. า (U+0E32) at 21
|
||||
7. ง (U+0E07) at 24
|
||||
8. ข (U+0E02) at 27
|
||||
9. ้ (U+0E49) at 30
|
||||
10. อ (U+0E2D) at 33
|
||||
11. ค (U+0E04) at 36
|
||||
12. ว (U+0E27) at 39
|
||||
13. า (U+0E32) at 42
|
||||
14. ม (U+0E21) at 45
|
||||
==DONE==
|
@ -1,8 +1,8 @@
|
||||
--TEST--
|
||||
locale_get_display_script() icu >= 4.8
|
||||
locale_get_display_script() icu = 4.8
|
||||
--SKIPIF--
|
||||
<?php if( !extension_loaded( 'intl' ) ) print 'skip'; ?>
|
||||
<?php if(version_compare(INTL_ICU_VERSION, '4.8') < 0) print 'skip'; ?>
|
||||
<?php if(version_compare(INTL_ICU_VERSION, '4.8') < 0 || version_compare(INTL_ICU_VERSION, '49') >= 0) print 'skip'; ?>
|
||||
--FILE--
|
||||
<?php
|
||||
|
||||
|
275
ext/intl/tests/locale_get_display_script3.phpt
Normal file
275
ext/intl/tests/locale_get_display_script3.phpt
Normal file
@ -0,0 +1,275 @@
|
||||
--TEST--
|
||||
locale_get_display_script() icu >= 49
|
||||
--SKIPIF--
|
||||
<?php if( !extension_loaded( 'intl' ) ) print 'skip'; ?>
|
||||
<?php if(version_compare(INTL_ICU_VERSION, '49') < 0) print 'skip'; ?>
|
||||
--FILE--
|
||||
<?php
|
||||
|
||||
/*
|
||||
* Try getting the display_script for different locales
|
||||
* with Procedural and Object methods.
|
||||
*/
|
||||
|
||||
function ut_main()
|
||||
{
|
||||
$res_str = '';
|
||||
|
||||
$disp_locales=array('en','fr','de');
|
||||
|
||||
$locales = array(
|
||||
'uk-ua_CALIFORNIA@currency=;currency=GRN',
|
||||
'root',
|
||||
'uk@currency=EURO',
|
||||
'Hindi',
|
||||
//Simple language subtag
|
||||
'de',
|
||||
'fr',
|
||||
'ja',
|
||||
'i-enochian', //(example of a grandfathered tag)
|
||||
//Language subtag plus Script subtag:
|
||||
'zh-Hant',
|
||||
'zh-Hans',
|
||||
'sr-Cyrl',
|
||||
'sr-Latn',
|
||||
//Language-Script-Region
|
||||
'zh-Hans-CN',
|
||||
'sr-Latn-CS',
|
||||
//Language-Variant
|
||||
'sl-rozaj',
|
||||
'sl-nedis',
|
||||
//Language-Region-Variant
|
||||
'de-CH-1901',
|
||||
'sl-IT-nedis',
|
||||
//Language-Script-Region-Variant
|
||||
'sl-Latn-IT-nedis',
|
||||
//Language-Region:
|
||||
'de-DE',
|
||||
'en-US',
|
||||
'es-419',
|
||||
//Private use subtags:
|
||||
'de-CH-x-phonebk',
|
||||
'az-Arab-x-AZE-derbend',
|
||||
//Extended language subtags
|
||||
'zh-min',
|
||||
'zh-min-nan-Hant-CN',
|
||||
//Private use registry values
|
||||
'x-whatever',
|
||||
'qaa-Qaaa-QM-x-southern',
|
||||
'sr-Latn-QM',
|
||||
'sr-Qaaa-CS',
|
||||
/*Tags that use extensions (examples ONLY: extensions MUST be defined
|
||||
by revision or update to this document or by RFC): */
|
||||
'en-US-u-islamCal',
|
||||
'zh-CN-a-myExt-x-private',
|
||||
'en-a-myExt-b-another',
|
||||
//Some Invalid Tags:
|
||||
'de-419-DE',
|
||||
'a-DE',
|
||||
'ar-a-aaa-b-bbb-a-ccc'
|
||||
);
|
||||
|
||||
|
||||
$res_str = '';
|
||||
|
||||
foreach( $locales as $locale )
|
||||
{
|
||||
$res_str .= "locale='$locale'\n";
|
||||
foreach( $disp_locales as $disp_locale )
|
||||
{
|
||||
$scr = ut_loc_get_display_script( $locale ,$disp_locale );
|
||||
$res_str .= "disp_locale=$disp_locale : display_script=$scr";
|
||||
$res_str .= "\n";
|
||||
}
|
||||
$res_str .= "-----------------\n";
|
||||
}
|
||||
|
||||
return $res_str;
|
||||
|
||||
}
|
||||
|
||||
include_once( 'ut_common.inc' );
|
||||
ut_run();
|
||||
|
||||
?>
|
||||
--EXPECT--
|
||||
locale='uk-ua_CALIFORNIA@currency=;currency=GRN'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='root'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='uk@currency=EURO'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='Hindi'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='de'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='fr'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='ja'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='i-enochian'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='zh-Hant'
|
||||
disp_locale=en : display_script=Traditional Han
|
||||
disp_locale=fr : display_script=chinois traditionnel
|
||||
disp_locale=de : display_script=Traditionelles Chinesisch
|
||||
-----------------
|
||||
locale='zh-Hans'
|
||||
disp_locale=en : display_script=Simplified Han
|
||||
disp_locale=fr : display_script=chinois simplifié
|
||||
disp_locale=de : display_script=Vereinfachtes Chinesisch
|
||||
-----------------
|
||||
locale='sr-Cyrl'
|
||||
disp_locale=en : display_script=Cyrillic
|
||||
disp_locale=fr : display_script=cyrillique
|
||||
disp_locale=de : display_script=Kyrillisch
|
||||
-----------------
|
||||
locale='sr-Latn'
|
||||
disp_locale=en : display_script=Latin
|
||||
disp_locale=fr : display_script=latin
|
||||
disp_locale=de : display_script=Lateinisch
|
||||
-----------------
|
||||
locale='zh-Hans-CN'
|
||||
disp_locale=en : display_script=Simplified Han
|
||||
disp_locale=fr : display_script=chinois simplifié
|
||||
disp_locale=de : display_script=Vereinfachtes Chinesisch
|
||||
-----------------
|
||||
locale='sr-Latn-CS'
|
||||
disp_locale=en : display_script=Latin
|
||||
disp_locale=fr : display_script=latin
|
||||
disp_locale=de : display_script=Lateinisch
|
||||
-----------------
|
||||
locale='sl-rozaj'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='sl-nedis'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='de-CH-1901'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='sl-IT-nedis'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='sl-Latn-IT-nedis'
|
||||
disp_locale=en : display_script=Latin
|
||||
disp_locale=fr : display_script=latin
|
||||
disp_locale=de : display_script=Lateinisch
|
||||
-----------------
|
||||
locale='de-DE'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='en-US'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='es-419'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='de-CH-x-phonebk'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='az-Arab-x-AZE-derbend'
|
||||
disp_locale=en : display_script=Arabic
|
||||
disp_locale=fr : display_script=arabe
|
||||
disp_locale=de : display_script=Arabisch
|
||||
-----------------
|
||||
locale='zh-min'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='zh-min-nan-Hant-CN'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='x-whatever'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='qaa-Qaaa-QM-x-southern'
|
||||
disp_locale=en : display_script=Qaaa
|
||||
disp_locale=fr : display_script=Qaaa
|
||||
disp_locale=de : display_script=Qaaa
|
||||
-----------------
|
||||
locale='sr-Latn-QM'
|
||||
disp_locale=en : display_script=Latin
|
||||
disp_locale=fr : display_script=latin
|
||||
disp_locale=de : display_script=Lateinisch
|
||||
-----------------
|
||||
locale='sr-Qaaa-CS'
|
||||
disp_locale=en : display_script=Qaaa
|
||||
disp_locale=fr : display_script=Qaaa
|
||||
disp_locale=de : display_script=Qaaa
|
||||
-----------------
|
||||
locale='en-US-u-islamCal'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='zh-CN-a-myExt-x-private'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='en-a-myExt-b-another'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='de-419-DE'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='a-DE'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
||||
locale='ar-a-aaa-b-bbb-a-ccc'
|
||||
disp_locale=en : display_script=
|
||||
disp_locale=fr : display_script=
|
||||
disp_locale=de : display_script=
|
||||
-----------------
|
27
ext/intl/tests/rbbiter___construct_basic.phpt
Normal file
27
ext/intl/tests/rbbiter___construct_basic.phpt
Normal file
@ -0,0 +1,27 @@
|
||||
--TEST--
|
||||
IntlRuleBasedBreakIterator::__construct: basic test
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$rules = <<<RULES
|
||||
\$LN = [[:letter:] [:number:]];
|
||||
\$S = [.;,:];
|
||||
|
||||
!!forward;
|
||||
\$LN+ {1};
|
||||
\$S+ {42};
|
||||
!!reverse;
|
||||
\$LN+ {1};
|
||||
\$S+ {42};
|
||||
!!safe_forward;
|
||||
!!safe_reverse;
|
||||
RULES;
|
||||
$rbbi = new IntlRuleBasedBreakIterator($rules);
|
||||
var_dump(get_class($rbbi));
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
string(26) "IntlRuleBasedBreakIterator"
|
||||
==DONE==
|
39
ext/intl/tests/rbbiter_getBinaryRules_basic.phpt
Normal file
39
ext/intl/tests/rbbiter_getBinaryRules_basic.phpt
Normal file
@ -0,0 +1,39 @@
|
||||
--TEST--
|
||||
IntlRuleBasedBreakIterator::getBinaryRules(): basic test
|
||||
--SKIPIF--
|
||||
<?php if( !extension_loaded( 'intl' ) ) print 'skip'; ?>
|
||||
<?php if(version_compare(INTL_ICU_VERSION, '4.8') < 0) print 'skip ICU >= 4.8 only'; ?>
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$rules = <<<RULES
|
||||
\$LN = [[:letter:] [:number:]];
|
||||
\$S = [.;,:];
|
||||
|
||||
!!forward;
|
||||
\$LN+ {1};
|
||||
\$S+ {42};
|
||||
!!reverse;
|
||||
\$LN+ {1};
|
||||
\$S+ {42};
|
||||
!!safe_forward;
|
||||
!!safe_reverse;
|
||||
RULES;
|
||||
$rbbi = new IntlRuleBasedBreakIterator($rules);
|
||||
$rbbi->setText('sdfkjsdf88á.... ,;');;
|
||||
|
||||
$br = $rbbi->getBinaryRules();
|
||||
|
||||
$rbbi2 = new IntlRuleBasedBreakIterator($br, true);
|
||||
|
||||
var_dump($rbbi->getRules(), $rbbi2->getRules());
|
||||
var_dump($rbbi->getRules() == $rbbi2->getRules());
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
string(128) "$LN = [[:letter:] [:number:]];$S = [.;,:];!!forward;$LN+ {1};$S+ {42};!!reverse;$LN+ {1};$S+ {42};!!safe_forward;!!safe_reverse;"
|
||||
string(128) "$LN = [[:letter:] [:number:]];$S = [.;,:];!!forward;$LN+ {1};$S+ {42};!!reverse;$LN+ {1};$S+ {42};!!safe_forward;!!safe_reverse;"
|
||||
bool(true)
|
||||
==DONE==
|
55
ext/intl/tests/rbbiter_getRuleStatusVec_basic.phpt
Normal file
55
ext/intl/tests/rbbiter_getRuleStatusVec_basic.phpt
Normal file
@ -0,0 +1,55 @@
|
||||
--TEST--
|
||||
IntlRuleBasedBreakIterator::getRuleStatusVec(): basic test
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$rules = <<<RULES
|
||||
\$LN = [[:letter:] [:number:]];
|
||||
\$S = [.;,:];
|
||||
|
||||
!!forward;
|
||||
\$LN+ {1};
|
||||
[^.]+ {4};
|
||||
\$S+ {42};
|
||||
!!reverse;
|
||||
\$LN+ {1};
|
||||
[^.]+ {4};
|
||||
\$S+ {42};
|
||||
!!safe_forward;
|
||||
!!safe_reverse;
|
||||
RULES;
|
||||
$rbbi = new IntlRuleBasedBreakIterator($rules);
|
||||
$rbbi->setText('sdfkjsdf88á.... ,;');;
|
||||
|
||||
do {
|
||||
var_dump($rbbi->current(), $rbbi->getRuleStatusVec());
|
||||
} while ($rbbi->next() != IntlBreakIterator::DONE);
|
||||
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
int(0)
|
||||
array(1) {
|
||||
[0]=>
|
||||
int(0)
|
||||
}
|
||||
int(12)
|
||||
array(2) {
|
||||
[0]=>
|
||||
int(1)
|
||||
[1]=>
|
||||
int(4)
|
||||
}
|
||||
int(16)
|
||||
array(1) {
|
||||
[0]=>
|
||||
int(42)
|
||||
}
|
||||
int(19)
|
||||
array(1) {
|
||||
[0]=>
|
||||
int(4)
|
||||
}
|
||||
==DONE==
|
42
ext/intl/tests/rbbiter_getRuleStatus_basic.phpt
Normal file
42
ext/intl/tests/rbbiter_getRuleStatus_basic.phpt
Normal file
@ -0,0 +1,42 @@
|
||||
--TEST--
|
||||
IntlRuleBasedBreakIterator::getRuleStatus(): basic test
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$rules = <<<RULES
|
||||
\$LN = [[:letter:] [:number:]];
|
||||
\$S = [.;,:];
|
||||
|
||||
!!forward;
|
||||
\$LN+ {1};
|
||||
\$S+ {42};
|
||||
!!reverse;
|
||||
\$LN+ {1};
|
||||
\$S+ {42};
|
||||
!!safe_forward;
|
||||
!!safe_reverse;
|
||||
RULES;
|
||||
$rbbi = new IntlRuleBasedBreakIterator($rules);
|
||||
$rbbi->setText('sdfkjsdf88á.... ,;');
|
||||
|
||||
do {
|
||||
echo "pos : {$rbbi->current()}\n",
|
||||
"rule status: {$rbbi->getRuleStatus()}\n";
|
||||
} while ($rbbi->next() != IntlBreakIterator::DONE);
|
||||
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
pos : 0
|
||||
rule status: 0
|
||||
pos : 12
|
||||
rule status: 1
|
||||
pos : 16
|
||||
rule status: 42
|
||||
pos : 17
|
||||
rule status: 0
|
||||
pos : 19
|
||||
rule status: 42
|
||||
==DONE==
|
28
ext/intl/tests/rbbiter_getRules_basic.phpt
Normal file
28
ext/intl/tests/rbbiter_getRules_basic.phpt
Normal file
@ -0,0 +1,28 @@
|
||||
--TEST--
|
||||
IntlRuleBasedBreakIterator::getRules(): basic test
|
||||
--FILE--
|
||||
<?php
|
||||
ini_set("intl.error_level", E_WARNING);
|
||||
ini_set("intl.default_locale", "pt_PT");
|
||||
|
||||
$rules = <<<RULES
|
||||
\$LN = [[:letter:] [:number:]];
|
||||
\$S = [.;,:];
|
||||
|
||||
!!forward;
|
||||
\$LN+ {1};
|
||||
\$S+ {42};
|
||||
!!reverse;
|
||||
\$LN+ {1};
|
||||
\$S+ {42};
|
||||
!!safe_forward;
|
||||
!!safe_reverse;
|
||||
RULES;
|
||||
$rbbi = new IntlRuleBasedBreakIterator($rules);
|
||||
var_dump($rbbi->getRules());
|
||||
|
||||
?>
|
||||
==DONE==
|
||||
--EXPECT--
|
||||
string(128) "$LN = [[:letter:] [:number:]];$S = [.;,:];!!forward;$LN+ {1};$S+ {42};!!reverse;$LN+ {1};$S+ {42};!!safe_forward;!!safe_reverse;"
|
||||
==DONE==
|
@ -25,10 +25,10 @@
|
||||
#include <unicode/ustring.h>
|
||||
#include "intl_convertcpp.h"
|
||||
extern "C" {
|
||||
#include "../php_intl.h"
|
||||
#define USE_TIMEZONE_POINTER 1
|
||||
#include "timezone_class.h"
|
||||
#include "intl_convert.h"
|
||||
#include "../locale/locale.h"
|
||||
#include <zend_exceptions.h>
|
||||
#include <ext/date/php_date.h>
|
||||
}
|
||||
|
@ -49,85 +49,6 @@ void transliterator_register_constants( INIT_FUNC_ARGS )
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
/* {{{ transliterator_parse_error_to_string
|
||||
* Transforms parse errors in strings.
|
||||
*/
|
||||
smart_str transliterator_parse_error_to_string( UParseError* pe )
|
||||
{
|
||||
smart_str ret = {0};
|
||||
char *buf;
|
||||
int u8len;
|
||||
UErrorCode status;
|
||||
int any = 0;
|
||||
|
||||
assert( pe != NULL );
|
||||
|
||||
smart_str_appends( &ret, "parse error " );
|
||||
if( pe->line > 0 )
|
||||
{
|
||||
smart_str_appends( &ret, "on line " );
|
||||
smart_str_append_long( &ret, (long ) pe->line );
|
||||
any = 1;
|
||||
}
|
||||
if( pe->offset >= 0 ) {
|
||||
if( any )
|
||||
smart_str_appends( &ret, ", " );
|
||||
else
|
||||
smart_str_appends( &ret, "at " );
|
||||
|
||||
smart_str_appends( &ret, "offset " );
|
||||
smart_str_append_long( &ret, (long ) pe->offset );
|
||||
any = 1;
|
||||
}
|
||||
|
||||
if (pe->preContext[0] != 0 ) {
|
||||
if( any )
|
||||
smart_str_appends( &ret, ", " );
|
||||
|
||||
smart_str_appends( &ret, "after \"" );
|
||||
intl_convert_utf16_to_utf8( &buf, &u8len, pe->preContext, -1, &status );
|
||||
if( U_FAILURE( status ) )
|
||||
{
|
||||
smart_str_appends( &ret, "(could not convert parser error pre-context to UTF-8)" );
|
||||
}
|
||||
else {
|
||||
smart_str_appendl( &ret, buf, u8len );
|
||||
efree( buf );
|
||||
}
|
||||
smart_str_appends( &ret, "\"" );
|
||||
any = 1;
|
||||
}
|
||||
|
||||
if( pe->postContext[0] != 0 )
|
||||
{
|
||||
if( any )
|
||||
smart_str_appends( &ret, ", " );
|
||||
|
||||
smart_str_appends( &ret, "before or at \"" );
|
||||
intl_convert_utf16_to_utf8( &buf, &u8len, pe->postContext, -1, &status );
|
||||
if( U_FAILURE( status ) )
|
||||
{
|
||||
smart_str_appends( &ret, "(could not convert parser error post-context to UTF-8)" );
|
||||
}
|
||||
else
|
||||
{
|
||||
smart_str_appendl( &ret, buf, u8len );
|
||||
efree( buf );
|
||||
}
|
||||
smart_str_appends( &ret, "\"" );
|
||||
any = 1;
|
||||
}
|
||||
|
||||
if( !any )
|
||||
{
|
||||
smart_str_free( &ret );
|
||||
smart_str_appends( &ret, "no parse error" );
|
||||
}
|
||||
|
||||
smart_str_0( &ret );
|
||||
return ret;
|
||||
}
|
||||
|
||||
/*
|
||||
* Local variables:
|
||||
* tab-width: 4
|
||||
|
@ -183,7 +183,7 @@ PHP_FUNCTION( transliterator_create_from_rules )
|
||||
{
|
||||
char *msg = NULL;
|
||||
smart_str parse_error_str;
|
||||
parse_error_str = transliterator_parse_error_to_string( &parse_error );
|
||||
parse_error_str = intl_parse_error_to_string( &parse_error );
|
||||
spprintf( &msg, 0, "transliterator_create_from_rules: unable to "
|
||||
"create ICU transliterator from rules (%s)", parse_error_str.c );
|
||||
smart_str_free( &parse_error_str );
|
||||
|
@ -35,6 +35,7 @@ static PHP_MINFO_FUNCTION(json);
|
||||
static PHP_FUNCTION(json_encode);
|
||||
static PHP_FUNCTION(json_decode);
|
||||
static PHP_FUNCTION(json_last_error);
|
||||
static PHP_FUNCTION(json_last_error_msg);
|
||||
|
||||
static const char digits[] = "0123456789abcdef";
|
||||
|
||||
@ -57,6 +58,9 @@ ZEND_END_ARG_INFO()
|
||||
|
||||
ZEND_BEGIN_ARG_INFO(arginfo_json_last_error, 0)
|
||||
ZEND_END_ARG_INFO()
|
||||
|
||||
ZEND_BEGIN_ARG_INFO(arginfo_json_last_error_msg, 0)
|
||||
ZEND_END_ARG_INFO()
|
||||
/* }}} */
|
||||
|
||||
/* {{{ json_functions[] */
|
||||
@ -64,6 +68,7 @@ static const zend_function_entry json_functions[] = {
|
||||
PHP_FE(json_encode, arginfo_json_encode)
|
||||
PHP_FE(json_decode, arginfo_json_decode)
|
||||
PHP_FE(json_last_error, arginfo_json_last_error)
|
||||
PHP_FE(json_last_error_msg, arginfo_json_last_error_msg)
|
||||
PHP_FE_END
|
||||
};
|
||||
/* }}} */
|
||||
@ -236,7 +241,6 @@ static void json_encode_array(smart_str *buf, zval **val, int options TSRMLS_DC)
|
||||
|
||||
if (myht && myht->nApplyCount > 1) {
|
||||
JSON_G(error_code) = PHP_JSON_ERROR_RECURSION;
|
||||
php_error_docref(NULL TSRMLS_CC, E_WARNING, "recursion detected");
|
||||
smart_str_appendl(buf, "null", 4);
|
||||
return;
|
||||
}
|
||||
@ -378,7 +382,6 @@ static void json_escape_string(smart_str *buf, char *s, int len, int options TSR
|
||||
efree(tmp);
|
||||
} else {
|
||||
JSON_G(error_code) = PHP_JSON_ERROR_INF_OR_NAN;
|
||||
php_error_docref(NULL TSRMLS_CC, E_WARNING, "double %.9g does not conform to the JSON spec", d);
|
||||
smart_str_appendc(buf, '0');
|
||||
}
|
||||
}
|
||||
@ -395,7 +398,6 @@ static void json_escape_string(smart_str *buf, char *s, int len, int options TSR
|
||||
}
|
||||
if (ulen < 0) {
|
||||
JSON_G(error_code) = PHP_JSON_ERROR_UTF8;
|
||||
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid UTF-8 sequence in argument");
|
||||
smart_str_appendl(buf, "null", 4);
|
||||
} else {
|
||||
smart_str_appendl(buf, "\"\"", 2);
|
||||
@ -527,7 +529,6 @@ static void json_encode_serializable_object(smart_str *buf, zval *val, int optio
|
||||
|
||||
if (myht && myht->nApplyCount > 1) {
|
||||
JSON_G(error_code) = PHP_JSON_ERROR_RECURSION;
|
||||
php_error_docref(NULL TSRMLS_CC, E_WARNING, "recursion detected");
|
||||
smart_str_appendl(buf, "null", 4);
|
||||
return;
|
||||
}
|
||||
@ -592,7 +593,6 @@ PHP_JSON_API void php_json_encode(smart_str *buf, zval *val, int options TSRMLS_
|
||||
efree(d);
|
||||
} else {
|
||||
JSON_G(error_code) = PHP_JSON_ERROR_INF_OR_NAN;
|
||||
php_error_docref(NULL TSRMLS_CC, E_WARNING, "double %.9g does not conform to the JSON spec", dbl);
|
||||
smart_str_appendc(buf, '0');
|
||||
}
|
||||
}
|
||||
@ -614,7 +614,6 @@ PHP_JSON_API void php_json_encode(smart_str *buf, zval *val, int options TSRMLS_
|
||||
|
||||
default:
|
||||
JSON_G(error_code) = PHP_JSON_ERROR_UNSUPPORTED_TYPE;
|
||||
php_error_docref(NULL TSRMLS_CC, E_WARNING, "type is unsupported");
|
||||
smart_str_appendl(buf, "null", 4);
|
||||
break;
|
||||
}
|
||||
@ -751,7 +750,7 @@ static PHP_FUNCTION(json_decode)
|
||||
/* }}} */
|
||||
|
||||
/* {{{ proto int json_last_error()
|
||||
Returns the error code of the last json_decode(). */
|
||||
Returns the error code of the last json_encode() or json_decode() call. */
|
||||
static PHP_FUNCTION(json_last_error)
|
||||
{
|
||||
if (zend_parse_parameters_none() == FAILURE) {
|
||||
@ -762,6 +761,40 @@ static PHP_FUNCTION(json_last_error)
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
/* {{{ proto string json_last_error_msg()
|
||||
Returns the error string of the last json_encode() or json_decode() call. */
|
||||
static PHP_FUNCTION(json_last_error_msg)
|
||||
{
|
||||
if (zend_parse_parameters_none() == FAILURE) {
|
||||
return;
|
||||
}
|
||||
|
||||
switch(JSON_G(error_code)) {
|
||||
case PHP_JSON_ERROR_NONE:
|
||||
RETURN_STRING("No error", 1);
|
||||
case PHP_JSON_ERROR_DEPTH:
|
||||
RETURN_STRING("Maximum stack depth exceeded", 1);
|
||||
case PHP_JSON_ERROR_STATE_MISMATCH:
|
||||
RETURN_STRING("State mismatch (invalid or malformed JSON)", 1);
|
||||
case PHP_JSON_ERROR_CTRL_CHAR:
|
||||
RETURN_STRING("Control character error, possibly incorrectly encoded", 1);
|
||||
case PHP_JSON_ERROR_SYNTAX:
|
||||
RETURN_STRING("Syntax error", 1);
|
||||
case PHP_JSON_ERROR_UTF8:
|
||||
RETURN_STRING("Malformed UTF-8 characters, possibly incorrectly encoded", 1);
|
||||
case PHP_JSON_ERROR_RECURSION:
|
||||
RETURN_STRING("Recursion detected", 1);
|
||||
case PHP_JSON_ERROR_INF_OR_NAN:
|
||||
RETURN_STRING("Inf and NaN cannot be JSON encoded", 1);
|
||||
case PHP_JSON_ERROR_UNSUPPORTED_TYPE:
|
||||
RETURN_STRING("Type is not supported", 1);
|
||||
default:
|
||||
RETURN_STRING("Unknown error", 1);
|
||||
}
|
||||
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
/*
|
||||
* Local variables:
|
||||
* tab-width: 4
|
||||
|
@ -10,11 +10,15 @@ $a[] = &$a;
|
||||
|
||||
var_dump($a);
|
||||
|
||||
echo "\n";
|
||||
|
||||
var_dump(json_encode($a));
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
echo "\n";
|
||||
|
||||
var_dump(json_encode($a, JSON_PARTIAL_OUTPUT_ON_ERROR));
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
echo "Done\n";
|
||||
?>
|
||||
@ -27,11 +31,11 @@ array(1) {
|
||||
}
|
||||
}
|
||||
|
||||
Warning: json_encode(): recursion detected in %s on line %d
|
||||
bool(false)
|
||||
int(6)
|
||||
string(%d) "Recursion detected"
|
||||
|
||||
Warning: json_encode(): recursion detected in %s on line %d
|
||||
string(8) "[[null]]"
|
||||
int(6)
|
||||
string(%d) "Recursion detected"
|
||||
Done
|
||||
|
@ -10,11 +10,15 @@ $a->prop = $a;
|
||||
|
||||
var_dump($a);
|
||||
|
||||
echo "\n";
|
||||
|
||||
var_dump(json_encode($a));
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
echo "\n";
|
||||
|
||||
var_dump(json_encode($a, JSON_PARTIAL_OUTPUT_ON_ERROR));
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
echo "Done\n";
|
||||
?>
|
||||
@ -24,11 +28,11 @@ object(stdClass)#%d (1) {
|
||||
*RECURSION*
|
||||
}
|
||||
|
||||
Warning: json_encode(): recursion detected in %s on line %d
|
||||
bool(false)
|
||||
int(6)
|
||||
string(%d) "Recursion detected"
|
||||
|
||||
Warning: json_encode(): recursion detected in %s on line %d
|
||||
string(22) "{"prop":{"prop":null}}"
|
||||
int(6)
|
||||
string(%d) "Recursion detected"
|
||||
Done
|
||||
|
@ -5,15 +5,15 @@ json_last_error() tests
|
||||
--FILE--
|
||||
<?php
|
||||
var_dump(json_decode("[1]"));
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
var_dump(json_decode("[[1]]", false, 2));
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
var_dump(json_decode("[1}"));
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
var_dump(json_decode('["' . chr(0) . 'abcd"]'));
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
var_dump(json_decode("[1"));
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
|
||||
echo "Done\n";
|
||||
@ -24,13 +24,17 @@ array(1) {
|
||||
int(1)
|
||||
}
|
||||
int(0)
|
||||
string(8) "No error"
|
||||
NULL
|
||||
int(1)
|
||||
string(28) "Maximum stack depth exceeded"
|
||||
NULL
|
||||
int(2)
|
||||
string(42) "State mismatch (invalid or malformed JSON)"
|
||||
NULL
|
||||
int(3)
|
||||
string(53) "Control character error, possibly incorrectly encoded"
|
||||
NULL
|
||||
int(4)
|
||||
string(12) "Syntax error"
|
||||
Done
|
||||
|
||||
|
@ -14,15 +14,7 @@ echo "Done\n";
|
||||
?>
|
||||
--EXPECTF--
|
||||
string(5) ""abc""
|
||||
|
||||
Warning: json_encode(): Invalid UTF-8 sequence in argument in %s on line %d
|
||||
bool(false)
|
||||
|
||||
Warning: json_encode(): Invalid UTF-8 sequence in argument in %s on line %d
|
||||
string(4) "null"
|
||||
|
||||
Warning: json_encode(): Invalid UTF-8 sequence in argument in %s on line %d
|
||||
|
||||
Warning: json_encode(): Invalid UTF-8 sequence in argument in %s on line %d
|
||||
string(17) "[null,null,"abc"]"
|
||||
Done
|
||||
|
@ -12,9 +12,5 @@ var_dump(json_encode("ab\xE0", JSON_UNESCAPED_UNICODE));
|
||||
--EXPECTF--
|
||||
string(156) ""latin 1234 -\/ russian \u043c\u0430\u043c\u0430 \u043c\u044b\u043b\u0430 \u0440\u0430\u043c\u0443 specialchars \u0002 \b \n U+1D11E >\ud834\udd1e<""
|
||||
string(100) ""latin 1234 -\/ russian мама мыла раму specialchars \u0002 \b \n U+1D11E >𝄞<""
|
||||
|
||||
Warning: json_encode(): Invalid UTF-8 sequence in argument in %s on line %d
|
||||
bool(false)
|
||||
|
||||
Warning: json_encode(): Invalid UTF-8 sequence in argument in %s on line %d
|
||||
bool(false)
|
||||
|
@ -8,36 +8,33 @@ Bug #54058 (json_last_error() invalid UTF-8 produces wrong error)
|
||||
$bad_utf8 = quoted_printable_decode('=B0');
|
||||
|
||||
json_encode($bad_utf8);
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
$a = new stdclass;
|
||||
$a->foo = quoted_printable_decode('=B0');
|
||||
json_encode($a);
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
$b = new stdclass;
|
||||
$b->foo = $bad_utf8;
|
||||
$b->bar = 1;
|
||||
json_encode($b);
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
$c = array(
|
||||
'foo' => $bad_utf8,
|
||||
'bar' => 1
|
||||
);
|
||||
json_encode($c);
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
?>
|
||||
--EXPECTF--
|
||||
|
||||
Warning: json_encode(): Invalid UTF-8 sequence in argument in %s on line %d
|
||||
int(5)
|
||||
|
||||
Warning: json_encode(): Invalid UTF-8 sequence in argument in %s on line %d
|
||||
string(56) "Malformed UTF-8 characters, possibly incorrectly encoded"
|
||||
int(5)
|
||||
|
||||
Warning: json_encode(): Invalid UTF-8 sequence in argument in %s on line %d
|
||||
string(56) "Malformed UTF-8 characters, possibly incorrectly encoded"
|
||||
int(5)
|
||||
|
||||
Warning: json_encode(): Invalid UTF-8 sequence in argument in %s on line %d
|
||||
string(56) "Malformed UTF-8 characters, possibly incorrectly encoded"
|
||||
int(5)
|
||||
string(56) "Malformed UTF-8 characters, possibly incorrectly encoded"
|
||||
|
39
ext/json/tests/bug61537.phpt
Normal file
39
ext/json/tests/bug61537.phpt
Normal file
@ -0,0 +1,39 @@
|
||||
--TEST--
|
||||
Bug #61537 (json_encode() incorrectly truncates/discards information)
|
||||
--SKIPIF--
|
||||
<?php if (!extension_loaded("json")) print "skip"; ?>
|
||||
--FILE--
|
||||
<?php
|
||||
$invalid_utf8 = "\x9f";
|
||||
|
||||
var_dump(json_encode($invalid_utf8));
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
var_dump(json_encode($invalid_utf8, JSON_PARTIAL_OUTPUT_ON_ERROR));
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
echo "\n";
|
||||
|
||||
$invalid_utf8 = "an invalid sequen\xce in the middle of a string";
|
||||
|
||||
var_dump(json_encode($invalid_utf8));
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
var_dump(json_encode($invalid_utf8, JSON_PARTIAL_OUTPUT_ON_ERROR));
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
?>
|
||||
--EXPECTF--
|
||||
bool(false)
|
||||
int(5)
|
||||
string(56) "Malformed UTF-8 characters, possibly incorrectly encoded"
|
||||
string(4) "null"
|
||||
int(5)
|
||||
string(56) "Malformed UTF-8 characters, possibly incorrectly encoded"
|
||||
|
||||
bool(false)
|
||||
int(5)
|
||||
string(56) "Malformed UTF-8 characters, possibly incorrectly encoded"
|
||||
string(4) "null"
|
||||
int(5)
|
||||
string(56) "Malformed UTF-8 characters, possibly incorrectly encoded"
|
@ -31,17 +31,13 @@ class JsonTest2 implements JsonSerializable {
|
||||
$obj1 = new JsonTest1();
|
||||
var_dump(json_encode($obj1, JSON_PARTIAL_OUTPUT_ON_ERROR));
|
||||
|
||||
echo "\n==\n";
|
||||
echo "==\n";
|
||||
|
||||
$obj2 = new JsonTest2();
|
||||
var_dump(json_encode($obj2, JSON_PARTIAL_OUTPUT_ON_ERROR));
|
||||
|
||||
?>
|
||||
--EXPECTF--
|
||||
Warning: json_encode(): recursion detected in %s on line %d
|
||||
string(44) "{"test":"123","me":{"test":"123","me":null}}"
|
||||
|
||||
==
|
||||
|
||||
Warning: json_encode(): recursion detected in %s on line %d
|
||||
string(44) "{"test":"123","me":{"test":"123","me":null}}"
|
||||
|
@ -1,5 +1,7 @@
|
||||
--TEST--
|
||||
An error is thrown when INF or NaN are encoded
|
||||
--SKIPIF--
|
||||
<?php if (!extension_loaded("json")) print "skip"; ?>
|
||||
--FILE--
|
||||
<?php
|
||||
|
||||
@ -8,37 +10,36 @@ $inf = INF;
|
||||
var_dump($inf);
|
||||
|
||||
var_dump(json_encode($inf));
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
var_dump(json_encode($inf, JSON_PARTIAL_OUTPUT_ON_ERROR));
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
echo "\n";
|
||||
|
||||
$nan = NAN;
|
||||
|
||||
var_dump($nan);
|
||||
|
||||
var_dump(json_encode($nan));
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
var_dump(json_encode($nan, JSON_PARTIAL_OUTPUT_ON_ERROR));
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
?>
|
||||
--EXPECTF--
|
||||
float(INF)
|
||||
|
||||
Warning: json_encode(): double INF does not conform to the JSON spec in %s on line %d
|
||||
bool(false)
|
||||
int(7)
|
||||
|
||||
Warning: json_encode(): double INF does not conform to the JSON spec in %s on line %d
|
||||
string(34) "Inf and NaN cannot be JSON encoded"
|
||||
string(1) "0"
|
||||
int(7)
|
||||
string(34) "Inf and NaN cannot be JSON encoded"
|
||||
|
||||
float(NAN)
|
||||
|
||||
Warning: json_encode(): double NAN does not conform to the JSON spec in %s on line %d
|
||||
bool(false)
|
||||
int(7)
|
||||
|
||||
Warning: json_encode(): double NAN does not conform to the JSON spec in %s on line %d
|
||||
string(34) "Inf and NaN cannot be JSON encoded"
|
||||
string(1) "0"
|
||||
int(7)
|
||||
string(34) "Inf and NaN cannot be JSON encoded"
|
||||
|
@ -150,8 +150,6 @@ string(4) "null"
|
||||
-- Iteration 25 --
|
||||
string(4) "null"
|
||||
-- Iteration 26 --
|
||||
|
||||
Warning: json_encode(): type is unsupported in %s on line %d
|
||||
bool(false)
|
||||
-- Iteration 27 --
|
||||
string(82) "{"MyInt":99,"MyFloat":123.45,"MyBool":true,"MyNull":null,"MyString":"Hello World"}"
|
||||
|
@ -1,5 +1,7 @@
|
||||
--TEST--
|
||||
An error is thrown when an unsupported type is encoded
|
||||
--SKIPIF--
|
||||
<?php if (!extension_loaded("json")) print "skip"; ?>
|
||||
--FILE--
|
||||
<?php
|
||||
|
||||
@ -8,19 +10,17 @@ $resource = fopen(__FILE__, "r");
|
||||
var_dump($resource);
|
||||
|
||||
var_dump(json_encode($resource));
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
var_dump(json_encode($resource, JSON_PARTIAL_OUTPUT_ON_ERROR));
|
||||
var_dump(json_last_error());
|
||||
var_dump(json_last_error(), json_last_error_msg());
|
||||
|
||||
?>
|
||||
--EXPECTF--
|
||||
resource(5) of type (stream)
|
||||
|
||||
Warning: json_encode(): type is unsupported in %s on line %d
|
||||
bool(false)
|
||||
int(8)
|
||||
|
||||
Warning: json_encode(): type is unsupported in %s on line %d
|
||||
string(21) "Type is not supported"
|
||||
string(4) "null"
|
||||
int(8)
|
||||
string(21) "Type is not supported"
|
||||
|
@ -789,6 +789,13 @@ MYSQLND_METHOD(mysqlnd_conn_data, connect_handshake)(MYSQLND_CONN_DATA * conn,
|
||||
conn->server_version = mnd_pestrdup(greet_packet->server_version, conn->persistent);
|
||||
|
||||
conn->greet_charset = mysqlnd_find_charset_nr(greet_packet->charset_no);
|
||||
if (!conn->greet_charset) {
|
||||
php_error_docref(NULL TSRMLS_CC, E_WARNING,
|
||||
"Server sent charset (%d) unknown to the client. Please, report to the developers", greet_packet->charset_no);
|
||||
SET_CLIENT_ERROR(*conn->error_info, CR_NOT_IMPLEMENTED, UNKNOWN_SQLSTATE,
|
||||
"Server sent charset unknown to the client. Please, report to the developers");
|
||||
goto err;
|
||||
}
|
||||
|
||||
if (FAIL == mysqlnd_connect_run_authentication(conn, user, passwd, db, db_len, (size_t) passwd_len,
|
||||
greet_packet, conn->options, mysql_flags TSRMLS_CC))
|
||||
|
@ -262,8 +262,10 @@ PHPAPI void _mysqlnd_get_client_stats(zval *return_value TSRMLS_DC ZEND_FILE_L
|
||||
ZEND_BEGIN_MODULE_GLOBALS(mysqlnd)
|
||||
zend_bool collect_statistics;
|
||||
zend_bool collect_memory_statistics;
|
||||
char* debug; /* The actual string */
|
||||
MYSQLND_DEBUG *dbg; /* The DBG object */
|
||||
char * debug; /* The actual string */
|
||||
char * trace_alloc_settings; /* The actual string */
|
||||
MYSQLND_DEBUG * dbg; /* The DBG object for standard tracing */
|
||||
MYSQLND_DEBUG * trace_alloc; /* The DBG object for allocation tracing */
|
||||
long net_cmd_buffer_size;
|
||||
long net_read_buffer_size;
|
||||
long log_mask;
|
||||
|
@ -65,8 +65,8 @@ const char * mysqlnd_debug_std_no_trace_funcs[] =
|
||||
|
||||
#if ZEND_DEBUG
|
||||
#else
|
||||
#define __zend_filename "/unknown/unknown"
|
||||
#define __zend_lineno 0
|
||||
#define __zend_orig_filename "/unknown/unknown"
|
||||
#define __zend_orig_lineno 0
|
||||
#endif
|
||||
|
||||
#define REAL_SIZE(s) (collect_memory_statistics? (s) + sizeof(size_t) : (s))
|
||||
@ -81,15 +81,15 @@ void * _mysqlnd_emalloc(size_t size MYSQLND_MEM_D)
|
||||
#if PHP_DEBUG
|
||||
long * threshold = &MYSQLND_G(debug_emalloc_fail_threshold);
|
||||
#endif
|
||||
DBG_ENTER(mysqlnd_emalloc_name);
|
||||
TRACE_ALLOC_ENTER(mysqlnd_emalloc_name);
|
||||
|
||||
DBG_INF_FMT("file=%-15s line=%4d", strrchr(__zend_filename, PHP_DIR_SEPARATOR) + 1, __zend_lineno);
|
||||
TRACE_ALLOC_INF_FMT("file=%-15s line=%4d", strrchr(__zend_orig_filename, PHP_DIR_SEPARATOR) + 1, __zend_orig_lineno);
|
||||
|
||||
#if PHP_DEBUG
|
||||
/* -1 is also "true" */
|
||||
if (*threshold) {
|
||||
#endif
|
||||
ret = emalloc(REAL_SIZE(size));
|
||||
ret = _emalloc(REAL_SIZE(size) ZEND_FILE_LINE_CC ZEND_FILE_LINE_ORIG_RELAY_CC);
|
||||
#if PHP_DEBUG
|
||||
--*threshold;
|
||||
} else if (*threshold == 0) {
|
||||
@ -97,13 +97,13 @@ void * _mysqlnd_emalloc(size_t size MYSQLND_MEM_D)
|
||||
}
|
||||
#endif
|
||||
|
||||
DBG_INF_FMT("size=%lu ptr=%p", size, ret);
|
||||
TRACE_ALLOC_INF_FMT("size=%lu ptr=%p", size, ret);
|
||||
|
||||
if (ret && collect_memory_statistics) {
|
||||
*(size_t *) ret = size;
|
||||
MYSQLND_INC_GLOBAL_STATISTIC_W_VALUE2(STAT_MEM_EMALLOC_COUNT, 1, STAT_MEM_EMALLOC_AMOUNT, size);
|
||||
}
|
||||
DBG_RETURN(FAKE_PTR(ret));
|
||||
TRACE_ALLOC_RETURN(FAKE_PTR(ret));
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
@ -116,14 +116,15 @@ void * _mysqlnd_pemalloc(size_t size, zend_bool persistent MYSQLND_MEM_D)
|
||||
#if PHP_DEBUG
|
||||
long * threshold = persistent? &MYSQLND_G(debug_malloc_fail_threshold):&MYSQLND_G(debug_emalloc_fail_threshold);
|
||||
#endif
|
||||
DBG_ENTER(mysqlnd_pemalloc_name);
|
||||
DBG_INF_FMT("file=%-15s line=%4d", strrchr(__zend_filename, PHP_DIR_SEPARATOR) + 1, __zend_lineno);
|
||||
TRACE_ALLOC_ENTER(mysqlnd_pemalloc_name);
|
||||
TRACE_ALLOC_INF_FMT("file=%-15s line=%4d persistent=%u",
|
||||
strrchr(__zend_orig_filename, PHP_DIR_SEPARATOR) + 1, __zend_orig_lineno,persistent);
|
||||
|
||||
#if PHP_DEBUG
|
||||
/* -1 is also "true" */
|
||||
if (*threshold) {
|
||||
#endif
|
||||
ret = pemalloc(REAL_SIZE(size), persistent);
|
||||
ret = (persistent) ? __zend_malloc(REAL_SIZE(size)) : _emalloc(REAL_SIZE(size) ZEND_FILE_LINE_CC ZEND_FILE_LINE_ORIG_RELAY_CC);
|
||||
#if PHP_DEBUG
|
||||
--*threshold;
|
||||
} else if (*threshold == 0) {
|
||||
@ -131,7 +132,7 @@ void * _mysqlnd_pemalloc(size_t size, zend_bool persistent MYSQLND_MEM_D)
|
||||
}
|
||||
#endif
|
||||
|
||||
DBG_INF_FMT("size=%lu ptr=%p persistent=%u", size, ret, persistent);
|
||||
TRACE_ALLOC_INF_FMT("size=%lu ptr=%p persistent=%u", size, ret, persistent);
|
||||
|
||||
if (ret && collect_memory_statistics) {
|
||||
enum mysqlnd_collected_stats s1 = persistent? STAT_MEM_MALLOC_COUNT:STAT_MEM_EMALLOC_COUNT;
|
||||
@ -140,7 +141,7 @@ void * _mysqlnd_pemalloc(size_t size, zend_bool persistent MYSQLND_MEM_D)
|
||||
MYSQLND_INC_GLOBAL_STATISTIC_W_VALUE2(s1, 1, s2, size);
|
||||
}
|
||||
|
||||
DBG_RETURN(FAKE_PTR(ret));
|
||||
TRACE_ALLOC_RETURN(FAKE_PTR(ret));
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
@ -153,15 +154,15 @@ void * _mysqlnd_ecalloc(unsigned int nmemb, size_t size MYSQLND_MEM_D)
|
||||
#if PHP_DEBUG
|
||||
long * threshold = &MYSQLND_G(debug_ecalloc_fail_threshold);
|
||||
#endif
|
||||
DBG_ENTER(mysqlnd_ecalloc_name);
|
||||
DBG_INF_FMT("file=%-15s line=%4d", strrchr(__zend_filename, PHP_DIR_SEPARATOR) + 1, __zend_lineno);
|
||||
DBG_INF_FMT("before: %lu", zend_memory_usage(FALSE TSRMLS_CC));
|
||||
TRACE_ALLOC_ENTER(mysqlnd_ecalloc_name);
|
||||
TRACE_ALLOC_INF_FMT("file=%-15s line=%4d", strrchr(__zend_orig_filename, PHP_DIR_SEPARATOR) + 1, __zend_orig_lineno);
|
||||
TRACE_ALLOC_INF_FMT("before: %lu", zend_memory_usage(FALSE TSRMLS_CC));
|
||||
|
||||
#if PHP_DEBUG
|
||||
/* -1 is also "true" */
|
||||
if (*threshold) {
|
||||
#endif
|
||||
ret = ecalloc(nmemb, REAL_SIZE(size));
|
||||
ret = _ecalloc(nmemb, REAL_SIZE(size) ZEND_FILE_LINE_CC ZEND_FILE_LINE_ORIG_RELAY_CC);
|
||||
#if PHP_DEBUG
|
||||
--*threshold;
|
||||
} else if (*threshold == 0) {
|
||||
@ -169,13 +170,13 @@ void * _mysqlnd_ecalloc(unsigned int nmemb, size_t size MYSQLND_MEM_D)
|
||||
}
|
||||
#endif
|
||||
|
||||
DBG_INF_FMT("after : %lu", zend_memory_usage(FALSE TSRMLS_CC));
|
||||
DBG_INF_FMT("size=%lu ptr=%p", size, ret);
|
||||
TRACE_ALLOC_INF_FMT("after : %lu", zend_memory_usage(FALSE TSRMLS_CC));
|
||||
TRACE_ALLOC_INF_FMT("size=%lu ptr=%p", size, ret);
|
||||
if (ret && collect_memory_statistics) {
|
||||
*(size_t *) ret = size;
|
||||
MYSQLND_INC_GLOBAL_STATISTIC_W_VALUE2(STAT_MEM_ECALLOC_COUNT, 1, STAT_MEM_ECALLOC_AMOUNT, size);
|
||||
}
|
||||
DBG_RETURN(FAKE_PTR(ret));
|
||||
TRACE_ALLOC_RETURN(FAKE_PTR(ret));
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
@ -188,14 +189,15 @@ void * _mysqlnd_pecalloc(unsigned int nmemb, size_t size, zend_bool persistent M
|
||||
#if PHP_DEBUG
|
||||
long * threshold = persistent? &MYSQLND_G(debug_calloc_fail_threshold):&MYSQLND_G(debug_ecalloc_fail_threshold);
|
||||
#endif
|
||||
DBG_ENTER(mysqlnd_pecalloc_name);
|
||||
DBG_INF_FMT("file=%-15s line=%4d", strrchr(__zend_filename, PHP_DIR_SEPARATOR) + 1, __zend_lineno);
|
||||
TRACE_ALLOC_ENTER(mysqlnd_pecalloc_name);
|
||||
TRACE_ALLOC_INF_FMT("file=%-15s line=%4d persistent=%u",
|
||||
strrchr(__zend_orig_filename, PHP_DIR_SEPARATOR) + 1, __zend_orig_lineno, persistent);
|
||||
|
||||
#if PHP_DEBUG
|
||||
/* -1 is also "true" */
|
||||
if (*threshold) {
|
||||
#endif
|
||||
ret = pecalloc(nmemb, REAL_SIZE(size), persistent);
|
||||
ret = (persistent) ? __zend_calloc(nmemb, REAL_SIZE(size)) : _ecalloc(nmemb, REAL_SIZE(size) ZEND_FILE_LINE_CC ZEND_FILE_LINE_ORIG_RELAY_CC);
|
||||
#if PHP_DEBUG
|
||||
--*threshold;
|
||||
} else if (*threshold == 0) {
|
||||
@ -203,7 +205,7 @@ void * _mysqlnd_pecalloc(unsigned int nmemb, size_t size, zend_bool persistent M
|
||||
}
|
||||
#endif
|
||||
|
||||
DBG_INF_FMT("size=%lu ptr=%p", size, ret);
|
||||
TRACE_ALLOC_INF_FMT("size=%lu ptr=%p", size, ret);
|
||||
|
||||
if (ret && collect_memory_statistics) {
|
||||
enum mysqlnd_collected_stats s1 = persistent? STAT_MEM_CALLOC_COUNT:STAT_MEM_ECALLOC_COUNT;
|
||||
@ -212,7 +214,7 @@ void * _mysqlnd_pecalloc(unsigned int nmemb, size_t size, zend_bool persistent M
|
||||
MYSQLND_INC_GLOBAL_STATISTIC_W_VALUE2(s1, 1, s2, size);
|
||||
}
|
||||
|
||||
DBG_RETURN(FAKE_PTR(ret));
|
||||
TRACE_ALLOC_RETURN(FAKE_PTR(ret));
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
@ -226,15 +228,15 @@ void * _mysqlnd_erealloc(void *ptr, size_t new_size MYSQLND_MEM_D)
|
||||
#if PHP_DEBUG
|
||||
long * threshold = &MYSQLND_G(debug_erealloc_fail_threshold);
|
||||
#endif
|
||||
DBG_ENTER(mysqlnd_erealloc_name);
|
||||
DBG_INF_FMT("file=%-15s line=%4d", strrchr(__zend_filename, PHP_DIR_SEPARATOR) + 1, __zend_lineno);
|
||||
DBG_INF_FMT("ptr=%p old_size=%lu, new_size=%lu", ptr, old_size, new_size);
|
||||
TRACE_ALLOC_ENTER(mysqlnd_erealloc_name);
|
||||
TRACE_ALLOC_INF_FMT("file=%-15s line=%4d", strrchr(__zend_orig_filename, PHP_DIR_SEPARATOR) + 1, __zend_orig_lineno);
|
||||
TRACE_ALLOC_INF_FMT("ptr=%p old_size=%lu, new_size=%lu", ptr, old_size, new_size);
|
||||
|
||||
#if PHP_DEBUG
|
||||
/* -1 is also "true" */
|
||||
if (*threshold) {
|
||||
#endif
|
||||
ret = erealloc(REAL_PTR(ptr), REAL_SIZE(new_size));
|
||||
ret = _erealloc(REAL_PTR(ptr), REAL_SIZE(new_size), 0 ZEND_FILE_LINE_CC ZEND_FILE_LINE_ORIG_RELAY_CC);
|
||||
#if PHP_DEBUG
|
||||
--*threshold;
|
||||
} else if (*threshold == 0) {
|
||||
@ -242,12 +244,12 @@ void * _mysqlnd_erealloc(void *ptr, size_t new_size MYSQLND_MEM_D)
|
||||
}
|
||||
#endif
|
||||
|
||||
DBG_INF_FMT("new_ptr=%p", (char*)ret);
|
||||
TRACE_ALLOC_INF_FMT("new_ptr=%p", (char*)ret);
|
||||
if (ret && collect_memory_statistics) {
|
||||
*(size_t *) ret = new_size;
|
||||
MYSQLND_INC_GLOBAL_STATISTIC_W_VALUE2(STAT_MEM_EREALLOC_COUNT, 1, STAT_MEM_EREALLOC_AMOUNT, new_size);
|
||||
}
|
||||
DBG_RETURN(FAKE_PTR(ret));
|
||||
TRACE_ALLOC_RETURN(FAKE_PTR(ret));
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
@ -261,9 +263,9 @@ void * _mysqlnd_perealloc(void *ptr, size_t new_size, zend_bool persistent MYSQL
|
||||
#if PHP_DEBUG
|
||||
long * threshold = persistent? &MYSQLND_G(debug_realloc_fail_threshold):&MYSQLND_G(debug_erealloc_fail_threshold);
|
||||
#endif
|
||||
DBG_ENTER(mysqlnd_perealloc_name);
|
||||
DBG_INF_FMT("file=%-15s line=%4d", strrchr(__zend_filename, PHP_DIR_SEPARATOR) + 1, __zend_lineno);
|
||||
DBG_INF_FMT("ptr=%p old_size=%lu new_size=%lu persistent=%u", ptr, old_size, new_size, persistent);
|
||||
TRACE_ALLOC_ENTER(mysqlnd_perealloc_name);
|
||||
TRACE_ALLOC_INF_FMT("file=%-15s line=%4d", strrchr(__zend_orig_filename, PHP_DIR_SEPARATOR) + 1, __zend_orig_lineno);
|
||||
TRACE_ALLOC_INF_FMT("ptr=%p old_size=%lu new_size=%lu persistent=%u", ptr, old_size, new_size, persistent);
|
||||
|
||||
#if PHP_DEBUG
|
||||
/* -1 is also "true" */
|
||||
@ -277,7 +279,7 @@ void * _mysqlnd_perealloc(void *ptr, size_t new_size, zend_bool persistent MYSQL
|
||||
}
|
||||
#endif
|
||||
|
||||
DBG_INF_FMT("new_ptr=%p", (char*)ret);
|
||||
TRACE_ALLOC_INF_FMT("new_ptr=%p", (char*)ret);
|
||||
|
||||
if (ret && collect_memory_statistics) {
|
||||
enum mysqlnd_collected_stats s1 = persistent? STAT_MEM_REALLOC_COUNT:STAT_MEM_EREALLOC_COUNT;
|
||||
@ -285,7 +287,7 @@ void * _mysqlnd_perealloc(void *ptr, size_t new_size, zend_bool persistent MYSQL
|
||||
*(size_t *) ret = new_size;
|
||||
MYSQLND_INC_GLOBAL_STATISTIC_W_VALUE2(s1, 1, s2, new_size);
|
||||
}
|
||||
DBG_RETURN(FAKE_PTR(ret));
|
||||
TRACE_ALLOC_RETURN(FAKE_PTR(ret));
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
@ -295,22 +297,22 @@ void _mysqlnd_efree(void *ptr MYSQLND_MEM_D)
|
||||
{
|
||||
size_t free_amount = 0;
|
||||
zend_bool collect_memory_statistics = MYSQLND_G(collect_memory_statistics);
|
||||
DBG_ENTER(mysqlnd_efree_name);
|
||||
DBG_INF_FMT("file=%-15s line=%4d", strrchr(__zend_filename, PHP_DIR_SEPARATOR) + 1, __zend_lineno);
|
||||
DBG_INF_FMT("ptr=%p", ptr);
|
||||
TRACE_ALLOC_ENTER(mysqlnd_efree_name);
|
||||
TRACE_ALLOC_INF_FMT("file=%-15s line=%4d", strrchr(__zend_orig_filename, PHP_DIR_SEPARATOR) + 1, __zend_orig_lineno);
|
||||
TRACE_ALLOC_INF_FMT("ptr=%p", ptr);
|
||||
|
||||
if (ptr) {
|
||||
if (collect_memory_statistics) {
|
||||
free_amount = *(size_t *)(((char*)ptr) - sizeof(size_t));
|
||||
DBG_INF_FMT("ptr=%p size=%u", ((char*)ptr) - sizeof(size_t), (unsigned int) free_amount);
|
||||
TRACE_ALLOC_INF_FMT("ptr=%p size=%u", ((char*)ptr) - sizeof(size_t), (unsigned int) free_amount);
|
||||
}
|
||||
efree(REAL_PTR(ptr));
|
||||
_efree(REAL_PTR(ptr) ZEND_FILE_LINE_CC ZEND_FILE_LINE_ORIG_RELAY_CC);
|
||||
}
|
||||
|
||||
if (collect_memory_statistics) {
|
||||
MYSQLND_INC_GLOBAL_STATISTIC_W_VALUE2(STAT_MEM_EFREE_COUNT, 1, STAT_MEM_EFREE_AMOUNT, free_amount);
|
||||
}
|
||||
DBG_VOID_RETURN;
|
||||
TRACE_ALLOC_VOID_RETURN;
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
@ -320,24 +322,25 @@ void _mysqlnd_pefree(void *ptr, zend_bool persistent MYSQLND_MEM_D)
|
||||
{
|
||||
size_t free_amount = 0;
|
||||
zend_bool collect_memory_statistics = MYSQLND_G(collect_memory_statistics);
|
||||
DBG_ENTER(mysqlnd_pefree_name);
|
||||
DBG_INF_FMT("file=%-15s line=%4d", strrchr(__zend_filename, PHP_DIR_SEPARATOR) + 1, __zend_lineno);
|
||||
DBG_INF_FMT("ptr=%p persistent=%u", ptr, persistent);
|
||||
TRACE_ALLOC_ENTER(mysqlnd_pefree_name);
|
||||
TRACE_ALLOC_INF_FMT("file=%-15s line=%4d", strrchr(__zend_orig_filename, PHP_DIR_SEPARATOR) + 1, __zend_orig_lineno);
|
||||
TRACE_ALLOC_INF_FMT("ptr=%p persistent=%u", ptr, persistent);
|
||||
|
||||
if (ptr) {
|
||||
if (collect_memory_statistics) {
|
||||
free_amount = *(size_t *)(((char*)ptr) - sizeof(size_t));
|
||||
DBG_INF_FMT("ptr=%p size=%u", ((char*)ptr) - sizeof(size_t), (unsigned int) free_amount);
|
||||
TRACE_ALLOC_INF_FMT("ptr=%p size=%u", ((char*)ptr) - sizeof(size_t), (unsigned int) free_amount);
|
||||
}
|
||||
pefree(REAL_PTR(ptr), persistent);
|
||||
(persistent) ? free(REAL_PTR(ptr)) : _efree(REAL_PTR(ptr) ZEND_FILE_LINE_CC ZEND_FILE_LINE_ORIG_RELAY_CC);
|
||||
}
|
||||
|
||||
if (collect_memory_statistics) {
|
||||
MYSQLND_INC_GLOBAL_STATISTIC_W_VALUE2(persistent? STAT_MEM_FREE_COUNT:STAT_MEM_EFREE_COUNT, 1,
|
||||
persistent? STAT_MEM_FREE_AMOUNT:STAT_MEM_EFREE_AMOUNT, free_amount);
|
||||
}
|
||||
DBG_VOID_RETURN;
|
||||
TRACE_ALLOC_VOID_RETURN;
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
|
||||
/* {{{ _mysqlnd_malloc */
|
||||
@ -348,8 +351,8 @@ void * _mysqlnd_malloc(size_t size MYSQLND_MEM_D)
|
||||
#if PHP_DEBUG
|
||||
long * threshold = &MYSQLND_G(debug_malloc_fail_threshold);
|
||||
#endif
|
||||
DBG_ENTER(mysqlnd_malloc_name);
|
||||
DBG_INF_FMT("file=%-15s line=%4d", strrchr(__zend_filename, PHP_DIR_SEPARATOR) + 1, __zend_lineno);
|
||||
TRACE_ALLOC_ENTER(mysqlnd_malloc_name);
|
||||
TRACE_ALLOC_INF_FMT("file=%-15s line=%4d", strrchr(__zend_orig_filename, PHP_DIR_SEPARATOR) + 1, __zend_orig_lineno);
|
||||
|
||||
#if PHP_DEBUG
|
||||
/* -1 is also "true" */
|
||||
@ -363,12 +366,12 @@ void * _mysqlnd_malloc(size_t size MYSQLND_MEM_D)
|
||||
}
|
||||
#endif
|
||||
|
||||
DBG_INF_FMT("size=%lu ptr=%p", size, ret);
|
||||
TRACE_ALLOC_INF_FMT("size=%lu ptr=%p", size, ret);
|
||||
if (ret && collect_memory_statistics) {
|
||||
*(size_t *) ret = size;
|
||||
MYSQLND_INC_GLOBAL_STATISTIC_W_VALUE2(STAT_MEM_MALLOC_COUNT, 1, STAT_MEM_MALLOC_AMOUNT, size);
|
||||
}
|
||||
DBG_RETURN(FAKE_PTR(ret));
|
||||
TRACE_ALLOC_RETURN(FAKE_PTR(ret));
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
@ -381,8 +384,8 @@ void * _mysqlnd_calloc(unsigned int nmemb, size_t size MYSQLND_MEM_D)
|
||||
#if PHP_DEBUG
|
||||
long * threshold = &MYSQLND_G(debug_calloc_fail_threshold);
|
||||
#endif
|
||||
DBG_ENTER(mysqlnd_calloc_name);
|
||||
DBG_INF_FMT("file=%-15s line=%4d", strrchr(__zend_filename, PHP_DIR_SEPARATOR) + 1, __zend_lineno);
|
||||
TRACE_ALLOC_ENTER(mysqlnd_calloc_name);
|
||||
TRACE_ALLOC_INF_FMT("file=%-15s line=%4d", strrchr(__zend_orig_filename, PHP_DIR_SEPARATOR) + 1, __zend_orig_lineno);
|
||||
|
||||
#if PHP_DEBUG
|
||||
/* -1 is also "true" */
|
||||
@ -396,12 +399,12 @@ void * _mysqlnd_calloc(unsigned int nmemb, size_t size MYSQLND_MEM_D)
|
||||
}
|
||||
#endif
|
||||
|
||||
DBG_INF_FMT("size=%lu ptr=%p", size, ret);
|
||||
TRACE_ALLOC_INF_FMT("size=%lu ptr=%p", size, ret);
|
||||
if (ret && collect_memory_statistics) {
|
||||
*(size_t *) ret = size;
|
||||
MYSQLND_INC_GLOBAL_STATISTIC_W_VALUE2(STAT_MEM_CALLOC_COUNT, 1, STAT_MEM_CALLOC_AMOUNT, size);
|
||||
}
|
||||
DBG_RETURN(FAKE_PTR(ret));
|
||||
TRACE_ALLOC_RETURN(FAKE_PTR(ret));
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
@ -414,10 +417,10 @@ void * _mysqlnd_realloc(void *ptr, size_t new_size MYSQLND_MEM_D)
|
||||
#if PHP_DEBUG
|
||||
long * threshold = &MYSQLND_G(debug_realloc_fail_threshold);
|
||||
#endif
|
||||
DBG_ENTER(mysqlnd_realloc_name);
|
||||
DBG_INF_FMT("file=%-15s line=%4d", strrchr(__zend_filename, PHP_DIR_SEPARATOR) + 1, __zend_lineno);
|
||||
DBG_INF_FMT("ptr=%p new_size=%lu ", new_size, ptr);
|
||||
DBG_INF_FMT("before: %lu", zend_memory_usage(TRUE TSRMLS_CC));
|
||||
TRACE_ALLOC_ENTER(mysqlnd_realloc_name);
|
||||
TRACE_ALLOC_INF_FMT("file=%-15s line=%4d", strrchr(__zend_orig_filename, PHP_DIR_SEPARATOR) + 1, __zend_orig_lineno);
|
||||
TRACE_ALLOC_INF_FMT("ptr=%p new_size=%lu ", new_size, ptr);
|
||||
TRACE_ALLOC_INF_FMT("before: %lu", zend_memory_usage(TRUE TSRMLS_CC));
|
||||
|
||||
#if PHP_DEBUG
|
||||
/* -1 is also "true" */
|
||||
@ -431,13 +434,13 @@ void * _mysqlnd_realloc(void *ptr, size_t new_size MYSQLND_MEM_D)
|
||||
}
|
||||
#endif
|
||||
|
||||
DBG_INF_FMT("new_ptr=%p", (char*)ret);
|
||||
TRACE_ALLOC_INF_FMT("new_ptr=%p", (char*)ret);
|
||||
|
||||
if (ret && collect_memory_statistics) {
|
||||
*(size_t *) ret = new_size;
|
||||
MYSQLND_INC_GLOBAL_STATISTIC_W_VALUE2(STAT_MEM_REALLOC_COUNT, 1, STAT_MEM_REALLOC_AMOUNT, new_size);
|
||||
}
|
||||
DBG_RETURN(FAKE_PTR(ret));
|
||||
TRACE_ALLOC_RETURN(FAKE_PTR(ret));
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
@ -447,14 +450,14 @@ void _mysqlnd_free(void *ptr MYSQLND_MEM_D)
|
||||
{
|
||||
size_t free_amount = 0;
|
||||
zend_bool collect_memory_statistics = MYSQLND_G(collect_memory_statistics);
|
||||
DBG_ENTER(mysqlnd_free_name);
|
||||
DBG_INF_FMT("file=%-15s line=%4d", strrchr(__zend_filename, PHP_DIR_SEPARATOR) + 1, __zend_lineno);
|
||||
DBG_INF_FMT("ptr=%p", ptr);
|
||||
TRACE_ALLOC_ENTER(mysqlnd_free_name);
|
||||
TRACE_ALLOC_INF_FMT("file=%-15s line=%4d", strrchr(__zend_orig_filename, PHP_DIR_SEPARATOR) + 1, __zend_orig_lineno);
|
||||
TRACE_ALLOC_INF_FMT("ptr=%p", ptr);
|
||||
|
||||
if (ptr) {
|
||||
if (collect_memory_statistics) {
|
||||
free_amount = *(size_t *)(((char*)ptr) - sizeof(size_t));
|
||||
DBG_INF_FMT("ptr=%p size=%u", ((char*)ptr) - sizeof(size_t), (unsigned int) free_amount);
|
||||
TRACE_ALLOC_INF_FMT("ptr=%p size=%u", ((char*)ptr) - sizeof(size_t), (unsigned int) free_amount);
|
||||
}
|
||||
free(REAL_PTR(ptr));
|
||||
}
|
||||
@ -462,7 +465,7 @@ void _mysqlnd_free(void *ptr MYSQLND_MEM_D)
|
||||
if (collect_memory_statistics) {
|
||||
MYSQLND_INC_GLOBAL_STATISTIC_W_VALUE2(STAT_MEM_FREE_COUNT, 1, STAT_MEM_FREE_AMOUNT, free_amount);
|
||||
}
|
||||
DBG_VOID_RETURN;
|
||||
TRACE_ALLOC_VOID_RETURN;
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
@ -476,11 +479,11 @@ char * _mysqlnd_pestrndup(const char * const ptr, size_t length, zend_bool persi
|
||||
{
|
||||
char * ret;
|
||||
zend_bool collect_memory_statistics = MYSQLND_G(collect_memory_statistics);
|
||||
DBG_ENTER(mysqlnd_pestrndup_name);
|
||||
DBG_INF_FMT("file=%-15s line=%4d", strrchr(__zend_filename, PHP_DIR_SEPARATOR) + 1, __zend_lineno);
|
||||
DBG_INF_FMT("ptr=%p", ptr);
|
||||
TRACE_ALLOC_ENTER(mysqlnd_pestrndup_name);
|
||||
TRACE_ALLOC_INF_FMT("file=%-15s line=%4d", strrchr(__zend_orig_filename, PHP_DIR_SEPARATOR) + 1, __zend_orig_lineno);
|
||||
TRACE_ALLOC_INF_FMT("ptr=%p", ptr);
|
||||
|
||||
ret = pemalloc(REAL_SIZE(length) + 1, persistent);
|
||||
ret = (persistent) ? __zend_malloc(REAL_SIZE(length + 1)) : _emalloc(REAL_SIZE(length + 1) ZEND_FILE_LINE_CC ZEND_FILE_LINE_ORIG_RELAY_CC);
|
||||
{
|
||||
size_t l = length;
|
||||
char * p = (char *) ptr;
|
||||
@ -496,7 +499,7 @@ char * _mysqlnd_pestrndup(const char * const ptr, size_t length, zend_bool persi
|
||||
MYSQLND_INC_GLOBAL_STATISTIC(persistent? STAT_MEM_STRNDUP_COUNT : STAT_MEM_ESTRNDUP_COUNT);
|
||||
}
|
||||
|
||||
DBG_RETURN(FAKE_PTR(ret));
|
||||
TRACE_ALLOC_RETURN(FAKE_PTR(ret));
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
@ -508,14 +511,14 @@ char * _mysqlnd_pestrdup(const char * const ptr, zend_bool persistent MYSQLND_ME
|
||||
smart_str tmp_str = {0, 0, 0};
|
||||
const char * p = ptr;
|
||||
zend_bool collect_memory_statistics = MYSQLND_G(collect_memory_statistics);
|
||||
DBG_ENTER(mysqlnd_pestrdup_name);
|
||||
DBG_INF_FMT("file=%-15s line=%4d", strrchr(__zend_filename, PHP_DIR_SEPARATOR) + 1, __zend_lineno);
|
||||
DBG_INF_FMT("ptr=%p", ptr);
|
||||
TRACE_ALLOC_ENTER(mysqlnd_pestrdup_name);
|
||||
TRACE_ALLOC_INF_FMT("file=%-15s line=%4d", strrchr(__zend_orig_filename, PHP_DIR_SEPARATOR) + 1, __zend_orig_lineno);
|
||||
TRACE_ALLOC_INF_FMT("ptr=%p", ptr);
|
||||
do {
|
||||
smart_str_appendc(&tmp_str, *p);
|
||||
} while (*p++);
|
||||
|
||||
ret = pemalloc(tmp_str.len + sizeof(size_t), persistent);
|
||||
ret = (persistent) ? __zend_malloc(tmp_str.len + sizeof(size_t)) : _emalloc(REAL_SIZE(tmp_str.len + sizeof(size_t)) ZEND_FILE_LINE_CC ZEND_FILE_LINE_ORIG_RELAY_CC);
|
||||
memcpy(FAKE_PTR(ret), tmp_str.c, tmp_str.len);
|
||||
|
||||
if (ret && collect_memory_statistics) {
|
||||
@ -524,7 +527,7 @@ char * _mysqlnd_pestrdup(const char * const ptr, zend_bool persistent MYSQLND_ME
|
||||
}
|
||||
smart_str_free(&tmp_str);
|
||||
|
||||
DBG_RETURN(FAKE_PTR(ret));
|
||||
TRACE_ALLOC_RETURN(FAKE_PTR(ret));
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
@ -549,7 +552,7 @@ PHPAPI void _mysqlnd_sprintf_free(char * p)
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
|
||||
/* {{{ _mysqlnd_vsprintf */
|
||||
PHPAPI int _mysqlnd_vsprintf(char ** pbuf, size_t max_len, const char * format, va_list ap)
|
||||
{
|
||||
return vspprintf(pbuf, max_len, format, ap);
|
||||
|
@ -26,8 +26,8 @@
|
||||
|
||||
extern const char * mysqlnd_debug_std_no_trace_funcs[];
|
||||
|
||||
#define MYSQLND_MEM_D TSRMLS_DC ZEND_FILE_LINE_DC ZEND_FILE_LINE_ORIG_DC
|
||||
#define MYSQLND_MEM_C TSRMLS_CC ZEND_FILE_LINE_CC ZEND_FILE_LINE_EMPTY_CC
|
||||
#define MYSQLND_MEM_D TSRMLS_DC ZEND_FILE_LINE_ORIG_DC
|
||||
#define MYSQLND_MEM_C TSRMLS_CC ZEND_FILE_LINE_CC
|
||||
|
||||
struct st_mysqlnd_allocator_methods
|
||||
{
|
||||
|
@ -450,20 +450,27 @@ const MYSQLND_CHARSET mysqlnd_charsets[] =
|
||||
{ 6, "hp8", "hp8_english_ci", 1, 1, "", NULL, NULL},
|
||||
{ 7, "koi8r", "koi8r_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 8, "latin1", "latin1_swedish_ci", 1, 1, "", NULL, NULL},
|
||||
{ 5, "latin1", "latin1_german_ci", 1, 1, "", NULL, NULL}, /* should be after 0x9 because swedish_ci is the default collation */
|
||||
{ 9, "latin2", "latin2_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 2, "latin2", "latin2_czech_cs", 1, 1, "", NULL, NULL}, /* should be after 0x9 because general_ci is the default collation */
|
||||
{ 10, "swe7", "swe7_swedish_ci", 1, 1, "", NULL, NULL},
|
||||
{ 11, "ascii", "ascii_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 12, "ujis", "ujis_japanese_ci", 1, 3, "", mysqlnd_mbcharlen_ujis, check_mb_ujis},
|
||||
{ 13, "sjis", "sjis_japanese_ci", 1, 2, "", mysqlnd_mbcharlen_sjis, check_mb_sjis},
|
||||
{ 16, "hebrew", "hebrew_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 17, "filename", "filename", 1, 5, "", NULL, NULL},
|
||||
{ 18, "tis620", "tis620_thai_ci", 1, 1, "", NULL, NULL},
|
||||
{ 19, "euckr", "euckr_korean_ci", 1, 2, "", mysqlnd_mbcharlen_euckr, check_mb_euckr},
|
||||
{ 21, "latin2", "latin2_hungarian_ci", 1, 1, "", NULL, NULL},
|
||||
{ 27, "latin2", "latin2_croatian_ci", 1, 1, "", NULL, NULL},
|
||||
{ 22, "koi8u", "koi8u_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 24, "gb2312", "gb2312_chinese_ci", 1, 2, "", mysqlnd_mbcharlen_gb2312, check_mb_gb2312},
|
||||
{ 25, "greek", "greek_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 26, "cp1250", "cp1250_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 28, "gbk", "gbk_chinese_ci", 1, 2, "", mysqlnd_mbcharlen_gbk, check_mb_gbk},
|
||||
{ 30, "latin5", "latin5_turkish_ci", 1, 1, "", NULL, NULL},
|
||||
{ 31, "latin1", "latin1_german2_ci", 1, 1, "", NULL, NULL},
|
||||
{ 15, "latin1", "latin1_danish_ci", 1, 1, "", NULL, NULL},
|
||||
{ 32, "armscii8", "armscii8_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 33, UTF8_MB3, UTF8_MB3"_general_ci", 1, 3, "UTF-8 Unicode", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
{ 35, "ucs2", "ucs2_general_ci", 2, 2, "UCS-2 Unicode", mysqlnd_mbcharlen_ucs2, check_mb_ucs2},
|
||||
@ -473,22 +480,11 @@ const MYSQLND_CHARSET mysqlnd_charsets[] =
|
||||
{ 39, "macroman", "macroman_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 40, "cp852", "cp852_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 41, "latin7", "latin7_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 51, "cp1251", "cp1251_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 20, "latin7", "latin7_estonian_cs", 1, 1, "", NULL, NULL},
|
||||
{ 57, "cp1256", "cp1256_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 59, "cp1257", "cp1257_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 63, "binary", "binary", 1, 1, "", NULL, NULL},
|
||||
{ 92, "geostd8", "geostd8_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 95, "cp932", "cp932_japanese_ci", 1, 2, "", mysqlnd_mbcharlen_cp932, check_mb_cp932},
|
||||
{ 97, "eucjpms", "eucjpms_japanese_ci", 1, 3, "", mysqlnd_mbcharlen_eucjpms, check_mb_eucjpms},
|
||||
{ 2, "latin2", "latin2_czech_cs", 1, 1, "", NULL, NULL},
|
||||
{ 5, "latin1", "latin1_german_ci", 1, 1, "", NULL, NULL},
|
||||
{ 14, "cp1251", "cp1251_bulgarian_ci", 1, 1, "", NULL, NULL},
|
||||
{ 15, "latin1", "latin1_danish_ci", 1, 1, "", NULL, NULL},
|
||||
{ 17, "filename", "filename", 1, 5, "", NULL, NULL},
|
||||
{ 20, "latin7", "latin7_estonian_cs", 1, 1, "", NULL, NULL},
|
||||
{ 21, "latin2", "latin2_hungarian_ci", 1, 1, "", NULL, NULL},
|
||||
{ 23, "cp1251", "cp1251_ukrainian_ci", 1, 1, "", NULL, NULL},
|
||||
{ 27, "latin2", "latin2_croatian_ci", 1, 1, "", NULL, NULL},
|
||||
{ 29, "cp1257", "cp1257_lithunian_ci", 1, 1, "", NULL, NULL},
|
||||
{ 31, "latin1", "latin1_german2_ci", 1, 1, "", NULL, NULL},
|
||||
{ 34, "cp1250", "cp1250_czech_cs", 1, 1, "", NULL, NULL},
|
||||
@ -500,6 +496,9 @@ const MYSQLND_CHARSET mysqlnd_charsets[] =
|
||||
{ 47, "latin1", "latin1_bin", 1, 1, "", NULL, NULL},
|
||||
{ 48, "latin1", "latin1_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 49, "latin1", "latin1_general_cs", 1, 1, "", NULL, NULL},
|
||||
{ 51, "cp1251", "cp1251_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 14, "cp1251", "cp1251_bulgarian_ci", 1, 1, "", NULL, NULL},
|
||||
{ 23, "cp1251", "cp1251_ukrainian_ci", 1, 1, "", NULL, NULL},
|
||||
{ 50, "cp1251", "cp1251_bin", 1, 1, "", NULL, NULL},
|
||||
{ 52, "cp1251", "cp1251_general_cs", 1, 1, "", NULL, NULL},
|
||||
{ 53, "macroman", "macroman_bin", 1, 1, "", NULL, NULL},
|
||||
@ -509,8 +508,8 @@ const MYSQLND_CHARSET mysqlnd_charsets[] =
|
||||
#ifdef USED_TO_BE_SO_BEFORE_MYSQL_5_5
|
||||
{ 60, "armascii8", "armascii8_bin", 1, 1, "", NULL, NULL},
|
||||
#endif
|
||||
{ 60, "utf32", "utf32_general_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
{ 61, "utf32", "utf32_bin", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*55*/{ 60, "utf32", "utf32_general_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*55*/{ 61, "utf32", "utf32_bin", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
{ 65, "ascii", "ascii_bin", 1, 1, "", NULL, NULL},
|
||||
{ 66, "cp1250", "cp1250_bin", 1, 1, "", NULL, NULL},
|
||||
{ 67, "cp1256", "cp1256_bin", 1, 1, "", NULL, NULL},
|
||||
@ -528,7 +527,6 @@ const MYSQLND_CHARSET mysqlnd_charsets[] =
|
||||
{ 80, "cp850", "cp850_bin", 1, 1, "", NULL, NULL},
|
||||
{ 81, "cp852", "cp852_bin", 1, 1, "", NULL, NULL},
|
||||
{ 82, "swe7", "swe7_bin", 1, 1, "", NULL, NULL},
|
||||
{ 93, "geostd8", "geostd8_bin", 1, 1, "", NULL, NULL},
|
||||
{ 83, UTF8_MB3, UTF8_MB3"_bin", 1, 3, "UTF-8 Unicode", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
{ 84, "big5", "big5_bin", 1, 2, "", mysqlnd_mbcharlen_big5, check_mb_big5},
|
||||
{ 85, "euckr", "euckr_bin", 1, 2, "", mysqlnd_mbcharlen_euckr, check_mb_euckr},
|
||||
@ -538,10 +536,14 @@ const MYSQLND_CHARSET mysqlnd_charsets[] =
|
||||
{ 89, "tis620", "tis620_bin", 1, 1, "", NULL, NULL},
|
||||
{ 90, "ucs2", "ucs2_bin", 2, 2, "UCS-2 Unicode", mysqlnd_mbcharlen_ucs2, check_mb_ucs2},
|
||||
{ 91, "ujis", "ujis_bin", 1, 3, "", mysqlnd_mbcharlen_ujis, check_mb_ujis},
|
||||
{ 92, "geostd8", "geostd8_general_ci", 1, 1, "", NULL, NULL},
|
||||
{ 93, "geostd8", "geostd8_bin", 1, 1, "", NULL, NULL},
|
||||
{ 94, "latin1", "latin1_spanish_ci", 1, 1, "", NULL, NULL},
|
||||
{ 95, "cp932", "cp932_japanese_ci", 1, 2, "", mysqlnd_mbcharlen_cp932, check_mb_cp932},
|
||||
{ 96, "cp932", "cp932_bin", 1, 2, "", mysqlnd_mbcharlen_cp932, check_mb_cp932},
|
||||
{ 99, "cp1250", "cp1250_polish_ci", 1, 1, "", NULL, NULL},
|
||||
{ 97, "eucjpms", "eucjpms_japanese_ci", 1, 3, "", mysqlnd_mbcharlen_eucjpms, check_mb_eucjpms},
|
||||
{ 98, "eucjpms", "eucjpms_bin", 1, 3, "", mysqlnd_mbcharlen_eucjpms, check_mb_eucjpms},
|
||||
{ 99, "cp1250", "cp1250_polish_ci", 1, 1, "", NULL, NULL},
|
||||
{ 128, "ucs2", "ucs2_unicode_ci", 2, 2, "", mysqlnd_mbcharlen_ucs2, check_mb_ucs2},
|
||||
{ 129, "ucs2", "ucs2_icelandic_ci", 2, 2, "", mysqlnd_mbcharlen_ucs2, check_mb_ucs2},
|
||||
{ 130, "ucs2", "ucs2_latvian_ci", 2, 2, "", mysqlnd_mbcharlen_ucs2, check_mb_ucs2},
|
||||
@ -562,7 +564,35 @@ const MYSQLND_CHARSET mysqlnd_charsets[] =
|
||||
{ 145, "ucs2", "ucs2_esperanto_ci", 2, 2, "", mysqlnd_mbcharlen_ucs2, check_mb_ucs2},
|
||||
{ 146, "ucs2", "ucs2_hungarian_ci", 2, 2, "", mysqlnd_mbcharlen_ucs2, check_mb_ucs2},
|
||||
{ 147, "ucs2", "ucs2_sinhala_ci", 2, 2, "", mysqlnd_mbcharlen_ucs2, check_mb_ucs2},
|
||||
{ 149, "ucs2", "ucs2_croatian_ci", 2, 2, "", mysqlnd_mbcharlen_ucs2, check_mb_ucs2}, /* MDB */
|
||||
{ 148, "ucs2", "ucs2_german2_ci", 2, 2, "", mysqlnd_mbcharlen_ucs2, check_mb_ucs2},
|
||||
{ 149, "ucs2", "ucs2_croatian_ci", 2, 2, "", mysqlnd_mbcharlen_ucs2, check_mb_ucs2},
|
||||
{ 150, "ucs2", "ucs2_unicode_520_ci", 2, 2, "", mysqlnd_mbcharlen_ucs2, check_mb_ucs2},
|
||||
{ 151, "ucs2", "ucs2_vietnamese_ci", 2, 2, "", mysqlnd_mbcharlen_ucs2, check_mb_ucs2},
|
||||
|
||||
/*56*/{160, "utf32", "utf32_unicode_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{161, "utf32", "utf32_icelandic_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{162, "utf32", "utf32_latvian_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{163, "utf32", "utf32_romanian_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{164, "utf32", "utf32_slovenian_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{165, "utf32", "utf32_polish_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{166, "utf32", "utf32_estonian_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{167, "utf32", "utf32_spanish_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{168, "utf32", "utf32_swedish_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{169, "utf32", "utf32_turkish_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{170, "utf32", "utf32_czech_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{171, "utf32", "utf32_danish_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{172, "utf32", "utf32_lithuanian_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{173, "utf32", "utf32_slovak_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{174, "utf32", "utf32_spanish2_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{175, "utf32", "utf32_roman_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{176, "utf32", "utf32_persian_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{177, "utf32", "utf32_esperanto_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{178, "utf32", "utf32_hungarian_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{179, "utf32", "utf32_sinhala_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{180, "utf32", "utf32_german2_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{181, "utf32", "utf32_croatian_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{182, "utf32", "utf32_unicode_520_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
/*56*/{183, "utf32", "utf32_vietnamese_ci", 4, 4, "UTF-32 Unicode", mysqlnd_mbcharlen_utf32, check_mb_utf32},
|
||||
|
||||
{ 192, UTF8_MB3, UTF8_MB3"_general_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
{ 193, UTF8_MB3, UTF8_MB3"_icelandic_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
@ -571,7 +601,7 @@ const MYSQLND_CHARSET mysqlnd_charsets[] =
|
||||
{ 196, UTF8_MB3, UTF8_MB3"_slovenian_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
{ 197, UTF8_MB3, UTF8_MB3"_polish_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
{ 198, UTF8_MB3, UTF8_MB3"_estonian_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
{ 119, UTF8_MB3, UTF8_MB3"_spanish_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
{ 199, UTF8_MB3, UTF8_MB3"_spanish_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
{ 200, UTF8_MB3, UTF8_MB3"_swedish_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
{ 201, UTF8_MB3, UTF8_MB3"_turkish_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
{ 202, UTF8_MB3, UTF8_MB3"_czech_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
@ -584,7 +614,10 @@ const MYSQLND_CHARSET mysqlnd_charsets[] =
|
||||
{ 209, UTF8_MB3, UTF8_MB3"_esperanto_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
{ 210, UTF8_MB3, UTF8_MB3"_hungarian_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
{ 211, UTF8_MB3, UTF8_MB3"_sinhala_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
{ 213, UTF8_MB3, UTF8_MB3"_croatian_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid}, /*MDB*/
|
||||
{ 211, UTF8_MB3, UTF8_MB3"_german2_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
{ 213, UTF8_MB3, UTF8_MB3"_croatian_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
{ 214, UTF8_MB3, UTF8_MB3"_unicode_520_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
{ 215, UTF8_MB3, UTF8_MB3"_vietnamese_ci", 1, 3, "", mysqlnd_mbcharlen_utf8mb3, check_mb_utf8mb3_valid},
|
||||
|
||||
{ 224, UTF8_MB4, UTF8_MB4"_unicode_ci", 1, 4, "", mysqlnd_mbcharlen_utf8, check_mb_utf8_valid},
|
||||
{ 225, UTF8_MB4, UTF8_MB4"_icelandic_ci", 1, 4, "", mysqlnd_mbcharlen_utf8, check_mb_utf8_valid},
|
||||
@ -606,6 +639,10 @@ const MYSQLND_CHARSET mysqlnd_charsets[] =
|
||||
{ 241, UTF8_MB4, UTF8_MB4"_esperanto_ci", 1, 4, "", mysqlnd_mbcharlen_utf8, check_mb_utf8_valid},
|
||||
{ 242, UTF8_MB4, UTF8_MB4"_hungarian_ci", 1, 4, "", mysqlnd_mbcharlen_utf8, check_mb_utf8_valid},
|
||||
{ 243, UTF8_MB4, UTF8_MB4"_sinhala_ci", 1, 4, "", mysqlnd_mbcharlen_utf8, check_mb_utf8_valid},
|
||||
{ 244, UTF8_MB4, UTF8_MB4"_german2_ci", 1, 4, "", mysqlnd_mbcharlen_utf8, check_mb_utf8_valid},
|
||||
{ 245, UTF8_MB4, UTF8_MB4"_croatian_ci", 1, 4, "", mysqlnd_mbcharlen_utf8, check_mb_utf8_valid},
|
||||
{ 246, UTF8_MB4, UTF8_MB4"_unicode_520_ci", 1, 4, "", mysqlnd_mbcharlen_utf8, check_mb_utf8_valid},
|
||||
{ 247, UTF8_MB4, UTF8_MB4"_vietnamese_ci", 1, 4, "", mysqlnd_mbcharlen_utf8, check_mb_utf8_valid},
|
||||
|
||||
{ 254, UTF8_MB3, UTF8_MB3"_general_cs", 1, 3, "", mysqlnd_mbcharlen_utf8, check_mb_utf8_valid},
|
||||
{ 0, NULL, NULL, 0, 0, NULL, NULL, NULL}
|
||||
|
@ -745,21 +745,26 @@ mysqlnd_debug_init(const char * skip_functions[] TSRMLS_DC)
|
||||
PHPAPI void _mysqlnd_debug(const char * mode TSRMLS_DC)
|
||||
{
|
||||
#if PHP_DEBUG
|
||||
MYSQLND_DEBUG *dbg = MYSQLND_G(dbg);
|
||||
MYSQLND_DEBUG * dbg = MYSQLND_G(dbg);
|
||||
if (!dbg) {
|
||||
MYSQLND_G(dbg) = dbg = mysqlnd_debug_init(mysqlnd_debug_std_no_trace_funcs TSRMLS_CC);
|
||||
if (!dbg) {
|
||||
return;
|
||||
struct st_mysqlnd_plugin_trace_log * trace_log_plugin = mysqlnd_plugin_find("debug_trace");
|
||||
if (trace_log_plugin) {
|
||||
dbg = trace_log_plugin->methods.trace_instance_init(mysqlnd_debug_std_no_trace_funcs TSRMLS_CC);
|
||||
if (!dbg) {
|
||||
return;
|
||||
}
|
||||
MYSQLND_G(dbg) = dbg;
|
||||
}
|
||||
}
|
||||
|
||||
dbg->m->close(dbg);
|
||||
dbg->m->set_mode(dbg, mode);
|
||||
while (zend_stack_count(&dbg->call_stack)) {
|
||||
zend_stack_del_top(&dbg->call_stack);
|
||||
}
|
||||
while (zend_stack_count(&dbg->call_time_stack)) {
|
||||
zend_stack_del_top(&dbg->call_time_stack);
|
||||
if (dbg) {
|
||||
dbg->m->close(dbg);
|
||||
dbg->m->set_mode(dbg, mode);
|
||||
while (zend_stack_count(&dbg->call_stack)) {
|
||||
zend_stack_del_top(&dbg->call_stack);
|
||||
}
|
||||
while (zend_stack_count(&dbg->call_time_stack)) {
|
||||
zend_stack_del_top(&dbg->call_time_stack);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
@ -101,44 +101,63 @@ PHPAPI char * mysqlnd_get_backtrace(uint max_levels, size_t * length TSRMLS_DC);
|
||||
#define DBG_INF_FMT_EX(dbg_obj, ...) do { if (dbg_skip_trace == FALSE) (dbg_obj)->m->log_va((dbg_obj), __LINE__, __FILE__, -1, "info : ", __VA_ARGS__); } while (0)
|
||||
#define DBG_ERR_FMT_EX(dbg_obj, ...) do { if (dbg_skip_trace == FALSE) (dbg_obj)->m->log_va((dbg_obj), __LINE__, __FILE__, -1, "error: ", __VA_ARGS__); } while (0)
|
||||
|
||||
#define DBG_BLOCK_ENTER_EX(dbg_obj, block_name) \
|
||||
{ \
|
||||
DBG_ENTER_EX(dbg_obj, (block_name));
|
||||
#define DBG_BLOCK_ENTER_EX(dbg_obj, block_name) DBG_BLOCK_ENTER_EX2((dbg_obj), NULL, (block_name))
|
||||
#define DBG_BLOCK_LEAVE_EX(dbg_obj) DBG_BLOCK_LEAVE_EX2((dbg_obj))
|
||||
|
||||
#define DBG_BLOCK_LEAVE_EX(dbg_obj) \
|
||||
DBG_LEAVE_EX((dbg_obj), ;) \
|
||||
#define DBG_BLOCK_ENTER_EX2(dbg_obj1, dbg_obj2, block_name) \
|
||||
{ \
|
||||
DBG_ENTER_EX2((dbg_obj1), (db_obj2), (block_name));
|
||||
|
||||
#define DBG_BLOCK_LEAVE_EX2(dbg_obj1, dbg_obj2) \
|
||||
DBG_LEAVE_EX2((dbg_obj1), (dbg_obj2), ;) \
|
||||
} \
|
||||
|
||||
|
||||
#define DBG_ENTER_EX(dbg_obj, func_name) \
|
||||
#define DBG_ENTER_EX(dbg_obj, func_name) DBG_ENTER_EX2((dbg_obj), (MYSQLND_DEBUG *) NULL, (func_name))
|
||||
#define DBG_LEAVE_EX(dbg_obj, leave) DBG_LEAVE_EX2((dbg_obj), (MYSQLND_DEBUG *) NULL, leave)
|
||||
|
||||
#define DBG_ENTER_EX2(dbg_obj1, dbg_obj2, func_name) \
|
||||
struct timeval __dbg_prof_tp = {0}; \
|
||||
uint64_t __dbg_prof_start = 0; /* initialization is needed */ \
|
||||
zend_bool dbg_skip_trace = TRUE; \
|
||||
if ((dbg_obj)) { \
|
||||
dbg_skip_trace = !(dbg_obj)->m->func_enter((dbg_obj), __LINE__, __FILE__, func_name, strlen(func_name)); \
|
||||
if ((dbg_obj1)) { \
|
||||
dbg_skip_trace = !(dbg_obj1)->m->func_enter((dbg_obj1), __LINE__, __FILE__, func_name, strlen(func_name)); \
|
||||
} \
|
||||
if (dbg_skip_trace); /* shut compiler's mouth */ \
|
||||
if ((dbg_obj2)) { \
|
||||
dbg_skip_trace = !(dbg_obj2)->m->func_enter((dbg_obj2), __LINE__, __FILE__, func_name, strlen(func_name)); \
|
||||
} \
|
||||
if (dbg_skip_trace); /* shut compiler's mouth */\
|
||||
do { \
|
||||
if ((dbg_obj) && (dbg_obj)->flags & MYSQLND_DEBUG_PROFILE_CALLS) { \
|
||||
if (((dbg_obj1) && (dbg_obj1)->flags & MYSQLND_DEBUG_PROFILE_CALLS) || \
|
||||
((dbg_obj2) && (dbg_obj2)->flags & MYSQLND_DEBUG_PROFILE_CALLS)) \
|
||||
{ \
|
||||
DBG_PROFILE_START_TIME(); \
|
||||
} \
|
||||
} while (0);
|
||||
|
||||
#define DBG_LEAVE_EX(dbg_obj, leave) \
|
||||
#define DBG_LEAVE_EX2(dbg_obj1, dbg_obj2, leave) \
|
||||
do {\
|
||||
if ((dbg_obj)) { \
|
||||
uint64_t this_call_duration = 0; \
|
||||
if ((dbg_obj)->flags & MYSQLND_DEBUG_PROFILE_CALLS) { \
|
||||
DBG_PROFILE_END_TIME(this_call_duration); \
|
||||
} \
|
||||
(dbg_obj)->m->func_leave((dbg_obj), __LINE__, __FILE__, this_call_duration); \
|
||||
uint64_t this_call_duration = 0; \
|
||||
if (((dbg_obj1) && (dbg_obj1)->flags & MYSQLND_DEBUG_PROFILE_CALLS) || \
|
||||
((dbg_obj2) && (dbg_obj2)->flags & MYSQLND_DEBUG_PROFILE_CALLS)) \
|
||||
{ \
|
||||
DBG_PROFILE_END_TIME(this_call_duration); \
|
||||
} \
|
||||
if ((dbg_obj1)) { \
|
||||
(dbg_obj1)->m->func_leave((dbg_obj1), __LINE__, __FILE__, this_call_duration); \
|
||||
} \
|
||||
if ((dbg_obj2)) { \
|
||||
(dbg_obj2)->m->func_leave((dbg_obj2), __LINE__, __FILE__, this_call_duration); \
|
||||
} \
|
||||
leave \
|
||||
} while (0);
|
||||
|
||||
#define DBG_RETURN_EX(dbg_obj, value) DBG_LEAVE_EX(dbg_obj, return (value);)
|
||||
|
||||
#define DBG_VOID_RETURN_EX(dbg_obj) DBG_LEAVE_EX(dbg_obj, return;)
|
||||
#define DBG_RETURN_EX(dbg_obj, value) DBG_LEAVE_EX((dbg_obj), return (value);)
|
||||
#define DBG_VOID_RETURN_EX(dbg_obj) DBG_LEAVE_EX((dbg_obj), return;)
|
||||
|
||||
#define DBG_RETURN_EX2(dbg_obj1, dbg_obj2, value) DBG_LEAVE_EX2((dbg_obj1), (dbg_obj2), return (value);)
|
||||
#define DBG_VOID_RETURN_EX2(dbg_obj1, dbg_obj2) DBG_LEAVE_EX2((dbg_obj1), (dbg_obj2), return;)
|
||||
|
||||
|
||||
|
||||
@ -168,6 +187,18 @@ static inline void DBG_ENTER_EX(MYSQLND_DEBUG * dbg_obj, const char * const func
|
||||
#define DBG_VOID_RETURN DBG_VOID_RETURN_EX(MYSQLND_G(dbg))
|
||||
#define DBG_BLOCK_LEAVE DBG_BLOCK_LEAVE_EX(MYSQLND_G(dbg))
|
||||
|
||||
|
||||
#define TRACE_ALLOC_INF(msg) DBG_INF_EX(MYSQLND_G(trace_alloc), (msg))
|
||||
#define TRACE_ALLOC_ERR(msg) DBG_ERR_EX(MYSQLND_G(trace_alloc), (msg))
|
||||
#define TRACE_ALLOC_INF_FMT(...) DBG_INF_FMT_EX(MYSQLND_G(trace_alloc), __VA_ARGS__)
|
||||
#define TRACE_ALLOC_ERR_FMT(...) DBG_ERR_FMT_EX(MYSQLND_G(trace_alloc), __VA_ARGS__)
|
||||
|
||||
#define TRACE_ALLOC_ENTER(func_name) DBG_ENTER_EX2(MYSQLND_G(dbg), MYSQLND_G(trace_alloc), (func_name))
|
||||
#define TRACE_ALLOC_BLOCK_ENTER(bname) DBG_BLOCK_ENTER_EX2(MYSQLND_G(dbg), MYSQLND_G(trace_alloc), (bname))
|
||||
#define TRACE_ALLOC_RETURN(value) DBG_RETURN_EX2(MYSQLND_G(dbg), MYSQLND_G(trace_alloc), (value))
|
||||
#define TRACE_ALLOC_VOID_RETURN DBG_VOID_RETURN_EX2(MYSQLND_G(dbg), MYSQLND_G(trace_alloc))
|
||||
#define TRACE_ALLOC_BLOCK_LEAVE DBG_BLOCK_LEAVE_EX2(MYSQLND_G(dbg), MYSQLND_G(trace_alloc))
|
||||
|
||||
#elif MYSQLND_DBG_ENABLED == 0
|
||||
|
||||
static inline void DBG_INF(const char * const msg) {}
|
||||
@ -176,10 +207,21 @@ static inline void DBG_INF_FMT(const char * const format, ...) {}
|
||||
static inline void DBG_ERR_FMT(const char * const format, ...) {}
|
||||
static inline void DBG_ENTER(const char * const func_name) {}
|
||||
#define DBG_BLOCK_ENTER(bname) {
|
||||
#define DBG_RETURN(value) return (value)
|
||||
#define DBG_VOID_RETURN return
|
||||
#define DBG_RETURN(value) return (value)
|
||||
#define DBG_VOID_RETURN return
|
||||
#define DBG_BLOCK_LEAVE }
|
||||
|
||||
|
||||
static inline void TRACE_ALLOC_INF(const char * const msg) {}
|
||||
static inline void TRACE_ALLOC_ERR(const char * const msg) {}
|
||||
static inline void TRACE_ALLOC_INF_FMT(const char * const format, ...) {}
|
||||
static inline void TRACE_ALLOC_ERR_FMT(const char * const format, ...) {}
|
||||
static inline void TRACE_ALLOC_ENTER(const char * const func_name) {}
|
||||
#define TRACE_ALLOC_BLOCK_ENTER(bname) {
|
||||
#define TRACE_ALLOC_RETURN(value) return (value)
|
||||
#define TRACE_ALLOC_VOID_RETURN return
|
||||
#define TRACE_ALLOC_BLOCK_LEAVE }
|
||||
|
||||
#endif
|
||||
|
||||
#endif /* MYSQLND_DEBUG_H */
|
||||
|
@ -221,6 +221,8 @@ static PHP_GINIT_FUNCTION(mysqlnd)
|
||||
mysqlnd_globals->collect_memory_statistics = FALSE;
|
||||
mysqlnd_globals->debug = NULL; /* The actual string */
|
||||
mysqlnd_globals->dbg = NULL; /* The DBG object*/
|
||||
mysqlnd_globals->trace_alloc_settings = NULL;
|
||||
mysqlnd_globals->trace_alloc = NULL;
|
||||
mysqlnd_globals->net_cmd_buffer_size = MYSQLND_NET_CMD_BUFFER_MIN_SIZE;
|
||||
mysqlnd_globals->net_read_buffer_size = 32768;
|
||||
mysqlnd_globals->net_read_timeout = 31536000;
|
||||
@ -253,6 +255,7 @@ PHP_INI_BEGIN()
|
||||
STD_PHP_INI_BOOLEAN("mysqlnd.collect_statistics", "1", PHP_INI_ALL, OnUpdateBool, collect_statistics, zend_mysqlnd_globals, mysqlnd_globals)
|
||||
STD_PHP_INI_BOOLEAN("mysqlnd.collect_memory_statistics", "0", PHP_INI_SYSTEM, OnUpdateBool, collect_memory_statistics, zend_mysqlnd_globals, mysqlnd_globals)
|
||||
STD_PHP_INI_ENTRY("mysqlnd.debug", NULL, PHP_INI_SYSTEM, OnUpdateString, debug, zend_mysqlnd_globals, mysqlnd_globals)
|
||||
STD_PHP_INI_ENTRY("mysqlnd.trace_alloc", NULL, PHP_INI_SYSTEM, OnUpdateString, trace_alloc_settings, zend_mysqlnd_globals, mysqlnd_globals)
|
||||
STD_PHP_INI_ENTRY("mysqlnd.net_cmd_buffer_size", MYSQLND_NET_CMD_BUFFER_MIN_SIZE_STR, PHP_INI_ALL, OnUpdateNetCmdBufferSize, net_cmd_buffer_size, zend_mysqlnd_globals, mysqlnd_globals)
|
||||
STD_PHP_INI_ENTRY("mysqlnd.net_read_buffer_size", "32768",PHP_INI_ALL, OnUpdateLong, net_read_buffer_size, zend_mysqlnd_globals, mysqlnd_globals)
|
||||
STD_PHP_INI_ENTRY("mysqlnd.net_read_timeout", "31536000", PHP_INI_SYSTEM, OnUpdateLong, net_read_timeout, zend_mysqlnd_globals, mysqlnd_globals)
|
||||
@ -306,11 +309,14 @@ static PHP_RINIT_FUNCTION(mysqlnd)
|
||||
MYSQLND_G(dbg) = NULL;
|
||||
if (trace_log_plugin) {
|
||||
MYSQLND_DEBUG * dbg = trace_log_plugin->methods.trace_instance_init(mysqlnd_debug_std_no_trace_funcs TSRMLS_CC);
|
||||
if (!dbg) {
|
||||
MYSQLND_DEBUG * trace_alloc = trace_log_plugin->methods.trace_instance_init(NULL TSRMLS_CC);
|
||||
if (!dbg || !trace_alloc) {
|
||||
return FAILURE;
|
||||
}
|
||||
dbg->m->set_mode(dbg, MYSQLND_G(debug));
|
||||
trace_alloc->m->set_mode(trace_alloc, MYSQLND_G(trace_alloc_settings));
|
||||
MYSQLND_G(dbg) = dbg;
|
||||
MYSQLND_G(trace_alloc) = trace_alloc;
|
||||
}
|
||||
}
|
||||
return SUCCESS;
|
||||
@ -324,13 +330,19 @@ static PHP_RINIT_FUNCTION(mysqlnd)
|
||||
*/
|
||||
static PHP_RSHUTDOWN_FUNCTION(mysqlnd)
|
||||
{
|
||||
MYSQLND_DEBUG *dbg = MYSQLND_G(dbg);
|
||||
MYSQLND_DEBUG * dbg = MYSQLND_G(dbg);
|
||||
MYSQLND_DEBUG * trace_alloc = MYSQLND_G(trace_alloc);
|
||||
DBG_ENTER("RSHUTDOWN");
|
||||
if (dbg) {
|
||||
dbg->m->close(dbg);
|
||||
dbg->m->free_handle(dbg);
|
||||
MYSQLND_G(dbg) = NULL;
|
||||
}
|
||||
if (trace_alloc) {
|
||||
trace_alloc->m->close(trace_alloc);
|
||||
trace_alloc->m->free_handle(trace_alloc);
|
||||
MYSQLND_G(trace_alloc) = NULL;
|
||||
}
|
||||
return SUCCESS;
|
||||
}
|
||||
/* }}} */
|
||||
|
@ -59,14 +59,14 @@ PHPAPI unsigned char *php_base64_encode(const unsigned char *str, int length, in
|
||||
unsigned char *p;
|
||||
unsigned char *result;
|
||||
|
||||
if ((length + 2) < 0 || ((length + 2) / 3) >= (1 << (sizeof(int) * 8 - 2))) {
|
||||
if (length < 0) {
|
||||
if (ret_length != NULL) {
|
||||
*ret_length = 0;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
result = (unsigned char *)safe_emalloc(((length + 2) / 3) * 4, sizeof(char), 1);
|
||||
result = (unsigned char *) safe_emalloc((length + 2) / 3, 4 * sizeof(char), 1);
|
||||
p = result;
|
||||
|
||||
while (length > 2) { /* keep going until we have less than 24 bits */
|
||||
|
@ -171,7 +171,7 @@ PHPAPI int crypt_execute(const char *password, const int pass_len, const char *s
|
||||
char *output;
|
||||
int needed = (sizeof(sha512_salt_prefix) - 1
|
||||
+ sizeof(sha512_rounds_prefix) + 9 + 1
|
||||
+ PHP_MAX_SALT_LEN + 43 + 1);
|
||||
+ salt_in_len + 1 + 86 + 1);
|
||||
output = emalloc(needed);
|
||||
|
||||
crypt_res = php_sha512_crypt_r(password, salt, output, needed);
|
||||
@ -189,7 +189,7 @@ PHPAPI int crypt_execute(const char *password, const int pass_len, const char *s
|
||||
char *output;
|
||||
int needed = (sizeof(sha256_salt_prefix) - 1
|
||||
+ sizeof(sha256_rounds_prefix) + 9 + 1
|
||||
+ PHP_MAX_SALT_LEN + 43 + 1);
|
||||
+ salt_in_len + 1 + 43 + 1);
|
||||
output = emalloc(needed);
|
||||
|
||||
crypt_res = php_sha256_crypt_r(password, salt, output, needed);
|
||||
|
25
ext/standard/tests/serialize/bug62373.phpt
Normal file
25
ext/standard/tests/serialize/bug62373.phpt
Normal file
@ -0,0 +1,25 @@
|
||||
--TEST--
|
||||
Bug #62373 (serialize() generates wrong reference to the object)
|
||||
--FILE--
|
||||
<?php
|
||||
class A {}
|
||||
class B {}
|
||||
|
||||
$size_of_ce = (((int)(log(PHP_INT_MAX) / log(2)) + 1 == 32 ? 368: 680) + 15) & ~15;
|
||||
$dummy = array();
|
||||
$b = new B();
|
||||
$period = $size_of_ce << 5;
|
||||
for ($i = 0; $i < $period * 3; $i++) {
|
||||
$a = new A();
|
||||
$s = unserialize(serialize(array($b, $a)));
|
||||
if ($s[0] === $s[1]) {
|
||||
echo "OOPS\n";
|
||||
break;
|
||||
}
|
||||
$dummy[] = $a;
|
||||
}
|
||||
|
||||
echo "OK\n";
|
||||
?>
|
||||
--EXPECT--
|
||||
OK
|
9
ext/standard/tests/strings/bug62443.phpt
Normal file
9
ext/standard/tests/strings/bug62443.phpt
Normal file
@ -0,0 +1,9 @@
|
||||
--TEST--
|
||||
Bug #62443 Crypt SHA256/512 Segfaults With Malformed Salt
|
||||
--FILE--
|
||||
<?php
|
||||
crypt("foo", '$5$'.chr(0).'abc');
|
||||
crypt("foo", '$6$'.chr(0).'abc');
|
||||
echo "OK!";
|
||||
--EXPECT--
|
||||
OK!
|
@ -541,12 +541,9 @@ static inline int php_add_var_hash(HashTable *var_hash, zval *var, void *var_old
|
||||
|
||||
/* relies on "(long)" being a perfect hash function for data pointers,
|
||||
* however the actual identity of an object has had to be determined
|
||||
* by its object handle and the class entry since 5.0. */
|
||||
* by its object handle since 5.0. */
|
||||
if ((Z_TYPE_P(var) == IS_OBJECT) && Z_OBJ_HT_P(var)->get_class_entry) {
|
||||
p = smart_str_print_long(id + sizeof(id) - 1,
|
||||
(((size_t)Z_OBJCE_P(var) << 5)
|
||||
| ((size_t)Z_OBJCE_P(var) >> (sizeof(long) * 8 - 5)))
|
||||
+ (long) Z_OBJ_HANDLE_P(var));
|
||||
p = smart_str_print_long(id + sizeof(id) - 1, (long) Z_OBJ_HANDLE_P(var));
|
||||
*(--p) = 'O';
|
||||
len = id + sizeof(id) - 1 - p;
|
||||
} else {
|
||||
|
@ -1173,6 +1173,9 @@ out:
|
||||
if (request_started) {
|
||||
php_request_shutdown((void *) 0);
|
||||
}
|
||||
if (translated_path) {
|
||||
free(translated_path);
|
||||
}
|
||||
return exit_status;
|
||||
err:
|
||||
sapi_deactivate(TSRMLS_C);
|
||||
|
Loading…
Reference in New Issue
Block a user