]> granicus.if.org Git - php/commitdiff
Respect property visibility in array_column
authorNikita Popov <nikic@php.net>
Sat, 16 Apr 2016 07:52:22 +0000 (09:52 +0200)
committerNikita Popov <nikic@php.net>
Sat, 16 Apr 2016 07:59:01 +0000 (09:59 +0200)
ext/standard/array.c
ext/standard/tests/array/array_column_property_visibility.phpt [new file with mode: 0644]

index 6f01198aef63b84d223b3dae7a181ce66abc4a7a..61723e584f6f5210aadf9bf8f241d89c42f871b2 100644 (file)
@@ -3521,18 +3521,17 @@ static inline zval *array_column_fetch_prop(zval *data, zval *name, zval *rv)
        zval *prop = NULL;
 
        if (Z_TYPE_P(data) == IS_OBJECT) {
-               zend_string *key = zval_get_string(name);
+               if (!Z_OBJ_HANDLER_P(data, has_property) || !Z_OBJ_HANDLER_P(data, read_property)) {
+                       return NULL;
+               }
 
                /* The has_property check is first performed in "exists" mode (which returns true for
                 * properties that are null but exist) and then in "has" mode to handle objects that
                 * implement __isset (which is not called in "exists" mode). */
-               if (!Z_OBJ_HANDLER_P(data, has_property)
-                               || Z_OBJ_HANDLER_P(data, has_property)(data, name, 2, NULL)
+               if (Z_OBJ_HANDLER_P(data, has_property)(data, name, 2, NULL)
                                || Z_OBJ_HANDLER_P(data, has_property)(data, name, 0, NULL)) {
-                       prop = zend_read_property(Z_OBJCE_P(data), data, ZSTR_VAL(key), ZSTR_LEN(key), 1, rv);
+                       prop = Z_OBJ_HANDLER_P(data, read_property)(data, name, BP_VAR_R, NULL, rv);
                }
-
-               zend_string_release(key);
        } else if (Z_TYPE_P(data) == IS_ARRAY) {
                if (Z_TYPE_P(name) == IS_STRING) {
                        prop = zend_hash_find(Z_ARRVAL_P(data), Z_STR_P(name));
diff --git a/ext/standard/tests/array/array_column_property_visibility.phpt b/ext/standard/tests/array/array_column_property_visibility.phpt
new file mode 100644 (file)
index 0000000..4639a3c
--- /dev/null
@@ -0,0 +1,27 @@
+--TEST--
+array_column() respects property visibility
+--FILE--
+<?php
+
+class Test {
+    private $prop;
+    public function __construct($value) {
+        $this->prop = $value;
+    }
+    public function __isset($name) {
+        return true;
+    }
+    public function __get($name) {
+        return "__get($this->prop)";
+    }
+}
+
+$arr = [new Test("foobar")];
+var_dump(array_column($arr, "prop"));
+
+?>
+--EXPECT--
+array(1) {
+  [0]=>
+  string(13) "__get(foobar)"
+}