dmitry          Tue Jan 29 09:59:42 2008 UTC

  Added files:                 (Branch: PHP_5_3)
    /ZendEngine2/tests  bug43918.phpt 

  Modified files:              
    /ZendEngine2        zend_gc.c zend_gc.h 
    /php-src/ext/simplexml      simplexml.c 
  Log:
  Fixed bug #43918 (Segmentation fault in garbage collector)
  
  
http://cvs.php.net/viewvc.cgi/ZendEngine2/zend_gc.c?r1=1.1.2.2&r2=1.1.2.3&diff_format=u
Index: ZendEngine2/zend_gc.c
diff -u ZendEngine2/zend_gc.c:1.1.2.2 ZendEngine2/zend_gc.c:1.1.2.3
--- ZendEngine2/zend_gc.c:1.1.2.2       Thu Jan 24 11:48:54 2008
+++ ZendEngine2/zend_gc.c       Tue Jan 29 09:59:42 2008
@@ -17,7 +17,7 @@
    +----------------------------------------------------------------------+
 */
 
-/* $Id: zend_gc.c,v 1.1.2.2 2008/01/24 11:48:54 dmitry Exp $ */
+/* $Id: zend_gc.c,v 1.1.2.3 2008/01/29 09:59:42 dmitry Exp $ */
 
 #include "zend.h"
 #include "zend_API.h"
@@ -47,6 +47,7 @@
 static void gc_globals_ctor_ex(zend_gc_globals *gc_globals TSRMLS_DC)
 {
        gc_globals->gc_enabled = 0;
+       gc_globals->gc_active = 0;
 
        gc_globals->buf = NULL;
 
@@ -156,8 +157,11 @@
                                zv->refcount__gc++;
                                gc_collect_cycles(TSRMLS_C);
                                zv->refcount__gc--;
-                               GC_ZVAL_SET_PURPLE(zv);
                                newRoot = GC_G(unused);
+                               if (!newRoot) {
+                                       return;
+                               }
+                               GC_ZVAL_SET_PURPLE(zv);
                        }
 
                        GC_G(unused) = newRoot->prev;
