1. Zend引擎主要包含两个核心部分:编译、执行:

执行阶段主要用到的数据结构:

opcode: php代码编译产生的zend虚拟机可识别的指令,php7有173个opcode,定义在 zend_vm_opcodes.hPHP中的所有语法实现都是由这些opcode组成的。

struct _zend_op {
const void *handler; //对应执行的C语言function,即每条opcode都有一个C function处理
znode_op op1; //操作数1
znode_op op2; //操作数2
znode_op result; //返回值
uint32_t extended_value;
uint32_t lineno;
zend_uchar opcode; //opcode指令
zend_uchar op1_type; //操作数1类型
zend_uchar op2_type; //操作数2类型
zend_uchar result_type; //返回值类型
};

zend_op_array : zend引擎执行阶段的输入数据结构,整个执行阶段都是操作这个数据结构。

       zend_op_array有三个核心部分:opcode指令(对应c的指令)

字面量存储(变量初始值、调用的函数名称、类名称、常量名称等等称之为字面量)

变量分配的情况 (当前array定义的变量 临时变量的数量 编号,执行初始化一次性分配zval,使用时完全按照标号索引不是根据变量名)

zend_executor_globals     PHP整个生命周期中最主要的一个结构,是一个全局变量,在main执行前分配(非ZTS下),直到PHP退出,它记录着当前请求全部的信息,经常见到的一个宏EG操作的就是这个结构。

定义在zend_globals.h中:

zend_execute_data  是执行过程中最核心的一个结构,每次函数的调用、include/require、eval等都会生成一个新的结构,它表示当前的作用域、代码的执行位置以及局部变量的分配等等,等同于机器码执行过程中stack的角色,后面分析具体执行流程的时候会详细分析其作用。

zend_execute_data与zend_op_array的关联关系:

2.执行过程

Zend的executor与linux二进制程序执行的过程是非常类似的。

在C程序执行时有两个寄存器ebp、esp分别指向当前作用栈的栈顶、栈底,局部变量全部分配在当前栈,函数调用、返回通过callret指令完成,调用时call将当前执行位置压入栈中,返回时ret将之前执行位置出栈,跳回旧的位置继续执行。

Zend VM中zend_execute_data就扮演了这两个角色,zend_execute_data.prev_execute_data保存的是调用方的信息,实现了call/retzend_execute_data后面会分配额外的内存空间用于局部变量的存储,实现了ebp/esp的作用。

a. 为当前作用域分配一块内存,充当运行栈,zend_execute_data结构、所有局部变量、中间变量等等都在此内存上分配

b.初始化全局变量符号表,然后将全局执行位置指针EG(current_execute_data)指向步骤a新分配的zend_execute_data,然后将zend_execute_data.opline指向op_array的起始位置

c.从EX(opline)开始调用各opcode的C处理handler(即_zend_op.handler),每执行完一条opcode将EX(opline)++继续执行下一条,直到执行完全部opcode

if语句将根据条件的成立与否决定EX(opline) + offset所加的偏移量,实现跳转

如果是函数调用,则首先从EG(function_table)中根据function_name取出此function对应的编译完成的zend_op_array,然后像步骤a一样新分配一个zend_execute_data结构,将EG(current_execute_data)赋值给新结构的prev_execute_data,再将EG(current_execute_data)指向新的zend_execute_data,最后从新的zend_execute_data.opline开始执行,切换到函数内部,函数执行完以后将EG(current_execute_data)重新指向EX(prev_execute_data),释放分配的运行栈,销毁局部变量,继续从原来函数调用的位置执行

类方法的调用与函数基本相同

d.全部opcode执行完成后将步骤a分配的内存释放,这个过程会将所有的局部变量"销毁",执行阶段结束

首先根据zend_execute_data、当前zend_op_array中局部/临时变量数计算需要的内存空间,编译阶段zend_op_array的结果,在编译过程中已经确定当前作用域下有多少个局部变量(func->op_array.last_var)、临时/中间/无用变量(func->op_array.T),从而在执行之初就将他们全部分配完成。

