From: Dmitry Stogov Date: Thu, 9 Jun 2016 12:07:44 +0000 (+0300) Subject: Fixed bug #72369 (array_merge() produces references in PHP7) X-Git-Tag: php-7.1.0alpha2~45^2~3 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=bfcf32237e32b46cba7ce2f9bcd36482978f8dd8;p=php Fixed bug #72369 (array_merge() produces references in PHP7) --- diff --git a/NEWS b/NEWS index e2c3b94c1e..fdb232695f 100644 --- a/NEWS +++ b/NEWS @@ -38,6 +38,7 @@ PHP NEWS . Fixed bug #72197 (pg_lo_create arbitrary read). (Anatol) - Standard: + . Fixed bug #72369 (array_merge() produces references in PHP7). (Dmitry) . Fixed bug #72300 (ignore_user_abort(false) has no effect). (Laruence) . Fixed bug #72229 (Wrong reference when serialize/unserialize an object). (Laruence) diff --git a/ext/standard/array.c b/ext/standard/array.c index d07daf819a..6c58e3aa74 100644 --- a/ext/standard/array.c +++ b/ext/standard/array.c @@ -3095,15 +3095,20 @@ PHPAPI int php_array_merge(HashTable *dest, HashTable *src) /* {{{ */ zend_string *string_key; ZEND_HASH_FOREACH_STR_KEY_VAL(src, string_key, src_entry) { - if (string_key) { - if (Z_REFCOUNTED_P(src_entry)) { + if (Z_REFCOUNTED_P(src_entry)) { + if (UNEXPECTED(Z_ISREF_P(src_entry)) + && UNEXPECTED(Z_REFCOUNT_P(src_entry) == 1)) { + ZVAL_UNREF(src_entry); + if (Z_REFCOUNTED_P(src_entry)) { + Z_ADDREF_P(src_entry); + } + } else { Z_ADDREF_P(src_entry); } + } + if (string_key) { zend_hash_update(dest, string_key, src_entry); } else { - if (Z_REFCOUNTED_P(src_entry)) { - Z_ADDREF_P(src_entry); - } zend_hash_next_index_insert_new(dest, src_entry); } } ZEND_HASH_FOREACH_END(); diff --git a/ext/standard/tests/array/bug72369.phpt b/ext/standard/tests/array/bug72369.phpt new file mode 100644 index 0000000000..63bb5625de --- /dev/null +++ b/ext/standard/tests/array/bug72369.phpt @@ -0,0 +1,16 @@ +--TEST-- +Bug #72369 (array_merge() produces references in PHP7) +--FILE-- + &$x]; +unset($x); +$a = ['test' => 'yyy']; +$a = array_merge($a, $d); +debug_zval_dump($a); +?> +--EXPECTF-- +array(1) refcount(%d){ + ["test"]=> + string(3) "xxx" refcount(%d) +}