php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #54367 Use of closure causes problem in ArrayAccess
Submitted: 2011-03-24 13:52 UTC Modified: 2011-05-11 08:58 UTC
From: jpauli@php.net Assigned: dmitry (profile)
Status: Closed Package: Scripting Engine problem
PHP Version: 5.3.6 OS: *nix
Private report: No CVE-ID: None
 [2011-03-24 13:52 UTC] jpauli@php.net
Description:
------------
Closures cant use variables from external context when the context is in ArrayAccess method

Test script:
---------------
<?php
class MyObjet implements ArrayAccess
{
    // All the stuff for ArrayAccess

    public function offsetGet ($offset)
    {
        return function ($var) use ($offset) { // here is the problem
              return sprintf('<%s>%s</%$1s>', $offset, $var);
        };
    }
}

$a = new MyObjet();

echo $a['p']('foo');

Expected result:
----------------
<p>foo</p>

Actual result:
--------------
PHP Notice:  Undefined variable: offset in {file.php} on line 11

Patches

Add a Patch

Pull Requests

Add a Pull Request

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2011-03-24 22:49 UTC] felipe@php.net
-Status: Open +Status: Assigned -Assigned To: +Assigned To: dmitry
 [2011-03-24 22:49 UTC] felipe@php.net
I can reproduce a crash with:
<?php
class MyObjet implements ArrayAccess
{
	public function __construct() {  }
    public function offsetSet($offset, $value) { }
    public function offsetExists($offset) {  }
    public function offsetUnset($offset) { }
    public function offsetGet ($offset) {
        return function ()  { };
    }
}

$a = new MyObjet();
echo $a['p']('foo');
?>

Breakpoint 1, 0x085368b3 in ZEND_SEND_VAL_SPEC_CONST_HANDLER (execute_data=0x8ade614, tsrm_ls=0x89022a0)
    at /home/felipe/dev/php5/Zend/zend_vm_execute.h:1719
1719			&& ARG_MUST_BE_SENT_BY_REF(EX(fbc), opline->op2.u.opline_num)) {
(gdb) p execute_data->fbc->common
$7 = {type = 90 'Z', function_name = 0x5a5a5a5a <Address 0x5a5a5a5a out of bounds>, scope = 0x5a5a5a5a, fn_flags = 1515870810, 
  prototype = 0x5a5a5a5a, num_args = 1515870810, required_num_args = 1515870810, arg_info = 0x5a5a5a5a, pass_rest_by_reference = 90 'Z', 
  return_reference = 90 'Z'}
 [2011-03-25 09:55 UTC] jpauli@php.net
Felipe: strange, I got no crash with your code (5.3.6,Linux, self-compiled)
 [2011-04-20 14:59 UTC] dmitry@php.net
Automatic comment from SVN on behalf of dmitry
Revision: http://svn.php.net/viewvc/?view=revision&amp;revision=310389
Log: Fixed bug #54367 (Use of closure causes problem in ArrayAccess).
 [2011-04-20 15:00 UTC] dmitry@php.net
-Status: Assigned +Status: Closed
 [2011-04-20 15:00 UTC] dmitry@php.net
This bug has been fixed in SVN.

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/.
 
Thank you for the report, and for helping us make PHP better.


 [2011-05-10 18:36 UTC] tony2001@php.net
-Status: Closed +Status: Re-Opened
 [2011-05-10 18:36 UTC] tony2001@php.net
The test for this bug causes invalid read and subsequent segfault in 5_3 (but works fine in trunk):
==17645== Invalid read of size 8
==17645==    at 0x93625F: _zval_ptr_dtor (zend_execute_API.c:446)
==17645==    by 0x97BAD6: zend_leave_helper_SPEC (zend_vm_execute.h:167)
==17645==    by 0x980ACE: ZEND_RETURN_SPEC_CONST_HANDLER (zend_vm_execute.h:1714)
==17645==    by 0x97B8E6: execute (zend_vm_execute.h:107)
==17645==    by 0x947FBE: zend_execute_scripts (zend.c:1194)
==17645==    by 0x8D2E56: php_execute_script (main.c:2275)
==17645==    by 0xA2C0A5: main (php_cli.c:1193)
==17645==  Address 0xa74fb98 is 56 bytes inside a block of size 264 free'd
==17645==    at 0x4C2599C: free (in /usr/lib64/valgrind/vgpreload_memcheck-amd64-linux.so)
==17645==    by 0x922C77: _efree (zend_alloc.c:2358)
==17645==    by 0x96F0A9: zend_closure_free_storage (zend_closures.c:190)
==17645==    by 0x975C47: zend_objects_store_del_ref_by_handle_ex (zend_objects_API.c:220)
==17645==    by 0x9759AE: zend_objects_store_del_ref (zend_objects_API.c:172)
==17645==    by 0x945591: _zval_dtor_func (zend_variables.c:52)
==17645==    by 0x93528B: _zval_dtor (zend_variables.h:35)
==17645==    by 0x93625A: _zval_ptr_dtor (zend_execute_API.c:445)
==17645==    by 0x97BAD6: zend_leave_helper_SPEC (zend_vm_execute.h:167)
==17645==    by 0x980ACE: ZEND_RETURN_SPEC_CONST_HANDLER (zend_vm_execute.h:1714)
==17645==    by 0x97B8E6: execute (zend_vm_execute.h:107)
==17645==    by 0x947FBE: zend_execute_scripts (zend.c:1194)
 [2011-05-11 08:58 UTC] dmitry@php.net
Automatic comment from SVN on behalf of dmitry
Revision: http://svn.php.net/viewvc/?view=revision&amp;revision=310938
Log: Fixed bug #54367 (Use of closure causes problem in ArrayAccess)
 [2011-05-11 08:58 UTC] dmitry@php.net
-Status: Re-Opened +Status: Closed
 [2011-05-11 08:58 UTC] dmitry@php.net
This bug has been fixed in SVN.

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/.
 
Thank you for the report, and for helping us make PHP better.


 
PHP Copyright © 2001-2024 The PHP Group
All rights reserved.
Last updated: Tue Mar 19 09:01:30 2024 UTC