惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

Cloudbric
Cloudbric
E
Exploit-DB.com RSS Feed
SecWiki News
SecWiki News
Forbes - Security
Forbes - Security
N
News | PayPal Newsroom
S
Security @ Cisco Blogs
Schneier on Security
Schneier on Security
V
V2EX - 技术
S
Secure Thoughts
W
WeLiveSecurity
Google DeepMind News
Google DeepMind News
C
CERT Recently Published Vulnerability Notes
NISL@THU
NISL@THU
S
Securelist
S
Security Archives - TechRepublic
Know Your Adversary
Know Your Adversary
V
Vulnerabilities – Threatpost
Security Latest
Security Latest
Recent Commits to openclaw:main
Recent Commits to openclaw:main
G
GRAHAM CLULEY
H
Hacker News: Front Page
Microsoft Azure Blog
Microsoft Azure Blog
I
Intezer
Google Online Security Blog
Google Online Security Blog
美团技术团队
阮一峰的网络日志
阮一峰的网络日志
T
The Exploit Database - CXSecurity.com
钛媒体:引领未来商业与生活新知
钛媒体:引领未来商业与生活新知
Webroot Blog
Webroot Blog
Jina AI
Jina AI
Engineering at Meta
Engineering at Meta
P
Proofpoint News Feed
The Cloudflare Blog
I
InfoQ
L
LangChain Blog
U
Unit 42
P
Proofpoint News Feed
S
Schneier on Security
S
Security Affairs
Y
Y Combinator Blog
T
Tenable Blog
N
News and Events Feed by Topic
MyScale Blog
MyScale Blog
量子位
Google DeepMind News
Google DeepMind News
Cyberwarzone
Cyberwarzone
博客园 - 聂微东
D
Darknet – Hacking Tools, Hacker News & Cyber Security
GbyAI
GbyAI
AWS News Blog
AWS News Blog

Comments for 风雪之隅

深入理解PHP7内核之OBJECT - 风雪之隅 关于调用约定(cdecl、fastcall、stcall、thiscall) 的一点知识 - 风雪之隅 PHP 8新特性之Attributes(注解) - 风雪之隅 博客迁移到腾讯云 - 风雪之隅 提升PHP性能之改变Zend引擎分发方式 - 风雪之隅 如何调试PHP的Core之获取基本信息 - 风雪之隅 请手动释放你的资源(Please release resources manually) - 风雪之隅 在Qcon 2015 北京上的演讲PPT - PHP7 Linux上配置Nginx+PHP5(FastCGI) - 风雪之隅 在PHP Module中获取$_GET/$_POST/$_COOKIE的方法研究 - 风雪之隅 深入理解Javascript之this关键字 - 风雪之隅 Yar-2.1 新功能介绍 - 风雪之隅 Yaf and Phalcon, which is faster? PHP5.2.*防止Hash冲突拒绝服务攻击的Patch - 风雪之隅 PHP中的Hash算法 - 风雪之隅 PHP单引号和双引号的区别 - 风雪之隅 深入理解PHP之数组(遍历顺序) - 风雪之隅 深入理解PHP原理之变量分离/引用(Variables Separation) - 风雪之隅 PHP Taint - 一个用来检测XSS/SQL/Shell注入漏洞的扩展 - 风雪之隅 BTwitter(Twitter In Bash) - 风雪之隅 automake,autoconf使用详解 - 风雪之隅 HTTPOXY漏洞说明 - 风雪之隅 Nginx(PHP/fastcgi)的PATH_INFO问题 - 风雪之隅 关于PHP浮点数你应该知道的(All 'bogus' about the float in PHP) 使用PHP Embed SAPI实现Opcodes查看器 - 风雪之隅 一个关于Zend O+的小分享 - 风雪之隅 深入理解PHP原理之对象(一) - 风雪之隅 在PHP中使用协程实现多任务调度 - 风雪之隅 一些PHP Coding Tips[2011/04/02最后更新] - 风雪之隅 Curl的毫秒超时的一个"Bug" - 风雪之隅 Javascript作用域原理 - 风雪之隅 深入理解PHP原理之Opcodes - 风雪之隅 深入理解Zend SAPIs(Zend SAPI Internals) - 风雪之隅 Nginx + PHP CGI的一个可能的安全漏洞 - 风雪之隅 PHP 8新特性之JIT简介 - 风雪之隅 PHP FFI详解 - 一种全新的PHP扩展方式 - 风雪之隅 令人困惑的strtotime - 风雪之隅 PHP的性能演进(从PHP5.0到PHP7.1的性能全评测) - 风雪之隅 让PHP7达到最高性能的几个Tips - 风雪之隅
PHP CLI模式下的多进程应用 - 风雪之隅
Prestige par · 2023-07-12 · via Comments for 风雪之隅

PHP在很多时候不适合做常驻的SHELL进程, 他没有专门的gc例程, 也没有有效的内存管理途径. 所以如果用PHP做常驻SHELL, 你会经常被内存耗尽导致abort而unhappy.
而且, 如果输入数据非法, 而脚本没有检测, 导致abort, 也会让你很不开心.
那? 怎么办呢?
多进程....

为什么呢?

 优点:
    1. 使用多进程, 子进程结束以后, 内核会负责回收资源
    2. 使用多进程,子进程异常退出不会导致整个进程Thread退出. 父进程还有机会重建流程.
    3. 一个常驻主进程, 只负责任务分发, 逻辑更清楚.

Then, 怎么做呢?
接下来, 我们使用PHP提供的POSIX和Pcntl系列函数, 来实现一个PHP命令解析器, 主进程负责接受用户输入, 然后fork子进程执行, 并负责回显子进程的结束状态.
代码如下, 我加了注释, 如果有不懂的地方, 可以翻阅手册相关函数, 或者回复留言.

#!/bin/env php
<?php
/** A example denoted muti-process application in php
 * @filename fork.php
 * @touch date Wed 10 Jun 2009 10:25:51 PM CST
 * @author Laruence<laruence@baidu.com>
 * @license http://www.zend.com/license/3_0.txt   PHP License 3.0
 * @version 1.0.0
*/
/** 确保这个函数只能运行在SHELL中 */
if (substr(php_sapi_name(), 0, 3) !== 'cli') {
    die("This Programe can only be run in CLI mode");
}
/**  关闭最大执行时间限制, 在CLI模式下, 这个语句其实不必要 */
set_time_limit(0);
$pid  = posix_getpid(); //取得主进程ID
$user = posix_getlogin(); //取得用户名
echo <<<eod
USAGE: [command | expression]
input php code to execute by fork a new process
input quit to exit
        Shell Executor version 1.0.0 by laruence
EOD;
while (true) {
        $prompt = "\n{$user}$ ";
        $input  = readline($prompt);
        readline_add_history($input);
        if ($input == 'quit') {
			break;
		}
        process_execute($input . ';');
}
exit(0);
function process_execute($input) {
        $pid = pcntl_fork(); //创建子进程
        if ($pid == 0) {//子进程
                $pid = posix_getpid();
                echo "* Process {$pid} was created, and Executed:\n\n";
                eval($input); //解析命令
                exit;
        } else {//主进程
                $pid = pcntl_wait($status, WUNTRACED); //取得子进程结束状态
                if (pcntl_wifexited($status)) {
                        echo "\n\n* Sub process: {$pid} exited with {$status}";
                }
        }
}
   

但有一点, 我一定要提醒:

Process Control should not be enabled within a webserver environment and unexpected results may happen if any Process Control functions are used within a webserver environment.  --摘自PHP手册

也就是说, 打消你在PHP Web开发中使用多进程的念头吧!