PHP  
 PHP: Test and Code Coverage Analysis
downloads | QA | documentation | faq | getting help | mailing lists | reporting bugs | php.net sites | links | my php.net 
 

LCOV - code coverage report
Current view: top level - ext/opcache - zend_persist_calc.c (source / functions) Hit Total Coverage
Test: PHP Code Coverage Lines: 120 187 64.2 %
Date: 2015-04-14 Functions: 8 9 88.9 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /*
       2             :    +----------------------------------------------------------------------+
       3             :    | Zend OPcache                                                         |
       4             :    +----------------------------------------------------------------------+
       5             :    | Copyright (c) 1998-2015 The PHP Group                                |
       6             :    +----------------------------------------------------------------------+
       7             :    | This source file is subject to version 3.01 of the PHP license,      |
       8             :    | that is bundled with this package in the file LICENSE, and is        |
       9             :    | available through the world-wide-web at the following url:           |
      10             :    | http://www.php.net/license/3_01.txt                                  |
      11             :    | If you did not receive a copy of the PHP license and are unable to   |
      12             :    | obtain it through the world-wide-web, please send a note to          |
      13             :    | license@php.net so we can mail you a copy immediately.               |
      14             :    +----------------------------------------------------------------------+
      15             :    | Authors: Andi Gutmans <andi@zend.com>                                |
      16             :    |          Zeev Suraski <zeev@zend.com>                                |
      17             :    |          Stanislav Malyshev <stas@zend.com>                          |
      18             :    |          Dmitry Stogov <dmitry@zend.com>                             |
      19             :    +----------------------------------------------------------------------+
      20             : */
      21             : 
      22             : #include "zend.h"
      23             : #include "ZendAccelerator.h"
      24             : #include "zend_persist.h"
      25             : #include "zend_extensions.h"
      26             : #include "zend_shared_alloc.h"
      27             : #include "zend_operators.h"
      28             : 
      29             : #define ADD_DUP_SIZE(m,s)  ZCG(current_persistent_script)->size += zend_shared_memdup_size((void*)m, s)
      30             : #define ADD_SIZE(m)        ZCG(current_persistent_script)->size += ZEND_ALIGNED_SIZE(m)
      31             : 
      32             : #define ADD_ARENA_SIZE(m)        ZCG(current_persistent_script)->arena_size += ZEND_ALIGNED_SIZE(m)
      33             : 
      34             : # define ADD_STRING(str) \
      35             :                 ADD_DUP_SIZE((str), _STR_HEADER_SIZE + (str)->len + 1)
      36             : # define ADD_INTERNED_STRING(str, do_free) do { \
      37             :                 if (!IS_ACCEL_INTERNED(str)) { \
      38             :                         zend_string *tmp = accel_new_interned_string(str); \
      39             :                         if (tmp != (str)) { \
      40             :                                 if (do_free) { \
      41             :                                         /*zend_string_release(str);*/ \
      42             :                                 } \
      43             :                                 (str) = tmp; \
      44             :                         } else { \
      45             :                                 ADD_STRING(str); \
      46             :                         } \
      47             :                 } \
      48             :         } while (0)
      49             : 
      50             : static void zend_persist_zval_calc(zval *z);
      51             : 
      52         958 : static void zend_hash_persist_calc(HashTable *ht, void (*pPersistElement)(zval *pElement))
      53             : {
      54             :         uint idx;
      55             :         Bucket *p;
      56             : 
      57         958 :         if (!(ht->u.flags & HASH_FLAG_INITIALIZED)) {
      58         865 :                 return;
      59             :         }
      60          93 :         if (ht->u.flags & HASH_FLAG_PACKED) {
      61          12 :                 ADD_SIZE(sizeof(Bucket) * ht->nNumUsed);
      62             :         } else {
      63          81 :                 ADD_SIZE(sizeof(Bucket) * ht->nNumUsed + sizeof(uint32_t) * ht->nTableSize);
      64             :         }
      65             : 
      66         278 :         for (idx = 0; idx < ht->nNumUsed; idx++) {
      67         185 :                 p = ht->arData + idx;
      68         370 :                 if (Z_TYPE(p->val) == IS_UNDEF) continue;
      69             : 
      70             :                 /* persist bucket and key */
      71         178 :                 if (p->key) {
      72         141 :                         zend_uchar flags = GC_FLAGS(p->key) & ~ (IS_STR_PERSISTENT | IS_STR_INTERNED | IS_STR_PERMANENT);
      73         141 :                         ADD_INTERNED_STRING(p->key, 1);
      74         141 :                         GC_FLAGS(p->key) |= flags;
      75             :                 }
      76             : 
      77         178 :                 pPersistElement(&p->val);
      78             :         }
      79             : }
      80             : 
      81           0 : static void zend_persist_ast_calc(zend_ast *ast)
      82             : {
      83             :         uint32_t i;
      84             : 
      85           0 :         if (ast->kind == ZEND_AST_ZVAL) {
      86           0 :                 ADD_SIZE(sizeof(zend_ast_zval));
      87           0 :                 zend_persist_zval_calc(zend_ast_get_zval(ast));
      88           0 :         } else if (zend_ast_is_list(ast)) {
      89           0 :                 zend_ast_list *list = zend_ast_get_list(ast);
      90           0 :                 ADD_SIZE(sizeof(zend_ast_list) - sizeof(zend_ast *) + sizeof(zend_ast *) * list->children);
      91           0 :                 for (i = 0; i < list->children; i++) {
      92           0 :                         if (list->child[i]) {
      93           0 :                                 zend_persist_ast_calc(list->child[i]);
      94             :                         }
      95             :                 }
      96             :         } else {
      97           0 :                 uint32_t children = zend_ast_get_num_children(ast);
      98           0 :                 ADD_SIZE(sizeof(zend_ast) - sizeof(zend_ast *) + sizeof(zend_ast *) * children);
      99           0 :                 for (i = 0; i < children; i++) {
     100           0 :                         if (ast->child[i]) {
     101           0 :                                 zend_persist_ast_calc(ast->child[i]);
     102             :                         }
     103             :                 }
     104             :         }
     105           0 : }
     106             : 
     107        3143 : static void zend_persist_zval_calc(zval *z)
     108             : {
     109             :         zend_uchar flags;
     110             :         uint size;
     111             : 
     112        3143 :         switch (Z_TYPE_P(z)) {
     113             :                 case IS_STRING:
     114             :                 case IS_CONSTANT:
     115        2427 :                         flags = Z_GC_FLAGS_P(z) & ~ (IS_STR_PERSISTENT | IS_STR_INTERNED | IS_STR_PERMANENT);
     116        2427 :                         ADD_INTERNED_STRING(Z_STR_P(z), 0);
     117        2427 :                         if (!Z_REFCOUNTED_P(z)) {
     118           0 :                                 Z_TYPE_FLAGS_P(z) &= ~ (IS_TYPE_REFCOUNTED | IS_TYPE_COPYABLE);
     119             :                         }
     120        2427 :                         Z_GC_FLAGS_P(z) |= flags;
     121        2427 :                         break;
     122             :                 case IS_ARRAY:
     123          74 :                         size = zend_shared_memdup_size(Z_ARR_P(z), sizeof(zend_array));
     124          74 :                         if (size) {
     125          74 :                                 ADD_SIZE(size);
     126          74 :                                 zend_hash_persist_calc(Z_ARRVAL_P(z), zend_persist_zval_calc);
     127             :                         }
     128          74 :                         break;
     129             :                 case IS_REFERENCE:
     130           0 :                         size = zend_shared_memdup_size(Z_REF_P(z), sizeof(zend_reference));
     131           0 :                         if (size) {
     132           0 :                                 ADD_SIZE(size);
     133           0 :                                 zend_persist_zval_calc(Z_REFVAL_P(z));
     134             :                         }
     135           0 :                         break;
     136             :                 case IS_CONSTANT_AST:
     137           0 :                         size = zend_shared_memdup_size(Z_AST_P(z), sizeof(zend_ast_ref));
     138           0 :                         if (size) {
     139           0 :                                 ADD_SIZE(size);
     140           0 :                                 zend_persist_ast_calc(Z_ASTVAL_P(z));
     141             :                         }
     142             :                         break;
     143             :         }
     144        3143 : }
     145             : 
     146         458 : static void zend_persist_op_array_calc_ex(zend_op_array *op_array)
     147             : {
     148         458 :         if (op_array->type != ZEND_USER_FUNCTION) {
     149           0 :                 return;
     150             :         }
     151             : 
     152         458 :         if (op_array->static_variables) {
     153          13 :                 ADD_DUP_SIZE(op_array->static_variables, sizeof(HashTable));
     154          13 :                 zend_hash_persist_calc(op_array->static_variables, zend_persist_zval_calc);
     155             :         }
     156             : 
     157         458 :         if (zend_shared_alloc_get_xlat_entry(op_array->opcodes)) {
     158             :                 /* already stored */
     159           0 :                 if (op_array->function_name) {
     160           0 :                         zend_string *new_name = zend_shared_alloc_get_xlat_entry(op_array->function_name);
     161           0 :                         if (IS_ACCEL_INTERNED(new_name)) {
     162           0 :                                 op_array->function_name = new_name;
     163             :                         }
     164             :                 }
     165           0 :                 return;
     166             :         }
     167             : 
     168         458 :         if (op_array->literals) {
     169         458 :                 zval *p = op_array->literals;
     170         458 :                 zval *end = p + op_array->last_literal;
     171         458 :                 ADD_DUP_SIZE(op_array->literals, sizeof(zval) * op_array->last_literal);
     172        3921 :                 while (p < end) {
     173        3005 :                         zend_persist_zval_calc(p);
     174        3005 :                         p++;
     175             :                 }
     176             :         }
     177             : 
     178         458 :         ADD_DUP_SIZE(op_array->opcodes, sizeof(zend_op) * op_array->last);
     179             : 
     180         458 :         if (op_array->function_name) {
     181          33 :                 zend_string *old_name = op_array->function_name;
     182          33 :                 zend_string *new_name = zend_shared_alloc_get_xlat_entry(old_name);
     183             : 
     184          33 :                 if (new_name) {
     185           0 :                         op_array->function_name = new_name;
     186             :                 } else {
     187          33 :                         ADD_INTERNED_STRING(op_array->function_name, 0);
     188          33 :                         zend_shared_alloc_register_xlat_entry(old_name, op_array->function_name);
     189             :                 }
     190             :     }
     191             : 
     192         458 :         if (op_array->filename) {
     193         458 :                 ADD_STRING(op_array->filename);
     194             :         }
     195             : 
     196         458 :         if (op_array->arg_info) {
     197          29 :                 zend_arg_info *arg_info = op_array->arg_info;
     198          29 :                 uint32_t num_args = op_array->num_args;
     199             :                 uint32_t i;
     200             : 
     201          29 :                 num_args = op_array->num_args;
     202          29 :                 if (op_array->fn_flags & ZEND_ACC_VARIADIC) {
     203           0 :                         num_args++;
     204             :                 }
     205          29 :                 if (op_array->fn_flags & ZEND_ACC_HAS_RETURN_TYPE) {
     206           4 :                         arg_info--;
     207           4 :                         num_args++;
     208             :                 }
     209          29 :                 ADD_DUP_SIZE(op_array->arg_info, sizeof(zend_arg_info) * num_args);
     210          29 :                 ADD_DUP_SIZE(arg_info, sizeof(zend_arg_info) * num_args);
     211          63 :                 for (i = 0; i < num_args; i++) {
     212          34 :                         if (arg_info[i].name) {
     213          30 :                                 ADD_INTERNED_STRING(arg_info[i].name, 1);
     214             :                         }
     215          34 :                         if (arg_info[i].class_name) {
     216           4 :                                 ADD_INTERNED_STRING(arg_info[i].class_name, 1);
     217             :                         }
     218             :                 }
     219             :         }
     220             : 
     221         458 :         if (op_array->brk_cont_array) {
     222          17 :                 ADD_DUP_SIZE(op_array->brk_cont_array, sizeof(zend_brk_cont_element) * op_array->last_brk_cont);
     223             :         }
     224             : 
     225         458 :         if (ZCG(accel_directives).save_comments && op_array->doc_comment) {
     226           0 :                 ADD_STRING(op_array->doc_comment);
     227             :         }
     228             : 
     229         458 :         if (op_array->try_catch_array) {
     230           8 :                 ADD_DUP_SIZE(op_array->try_catch_array, sizeof(zend_try_catch_element) * op_array->last_try_catch);
     231             :         }
     232             : 
     233         458 :         if (op_array->vars) {
     234             :                 int i;
     235             : 
     236          71 :                 ADD_DUP_SIZE(op_array->vars, sizeof(zend_string*) * op_array->last_var);
     237         239 :                 for (i = 0; i < op_array->last_var; i++) {
     238         168 :                         ADD_INTERNED_STRING(op_array->vars[i], 0);
     239             :                 }
     240             :         }
     241             : }
     242             : 
     243          33 : static void zend_persist_op_array_calc(zval *zv)
     244             : {
     245          33 :         ADD_ARENA_SIZE(sizeof(zend_op_array));
     246          33 :         zend_persist_op_array_calc_ex(Z_PTR_P(zv));
     247          33 : }
     248             : 
     249           2 : static void zend_persist_property_info_calc(zval *zv)
     250             : {
     251           2 :         zend_property_info *prop = Z_PTR_P(zv);
     252             : 
     253           2 :         ADD_ARENA_SIZE(sizeof(zend_property_info));
     254           2 :         ADD_INTERNED_STRING(prop->name, 0);
     255           2 :         if (ZCG(accel_directives).save_comments && prop->doc_comment) {
     256           0 :                 ADD_STRING(prop->doc_comment);
     257             :         }
     258           2 : }
     259             : 
     260           7 : static void zend_persist_class_entry_calc(zval *zv)
     261             : {
     262           7 :         zend_class_entry *ce = Z_PTR_P(zv);
     263             : 
     264           7 :         if (ce->type == ZEND_USER_CLASS) {
     265           7 :                 ADD_ARENA_SIZE(sizeof(zend_class_entry));
     266           7 :                 ADD_INTERNED_STRING(ce->name, 0);
     267           7 :                 zend_hash_persist_calc(&ce->function_table, zend_persist_op_array_calc);
     268           7 :                 if (ce->default_properties_table) {
     269             :                     int i;
     270             : 
     271           0 :                         ADD_SIZE(sizeof(zval) * ce->default_properties_count);
     272           0 :                         for (i = 0; i < ce->default_properties_count; i++) {
     273           0 :                                 zend_persist_zval_calc(&ce->default_properties_table[i]);
     274             :                         }
     275             :                 }
     276           7 :                 if (ce->default_static_members_table) {
     277             :                     int i;
     278             : 
     279           1 :                         ADD_SIZE(sizeof(zval) * ce->default_static_members_count);
     280           3 :                         for (i = 0; i < ce->default_static_members_count; i++) {
     281           2 :                                 zend_persist_zval_calc(&ce->default_static_members_table[i]);
     282             :                         }
     283             :                 }
     284           7 :                 zend_hash_persist_calc(&ce->constants_table, zend_persist_zval_calc);
     285             : 
     286           7 :                 if (ZEND_CE_FILENAME(ce)) {
     287           7 :                         ADD_STRING(ZEND_CE_FILENAME(ce));
     288             :                 }
     289           7 :                 if (ZCG(accel_directives).save_comments && ZEND_CE_DOC_COMMENT(ce)) {
     290           0 :                         ADD_STRING(ZEND_CE_DOC_COMMENT(ce));
     291             :                 }
     292             : 
     293           7 :                 zend_hash_persist_calc(&ce->properties_info, zend_persist_property_info_calc);
     294             : 
     295           7 :                 if (ce->trait_aliases) {
     296           0 :                         int i = 0;
     297           0 :                         while (ce->trait_aliases[i]) {
     298           0 :                                 if (ce->trait_aliases[i]->trait_method) {
     299           0 :                                         if (ce->trait_aliases[i]->trait_method->method_name) {
     300           0 :                                                 ADD_INTERNED_STRING(ce->trait_aliases[i]->trait_method->method_name, 0);
     301             :                                         }
     302           0 :                                         if (ce->trait_aliases[i]->trait_method->class_name) {
     303           0 :                                                 ADD_INTERNED_STRING(ce->trait_aliases[i]->trait_method->class_name, 0);
     304             :                                         }
     305           0 :                                         ADD_SIZE(sizeof(zend_trait_method_reference));
     306             :                                 }
     307             : 
     308           0 :                                 if (ce->trait_aliases[i]->alias) {
     309           0 :                                         ADD_INTERNED_STRING(ce->trait_aliases[i]->alias, 0);
     310             :                                 }
     311           0 :                                 ADD_SIZE(sizeof(zend_trait_alias));
     312           0 :                                 i++;
     313             :                         }
     314           0 :                         ADD_SIZE(sizeof(zend_trait_alias*) * (i + 1));
     315             :                 }
     316             : 
     317           7 :                 if (ce->trait_precedences) {
     318           0 :                         int i = 0;
     319             : 
     320           0 :                         while (ce->trait_precedences[i]) {
     321           0 :                                 ADD_INTERNED_STRING(ce->trait_precedences[i]->trait_method->method_name, 0);
     322           0 :                                 ADD_INTERNED_STRING(ce->trait_precedences[i]->trait_method->class_name, 0);
     323           0 :                                 ADD_SIZE(sizeof(zend_trait_method_reference));
     324             : 
     325           0 :                                 if (ce->trait_precedences[i]->exclude_from_classes) {
     326           0 :                                         int j = 0;
     327             : 
     328           0 :                                         while (ce->trait_precedences[i]->exclude_from_classes[j].class_name) {
     329           0 :                                                 ADD_INTERNED_STRING(ce->trait_precedences[i]->exclude_from_classes[j].class_name, 0);
     330           0 :                                                 j++;
     331             :                                         }
     332           0 :                                         ADD_SIZE(sizeof(zend_class_entry*) * (j + 1));
     333             :                                 }
     334           0 :                                 ADD_SIZE(sizeof(zend_trait_precedence));
     335           0 :                                 i++;
     336             :                         }
     337           0 :                         ADD_SIZE(sizeof(zend_trait_precedence*) * (i + 1));
     338             :                 }
     339             :         }
     340           7 : }
     341             : 
     342         425 : static void zend_accel_persist_class_table_calc(HashTable *class_table)
     343             : {
     344         425 :         zend_hash_persist_calc(class_table, zend_persist_class_entry_calc);
     345         425 : }
     346             : 
     347         425 : uint zend_accel_script_persist_calc(zend_persistent_script *new_persistent_script, char *key, unsigned int key_length)
     348             : {
     349         425 :         new_persistent_script->mem = NULL;
     350         425 :         new_persistent_script->size = 0;
     351         425 :         new_persistent_script->arena_mem = NULL;
     352         425 :         new_persistent_script->arena_size = 0;
     353         425 :         ZCG(current_persistent_script) = new_persistent_script;
     354             : 
     355         425 :         ADD_DUP_SIZE(new_persistent_script, sizeof(zend_persistent_script));
     356         425 :         ADD_DUP_SIZE(key, key_length + 1);
     357         425 :         ADD_STRING(new_persistent_script->full_path);
     358             : 
     359         425 :         zend_accel_persist_class_table_calc(&new_persistent_script->class_table);
     360         425 :         zend_hash_persist_calc(&new_persistent_script->function_table, zend_persist_op_array_calc);
     361         425 :         zend_persist_op_array_calc_ex(&new_persistent_script->main_op_array);
     362             : 
     363         425 :         new_persistent_script->size += new_persistent_script->arena_size;
     364             : 
     365         425 :         ZCG(current_persistent_script) = NULL;
     366             : 
     367         425 :         return new_persistent_script->size;
     368             : }

Generated by: LCOV version 1.10

Generated at Tue, 14 Apr 2015 11:48:46 +0000 (11 days ago)

Copyright © 2005-2015 The PHP Group
All rights reserved.