PHP扩展-生命周期和内存管理

高洛峰
发布: 2016-11-17 14:06:28
原创
1252人浏览过

1. PHP源码结构

php的内核子系统有两个,ze(zend engine)和php core.
ze负责将php脚本解析成机器码(也成为token符)后,在进程空间执行这些机器码;ze还负责内存管理,变量作用域管理和对php函数的调度管理。

PHP Core负责和SAPI层的通信;PHP Core也为safe_mode, open_basedir的检查提供了统一控制层;PHP Core还提供了streams层,用于用户域的文件和网络IO操作。其中SAPI(Server Application Programming Interface)通常包含Nginx,Apache,IIS,CLI,CGI等主机环境。

PHP扩展在ZE和PHP Core的基础上提供对各种常用操作的封装,比如对mysql,redis,memcache,sqlite等的读写,对json,xml文件的解析,对soap,sokcet,curl的网络协议的封装,对加密解密压缩解压缩等的封装,对图像处理的封装等等。有些扩展是从零开始实现某个功能,比如按照redis的通信协议使用C来实现和redis的通信;有些扩展则是通过调用系统已有的库,比如图片处理的gb扩展需要系统本身要安装了相应的gd库。
在PHP源码php-5.6.24/ext中提供了78个扩展。

总之,由ZE和PHP Core提供基础的架构,由EXT(扩展)提供用户域的各种操作。
以php-5.6.24源码为例,ZE对应文件夹php-5.6.24/Zend, PHP Core对应文件夹php-5.6.24/main, 扩展对应文件夹php-5.6.24/ext。

2. PHP扩展的生命周期

PHP在接收到SAPI命令时,首先初始化并启动它的内核子系统,在内核子系统的启动快结束时,PHP开始加载它的扩展代码并对扩展初始化,此时PHP将调用每个模块的初始化例程Module Initialization routine (MINIT)。

立即学习PHP免费学习笔记(深入)”;

MINIT(Module Initialization)
PHP调用MINIT相关例程,使得每个扩展有机会初始化内部变量、分配资源、注册资源处理句柄,以及向ZE注册自己的函数,以便于脚本调用这其中的函数时候ZE知道执行哪些代码

RINIT(Request Initialization)
在模块初始化完成后,PHP等待来自SAPI的请求,当接收到SAPI请求后,由ZE为当前被请求的php脚本创建运行环境,并调用每个扩展的Request Initialization(RINIT)函数,使得每个扩展有机会设定特定的环境变量,根据请求分配资源,或者执行其他任务,如审核。

这里所说的SAPI请求分为两类,一类是Apache, IIS, 和其他成熟的web server SAPIs,他们在启动时PHP先执行了MINIT,之后等待来自用户的页面请求,当收到请求后执行RINIT;另一类SAPI请求则是CGI or CLI SAPIs,PHP在收到这类SAPI请求时,执行完MINIT马上就执行RINIT。

当RINIT请求初始化完毕后,ZE接回控制权并将当前被请求的脚本翻译成tokens, 最终构成opcodes(操作码),opcodes被执行过程中,如果某个opcode要求执行某个扩展函数,这是ZE就会将相关参数绑定到改函数,并将控制权临时交给该函数去执行,直到该函数执行完毕。

存了个图
存了个图

视频图片解析/字幕/剪辑,视频高清保存/图片源图提取

存了个图 17
查看详情 存了个图

RSHUTDOWN(Request Shutdown)
PHP脚本运行结束后,PHP调用每个扩展的请求关闭(RSHUTDOWN)函数以执行最后的清理工作(如将session变量存入磁盘)。接下来,ZE执行清理过程(垃圾收集),有效地对之前的请求期间用到的每个变量执行unset()。

MSHUTDOWN(Module Shutdown)
当RSHUTDOWN完成后,PHP继续等待SAPI的其他文档请求或者是关闭信号。对于CGI和CLI等SAPI,没有“下一个请求”,所以SAPI立刻开始关闭。关闭期间,PHP再次遍历每个扩展,调用其模块关闭(MSHUTDOWN)函数,并最终关闭自己的内核子系统。

GINIT
初始化全局变量

GSHUTDOWN
释放全局变量

MINFO
设置phpinfo模块的信息,phpinfo要等级每个扩展的配置信息

// main/php.h
 #define PHP_MINIT       ZEND_MODULE_STARTUP_N
 #define PHP_MSHUTDOWN   ZEND_MODULE_SHUTDOWN_N
 #define PHP_RINIT       ZEND_MODULE_ACTIVATE_N
 #define PHP_RSHUTDOWN   ZEND_MODULE_DEACTIVATE_N
 #define PHP_MINFO       ZEND_MODULE_INFO_N
 #define PHP_GINIT       ZEND_GINIT
 #define PHP_GSHUTDOWN   ZEND_GSHUTDOWN

 #define PHP_MINIT_FUNCTION      ZEND_MODULE_STARTUP_D
 #define PHP_MSHUTDOWN_FUNCTION  ZEND_MODULE_SHUTDOWN_D
 #define PHP_RINIT_FUNCTION      ZEND_MODULE_ACTIVATE_D
 #define PHP_RSHUTDOWN_FUNCTION  ZEND_MODULE_DEACTIVATE_D
 #define PHP_MINFO_FUNCTION      ZEND_MODULE_INFO_D
 #define PHP_GINIT_FUNCTION      ZEND_GINIT_FUNCTION
 #define PHP_GSHUTDOWN_FUNCTION  ZEND_GSHUTDOWN_FUNCTION
登录后复制

 

3. PHP扩展的内存管理

ZE在执行自己内部的内存管理时,通过附加的标志来标识某某内存变量是否是持久性的,对于非持久内存,ZE会去清理。但在扩展内部最好还是自己去清理非持久内存,因为扩展自己请求分配的非持久内存,将在长时间内保持为未回收状态,这样与之相关的资源长时间得不到释放。

相关标签:
php
PHP速学教程(入门到精通)
PHP速学教程(入门到精通)

PHP怎么学习?PHP怎么入门?PHP在哪学?PHP怎么学才快?不用担心,这里为大家提供了PHP速学教程(入门到精通),有需要的小伙伴保存下载就能学习啦!

下载
来源:php中文网
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn
最新问题
开源免费商场系统广告
热门教程
更多>
最新下载
更多>
网站特效
网站源码
网站素材
前端模板
关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新 English
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送
PHP中文网APP
随时随地碎片化学习

Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号