diff options
author | Anatol Belski <ab@php.net> | 2014-06-03 20:43:58 +0200 |
---|---|---|
committer | Anatol Belski <ab@php.net> | 2014-06-03 20:43:58 +0200 |
commit | 20568e502814fffc41d91a22edaf75ff5ae19d5c (patch) | |
tree | b2fe1605e665c04d31f7716dbb2baa87bdee2464 | |
parent | 0817a2c7679a2749f44ba5b17b4387ef000a3de3 (diff) | |
download | php-git-20568e502814fffc41d91a22edaf75ff5ae19d5c.tar.gz |
Fixed regression introduced by patch for bug #67072
This applies to 5.4 and 5.5 only as a legacy fix.
-rw-r--r-- | ext/standard/tests/serialize/005.phpt | 8 | ||||
-rw-r--r-- | ext/standard/var_unserializer.c | 68 | ||||
-rw-r--r-- | ext/standard/var_unserializer.re | 6 |
3 files changed, 44 insertions, 38 deletions
diff --git a/ext/standard/tests/serialize/005.phpt b/ext/standard/tests/serialize/005.phpt index 2df270154d..07d47bd8c7 100644 --- a/ext/standard/tests/serialize/005.phpt +++ b/ext/standard/tests/serialize/005.phpt @@ -156,11 +156,9 @@ object(TestNAOld)#%d (0) { } ===NANew=== unserializer(TestNANew) - -Warning: Erroneous data format for unserializing 'TestNANew' in %s005.php on line %d - -Notice: unserialize(): Error at offset 19 of 20 bytes in %s005.php on line %d -bool(false) +TestNew::__wakeup() +object(TestNANew)#1 (0) { +} ===NANew2=== unserializer(TestNANew2) TestNew::unserialize() diff --git a/ext/standard/var_unserializer.c b/ext/standard/var_unserializer.c index 003bac9547..29d2e0f7ed 100644 --- a/ext/standard/var_unserializer.c +++ b/ext/standard/var_unserializer.c @@ -1,4 +1,4 @@ -/* Generated by re2c 0.13.5 on Fri Apr 18 15:07:27 2014 */ +/* Generated by re2c 0.13.5 on Tue Jun 3 10:23:35 2014 */ #line 1 "ext/standard/var_unserializer.re" /* +----------------------------------------------------------------------+ @@ -396,7 +396,11 @@ static inline long object_common1(UNSERIALIZE_PARAMETER, zend_class_entry *ce) (*p) += 2; - if (ce->serialize == NULL) { + /* The internal class check here is a BC fix only, userspace classes implementing the + Serializable interface have eventually an inconsistent behavior at this place when + unserialized from a manipulated string. Additionaly the interal classes can possibly + crash PHP so they're still disabled here. */ + if (ce->serialize == NULL || ZEND_INTERNAL_CLASS != ce->type) { object_init_ex(*rval, ce); } else { /* If this class implements Serializable, it should not land here but in object_custom(). The passed string @@ -469,7 +473,7 @@ PHPAPI int php_var_unserialize(UNSERIALIZE_PARAMETER) -#line 473 "ext/standard/var_unserializer.c" +#line 477 "ext/standard/var_unserializer.c" { YYCTYPE yych; static const unsigned char yybm[] = { @@ -529,9 +533,9 @@ yy2: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy95; yy3: -#line 824 "ext/standard/var_unserializer.re" +#line 828 "ext/standard/var_unserializer.re" { return 0; } -#line 535 "ext/standard/var_unserializer.c" +#line 539 "ext/standard/var_unserializer.c" yy4: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy89; @@ -574,13 +578,13 @@ yy13: goto yy3; yy14: ++YYCURSOR; -#line 818 "ext/standard/var_unserializer.re" +#line 822 "ext/standard/var_unserializer.re" { /* this is the case where we have less data than planned */ php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Unexpected end of serialized data"); return 0; /* not sure if it should be 0 or 1 here? */ } -#line 584 "ext/standard/var_unserializer.c" +#line 588 "ext/standard/var_unserializer.c" yy16: yych = *++YYCURSOR; goto yy3; @@ -610,7 +614,7 @@ yy20: yych = *++YYCURSOR; if (yych != '"') goto yy18; ++YYCURSOR; -#line 672 "ext/standard/var_unserializer.re" +#line 676 "ext/standard/var_unserializer.re" { size_t len, len2, len3, maxlen; long elements; @@ -756,7 +760,7 @@ yy20: return object_common2(UNSERIALIZE_PASSTHRU, elements); } -#line 760 "ext/standard/var_unserializer.c" +#line 764 "ext/standard/var_unserializer.c" yy25: yych = *++YYCURSOR; if (yych <= ',') { @@ -781,7 +785,7 @@ yy27: yych = *++YYCURSOR; if (yych != '"') goto yy18; ++YYCURSOR; -#line 664 "ext/standard/var_unserializer.re" +#line 668 "ext/standard/var_unserializer.re" { INIT_PZVAL(*rval); @@ -789,7 +793,7 @@ yy27: return object_common2(UNSERIALIZE_PASSTHRU, object_common1(UNSERIALIZE_PASSTHRU, ZEND_STANDARD_CLASS_DEF_PTR)); } -#line 793 "ext/standard/var_unserializer.c" +#line 797 "ext/standard/var_unserializer.c" yy32: yych = *++YYCURSOR; if (yych == '+') goto yy33; @@ -810,7 +814,7 @@ yy34: yych = *++YYCURSOR; if (yych != '{') goto yy18; ++YYCURSOR; -#line 644 "ext/standard/var_unserializer.re" +#line 648 "ext/standard/var_unserializer.re" { long elements = parse_iv(start + 2); /* use iv() not uiv() in order to check data range */ @@ -830,7 +834,7 @@ yy34: return finish_nested_data(UNSERIALIZE_PASSTHRU); } -#line 834 "ext/standard/var_unserializer.c" +#line 838 "ext/standard/var_unserializer.c" yy39: yych = *++YYCURSOR; if (yych == '+') goto yy40; @@ -851,7 +855,7 @@ yy41: yych = *++YYCURSOR; if (yych != '"') goto yy18; ++YYCURSOR; -#line 615 "ext/standard/var_unserializer.re" +#line 619 "ext/standard/var_unserializer.re" { size_t len, maxlen; char *str; @@ -880,7 +884,7 @@ yy41: ZVAL_STRINGL(*rval, str, len, 0); return 1; } -#line 884 "ext/standard/var_unserializer.c" +#line 888 "ext/standard/var_unserializer.c" yy46: yych = *++YYCURSOR; if (yych == '+') goto yy47; @@ -901,7 +905,7 @@ yy48: yych = *++YYCURSOR; if (yych != '"') goto yy18; ++YYCURSOR; -#line 587 "ext/standard/var_unserializer.re" +#line 591 "ext/standard/var_unserializer.re" { size_t len, maxlen; char *str; @@ -929,7 +933,7 @@ yy48: ZVAL_STRINGL(*rval, str, len, 1); return 1; } -#line 933 "ext/standard/var_unserializer.c" +#line 937 "ext/standard/var_unserializer.c" yy53: yych = *++YYCURSOR; if (yych <= '/') { @@ -1017,7 +1021,7 @@ yy61: } yy63: ++YYCURSOR; -#line 577 "ext/standard/var_unserializer.re" +#line 581 "ext/standard/var_unserializer.re" { #if SIZEOF_LONG == 4 use_double: @@ -1027,7 +1031,7 @@ use_double: ZVAL_DOUBLE(*rval, zend_strtod((const char *)start + 2, NULL)); return 1; } -#line 1031 "ext/standard/var_unserializer.c" +#line 1035 "ext/standard/var_unserializer.c" yy65: yych = *++YYCURSOR; if (yych <= ',') { @@ -1086,7 +1090,7 @@ yy73: yych = *++YYCURSOR; if (yych != ';') goto yy18; ++YYCURSOR; -#line 562 "ext/standard/var_unserializer.re" +#line 566 "ext/standard/var_unserializer.re" { *p = YYCURSOR; INIT_PZVAL(*rval); @@ -1101,7 +1105,7 @@ yy73: return 1; } -#line 1105 "ext/standard/var_unserializer.c" +#line 1109 "ext/standard/var_unserializer.c" yy76: yych = *++YYCURSOR; if (yych == 'N') goto yy73; @@ -1128,7 +1132,7 @@ yy79: if (yych <= '9') goto yy79; if (yych != ';') goto yy18; ++YYCURSOR; -#line 535 "ext/standard/var_unserializer.re" +#line 539 "ext/standard/var_unserializer.re" { #if SIZEOF_LONG == 4 int digits = YYCURSOR - start - 3; @@ -1155,7 +1159,7 @@ yy79: ZVAL_LONG(*rval, parse_iv(start + 2)); return 1; } -#line 1159 "ext/standard/var_unserializer.c" +#line 1163 "ext/standard/var_unserializer.c" yy83: yych = *++YYCURSOR; if (yych <= '/') goto yy18; @@ -1163,24 +1167,24 @@ yy83: yych = *++YYCURSOR; if (yych != ';') goto yy18; ++YYCURSOR; -#line 528 "ext/standard/var_unserializer.re" +#line 532 "ext/standard/var_unserializer.re" { *p = YYCURSOR; INIT_PZVAL(*rval); ZVAL_BOOL(*rval, parse_iv(start + 2)); return 1; } -#line 1174 "ext/standard/var_unserializer.c" +#line 1178 "ext/standard/var_unserializer.c" yy87: ++YYCURSOR; -#line 521 "ext/standard/var_unserializer.re" +#line 525 "ext/standard/var_unserializer.re" { *p = YYCURSOR; INIT_PZVAL(*rval); ZVAL_NULL(*rval); return 1; } -#line 1184 "ext/standard/var_unserializer.c" +#line 1188 "ext/standard/var_unserializer.c" yy89: yych = *++YYCURSOR; if (yych <= ',') { @@ -1203,7 +1207,7 @@ yy91: if (yych <= '9') goto yy91; if (yych != ';') goto yy18; ++YYCURSOR; -#line 498 "ext/standard/var_unserializer.re" +#line 502 "ext/standard/var_unserializer.re" { long id; @@ -1226,7 +1230,7 @@ yy91: return 1; } -#line 1230 "ext/standard/var_unserializer.c" +#line 1234 "ext/standard/var_unserializer.c" yy95: yych = *++YYCURSOR; if (yych <= ',') { @@ -1249,7 +1253,7 @@ yy97: if (yych <= '9') goto yy97; if (yych != ';') goto yy18; ++YYCURSOR; -#line 477 "ext/standard/var_unserializer.re" +#line 481 "ext/standard/var_unserializer.re" { long id; @@ -1270,9 +1274,9 @@ yy97: return 1; } -#line 1274 "ext/standard/var_unserializer.c" +#line 1278 "ext/standard/var_unserializer.c" } -#line 826 "ext/standard/var_unserializer.re" +#line 830 "ext/standard/var_unserializer.re" return 0; diff --git a/ext/standard/var_unserializer.re b/ext/standard/var_unserializer.re index b3f5d29ca2..cd4d53b5c1 100644 --- a/ext/standard/var_unserializer.re +++ b/ext/standard/var_unserializer.re @@ -400,7 +400,11 @@ static inline long object_common1(UNSERIALIZE_PARAMETER, zend_class_entry *ce) (*p) += 2; - if (ce->serialize == NULL) { + /* The internal class check here is a BC fix only, userspace classes implementing the + Serializable interface have eventually an inconsistent behavior at this place when + unserialized from a manipulated string. Additionaly the interal classes can possibly + crash PHP so they're still disabled here. */ + if (ce->serialize == NULL || ZEND_INTERNAL_CLASS != ce->type) { object_init_ex(*rval, ce); } else { /* If this class implements Serializable, it should not land here but in object_custom(). The passed string |