]> granicus.if.org Git - php/commitdiff
Change GC_COLLECTABLE flag into GC_NOT_COLLECTABLE to simplify GC_MAY_LEAK() check
authorDmitry Stogov <dmitry@zend.com>
Mon, 15 Jun 2020 11:26:22 +0000 (14:26 +0300)
committerDmitry Stogov <dmitry@zend.com>
Mon, 15 Jun 2020 11:26:22 +0000 (14:26 +0300)
14 files changed:
Zend/zend_ast.c
Zend/zend_gc.c
Zend/zend_gc.h
Zend/zend_hash.c
Zend/zend_objects.c
Zend/zend_string.h
Zend/zend_types.h
Zend/zend_vm_def.h
Zend/zend_vm_execute.h
ext/ffi/ffi.c
ext/opcache/ZendAccelerator.c
ext/opcache/jit/zend_jit_x86.dasc
ext/opcache/zend_file_cache.c
ext/opcache/zend_persist.c

index b55f06604e723497f7851fb0f60fe7cb8158d768..6a1c2d692ff9ced4827a0b263e6818745e67a9de 100644 (file)
@@ -846,7 +846,7 @@ ZEND_API zend_ast_ref * ZEND_FASTCALL zend_ast_copy(zend_ast *ast)
        ref = emalloc(tree_size);
        zend_ast_tree_copy(ast, GC_AST(ref));
        GC_SET_REFCOUNT(ref, 1);
-       GC_TYPE_INFO(ref) = IS_CONSTANT_AST;
+       GC_TYPE_INFO(ref) = GC_CONSTANT_AST;
        return ref;
 }
 
index 5dd11f1597b4b52a9651771d81518a06a7aacbb9..aa9602ff044719623ec788d25ce0e95dc666e6e1 100644 (file)
@@ -1574,7 +1574,7 @@ ZEND_API int zend_gc_collect_cycles(void)
                                        zend_object *obj = (zend_object*)p;
 
                                        EG(objects_store).object_buckets[obj->handle] = SET_OBJ_INVALID(obj);
-                                       GC_TYPE_INFO(obj) = IS_NULL |
+                                       GC_TYPE_INFO(obj) = GC_NULL |
                                                (GC_TYPE_INFO(obj) & ~GC_TYPE_MASK);
                                        /* Modify current before calling free_obj (bug #78811: free_obj() can cause the root buffer (with current) to be reallocated.) */
                                        current->ref = GC_MAKE_GARBAGE(((char*)obj) - obj->handlers->offset);
