diff options
Diffstat (limited to 'ext/spl')
| -rwxr-xr-x | ext/spl/spl_array.c | 31 | ||||
| -rwxr-xr-x | ext/spl/spl_directory.c | 12 | ||||
| -rwxr-xr-x | ext/spl/spl_sxe.c | 5 | ||||
| -rw-r--r-- | ext/spl/tests/bug41691.phpt | 31 | ||||
| -rw-r--r-- | ext/spl/tests/bug41692.phpt | 40 | ||||
| -rw-r--r-- | ext/spl/tests/bug42259.phpt | 49 | ||||
| -rw-r--r-- | ext/spl/tests/bug42364.phpt | 18 |
7 files changed, 168 insertions, 18 deletions
diff --git a/ext/spl/spl_array.c b/ext/spl/spl_array.c index 8079088d8..0ba3ff10a 100755 --- a/ext/spl/spl_array.c +++ b/ext/spl/spl_array.c @@ -16,7 +16,7 @@ +----------------------------------------------------------------------+ */ -/* $Id: spl_array.c,v 1.71.2.17.2.11 2007/04/06 17:57:10 helly Exp $ */ +/* $Id: spl_array.c,v 1.71.2.17.2.13 2007/07/20 10:53:56 tony2001 Exp $ */ #ifdef HAVE_CONFIG_H # include "config.h" @@ -72,7 +72,7 @@ typedef struct _spl_array_object { static inline HashTable *spl_array_get_hash_table(spl_array_object* intern, int check_std_props TSRMLS_DC) { if ((intern->ar_flags & SPL_ARRAY_IS_SELF) != 0) { return intern->std.properties; - } else if ((intern->ar_flags & SPL_ARRAY_USE_OTHER) && (check_std_props == 0 || (intern->ar_flags & SPL_ARRAY_STD_PROP_LIST) == 0)) { + } else if ((intern->ar_flags & SPL_ARRAY_USE_OTHER) && (check_std_props == 0 || (intern->ar_flags & SPL_ARRAY_STD_PROP_LIST) == 0) && Z_TYPE_P(intern->array) == IS_OBJECT) { spl_array_object *other = (spl_array_object*)zend_object_store_get_object(intern->array TSRMLS_CC); return spl_array_get_hash_table(other, check_std_props TSRMLS_CC); } else if ((intern->ar_flags & ((check_std_props ? SPL_ARRAY_STD_PROP_LIST : 0) | SPL_ARRAY_IS_SELF)) != 0) { @@ -891,7 +891,7 @@ SPL_METHOD(Array, __construct) { zval *object = getThis(); spl_array_object *intern; - zval *array; + zval **array; long ar_flags = 0; char *class_name; int class_name_len; @@ -904,11 +904,15 @@ SPL_METHOD(Array, __construct) intern = (spl_array_object*)zend_object_store_get_object(object TSRMLS_CC); - if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "z|ls", &array, &ar_flags, &class_name, &class_name_len) == FAILURE) { + if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "Z|ls", &array, &ar_flags, &class_name, &class_name_len) == FAILURE) { php_set_error_handling(EH_NORMAL, NULL TSRMLS_CC); return; } + if (Z_TYPE_PP(array) == IS_ARRAY) { + SEPARATE_ZVAL_IF_NOT_REF(array); + } + if (ZEND_NUM_ARGS() > 2) { if (zend_lookup_class(class_name, class_name_len, &pce_get_iterator TSRMLS_CC) == FAILURE) { zend_throw_exception(spl_ce_InvalidArgumentException, "A class that implements Iterator must be specified", 0 TSRMLS_CC); @@ -920,25 +924,25 @@ SPL_METHOD(Array, __construct) ar_flags &= ~SPL_ARRAY_INT_MASK; - if (Z_TYPE_P(array) == IS_OBJECT && (Z_OBJ_HT_P(array) == &spl_handler_ArrayObject || Z_OBJ_HT_P(array) == &spl_handler_ArrayIterator)) { + if (Z_TYPE_PP(array) == IS_OBJECT && (Z_OBJ_HT_PP(array) == &spl_handler_ArrayObject || Z_OBJ_HT_PP(array) == &spl_handler_ArrayIterator)) { zval_ptr_dtor(&intern->array); if (ZEND_NUM_ARGS() == 1) { - spl_array_object *other = (spl_array_object*)zend_object_store_get_object(array TSRMLS_CC); + spl_array_object *other = (spl_array_object*)zend_object_store_get_object(*array TSRMLS_CC); ar_flags = other->ar_flags & ~SPL_ARRAY_INT_MASK; } ar_flags |= SPL_ARRAY_USE_OTHER; - intern->array = array; + intern->array = *array; } else { - if (Z_TYPE_P(array) != IS_OBJECT && Z_TYPE_P(array) != IS_ARRAY) { + if (Z_TYPE_PP(array) != IS_OBJECT && Z_TYPE_PP(array) != IS_ARRAY) { php_set_error_handling(EH_NORMAL, NULL TSRMLS_CC); zend_throw_exception(spl_ce_InvalidArgumentException, "Passed variable is not an array or object, using empty array instead", 0 TSRMLS_CC); return; } zval_ptr_dtor(&intern->array); - intern->array = array; + intern->array = *array; } - if (object == array) { + if (object == *array) { intern->ar_flags |= SPL_ARRAY_IS_SELF; intern->ar_flags &= ~SPL_ARRAY_USE_OTHER; } else { @@ -946,12 +950,12 @@ SPL_METHOD(Array, __construct) } intern->ar_flags |= ar_flags; ZVAL_ADDREF(intern->array); - if (Z_TYPE_P(array) == IS_OBJECT) { - zend_object_get_properties_t handler = Z_OBJ_HANDLER_P(array, get_properties); + if (Z_TYPE_PP(array) == IS_OBJECT) { + zend_object_get_properties_t handler = Z_OBJ_HANDLER_PP(array, get_properties); if ((handler != std_object_handlers.get_properties && handler != spl_array_get_properties) || !spl_array_get_hash_table(intern, 0 TSRMLS_CC)) { php_set_error_handling(EH_NORMAL, NULL TSRMLS_CC); - zend_throw_exception_ex(spl_ce_InvalidArgumentException, 0 TSRMLS_CC, "Overloaded object of type %s is not compatible with %s", Z_OBJCE_P(array)->name, intern->std.ce->name); + zend_throw_exception_ex(spl_ce_InvalidArgumentException, 0 TSRMLS_CC, "Overloaded object of type %s is not compatible with %s", Z_OBJCE_PP(array)->name, intern->std.ce->name); return; } } @@ -1052,6 +1056,7 @@ SPL_METHOD(Array, exchangeArray) } zval_ptr_dtor(&intern->array); intern->array = *array; + intern->ar_flags &= ~SPL_ARRAY_USE_OTHER; } if (object == *array) { intern->ar_flags |= SPL_ARRAY_IS_SELF; diff --git a/ext/spl/spl_directory.c b/ext/spl/spl_directory.c index 3d8fe6dc2..43f13a534 100755 --- a/ext/spl/spl_directory.c +++ b/ext/spl/spl_directory.c @@ -16,7 +16,7 @@ +----------------------------------------------------------------------+ */ -/* $Id: spl_directory.c,v 1.45.2.27.2.20 2007/04/09 15:34:55 dmitry Exp $ */ +/* $Id: spl_directory.c,v 1.45.2.27.2.22 2007/08/21 22:45:53 johannes Exp $ */ #ifdef HAVE_CONFIG_H # include "config.h" @@ -829,7 +829,11 @@ SPL_METHOD(SplFileInfo, getLinkTarget) php_set_error_handling(EH_THROW, spl_ce_RuntimeException TSRMLS_CC); +#ifdef HAVE_SYMLINK ret = readlink(intern->file_name, buff, MAXPATHLEN-1); +#else + ret = -1; /* always fail if not implemented */ +#endif if (ret == -1) { zend_throw_exception_ex(spl_ce_RuntimeException, 0 TSRMLS_CC, "Unable to read link %s, error: %s", intern->file_name, strerror(errno)); @@ -854,7 +858,11 @@ SPL_METHOD(SplFileInfo, getRealPath) php_set_error_handling(EH_THROW, spl_ce_RuntimeException TSRMLS_CC); - if (VCWD_REALPATH(intern->file_name, buff)) { + if (intern->type == SPL_FS_DIR && !intern->file_name && intern->u.dir.entry.d_name[0]) { + spl_filesystem_object_get_file_name(intern TSRMLS_CC); + } + + if (intern->file_name_len && VCWD_REALPATH(intern->file_name, buff)) { #ifdef ZTS if (VCWD_ACCESS(buff, F_OK)) { RETVAL_FALSE; diff --git a/ext/spl/spl_sxe.c b/ext/spl/spl_sxe.c index 419ca5b46..b7a5eac99 100755 --- a/ext/spl/spl_sxe.c +++ b/ext/spl/spl_sxe.c @@ -16,7 +16,7 @@ +----------------------------------------------------------------------+ */ -/* $Id: spl_sxe.c,v 1.8.2.5.2.1 2007/01/01 09:36:07 sebastian Exp $ */ +/* $Id: spl_sxe.c,v 1.8.2.5.2.2 2007/08/14 12:10:46 rrichards Exp $ */ #ifdef HAVE_CONFIG_H # include "config.h" @@ -142,8 +142,7 @@ SPL_METHOD(SimpleXMLIterator, getChildren) if (!sxe->iter.data || sxe->iter.type == SXE_ITER_ATTRLIST) { return; /* return NULL */ } - return_value->type = IS_OBJECT; - return_value->value.obj = zend_objects_store_clone_obj(sxe->iter.data TSRMLS_CC); + RETURN_ZVAL(sxe->iter.data, 1, 0); } /* {{{ proto int SimpleXMLIterator::count() diff --git a/ext/spl/tests/bug41691.phpt b/ext/spl/tests/bug41691.phpt new file mode 100644 index 000000000..1527ca3bd --- /dev/null +++ b/ext/spl/tests/bug41691.phpt @@ -0,0 +1,31 @@ +--TEST-- +Bug #41691 (ArrayObject::exchangeArray hangs Apache) +--SKIPIF-- +<?php if (!extension_loaded("spl")) print "skip"; ?> +--FILE-- +<?php + +class A extends ArrayObject { + public function __construct($dummy, $flags) { + parent::__construct($this, $flags); + } + public $a; + public $b; + public $c; +} + +$a = new A(null, ArrayObject::ARRAY_AS_PROPS ); +var_dump($a->exchangeArray(array('a'=>1,'b'=>1,'c'=>1))); + +echo "Done\n"; +?> +--EXPECTF-- +array(3) { + ["a"]=> + NULL + ["b"]=> + NULL + ["c"]=> + NULL +} +Done diff --git a/ext/spl/tests/bug41692.phpt b/ext/spl/tests/bug41692.phpt new file mode 100644 index 000000000..8a2b958fc --- /dev/null +++ b/ext/spl/tests/bug41692.phpt @@ -0,0 +1,40 @@ +--TEST-- +Bug #41692 (ArrayObject shows weird behaviour in respect to inheritance) +--FILE-- +<?php + +class Bar extends ArrayObject { + private $foo = array( 1, 2, 3 ); + function __construct() + { + parent::__construct($this->foo); + } +} + +$foo = new Bar(); +var_dump($foo); +$foo['foo'] = 23; + +$bar = new Bar(); +var_dump($bar); + +echo "Done\n"; +?> +--EXPECTF-- +object(Bar)#%d (3) { + [0]=> + int(1) + [1]=> + int(2) + [2]=> + int(3) +} +object(Bar)#%d (3) { + [0]=> + int(1) + [1]=> + int(2) + [2]=> + int(3) +} +Done diff --git a/ext/spl/tests/bug42259.phpt b/ext/spl/tests/bug42259.phpt new file mode 100644 index 000000000..22c8bc5d6 --- /dev/null +++ b/ext/spl/tests/bug42259.phpt @@ -0,0 +1,49 @@ +--TEST-- +Bug #42259 (SimpleXMLIterator loses ancestry) +--SKIPIF-- +if (!extension_loaded("spl")) print "skip"; +if (!extension_loaded('simplexml')) print 'skip'; +if (!extension_loaded("libxml")) print "skip LibXML not present"; +if (!class_exists('RecursiveIteratorIterator')) print 'skip RecursiveIteratorIterator not available'; +--FILE-- +<?php +$xml =<<<EOF +<xml> + <fieldset1> + <field1/> + <field2/> + </fieldset1> + <fieldset2> + <options> + <option1/> + <option2/> + <option3/> + </options> + <field1/> + <field2/> + </fieldset2> +</xml> +EOF; + +$sxe = new SimpleXMLIterator($xml); +$rit = new RecursiveIteratorIterator($sxe, RecursiveIteratorIterator::LEAVES_ONLY); +foreach ($rit as $child) { + $path = ''; + $ancestry = $child->xpath('ancestor-or-self::*'); + foreach ($ancestry as $ancestor) { + $path .= $ancestor->getName() . '/'; + } + $path = substr($path, 0, strlen($path) - 1); + echo count($ancestry) . ' steps: ' . $path . PHP_EOL; +} +?> +===DONE=== +--EXPECT-- +3 steps: xml/fieldset1/field1 +3 steps: xml/fieldset1/field2 +4 steps: xml/fieldset2/options/option1 +4 steps: xml/fieldset2/options/option2 +4 steps: xml/fieldset2/options/option3 +3 steps: xml/fieldset2/field1 +3 steps: xml/fieldset2/field2 +===DONE=== diff --git a/ext/spl/tests/bug42364.phpt b/ext/spl/tests/bug42364.phpt new file mode 100644 index 000000000..b218be36a --- /dev/null +++ b/ext/spl/tests/bug42364.phpt @@ -0,0 +1,18 @@ +--TEST-- +Bug #42364 (Crash when using getRealPath with DirectoryIterator) +--SKIPIF-- +<?php if (!extension_loaded("spl")) print "skip"; ?> +--FILE-- +<?php +$it = new DirectoryIterator(dirname(__FILE__)); + +foreach ($it as $e) { + if (gettype($e->getRealPath()) != "string") { + echo $e->getFilename(), " is a ", gettype($e->getRealPath()), "\n"; + } +} + +echo "===DONE===" +?> +--EXPECT-- +===DONE=== |
