Edit report at https://bugs.php.net/bug.php?id=64417&edit=1
ID: 64417 Updated by: dmi...@php.net Reported by: me at fixxxer dot me Summary: BC break: ArrayAccess::&offsetGet() in a trait causes fatal error. Status: Closed Type: Bug Package: Scripting Engine problem Operating System: any PHP Version: 5.4Git-2013-03-12 (snap) Assigned To: dmitry Block user comment: N Private report: N New Comment: The fix for this bug has been committed. Snapshots of the sources are packaged every three hours; this change will be in the next snapshot. You can grab the snapshot at http://snaps.php.net/. For Windows: http://windows.php.net/snapshots/ Thank you for the report, and for helping us make PHP better. Previous Comments: ------------------------------------------------------------------------ [2013-03-19 09:15:53] dmi...@php.net Automatic comment on behalf of dmi...@zend.com Revision: http://git.php.net/?p=php-src.git;a=commit;h=e62bb0325763d9847847dd198e05c9b3147caf05 Log: Fixed bug #64417 (ArrayAccess::&offsetGet() in a trait causes fatal error) ------------------------------------------------------------------------ [2013-03-14 13:44:49] larue...@php.net dmitry, please look at this one. ------------------------------------------------------------------------ [2013-03-12 22:39:06] me at fixxxer dot me Description: ------------ http://www.php.net/manual/en/arrayaccess.offsetget.php "While direct modification triggers a call to ArrayAccess::offsetSet(), indirect modification triggers a call to ArrayAccess::offsetGet(). In that case, the implementation of ArrayAccess::offsetGet() must be able to return by reference, otherwise an E_NOTICE message is raised.". When &offsetGet() is implemented in a trait, this got broken in 5.4.11 with this commit: https://github.com/php/php-src/commit/3f8c729e693c432b438cd33679182260d8732e30 The patch attached just comments out the check which causes the error. There should be a better way to deal with this problem. Test script: --------------- <?php // This code is mostly the same as in the // http://www.php.net/manual/en/class.arrayaccess.php example, // but changed to use traits. trait aa { private $container = array(); public function offsetSet($offset, $value) { if (is_null($offset)) { $this->container[] = $value; } else { $this->container[$offset] = $value; } } public function offsetExists($offset) { return isset($this->container[$offset]); } public function offsetUnset($offset) { unset($this->container[$offset]); } public function &offsetGet($offset) { $result = null; if (isset($this->container[$offset])) { $result = &$this->container[$offset]; } return $result; } } class obj implements ArrayAccess { use aa; } $o = new obj; $o['x'] = 1; ++$o['x']; echo $o['x'], "\n"; Expected result: ---------------- $ ./php-5.4.10/sapi/cli/php OffsetGet.php 2 Actual result: -------------- $ ./php5.4-201303122030/sapi/cli/php OffsetGet.php Fatal error: Declaration of & aa::offsetGet($offset) must be compatible with ArrayAccess::offsetGet($offset) in /home/build/tmp/OffsetGet.php on line 28 ------------------------------------------------------------------------ -- Edit this bug report at https://bugs.php.net/bug.php?id=64417&edit=1