@@ -1589,7 +1589,7 @@ ZEND_API int zend_gc_collect_cycles(void)
                                } else if (GC_TYPE(p) == IS_ARRAY) {
                                        zend_array *arr = (zend_array*)p;
 
-                                       GC_TYPE_INFO(arr) = IS_NULL |
+                                       GC_TYPE_INFO(arr) = GC_NULL |
                                                (GC_TYPE_INFO(arr) & ~GC_TYPE_MASK);
 
                                        /* GC may destroy arrays with rc>1. This is valid and safe. */
index 8fc0073181a9d6a4a8b97c3cce72dbb8432dab69..b334173763f76a4d70edf0f97c8f28c6c8cf71c5 100644 (file)
@@ -66,12 +66,11 @@ END_EXTERN_C()
 
 #define GC_MAY_LEAK(ref) \
        ((GC_TYPE_INFO(ref) & \
-               (GC_INFO_MASK | (GC_COLLECTABLE << GC_FLAGS_SHIFT))) == \
-       (GC_COLLECTABLE << GC_FLAGS_SHIFT))
+               (GC_INFO_MASK | (GC_NOT_COLLECTABLE << GC_FLAGS_SHIFT))) == 0)
 
 static zend_always_inline void gc_check_possible_root(zend_refcounted *ref)
 {
-       if (EXPECTED(GC_TYPE_INFO(ref) == IS_REFERENCE)) {
+       if (EXPECTED(GC_TYPE_INFO(ref) == GC_REFERENCE)) {
                zval *zv = &((zend_reference*)ref)->val;
 
                if (!Z_COLLECTABLE_P(zv)) {
index ae67adcf0a900044995f0681a7e2c374f87d252e..37e46cd8bc2969066d6f496eb19a6445157c8c0a 100644 (file)
@@ -249,7 +249,7 @@ ZEND_API const HashTable zend_empty_array = {
 static zend_always_inline void _zend_hash_init_int(HashTable *ht, uint32_t nSize, dtor_func_t pDestructor, zend_bool persistent)
 {
        GC_SET_REFCOUNT(ht, 1);
-       GC_TYPE_INFO(ht) = IS_ARRAY | (persistent ? (GC_PERSISTENT << GC_FLAGS_SHIFT) : (GC_COLLECTABLE << GC_FLAGS_SHIFT));
+       GC_TYPE_INFO(ht) = GC_ARRAY | (persistent ? ((GC_PERSISTENT|GC_NOT_COLLECTABLE) << GC_FLAGS_SHIFT) : 0);
        HT_FLAGS(ht) = HASH_FLAG_UNINITIALIZED;
        ht->nTableMask = HT_MIN_MASK;
        HT_SET_DATA_ADDR(ht, &uninitialized_bucket);
@@ -1618,7 +1618,7 @@ ZEND_API void ZEND_FASTCALL zend_array_destroy(HashTable *ht)
 
        /* break possible cycles */
        GC_REMOVE_FROM_BUFFER(ht);
-       GC_TYPE_INFO(ht) = IS_NULL /*???| (GC_WHITE << 16)*/;
+       GC_TYPE_INFO(ht) = GC_NULL /*???| (GC_WHITE << 16)*/;
 
        if (ht->nNumUsed) {
                /* In some rare cases destructors of regular arrays may be changed */
@@ -2071,7 +2071,7 @@ ZEND_API HashTable* ZEND_FASTCALL zend_array_dup(HashTable *source)
 
        ALLOC_HASHTABLE(target);
        GC_SET_REFCOUNT(target, 1);
-       GC_TYPE_INFO(target) = IS_ARRAY | (GC_COLLECTABLE << GC_FLAGS_SHIFT);
+       GC_TYPE_INFO(target) = GC_ARRAY;
 
        target->pDestructor = ZVAL_PTR_DTOR;
 
index 0e873f06812933de86921050446278f47bf4e707..14ca14a4b1764e5ed75bbb4f86d78d94e3251f4c 100644 (file)
@@ -29,7 +29,7 @@
 static zend_always_inline void _zend_object_std_init(zend_object *object, zend_class_entry *ce)
 {
        GC_SET_REFCOUNT(object, 1);
-       GC_TYPE_INFO(object) = IS_OBJECT | (GC_COLLECTABLE << GC_FLAGS_SHIFT);
+       GC_TYPE_INFO(object) = GC_OBJECT;
        object->ce = ce;
        object->properties = NULL;
        zend_objects_store_put(object);
index eb5ab09a6ea1d1693f7a20cd6a6c8c418cc27983..98bd735976487f114336b2b2b8c6bd8a243781a0 100644 (file)
@@ -86,7 +86,7 @@ END_EXTERN_C()
 #define ZSTR_ALLOCA_ALLOC(str, _len, use_heap) do { \
        (str) = (zend_string *)do_alloca(ZEND_MM_ALIGNED_SIZE_EX(_ZSTR_STRUCT_SIZE(_len), 8), (use_heap)); \
        GC_SET_REFCOUNT(str, 1); \
-       GC_TYPE_INFO(str) = IS_STRING; \
+       GC_TYPE_INFO(str) = GC_STRING; \
        ZSTR_H(str) = 0; \
        ZSTR_LEN(str) = _len; \
 } while (0)
@@ -141,7 +141,7 @@ static zend_always_inline zend_string *zend_string_alloc(size_t len, int persist
        zend_string *ret = (zend_string *)pemalloc(ZEND_MM_ALIGNED_SIZE(_ZSTR_STRUCT_SIZE(len)), persistent);
 
        GC_SET_REFCOUNT(ret, 1);
-       GC_TYPE_INFO(ret) = IS_STRING | ((persistent ? IS_STR_PERSISTENT : 0) << GC_FLAGS_SHIFT);
+       GC_TYPE_INFO(ret) = GC_STRING | ((persistent ? IS_STR_PERSISTENT : 0) << GC_FLAGS_SHIFT);
        ZSTR_H(ret) = 0;
        ZSTR_LEN(ret) = len;
        return ret;
@@ -152,7 +152,7 @@ static zend_always_inline zend_string *zend_string_safe_alloc(size_t n, size_t m
        zend_string *ret = (zend_string *)safe_pemalloc(n, m, ZEND_MM_ALIGNED_SIZE(_ZSTR_STRUCT_SIZE(l)), persistent);
 
        GC_SET_REFCOUNT(ret, 1);
-       GC_TYPE_INFO(ret) = IS_STRING | ((persistent ? IS_STR_PERSISTENT : 0) << GC_FLAGS_SHIFT);
+       GC_TYPE_INFO(ret) = GC_STRING | ((persistent ? IS_STR_PERSISTENT : 0) << GC_FLAGS_SHIFT);
        ZSTR_H(ret) = 0;
        ZSTR_LEN(ret) = (n * m) + l;
        return ret;
index 52997488736f834618ba2a3262e2a419298e8b41..10a751d1b4f2cfe8c9db21c5869ee24d8ac2146c 100644 (file)
@@ -653,14 +653,19 @@ static zend_always_inline uint32_t zval_gc_info(uint32_t gc_type_info) {
 #define Z_GC_TYPE_INFO_P(zval_p)       Z_GC_TYPE_INFO(*(zval_p))
 
 /* zval_gc_flags(zval.value->gc.u.type_info) (common flags) */
-#define GC_COLLECTABLE                         (1<<4)
+#define GC_NOT_COLLECTABLE                     (1<<4)
 #define GC_PROTECTED                (1<<5) /* used for recursion detection */
 #define GC_IMMUTABLE                (1<<6) /* can't be changed in place */
 #define GC_PERSISTENT               (1<<7) /* allocated using malloc */
 #define GC_PERSISTENT_LOCAL         (1<<8) /* persistent, but thread-local */
 
-#define GC_ARRAY                                       (IS_ARRAY          | (GC_COLLECTABLE << GC_FLAGS_SHIFT))
-#define GC_OBJECT                                      (IS_OBJECT         | (GC_COLLECTABLE << GC_FLAGS_SHIFT))
+#define GC_NULL                                                (IS_NULL         | (GC_NOT_COLLECTABLE << GC_FLAGS_SHIFT))
+#define GC_STRING                                      (IS_STRING       | (GC_NOT_COLLECTABLE << GC_FLAGS_SHIFT))
+#define GC_ARRAY                                       IS_ARRAY
+#define GC_OBJECT                                      IS_OBJECT
+#define GC_RESOURCE                                    (IS_RESOURCE     | (GC_NOT_COLLECTABLE << GC_FLAGS_SHIFT))
+#define GC_REFERENCE                           (IS_REFERENCE    | (GC_NOT_COLLECTABLE << GC_FLAGS_SHIFT))
+#define GC_CONSTANT_AST                                (IS_CONSTANT_AST | (GC_NOT_COLLECTABLE << GC_FLAGS_SHIFT))
 
 /* zval.u1.v.type_flags */
 #define IS_TYPE_REFCOUNTED                     (1<<0)
@@ -974,7 +979,7 @@ static zend_always_inline uint32_t zval_gc_info(uint32_t gc_type_info) {
                (zend_resource *) emalloc(sizeof(zend_resource));               \
                zval *__z;                                                                                              \
                GC_SET_REFCOUNT(_res, 1);                                                               \
-               GC_TYPE_INFO(_res) = IS_RESOURCE;                                               \
+               GC_TYPE_INFO(_res) = GC_RESOURCE;                                               \
                _res->handle = (h);                                                                             \
                _res->type = (t);                                                                               \
                _res->ptr = (p);                                                                                \
@@ -988,7 +993,7 @@ static zend_always_inline uint32_t zval_gc_info(uint32_t gc_type_info) {
                (zend_resource *) malloc(sizeof(zend_resource));                \
                zval *__z;                                                                                              \
                GC_SET_REFCOUNT(_res, 1);                                                               \
-               GC_TYPE_INFO(_res) = IS_RESOURCE |                                              \
+               GC_TYPE_INFO(_res) = GC_RESOURCE |                                              \
                        (GC_PERSISTENT << GC_FLAGS_SHIFT);                                      \
                _res->handle = (h);                                                                             \
                _res->type = (t);                                                                               \
@@ -1008,7 +1013,7 @@ static zend_always_inline uint32_t zval_gc_info(uint32_t gc_type_info) {
                zend_reference *_ref =                                                                  \
                (zend_reference *) emalloc(sizeof(zend_reference));             \
                GC_SET_REFCOUNT(_ref, 1);                                                               \
-               GC_TYPE_INFO(_ref) = IS_REFERENCE;                                              \
+               GC_TYPE_INFO(_ref) = GC_REFERENCE;                                              \
                _ref->sources.ptr = NULL;                                                                       \
                Z_REF_P(z) = _ref;                                                                              \
                Z_TYPE_INFO_P(z) = IS_REFERENCE_EX;                                             \
@@ -1018,7 +1023,7 @@ static zend_always_inline uint32_t zval_gc_info(uint32_t gc_type_info) {
                zend_reference *_ref =                                                                  \
                (zend_reference *) emalloc(sizeof(zend_reference));             \
                GC_SET_REFCOUNT(_ref, 1);                                                               \
-               GC_TYPE_INFO(_ref) = IS_REFERENCE;                                              \
+               GC_TYPE_INFO(_ref) = GC_REFERENCE;                                              \
                ZVAL_COPY_VALUE(&_ref->val, r);                                                 \
                _ref->sources.ptr = NULL;                                                                       \
                Z_REF_P(z) = _ref;                                                                              \
@@ -1030,7 +1035,7 @@ static zend_always_inline uint32_t zval_gc_info(uint32_t gc_type_info) {
                zend_reference *_ref =                                                                  \
                        (zend_reference *) emalloc(sizeof(zend_reference));     \
                GC_SET_REFCOUNT(_ref, (refcount));                                              \
-               GC_TYPE_INFO(_ref) = IS_REFERENCE;                                              \
+               GC_TYPE_INFO(_ref) = GC_REFERENCE;                                              \
                ZVAL_COPY_VALUE(&_ref->val, _z);                                                \
                _ref->sources.ptr = NULL;                                                                       \
                Z_REF_P(_z) = _ref;                                                                             \
@@ -1041,7 +1046,7 @@ static zend_always_inline uint32_t zval_gc_info(uint32_t gc_type_info) {
                zend_reference *_ref =                                                                  \
                (zend_reference *) malloc(sizeof(zend_reference));              \
                GC_SET_REFCOUNT(_ref, 1);                                                               \
-               GC_TYPE_INFO(_ref) = IS_REFERENCE |                                             \
+               GC_TYPE_INFO(_ref) = GC_REFERENCE |                                             \
                        (GC_PERSISTENT << GC_FLAGS_SHIFT);                                      \
                ZVAL_COPY_VALUE(&_ref->val, r);                                                 \
                _ref->sources.ptr = NULL;                                                                       \
index b8b0dc5e3a804f92ddca7e300f23b5785f6ee2ed..768101f9b3a75209d80af860095910805e351433 100644 (file)
@@ -8250,7 +8250,7 @@ ZEND_VM_HANDLER(183, ZEND_BIND_STATIC, CV, UNUSED, REF)
                if (UNEXPECTED(!Z_ISREF_P(value))) {
                        zend_reference *ref = (zend_reference*)emalloc(sizeof(zend_reference));
                        GC_SET_REFCOUNT(ref, 2);
-                       GC_TYPE_INFO(ref) = IS_REFERENCE;
+                       GC_TYPE_INFO(ref) = GC_REFERENCE;
                        ZVAL_COPY_VALUE(&ref->val, value);
                        ref->sources.ptr = NULL;
                        Z_REF_P(value) = ref;
index 16779b66167d6af59c67963f6d05c2cd7618a5c9..a6f2ed827e4047b7830344cf1b49f5efd04d3a38 100644 (file)
@@ -45113,7 +45113,7 @@ static ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL ZEND_BIND_STATIC_SPEC_CV_UNUSED_HAN
                if (UNEXPECTED(!Z_ISREF_P(value))) {
                        zend_reference *ref = (zend_reference*)emalloc(sizeof(zend_reference));
                        GC_SET_REFCOUNT(ref, 2);
-                       GC_TYPE_INFO(ref) = IS_REFERENCE;
+                       GC_TYPE_INFO(ref) = GC_REFERENCE;
                        ZVAL_COPY_VALUE(&ref->val, value);
                        ref->sources.ptr = NULL;
                        Z_REF_P(value) = ref;
index 59d4738d38e1fd14023b2183334f942775bc86a5..4de14fe738a9cd60f2a39da7cac47fce50ee765f 100644 (file)
@@ -231,7 +231,7 @@ static zend_always_inline void zend_ffi_type_dtor(zend_ffi_type *type) /* {{{ */
 static zend_always_inline void zend_ffi_object_init(zend_object *object, zend_class_entry *ce) /* {{{ */
 {
        GC_SET_REFCOUNT(object, 1);
-       GC_TYPE_INFO(object) = IS_OBJECT | ((GC_COLLECTABLE | IS_OBJ_DESTRUCTOR_CALLED) << GC_FLAGS_SHIFT);
+       GC_TYPE_INFO(object) = GC_OBJECT | (IS_OBJ_DESTRUCTOR_CALLED << GC_FLAGS_SHIFT);
        object->ce = ce;
        object->properties = NULL;
        zend_objects_store_put(object);
index aa81410c82f1e15ab1e7ff746fed5140ab24acbb..ae4d31518809fd563523da177b378c8c2336d72a 100644 (file)
@@ -507,7 +507,7 @@ zend_string* ZEND_FASTCALL accel_new_interned_string(zend_string *str)
        STRTAB_COLLISION(s) = *hash_slot;
        *hash_slot = STRTAB_STR_TO_POS(&ZCSG(interned_strings), s);
        GC_SET_REFCOUNT(s, 1);
-       GC_TYPE_INFO(s) = IS_STRING | ((IS_STR_INTERNED | IS_STR_PERMANENT) << GC_FLAGS_SHIFT);
+       GC_TYPE_INFO(s) = GC_STRING | ((IS_STR_INTERNED | IS_STR_PERMANENT) << GC_FLAGS_SHIFT);
        ZSTR_H(s) = h;
        ZSTR_LEN(s) = ZSTR_LEN(str);
        memcpy(ZSTR_VAL(s), ZSTR_VAL(str), ZSTR_LEN(s) + 1);
index 475265bf7d42cb995d4f0bc419bfb29b6b1646d5..97d4fbe77ae31603ed1ba94d19312f10cc49f867 100644 (file)
@@ -1253,9 +1253,7 @@ static void* dasm_labels[zend_lb_MAX];
 |.endmacro
 
 |.macro IF_GC_MAY_NOT_LEAK, ptr, tmp_reg, label
-|      mov tmp_reg, dword [ptr + 4]
-|      and tmp_reg, (GC_INFO_MASK | (GC_COLLECTABLE << GC_FLAGS_SHIFT))
-|      cmp tmp_reg, (GC_COLLECTABLE << GC_FLAGS_SHIFT)
+|      test dword [ptr + 4],(GC_INFO_MASK | (GC_NOT_COLLECTABLE << GC_FLAGS_SHIFT))
 |      jne label
 |.endmacro
 
index 03271678c568aae2f89631a535beb71bf0fb10b6..7bf36b7931e5a33b7576a12f95b7ecfbb7fb21bf 100644 (file)
@@ -280,7 +280,7 @@ static void *zend_file_cache_unserialize_interned(zend_string *str, int in_shm)
                        memcpy(ret, str, size);
                        /* String wasn't interned but we will use it as interned anyway */
                        GC_SET_REFCOUNT(ret, 1);
-                       GC_TYPE_INFO(ret) = IS_STRING | ((IS_STR_INTERNED | IS_STR_PERSISTENT | IS_STR_PERMANENT) << GC_FLAGS_SHIFT);
+                       GC_TYPE_INFO(ret) = GC_STRING | ((IS_STR_INTERNED | IS_STR_PERSISTENT | IS_STR_PERMANENT) << GC_FLAGS_SHIFT);
                }
        } else {
                ret = str;
index 11f26cc123240a891993613d91772c3cc1284b19..1ad195c6899fe1ce284b1d164ee33e0984cd0632 100644 (file)
@@ -37,9 +37,9 @@
 
 #define zend_set_str_gc_flags(str) do { \
        if (file_cache_only) { \
-               GC_TYPE_INFO(str) = IS_STRING | (IS_STR_INTERNED << GC_FLAGS_SHIFT); \
+               GC_TYPE_INFO(str) = GC_STRING | (IS_STR_INTERNED << GC_FLAGS_SHIFT); \
        } else { \
-               GC_TYPE_INFO(str) = IS_STRING | ((IS_STR_INTERNED | IS_STR_PERMANENT) << GC_FLAGS_SHIFT); \
+               GC_TYPE_INFO(str) = GC_STRING | ((IS_STR_INTERNED | IS_STR_PERMANENT) << GC_FLAGS_SHIFT); \
        } \
 } while (0)
 
@@ -286,7 +286,7 @@ static HashTable *zend_persist_attributes(HashTable *attributes)
 
                ptr = zend_shared_memdup_put_free(attributes, sizeof(HashTable));
                GC_SET_REFCOUNT(ptr, 2);
-               GC_TYPE_INFO(ptr) = IS_ARRAY | (IS_ARRAY_IMMUTABLE << GC_FLAGS_SHIFT);
+               GC_TYPE_INFO(ptr) = GC_ARRAY | ((IS_ARRAY_IMMUTABLE|GC_NOT_COLLECTABLE) << GC_FLAGS_SHIFT);
        }
 
        return ptr;
@@ -456,7 +456,7 @@ static void zend_persist_op_array_ex(zend_op_array *op_array, zend_persistent_sc
                op_array->static_variables = zend_shared_memdup_put_free(op_array->static_variables, sizeof(HashTable));
                /* make immutable array */
                GC_SET_REFCOUNT(op_array->static_variables, 2);
-               GC_TYPE_INFO(op_array->static_variables) = IS_ARRAY | (IS_ARRAY_IMMUTABLE << GC_FLAGS_SHIFT);
+               GC_TYPE_INFO(op_array->static_variables) = GC_ARRAY | ((IS_ARRAY_IMMUTABLE|GC_NOT_COLLECTABLE) << GC_FLAGS_SHIFT);
        }
        ZEND_MAP_PTR_INIT(op_array->static_variables_ptr, &op_array->static_variables);