Bug #69732 [Opn]: can induce segmentation fault with basic php code
| From: | requinix@php.net | Date: | Sat, 30 May 2015 01:27:07 +0000 |
| Subject: | Bug #69732 [Opn]: can induce segmentation fault with basic php code | ||
| References: | 1 | Groups: | php.bugs |
| Request: | Send a blank email to php-bugs+get-193010@lists.php.net to get a copy of this message | ||
Edit report at https://bugs.php.net/bug.php?id=69732&edit=1
ID: 69732
Updated by: requinix@php.net
Reported by: will dot o dot west at gmail dot com
Summary: can induce segmentation fault with basic php code
Status: Open
Type: Bug
Package: Reproducible crash
Operating System: OSX / Ubuntu Trusty
PHP Version: 5.5.25
Block user comment: N
Private report: N
New Comment:
The segfault is because of infinite recursion: if ->foo does not exist then __get(foo) will be
called, which tries to do ->foo, which does not exist so __get(foo) will be called... until PHP
dies.
__get() should never blindly do a ->$name for this reason. If anything it should manually test
for the presence of the property, like with get_object_vars(), before attempting to return it.
If there is a bug here it's because $wpq->interesting =& ret_assoc() does not behave
like a regular assignment (given that ret_assoc() isn't returning by-reference), creating the
property on $wpq. If you dump $wpq after this line you'll see it doesn't have a
$interesting property - just $unreferenced.
Making ret_assoc() return by-ref results in a fatal error "Cannot assign by reference to
overloaded object". I too don't think that should be a problem if __set is not implemented
and assignment should behave normally (ie, creating the property).
Previous Comments:
------------------------------------------------------------------------
[2015-05-29 16:16:40] will dot o dot west at gmail dot com
Description:
------------
The following snippet is a minimal reproduction of an segv found in a WordPress site, wherein a
theme was stashing data in an undeclared field of the WP_Query object, which has a __get but no
__set. Its not clear whether this worked as intended in any prior versions of php.
Test script:
---------------
<?php
class wpq {
private $unreferenced;
public function __get($name) {
return $this->$name;
}
}
function ret_assoc() {
return array('foo' => 'bar');
}
$wpq = new wpq;
$wpq->interesting =& ret_assoc();
$x = $wpq->interesting;
printf("%s\n", $x);
Expected result:
----------------
likely printing an empty string
Actual result:
--------------
Segmentation fault: 11
------------------------------------------------------------------------
--
Edit this bug report at https://bugs.php.net/bug.php?id=69732&edit=1