]> granicus.if.org Git - php/commitdiff
Fixed string handling (string cached in SHM marked as permanent, strings stored in...
authorDmitry Stogov <dmitry@zend.com>
Tue, 12 May 2015 10:45:52 +0000 (13:45 +0300)
committerDmitry Stogov <dmitry@zend.com>
Tue, 12 May 2015 10:45:52 +0000 (13:45 +0300)
Fixed anonymous class support

ext/opcache/ZendAccelerator.c
ext/opcache/zend_file_cache.c
ext/opcache/zend_file_cache.h

index 847746b01f87504e69ca3a851002f9cae21870cc..c9f58963acd0005557aff09b61872f5700b5ae2f 100644 (file)
@@ -1199,7 +1199,7 @@ static zend_persistent_script *cache_script_in_file_cache(zend_persistent_script
 
        new_persistent_script->dynamic_members.checksum = zend_accel_script_checksum(new_persistent_script);
 
-       zend_file_cache_script_store(new_persistent_script);
+       zend_file_cache_script_store(new_persistent_script, 0);
 
        *from_shared_memory = 1;
        return new_persistent_script;
@@ -1320,7 +1320,7 @@ static zend_persistent_script *cache_script_in_shared_memory(zend_persistent_scr
 #ifdef HAVE_OPCACHE_FILE_CACHE
        if (ZCG(accel_directives).file_cache) {
                SHM_PROTECT();
-               zend_file_cache_script_store(new_persistent_script);
+               zend_file_cache_script_store(new_persistent_script, 1);
                SHM_UNPROTECT();
        }
 #endif
@@ -1967,26 +1967,22 @@ static void zend_reset_cache_vars(void)
        ZCSG(force_restart_time) = 0;
 }
 
-#ifndef ZTS
 static void accel_reset_pcre_cache(void)
 {
        Bucket *p;
 
        ZEND_HASH_FOREACH_BUCKET(&PCRE_G(pcre_cache), p) {
                /* Remove PCRE cache entries with inconsistent keys */
-               if (IS_ACCEL_INTERNED(p->key)) {
+               if (IS_INTERNED(p->key)) {
                        p->key = NULL;
                        zend_hash_del_bucket(&PCRE_G(pcre_cache), p);
                }
        } ZEND_HASH_FOREACH_END();
 }
-#endif
 
 static void accel_activate(void)
 {
-#ifndef ZTS
        zend_bool reset_pcre = 0;
-#endif
 
        if (!ZCG(enabled) || !accel_startup_ok) {
                return;
@@ -2069,10 +2065,8 @@ static void accel_activate(void)
                                }
                                accel_restart_leave();
                        }
-#ifndef ZTS
                } else {
                        reset_pcre = 1;
-#endif
                }
                zend_shared_alloc_unlock();
        }
@@ -2086,11 +2080,9 @@ static void accel_activate(void)
                /* Reset in-process realpath cache */
                realpath_cache_clean();
 
-#ifndef ZTS
                accel_reset_pcre_cache();
        } else if (reset_pcre) {
                accel_reset_pcre_cache();
-#endif
        }
 }
 
@@ -2673,11 +2665,11 @@ void accel_shutdown(void)
                zend_hash_clean(CG(function_table));
                zend_hash_clean(CG(class_table));
                zend_hash_clean(EG(zend_constants));
-
-               accel_reset_pcre_cache();
 #endif
        }
 
+       accel_reset_pcre_cache();
+
        zend_new_interned_string = orig_new_interned_string;
        zend_interned_strings_snapshot = orig_interned_strings_snapshot;
        zend_interned_strings_restore = orig_interned_strings_restore;
