summaryrefslogtreecommitdiff
path: root/Zend/zend_constants.c
diff options
context:
space:
mode:
authorDmitry Stogov <dmitry@zend.com>2017-11-01 10:34:39 +0300
committerDmitry Stogov <dmitry@zend.com>2017-11-01 10:34:39 +0300
commite0924c52fc7c69b483b5416c609ce7f008584845 (patch)
treec6289f109c990d29029a9451e7c0ef6cb5dc431f /Zend/zend_constants.c
parenta8a17a72b06e6ea39a70eaf45ad2c3d6668e29ba (diff)
downloadphp-git-e0924c52fc7c69b483b5416c609ce7f008584845.tar.gz
Fixed string interning during constants substitution
Diffstat (limited to 'Zend/zend_constants.c')
-rw-r--r--Zend/zend_constants.c26
1 files changed, 16 insertions, 10 deletions
diff --git a/Zend/zend_constants.c b/Zend/zend_constants.c
index 100d0a263b..bbb4824d1d 100644
--- a/Zend/zend_constants.c
+++ b/Zend/zend_constants.c
@@ -445,13 +445,21 @@ ZEND_API zend_constant* ZEND_FASTCALL zend_quick_get_constant(const zval *key, u
static void* zend_hash_add_constant(HashTable *ht, zend_string *key, zend_constant *c)
{
- void *ret;
- zend_constant *copy = pemalloc(sizeof(zend_constant), c->flags & CONST_PERSISTENT);
-
- memcpy(copy, c, sizeof(zend_constant));
- ret = zend_hash_add_ptr(ht, key, copy);
- if (!ret) {
- pefree(copy, c->flags & CONST_PERSISTENT);
+ zval *ret, tmp;
+ zend_constant *copy;
+
+ ZVAL_PTR(&tmp, NULL);
+ ret = zend_hash_add(ht, key, &tmp);
+ if (EXPECTED(ret)) {
+ Z_PTR_P(ret) = copy = pemalloc(sizeof(zend_constant), c->flags & CONST_PERSISTENT);
+ memcpy(copy, c, sizeof(zend_constant));
+ if (Z_TYPE(copy->value) == IS_STRING && !ZSTR_IS_INTERNED(Z_STR(copy->value))) {
+ SEPARATE_STRING(&copy->value);
+ Z_STR(copy->value) = zend_new_interned_string(Z_STR(copy->value));
+ if (ZSTR_IS_INTERNED(Z_STR(copy->value))) {
+ Z_TYPE_FLAGS(copy->value) &= ~ (IS_TYPE_REFCOUNTED | IS_TYPE_COPYABLE);
+ }
+ }
}
return ret;
}
@@ -466,9 +474,7 @@ ZEND_API int zend_register_constant(zend_constant *c)
printf("Registering constant for module %d\n", c->module_number);
#endif
- if (c->module_number != PHP_USER_CONSTANT) {
- c->name = zend_new_interned_string(c->name);
- }
+ c->name = zend_new_interned_string(c->name);
if (!(c->flags & CONST_CS)) {
lowercase_name = zend_string_alloc(ZSTR_LEN(c->name), c->flags & CONST_PERSISTENT);