diff options
author | Dmitry Stogov <dmitry@zend.com> | 2016-12-02 12:34:46 +0300 |
---|---|---|
committer | Dmitry Stogov <dmitry@zend.com> | 2016-12-02 12:34:46 +0300 |
commit | 67d90a4870499f53faefc3314f50181d4150d7d0 (patch) | |
tree | 55b8880f0209ab442cb345f5cb9a6e1aef03f18b | |
parent | fcaccbaa22784084d2cb59821b4e66c230702851 (diff) | |
download | php-git-67d90a4870499f53faefc3314f50181d4150d7d0.tar.gz |
Fixed possible memory leak in &=, |=, ^=.
-rw-r--r-- | Zend/tests/self_and.phpt | 10 | ||||
-rw-r--r-- | Zend/tests/self_or.phpt | 10 | ||||
-rw-r--r-- | Zend/tests/self_xor.phpt | 12 | ||||
-rw-r--r-- | Zend/zend_operators.c | 9 |
4 files changed, 40 insertions, 1 deletions
diff --git a/Zend/tests/self_and.phpt b/Zend/tests/self_and.phpt index cdcde77992..e9ddc849eb 100644 --- a/Zend/tests/self_and.phpt +++ b/Zend/tests/self_and.phpt @@ -6,6 +6,8 @@ ANDing strings $s = "123"; $s1 = "test"; $s2 = "45345some"; +$s3 = str_repeat("f", 1); +$s4 = str_repeat("f", 2); $s &= 22; var_dump($s); @@ -16,10 +18,18 @@ var_dump($s1); $s2 &= 33; var_dump($s2); +$s3 &= " "; +var_dump($s3); + +$s4 &= " "; +var_dump($s4); + echo "Done\n"; ?> --EXPECTF-- int(18) int(0) int(33) +string(1) " " +string(2) " " Done diff --git a/Zend/tests/self_or.phpt b/Zend/tests/self_or.phpt index ae667bff16..991aafa980 100644 --- a/Zend/tests/self_or.phpt +++ b/Zend/tests/self_or.phpt @@ -6,6 +6,8 @@ ORing strings $s = "123"; $s1 = "test"; $s2 = "45345some"; +$s3 = str_repeat("f", 1); +$s4 = str_repeat("f", 2); $s |= 22; var_dump($s); @@ -16,10 +18,18 @@ var_dump($s1); $s2 |= 33; var_dump($s2); +$s3 |= " "; +var_dump($s3); + +$s4 |= " "; +var_dump($s4); + echo "Done\n"; ?> --EXPECTF-- int(127) int(11) int(45345) +string(1) "f" +string(2) "ff" Done diff --git a/Zend/tests/self_xor.phpt b/Zend/tests/self_xor.phpt index a7e43f539d..1577690a89 100644 --- a/Zend/tests/self_xor.phpt +++ b/Zend/tests/self_xor.phpt @@ -6,6 +6,8 @@ XORing strings $s = "123"; $s1 = "test"; $s2 = "45345some"; +$s3 = str_repeat("f", 1); +$s4 = str_repeat("f", 2); $s ^= 22; var_dump($s); @@ -16,10 +18,18 @@ var_dump($s1); $s2 ^= 33; var_dump($s2); +$s3 |= " "; +var_dump($s3); + +$s4 |= " "; +var_dump($s4); + echo "Done\n"; ?> --EXPECTF-- int(109) int(11) int(45312) -Done +string(1) "f" +string(2) "ff" +Done
\ No newline at end of file diff --git a/Zend/zend_operators.c b/Zend/zend_operators.c index a02551b1bd..2d7fd96279 100644 --- a/Zend/zend_operators.c +++ b/Zend/zend_operators.c @@ -1349,6 +1349,9 @@ ZEND_API int ZEND_FASTCALL bitwise_or_function(zval *result, zval *op1, zval *op if (EXPECTED(Z_STRLEN_P(op1) >= Z_STRLEN_P(op2))) { if (EXPECTED(Z_STRLEN_P(op1) == Z_STRLEN_P(op2)) && Z_STRLEN_P(op1) == 1) { zend_uchar or = (zend_uchar) (*Z_STRVAL_P(op1) | *Z_STRVAL_P(op2)); + if (result==op1) { + zend_string_release(Z_STR_P(result)); + } if (CG(one_char_string)[or]) { ZVAL_INTERNED_STR(result, CG(one_char_string)[or]); } else { @@ -1416,6 +1419,9 @@ ZEND_API int ZEND_FASTCALL bitwise_and_function(zval *result, zval *op1, zval *o if (EXPECTED(Z_STRLEN_P(op1) >= Z_STRLEN_P(op2))) { if (EXPECTED(Z_STRLEN_P(op1) == Z_STRLEN_P(op2)) && Z_STRLEN_P(op1) == 1) { zend_uchar and = (zend_uchar) (*Z_STRVAL_P(op1) & *Z_STRVAL_P(op2)); + if (result==op1) { + zend_string_release(Z_STR_P(result)); + } if (CG(one_char_string)[and]) { ZVAL_INTERNED_STR(result, CG(one_char_string)[and]); } else { @@ -1483,6 +1489,9 @@ ZEND_API int ZEND_FASTCALL bitwise_xor_function(zval *result, zval *op1, zval *o if (EXPECTED(Z_STRLEN_P(op1) >= Z_STRLEN_P(op2))) { if (EXPECTED(Z_STRLEN_P(op1) == Z_STRLEN_P(op2)) && Z_STRLEN_P(op1) == 1) { zend_uchar xor = (zend_uchar) (*Z_STRVAL_P(op1) ^ *Z_STRVAL_P(op2)); + if (result==op1) { + zend_string_release(Z_STR_P(result)); + } if (CG(one_char_string)[xor]) { ZVAL_INTERNED_STR(result, CG(one_char_string)[xor]); } else { |