index ae0784fa18fd071e1c5c5b88623ddfa1fe0fca9b..353eecb7f25ced2eb3558609ec1ddf4262062d6c 100644 (file)
@@ -111,6 +111,13 @@ static int zend_file_cache_flock(int fd, int type)
                                (ptr) = zend_file_cache_serialize_interned((zend_string*)(ptr), info); \
                        } else { \
                                ZEND_ASSERT(IS_UNSERIALIZED(ptr)); \
+                               /* script->corrupted shows if the script in SHM or not */ \
+                               if (EXPECTED(script->corrupted)) { \
+                                       GC_FLAGS(ptr) |= IS_STR_INTERNED | IS_STR_PERMANENT; \
+                               } else { \
+                                       GC_FLAGS(ptr) |= IS_STR_INTERNED; \
+                                       GC_FLAGS(ptr) &= ~IS_STR_PERMANENT; \
+                               } \
                                (ptr) = (void*)((char*)(ptr) - (char*)script->mem); \
                        } \
                } \
@@ -122,6 +129,13 @@ static int zend_file_cache_flock(int fd, int type)
                        } else { \
                                ZEND_ASSERT(IS_SERIALIZED(ptr)); \
                                (ptr) = (void*)((char*)buf + (size_t)(ptr)); \
+                               /* script->corrupted shows if the script in SHM or not */ \
+                               if (EXPECTED(script->corrupted)) { \
+                                       GC_FLAGS(ptr) |= IS_STR_INTERNED | IS_STR_PERMANENT; \
+                               } else { \
+                                       GC_FLAGS(ptr) |= IS_STR_INTERNED; \
+                                       GC_FLAGS(ptr) &= ~IS_STR_PERMANENT; \
+                               } \
                        } \
                } \
        } while (0)
@@ -376,6 +390,8 @@ static void zend_file_cache_serialize_op_array(zend_op_array            *op_arra
                                case ZEND_JMP:
                                case ZEND_GOTO:
                                case ZEND_FAST_CALL:
+                               case ZEND_DECLARE_ANON_CLASS:
+                               case ZEND_DECLARE_ANON_INHERITED_CLASS:
                                        SERIALIZE_PTR(opline->op1.jmp_addr);
                                        break;
                                case ZEND_JMPZNZ:
@@ -649,7 +665,7 @@ static void zend_file_cache_serialize(zend_persistent_script   *script,
        new_script->mem = NULL;
 }
 
-int zend_file_cache_script_store(zend_persistent_script *script)
+int zend_file_cache_script_store(zend_persistent_script *script, int in_shm)
 {
        size_t len;
        int fd;
@@ -704,7 +720,9 @@ int zend_file_cache_script_store(zend_persistent_script *script)
        ZCG(mem) = zend_string_alloc(4096 - (_STR_HEADER_SIZE + 1), 0);
 
        zend_shared_alloc_init_xlat_table();
+       script->corrupted = in_shm; /* used to check if script restored to SHM or process memory */
        zend_file_cache_serialize(script, &info, buf);
+       script->corrupted = 0;
        zend_shared_alloc_destroy_xlat_table();
 
        info.checksum = zend_adler32(ADLER32_INIT, buf, script->size);
@@ -893,6 +911,8 @@ static void zend_file_cache_unserialize_op_array(zend_op_array           *op_arr
                                case ZEND_JMP:
                                case ZEND_GOTO:
                                case ZEND_FAST_CALL:
+                               case ZEND_DECLARE_ANON_CLASS:
+                               case ZEND_DECLARE_ANON_INHERITED_CLASS:
                                        UNSERIALIZE_PTR(opline->op1.jmp_addr);
                                        break;
                                case ZEND_JMPZNZ:
index 0660bfbc6f82f40f7abc7fa369565bb9473fa259..575a6aa72a3f3a987fdfda456717865a9a37b351 100644 (file)
@@ -19,7 +19,7 @@
 #ifndef ZEND_FILE_CACHE_H
 #define ZEND_FILE_CACHE_H
 
-int zend_file_cache_script_store(zend_persistent_script *script);
+int zend_file_cache_script_store(zend_persistent_script *script, int in_shm);
 zend_persistent_script *zend_file_cache_script_load(zend_file_handle *file_handle);
 void zend_file_cache_invalidate(zend_string *full_path);