@@ -183,7 +187,8 @@
 {
        struct _store_object *obj;
 
-       if (UNEXPECTED(Z_OBJ_HT_P(zv)->get_properties == NULL)) {
+       if (UNEXPECTED(Z_OBJ_HT_P(zv)->get_properties == NULL ||
+           EG(objects_store).object_buckets == NULL)) {
                return;
        }
 
@@ -203,9 +208,12 @@
                                zv->refcount__gc++;
                                gc_collect_cycles(TSRMLS_C);
                                zv->refcount__gc--;
+                               newRoot = GC_G(unused);
+                               if (!newRoot) {
+                                       return;
+                               }
                                obj = 
&EG(objects_store).object_buckets[Z_OBJ_HANDLE_P(zv)].bucket.obj;
                                GC_SET_PURPLE(obj->buffered);
-                               newRoot = GC_G(unused);
                        }
 
                        GC_G(unused) = newRoot->prev;
@@ -240,7 +248,7 @@
 {
        GC_ZVAL_SET_BLACK(pz);
 
-       if (Z_TYPE_P(pz) == IS_OBJECT) {
+       if (Z_TYPE_P(pz) == IS_OBJECT && EG(objects_store).object_buckets) {
                struct _store_object *obj = 
&EG(objects_store).object_buckets[Z_OBJ_HANDLE_P(pz)].bucket.obj;
 
                obj->refcount++;
@@ -282,7 +290,7 @@
                GC_BENCH_INC(zval_marked_grey);
                GC_ZVAL_SET_COLOR(pz, GC_GREY);
 
-               if (Z_TYPE_P(pz) == IS_OBJECT) {
+               if (Z_TYPE_P(pz) == IS_OBJECT && 
EG(objects_store).object_buckets) {
                        struct _store_object *obj = 
&EG(objects_store).object_buckets[Z_OBJ_HANDLE_P(pz)].bucket.obj;
 
                        obj->refcount--;
@@ -309,7 +317,7 @@
        gc_root_buffer *current = GC_G(roots).next;
 
        while (current != &GC_G(roots)) {
-               if (current->handle) {
+               if (current->handle && EG(objects_store).object_buckets) {
                        struct _store_object *obj = 
&EG(objects_store).object_buckets[current->handle].bucket.obj;
 
                        if (GC_GET_COLOR(obj->buffered) == GC_PURPLE) {
@@ -337,15 +345,17 @@
 
 static void zobj_scan(zval *pz TSRMLS_DC)
 {
-       struct _store_object *obj = 
&EG(objects_store).object_buckets[Z_OBJ_HANDLE_P(pz)].bucket.obj;
+       if (EG(objects_store).object_buckets) {
+               struct _store_object *obj = 
&EG(objects_store).object_buckets[Z_OBJ_HANDLE_P(pz)].bucket.obj;
 
-       if (GC_GET_COLOR(obj->buffered) == GC_GREY) {
-               if (obj->refcount > 0) {
-                       zobj_scan_black(obj, pz TSRMLS_CC);
-               } else {
-                       GC_SET_COLOR(obj->buffered, GC_WHITE);
-                       if (EXPECTED(Z_OBJ_HANDLER_P(pz, get_properties) != 
NULL)) {
-                               zend_hash_apply(Z_OBJPROP_P(pz), (apply_func_t) 
children_scan TSRMLS_CC);
+               if (GC_GET_COLOR(obj->buffered) == GC_GREY) {
+                       if (obj->refcount > 0) {
+                               zobj_scan_black(obj, pz TSRMLS_CC);
+                       } else {
+                               GC_SET_COLOR(obj->buffered, GC_WHITE);
+                               if (EXPECTED(Z_OBJ_HANDLER_P(pz, 
get_properties) != NULL)) {
+                                       zend_hash_apply(Z_OBJPROP_P(pz), 
(apply_func_t) children_scan TSRMLS_CC);
+                               }
                        }
                }
        }
@@ -400,14 +410,16 @@
 
 static void zobj_collect_white(zval *pz TSRMLS_DC)
 {
-       zend_object_handle handle = Z_OBJ_HANDLE_P(pz);
-       struct _store_object *obj = 
&EG(objects_store).object_buckets[handle].bucket.obj;
+       if (EG(objects_store).object_buckets) {
+               zend_object_handle handle = Z_OBJ_HANDLE_P(pz);
+               struct _store_object *obj = 
&EG(objects_store).object_buckets[handle].bucket.obj;
 
-       if (obj->buffered == (gc_root_buffer*)GC_WHITE) {
-               GC_SET_BLACK(obj->buffered);
+               if (obj->buffered == (gc_root_buffer*)GC_WHITE) {
+                       GC_SET_BLACK(obj->buffered);
 
-               if (EXPECTED(Z_OBJ_HANDLER_P(pz, get_properties) != NULL)) {
-                       zend_hash_apply(Z_OBJPROP_P(pz), (apply_func_t) 
children_collect_white TSRMLS_CC);
+                       if (EXPECTED(Z_OBJ_HANDLER_P(pz, get_properties) != 
NULL)) {
+                               zend_hash_apply(Z_OBJPROP_P(pz), (apply_func_t) 
children_collect_white TSRMLS_CC);
+                       }
                }
        }
 }
@@ -446,7 +458,7 @@
        gc_root_buffer *current = GC_G(roots).next;
 
        while (current != &GC_G(roots)) {
-               if (current->handle) {
+               if (current->handle && EG(objects_store).object_buckets) {
                        struct _store_object *obj = 
&EG(objects_store).object_buckets[current->handle].bucket.obj;
                        zval z;
 
@@ -472,11 +484,16 @@
        if (GC_G(roots).next != &GC_G(roots)) {
                zval_gc_info *p, *q;
 
+               if (GC_G(gc_active)) {
+                       return 0;
+               }
                GC_G(gc_runs)++;
                GC_G(zval_to_free) = NULL;
                gc_mark_roots(TSRMLS_C);
+               GC_G(gc_active) = 1;
                gc_scan_roots(TSRMLS_C);
                gc_collect_roots(TSRMLS_C);
+               GC_G(gc_active) = 0;
 
                p = GC_G(zval_to_free);
                GC_G(zval_to_free) = NULL;
http://cvs.php.net/viewvc.cgi/ZendEngine2/zend_gc.h?r1=1.1.2.2&r2=1.1.2.3&diff_format=u
Index: ZendEngine2/zend_gc.h
diff -u ZendEngine2/zend_gc.h:1.1.2.2 ZendEngine2/zend_gc.h:1.1.2.3
--- ZendEngine2/zend_gc.h:1.1.2.2       Thu Jan 24 10:49:26 2008
+++ ZendEngine2/zend_gc.h       Tue Jan 29 09:59:42 2008
@@ -17,7 +17,7 @@
    +----------------------------------------------------------------------+
 */
 
-/* $Id: zend_gc.h,v 1.1.2.2 2008/01/24 10:49:26 dmitry Exp $ */
+/* $Id: zend_gc.h,v 1.1.2.3 2008/01/29 09:59:42 dmitry Exp $ */
 
 #ifndef ZEND_GC_H
 #define ZEND_GC_H
@@ -98,6 +98,7 @@
 
 typedef struct _zend_gc_globals {
        zend_bool         gc_enabled;
+       zend_bool         gc_active;
 
        gc_root_buffer   *buf;                          /* preallocated arrays 
of buffers   */
        gc_root_buffer    roots;                        /* list of possible 
roots of cycles */
http://cvs.php.net/viewvc.cgi/php-src/ext/simplexml/simplexml.c?r1=1.151.2.22.2.35.2.8&r2=1.151.2.22.2.35.2.9&diff_format=u
Index: php-src/ext/simplexml/simplexml.c
diff -u php-src/ext/simplexml/simplexml.c:1.151.2.22.2.35.2.8 
php-src/ext/simplexml/simplexml.c:1.151.2.22.2.35.2.9
--- php-src/ext/simplexml/simplexml.c:1.151.2.22.2.35.2.8       Wed Jan 23 
09:52:57 2008
+++ php-src/ext/simplexml/simplexml.c   Tue Jan 29 09:59:42 2008
@@ -18,7 +18,7 @@
   +----------------------------------------------------------------------+
 */
 
-/* $Id: simplexml.c,v 1.151.2.22.2.35.2.8 2008/01/23 09:52:57 tony2001 Exp $ */
+/* $Id: simplexml.c,v 1.151.2.22.2.35.2.9 2008/01/29 09:59:42 dmitry Exp $ */
 
 #ifdef HAVE_CONFIG_H
 #include "config.h"
@@ -1081,6 +1081,9 @@
                zend_hash_init(rv, 0, NULL, ZVAL_PTR_DTOR, 0);
        }
        else if (sxe->properties) {
+               if (GC_G(gc_active)) {
+                       return sxe->properties;
+               }
                zend_hash_clean(sxe->properties);
                rv = sxe->properties;
        } else {
@@ -2504,7 +2507,7 @@
 {
        php_info_print_table_start();
        php_info_print_table_header(2, "Simplexml support", "enabled");
-       php_info_print_table_row(2, "Revision", "$Revision: 1.151.2.22.2.35.2.8 
$");
+       php_info_print_table_row(2, "Revision", "$Revision: 1.151.2.22.2.35.2.9 
$");
        php_info_print_table_row(2, "Schema support",
 #ifdef LIBXML_SCHEMAS_ENABLED
                "enabled");

http://cvs.php.net/viewvc.cgi/ZendEngine2/tests/bug43918.phpt?view=markup&rev=1.1
Index: ZendEngine2/tests/bug43918.phpt
+++ ZendEngine2/tests/bug43918.phpt

-- 
PHP CVS Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php

Reply via email to