Bug #79002 [NEW]: Serializing uninitialized typed properties with __sleep makes unserialize throw
| From: | tandre@php.net | Date: | Thu, 19 Dec 2019 16:10:44 +0000 |
| Subject: | Bug #79002 [NEW]: Serializing uninitialized typed properties with __sleep makes unserialize throw | ||
| Groups: | php.bugs | ||
| Request: | Send a blank email to php-bugs+get-224425@lists.php.net to get a copy of this message | ||
From: tandre
Operating system: Any
PHP version: 7.4.1
Package: Scripting Engine problem
Bug Type: Bug
Bug description:Serializing uninitialized typed properties with __sleep makes unserialize throw
Description:
------------
When __sleep includes uninitialized typed properties, serialize() will
succeed (behaves as if the value was null), but unserialize() will cause
a TypeError to be thrown if the value wasn't nullable.
I didn't see any mention of how uninitialized typed properties should
behave for __sleep in the RFC or RFC/PR discussion.
Is the current behavior in 7.4 and 8.0-dev for __sleep on uninitialized
properties by design, or is it an edge case that was overlooked? It
seems surprising that data serializes successfully, but throws when it
gets unserialized for the same class declaration.
I checked https://wiki.php.net/rfc/typed_properties_v2
,
https://externals.io/message/102333 , and
https://externals.io/message/103148 , and
didn't see any references to
__sleep (just "I wouldn't lose sleep
if we wanted to keep the GA date where it is.")
I also didn't see any mention of __sleep in php/php-src#3734 , or in the
changes of the PR. (or in bugs.php.net)
Noticed in
https://github.com/igbinary/igbinary/pull/250#discussion_r355812953
Test script:
---------------
<?php
class HasProp {
public int $x;
public function __sleep() { return ['x']; }
}
$x = new HasProp();
// string(28) "O:7:"HasProp":1:{s:1:"x";N;}"
var_dump($s = serialize($x));
// Fatal error: Uncaught TypeError: Typed property HasProp::$x must be
int, null used in ...
unserialize($s);
Expected result:
----------------
Unserialize() should not throw, and should generate an instance of
HasProp, with an uninitialized HasProp.
Ideally, serialize() should skip over the property $x. This would make
it match the original data's representation for both typed nullable and
non-nullable properties.
Actual result:
--------------
This throws a TypeError when unserializing the data it just serialized
--
Edit bug report at https://bugs.php.net/bug.php?id=79002&edit=1
--
Fix committed: https://bugs.php.net/fix.php?id=79002&r=fixed
Fixed in release: https://bugs.php.net/fix.php?id=79002&r=alreadyfixed
Need backtrace: https://bugs.php.net/fix.php?id=79002&r=needtrace
Need Reproduce Script: https://bugs.php.net/fix.php?id=79002&r=needscript
Try newer version: https://bugs.php.net/fix.php?id=79002&r=oldversion
Not developer issue: https://bugs.php.net/fix.php?id=79002&r=support
Expected behavior: https://bugs.php.net/fix.php?id=79002&r=notwrong
Not enough info: https://bugs.php.net/fix.php?id=79002&r=notenoughinfo
Submitted twice: https://bugs.php.net/fix.php?id=79002&r=submittedtwice
register_globals: https://bugs.php.net/fix.php?id=79002&r=globals
PHP version support discontinued: https://bugs.php.net/fix.php?id=79002&r=phptooold
Daylight Savings: https://bugs.php.net/fix.php?id=79002&r=dst
IIS Stability: https://bugs.php.net/fix.php?id=79002&r=isapi
Install GNU Sed: https://bugs.php.net/fix.php?id=79002&r=gnused
Floating point limitations: https://bugs.php.net/fix.php?id=79002&r=float
No Zend Extensions: https://bugs.php.net/fix.php?id=79002&r=nozend
MySQL Configuration Error: https://bugs.php.net/fix.php?id=79002&r=mysqlcfg