php的zend引擎执行过程 一的更多相关文章

  1. 【JS】js引擎执行过程

    概述 js引擎执行过程主要分为三个阶段,分别是语法分析,预编译和执行阶段,上篇文章我们介绍了语法分析和预编译阶段,那么我们先做个简单概括,如下: 语法分析: 分别对加载完成的代码块进行语法检验,语法正 ...

  2. JVM-绘图展现字节码执行引擎执行过程

    在我的上一篇博客JVM-String比较-字节码分析中介绍了String字符串比较的原因,借着分析字节码的机会,我这篇博客将会绘图展现方法内部字节码执行过程. 话不多说,贴上我们将要分析的Java方法 ...

  3. javascript引擎执行的过程的理解--执行阶段

    一.概述 同步更新sau交流学习社区(nodeJSBlog):javascript引擎执行的过程的理解--执行阶段 js引擎执行过程主要分为三个阶段,分别是语法分析,预编译和执行阶段,上篇文章我们介绍 ...

  4. (转载)js引擎的执行过程(二)

    概述 js引擎执行过程主要分为三个阶段,分别是语法分析,预编译和执行阶段,上篇文章我们介绍了语法分析和预编译阶段,那么我们先做个简单概括,如下: 语法分析: 分别对加载完成的代码块进行语法检验,语法正 ...

  5. (转载)js引擎的执行过程(一)

    概述 js是一种非常灵活的语言,理解js引擎的执行过程对我们学习javascript非常重要,但是网上讲解js引擎的文章也大多是浅尝辄止或者只局部分析,例如只分析事件循环(Event Loop)或者变 ...

  6. 【java虚拟机系列】从java虚拟机字节码执行引擎的执行过程来彻底理解java的多态性

    我们知道面向对象语言的三大特点之一就是多态性,而java作为一种面向对象的语言,自然也满足多态性,我们也知道java中的多态包括重载与重写,我们也知道在C++中动态多态是通过虚函数来实现的,而虚函数是 ...

  7. javascript引擎执行的过程的理解--语法分析和预编译阶段

    一.概述 js是一种非常灵活的语言,理解js引擎的执行过程对于我们学习js是非常有必要的.看了很多这方便文章,大多数是讲的是事件循环(event loop)或者变量提升的等,并没有全面分析其中的过程. ...

  8. JS引擎线程的执行过程的三个阶段(二)

    继续JS引擎线程的执行过程的三个阶段(一) 内容, 如下: 三. 执行阶段 1. 网页的线程 永远只有JS引擎线程在执行JS脚本程序,其他三个线程只负责将满足触发条件的处理函数推进事件队列,等待JS引 ...

  9. JS引擎线程的执行过程的三个阶段(一)

    浏览器首先按顺序加载由<script>标签分割的js代码块,加载js代码块完毕后,立刻进入以下三个阶段,然后再按顺序查找下一个代码块,再继续执行以下三个阶段,无论是外部脚本文件(不异步加载 ...

随机推荐

  1. Laravel中不可逆的加密方法

    1 //对 A 密码使用Bcrypt 加密 2 $password = Hash::make('secret'); 3 4 //你也可直接使用 bcrypt 的 function 5 $passwor ...

  2. jsp jstl标签库核心标签

    JSTL标签库介绍 JSTL标签库的使用时为了弥补html标签的不足,规范自定义标签的使用而诞生的.使用标签的目的就是不希望在jsp页面中出现java逻辑代码 全称:JSTL标签库分类 核心标签库使用 ...

  3. Arrow function restore

    Arrow function restore 为什么叫Arrow Function?因为它的定义用的就是一个箭头: x => x * x 上面的箭头函数相当于: function (x) { r ...

  4. SQL Server 调优系列基础篇 - 常用运算符总结

    前言 上一篇我们介绍了如何查看查询计划,本篇将介绍在我们查看的查询计划时的分析技巧,以及几种我们常用的运算符优化技巧,同样侧重基础知识的掌握. 通过本篇可以了解我们平常所写的T-SQL语句,在SQL ...

  5. 玩转X-CTR100 l STM32F4 l DS18B20单总线温度传感器

    我造轮子,你造车,创客一起造起来!塔克创新资讯[塔克社区 www.xtark.cn ][塔克博客 www.cnblogs.com/xtark/ ]      本文介绍X-CTR100控制器 扩展DS1 ...

  6. SharePoint Visio Graphics Service-PowerShell

    1. 配置托管服务账户 Set-SPVisioExternalData -VisioServiceApplication "Visio Graphics Service" –Una ...

  7. SWIFT中切換UIContainerView內的Controller

    如下,一个UIContainerView内切换两个Controller,当点击登录的时候UIContainerView的视图为LoginController,当点击登记的时候UIContainerVi ...

  8. UI基础:target...action设计模式,手势识别器.UIimageview

    使用target..action和delegate设计模式可以实现解耦.使代码更加优化. 手势识别器: 手势识别器:是对触摸事件做了封装,无需自己去判断某个手势是否触发,手势识别器本身起到了识别作用, ...

  9. 怎么在windows7下搭建服务器

    怎么在windows7系统安装IIS 图文教程 http://jingyan.baidu.com/article/1e5468f92f6e05484961b703.html 以下本人为列:第一步:先按 ...

  10. 原生JS 的cookie和jq的cookie,

    COOKIE基础及应用:1.什么是COOKIE==>页面用来保存信息,比如:自动登录,记住用户名2.COOKIE的特性:  --同一个网站中,所有的页面共享同一套cookie  --数量,大小有 ...