php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #55406 get_object_vars and array casting when extending ArrayObject
Submitted: 2011-08-11 19:59 UTC Modified: 2012-11-16 18:37 UTC
From: chrisstocktonaz at gmail dot com Assigned:
Status: Not a bug Package: SPL related
PHP Version: 5.4.0alpha3 OS: Linux
Private report: No CVE-ID: None
Welcome back! If you're the original bug submitter, here's where you can edit the bug or add additional notes.
If this is not your bug, you can add a comment by following this link.
If this is your bug, but you forgot your password, you can retrieve your password here.
Password:
Status:
Package:
Bug Type:
Summary:
From: chrisstocktonaz at gmail dot com
New email:
PHP Version: OS:

 

 [2011-08-11 19:59 UTC] chrisstocktonaz at gmail dot com
Description:
------------
As discussed on internals mailing list here [1], ArrayObject I think is overriding 
the get_properties handler in a bit to simple of a way. I think the ArrayObject 
should merge the spl hash with the default handler.

[1] http://news.php.net/php.internals/54508 

Test script:
---------------
--Code
class TestOne {
  public $TestOne_1 = 1;
}

class TestTwo extends ArrayObject {
  public $TestTwo_1 = 1;
}

class TestThree extends TestTwo {
  public $TestThree_1 = 1;
}

$t1 = new TestOne;
var_dump((array) $t1, get_object_vars($t1));

$t2 = new TestTwo;
var_dump((array) $t2, get_object_vars($t2));

$t3 = new TestThree;
var_dump((array) $t3, get_object_vars($t3));

Expected result:
----------------
array(1) {
  ["TestOne_1"]=>
  int(1)
}
array(1) {
  ["TestOne_1"]=>
  int(1)
}

array(0) {
//  TestOne_1
//  TestTwo_1
}
array(0) {
//  TestOne_1
//  TestTwo_1
}

array(0) {
//  TestOne_1
//  TestTwo_1
//  TestThree_1
}
array(0) {
//  TestOne_1
//  TestTwo_1
//  TestThree_1
}

Actual result:
--------------
array(1) {
  ["TestOne_1"]=>
  int(1)
}
array(1) {
  ["TestOne_1"]=>
  int(1)
}

array(0) {
}
array(0) {
}

array(0) {
}
array(0) {
}

Patches

Add a Patch

Pull Requests

Add a Pull Request

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2011-08-11 20:41 UTC] chrisstocktonaz at gmail dot com
My expected result had a typo, "TestOne_1" would not exist in testtwo or 
testthree classes. Here is a patch for this:


--- ext/spl/spl_array.c 2011-07-25 04:35:02.000000000 -0700
+++ ext/spl/spl_array.c   2011-08-11 13:38:52.000000000 -0700
@@ -746,7 +746,12 @@
 {
        spl_array_object *intern = 
(spl_array_object*)zend_object_store_get_object(object TSRMLS_CC);

-       return spl_array_get_hash_table(intern, 1 TSRMLS_CC);
+        HashTable *hh = zend_std_get_properties(object TSRMLS_CC);
+        HashTable *ht = spl_array_get_hash_table(intern, 1 TSRMLS_CC);
+
+        zend_hash_merge(hh, ht, NULL, NULL, sizeof(zend_class_entry *), 0);
+
+       return hh;
 } /* }}} */

 static HashTable* spl_array_get_debug_info(zval *obj, int *is_temp TSRMLS_DC) 
/* {{{ */
 [2011-08-12 11:09 UTC] RQuadling at GMail dot com
Adding ...

 public function __construct (array $input = array(), $flags = 
ArrayObject::STD_PROP_LIST, $iterator_class = 'ArrayIterator') {
  parent::__construct($input, $flags, $iterator_class); 
 }

as the constructor for TestTwo will output ...

array(1) {
  ["TestOne_1"]=>
  int(1)
}
array(1) {
  ["TestOne_1"]=>
  int(1)
}
array(1) {
  ["TestTwo_1"]=>
  int(1)
}
array(1) {
  ["TestTwo_1"]=>
  int(1)
}
array(2) {
  ["TestThree_1"]=>
  int(1)
  ["TestTwo_1"]=>
  int(1)
}
array(2) {
  ["TestThree_1"]=>
  int(1)
  ["TestTwo_1"]=>
  int(1)
}

So, is this a bug?

Dox says ...
"ArrayObject::STD_PROP_LIST 
Properties of the object have their normal functionality when accessed as list 
(var_dump, foreach, etc.)."

So, without this flag (a bitmask) being set, the "properties" aren't accessible 
in the way you think they should be.
 [2012-11-16 18:37 UTC] levim@php.net
-Status: Open +Status: Not a bug
 [2012-11-16 18:37 UTC] levim@php.net
This is the expected behavior (I think). ArrayObject is complex and doesn't work 
as most people would expect. It's hard for me to keep straight sometimes.  You 
need to set the STD_PROP_LIST bit for this to behave the way you are expecting.
 
PHP Copyright © 2001-2024 The PHP Group
All rights reserved.
Last updated: Tue Apr 30 12:01:30 2024 UTC