• 欢迎访问搞代码网站,推荐使用最新版火狐浏览器和Chrome浏览器访问本网站!
  • 如果您觉得本站非常有看点,那么赶紧使用Ctrl+D 收藏搞代码吧

PHP内核探索:zend_execute的具体执行过程

php 搞代码 4年前 (2022-01-23) 18次浏览 已收录 0个评论

PHP内核探索:zend_execute的具体执行过程

解释器引擎最终执行op的函数是zend_execute,实际上zend_execute是一个函数指针,在引擎初始化的时候zend_execute默认指向了execute,这个execute定义在{PHPSRC}/Zend/zend_vm_execute.h:

ZEND_API void execute(zend_op_array *op_array TSRMLS_DC)  {      zend_execute_data *execute_data;      zend_bool nested = 0;      zend_bool original_in_execution = EG(in_execution);          if (EG(exception)) {          return;      }        EG(in_execution) = 1;    zend_vm_enter:      /* Initialize execute_data */      execute_data = (zend_execute_data *)zend_vm_stack_alloc(          ZEND_MM_ALIGNED_SIZE(sizeof(zend_execute_data)) +          ZEND_MM_ALIGNED_SIZE(sizeof(zval**) * op_array->last_var * (EG(active_symbol_table) ? 1 : 2)) +          ZEND_MM_ALIGNED_SIZE(sizeof(temp_variable)) * op_array->T TSRMLS_CC);        EX(CVs) = (zval***)((char*)execute_data + ZEND_MM_ALIGNED_SIZE(sizeof(zend_execute_data)));      memset(EX(CVs), 0, sizeof(zval**) * op_array->last_var);      EX(Ts) = (temp_variable *)(((char*)EX(CVs)) + ZEND_MM_ALIGNED_SIZE(sizeof(zval**) * op_array->last_var * (EG(active_symbol_table) ? 1 : 2)));      EX(fbc) = NULL;      EX(called_scope) = NULL;      EX(object) = NULL;      EX(old_error_reporting) = NULL;      EX(op_array) = op_array;      EX(symbol_table) = EG(active_symbol_table);      EX(prev_execute_data) = EG(current_execute_data);      EG(current_execute_data) = execute_data;      EX(nested) = nested;      nested = 1;        if (op_array->start_op) {          ZEND_VM_SET_OPCODE(op_array->start_op);      } else {          ZEND_VM_SET_OPCODE(op_array->opcodes);      }        if (op_array->this_var != -1 && EG(This)) {          Z_ADDREF_P(EG(This)); /* For $this pointer */          if (!EG(active_symbol_table)) {              EX(CVs)[op_array->this_var] = (zval**)EX(CVs) + (op_array->last_var + op_array->this_var);              *EX(CVs)[op_array->this_var] = EG(This);          } else {              if (zend_hash_add(EG(active_symbol_table), "this", sizeof("this"), &EG(This), sizeof(zval *), (void**)&EX(CVs)[op_array->this_var])==FAILURE) {                  Z_DELREF_P(EG(This));              }          }      }        EG(opline_ptr) = &EX(opline);        EX(function_state).function = (zend_function *) op_array;      EX(function_state).arguments = NULL;            while (1) {          int ret;  #ifdef ZEND_WIN32          if (EG(timed_out)) {              zend_timeout(0);          }  #endif            if ((ret = EX(opline)->handler(execute_data TSRMLS_CC)) > 0) {              switch (ret) {                  case 1:                      EG(in_execution) = original_in_execution;                      return;                  case 2:                      op_array = EG(active_op_array);                      goto zend_vm_enter;                  case 3:                      execute_data = EG(current_execute_data);                  default:                      break;              }          }        }      zend_error_noreturn(E_ERROR, "Arrived at end of main loop which shouldn't happen");  }

此函数的参数为op_array,这是一个指向zend_op_array的指针,op_array是在编译过程中生成,这里有必要介绍一下zend_op_array这个类型。

zend_op_array简介

此类型的定义在{PHPSRC}/Zend/zend_compile.h:

struct _zend_op_array {      /* Common elements */      zend_uchar type;      char *function_name;              zend_class_entry *scope;      zend_uint fn_flags;      union _zend_function *prototype;      zend_uint num_args;      zend_uint required_num_args;      zend_arg_info *arg_info;      zend_bool pass_rest_by_reference;      unsigned char return_reference;      /* END of common elements */        zend_bool done_pa<div style="color:transparent">本文来源gaodai.ma#com搞##代!^码@网*</div><pre>搞gaodaima代码

ss_two; zend_uint *refcount; zend_op *opcodes; zend_uint last, size; zend_compiled_variable *vars; int last_var, size_var; zend_uint T; zend_brk_cont_element *brk_cont_array; int last_brk_cont; int current_brk_cont; zend_try_catch_element *try_catch_array; int last_try_catch; /* static variables support */ HashTable *static_variables; zend_op *start_op; int backpatch_count; zend_uint this_var; char *filename; zend_uint line_start; zend_uint line_end; char *doc_comment; zend_uint doc_comment_len; zend_uint early_binding; /* the linked list of delayed declarations */ void *reserved[ZEND_MAX_RESERVED_RESOURCES]; }; typedef struct _zend_op_array zend_op_array;


搞代码网(gaodaima.com)提供的所有资源部分来自互联网,如果有侵犯您的版权或其他权益,请说明详细缘由并提供版权或权益证明然后发送到邮箱[email protected],我们会在看到邮件的第一时间内为您处理,或直接联系QQ:872152909。本网站采用BY-NC-SA协议进行授权
转载请注明原文链接:PHP内核探索:zend_execute的具体执行过程
喜欢 (0)
[搞代码]
分享 (0)
发表我的评论
取消评论

表情 贴图 加粗 删除线 居中 斜体 签到

Hi,您需要填写昵称和邮箱!

  • 昵称 (必填)
  • 邮箱 (必填)
  • 网址