이 기사의 내용은 PHP 시스템 프로그래밍에서 다중 프로세스 프로그래밍과 고아 프로세스 및 좀비 프로세스의 소개를 공유하는 것입니다. 필요한 친구가 참조할 수 있습니다.
다중 프로세스 프로그래밍은 시스템 프로그래밍의 일부이기도 하지만 PHP 프로그래머는 일반적으로 다중 프로세스 문제에 신경 쓸 필요가 없습니다. 왜냐하면 웹 서버나 PHP-FPM이 이미 프로세스 문제를 관리해 주었기 때문입니다. 하지만 PHP를 사용하여 개발하려는 경우에는 CLI 프로그램, 멀티프로세스 프로그래밍은 필수적인 기본 기술입니다.
PHP의 프로세스 제어 방법은 주로 PCNTL(Process Control) 확장을 사용합니다. 따라서 다중 프로세스 프로그래밍을 수행하기 전에 먼저 PHP에 최신 PCNTL 확장이 설치되어 있는지 확인해야 합니다. php를 입력할 수 있습니다. - 현재 설치된 확장을 보기 위한 m 명령:
이 확장은 프로세스 작업을 위한 일련의 메소드를 제공합니다:
PCNTL 函数 pcntl_alarm — 为进程设置一个alarm闹钟信号 pcntl_errno — 别名 pcntl_get_last_error pcntl_exec — 在当前进程空间执行指定程序 pcntl_fork — 在当前进程当前位置产生分支(子进程)。 pcntl_get_last_error — Retrieve the error number set by the last pcntl function which failed pcntl_getpriority — 获取任意进程的优先级 pcntl_setpriority — 修改任意进程的优先级 pcntl_signal_dispatch — 调用等待信号的处理器 pcntl_signal_get_handler — Get the current handler for specified signal pcntl_signal — 安装一个信号处理器 pcntl_sigprocmask — 设置或检索阻塞信号 pcntl_sigtimedwait — 带超时机制的信号等待 pcntl_sigwaitinfo — 等待信号 pcntl_strerror — Retrieve the system error message associated with the given errno pcntl_wait — 等待或返回fork的子进程状态 pcntl_waitpid — 等待或返回fork的子进程状态 pcntl_wexitstatus — 返回一个中断的子进程的返回代码 pcntl_wifexited — 检查状态代码是否代表一个正常的退出。 pcntl_wifsignaled — 检查子进程状态码是否代表由于某个信号而中断 pcntl_wifstopped — 检查子进程当前是否已经停止 pcntl_wstopsig — 返回导致子进程停止的信号 pcntl_wtermsig — 返回导致子进程中断的信号
pcntl_fork — 현재 프로세스의 현재 위치에 브랜치(자식 프로세스)를 생성합니다. 주석: 포크는 하위 프로세스, 상위 프로세스 및 하위 프로세스를 생성합니다. 모두 포크 위치에서 시작하여 아래쪽으로 계속됩니다. 차이점은 부모 프로세스를 실행하는 동안 얻은 포크 반환 값은 자식 프로세스 번호이고 자식 프로세스는 0을 얻는다는 것입니다.
분할된 하위 프로세스는 상위 프로세스의 거의 완전한 복사본입니다. 상위 및 하위 프로세스는 코드 세그먼트를 공유하지만 상위 및 하위 프로세스의 데이터 세그먼트, 힙 및 스택은 서로 독립적입니다. 처음에는 하위 프로세스가 완전히 상위 프로세스의 데이터가 복사되지만 이후 수정 사항은 서로 영향을 미치지 않습니다.
int pcntl_fork ( void )
5개의 하위 프로세스 생성 코드 데모:
<?php for($i = 0; $i < 5; $i++) { $pid = pcntl_fork(); //创建子进程,子进程也是从这里开始执行。 if ($pid == 0) { break; //由于子进程也会执行循环的代码,所以让子进程退出循环,否则子进程又会创建自己的子进程。 } } sleep($i); //第一个创建的子进程将睡眠0秒,第二个将睡眠1s,依次类推...主进程会睡眠5秒 if ($i < 5) { exit("第 " . ($i+1) . " 个子进程退出..." . time() . PHP_EOL); } else { exit("父进程退出..." . time() . PHP_EOL); }
실행 결과:
[root@localhost process]# php process.php 第 1 个子进程退出...1503322773 第 2 个子进程退出...1503322774 第 3 个子进程退出...1503322775 第 4 个子进程退出...1503322776 第 5 个子进程退出...1503322777 父进程退出...1503322778
pcntl_fork 함수에 대해 이해해야 할 핵심 사항: “fork는 하위 프로세스를 생성합니다. 상위 프로세스와 하위 프로세스 모두 포크 위치에서 계속 실행됩니다. 차이점은 상위 프로세스 실행 중에 포크가 반환된다는 것입니다. 값은 하위 프로세스 번호이고 하위 프로세스는 0"을 얻습니다.
프로세스가 종료되지 않도록 위 코드를 약간 수정한 다음 ps 명령을 사용하여 시스템 상태를 확인합니다.
<?php for($i = 0; $i < 5; $i++) { $pid = pcntl_fork(); if ($pid == 0) { break; //由于子进程也会执行循环的代码,所以让子进程退出循环 } } sleep($i); //第一个创建的子进程将睡眠0秒,第二个将睡眠1s,依次类推...主进程会睡眠5秒 /* if ($i < 5) { exit("第 " . ($i+1) . " 个子进程退出..." . time() . PHP_EOL); } else { exit("父进程退出..." . time() . PHP_EOL); } */ while(1) { sleep(1); //执行死循环不退出 }
실행 후 ps -ef | grep php 를 입력하면 시스템 프로세스를 볼 수 있습니다
[root@localhost ~]# ps -ef | grep php root 3670 3609 0 21:54 pts/0 00:00:00 php process.php root 3671 3670 0 21:54 pts/0 00:00:00 php process.php root 3672 3670 0 21:54 pts/0 00:00:00 php process.php root 3673 3670 0 21:54 pts/0 00:00:00 php process.php root 3674 3670 0 21:54 pts/0 00:00:00 php process.php root 3675 3670 0 21:54 pts/0 00:00:00 php process.php root 3677 3646 0 21:54 pts/1 00:00:00 grep php
6개의 php process.php 프로세스를 볼 수 있습니다. 는 프로세스 번호이고 세 번째 열은 프로세스의 상위 프로세스 번호입니다. 다음 5개 프로세스의 상위 프로세스 번호는 모두 첫 번째 프로세스의 프로세스 번호임을 알 수 있습니다.
위 코드는 하위 프로세스와 상위 프로세스 모두 동일한 코드를 실행합니다. 하위 프로세스와 상위 프로세스가 서로 다른 작업을 수행하도록 하는 방법이 있습니까? 프로세스가 하위 프로세스를 실행합니다. 상위 프로세스의 코드가 상위 프로세스의 코드를 실행합니다.
<?php $ppid = posix_getpid(); //记录父进程的进程号 for($i = 0; $i < 5; $i++) { $pid = pcntl_fork(); if ($pid == 0) { break; //由于子进程也会执行循环的代码,所以让子进程退出循环 } } if ($ppid == posix_getpid()) { //父进程 while(1) { sleep(1); } } else { //子进程 for($i = 0; $i < 100; $i ++) { echo "子进程" . posix_getpid() . " 循环 $i ...\n"; sleep(1); } }
[root@localhost process]# php process.php 子进程6677 循环 0 ... 子进程6676 循环 0 ... 子进程6678 循环 0 ... 子进程6680 循环 0 ... 子进程6679 循环 0 ... 子进程6677 循环 1 ... 子进程6676 循环 1 ... 子进程6678 循环 1 ... 子进程6680 循环 1 ... 子进程6679 循环 1 ... 子进程6677 循环 2 ... 子进程6676 循环 2 ... 子进程6678 循环 2 ... 子进程6680 循环 2 ...
실제로 위 프로그램의 상위 프로세스와 하위 프로세스는 여전히 동일한 코드를 실행합니다. , 그러나 입력된 if 분기가 다르며 pcntl_exec는 하위 프로세스가 상위 프로세스의 영향을 완전히 벗어나 새 프로그램을 실행하도록 할 수 있습니다.
pcntl_exec — 在当前进程空间执行指定程序
void pcntl_exec ( string $path [, array $args [, array $envs ]] )
path
path必须时可执行二进制文件路径或一个在文件第一行指定了 一个可执行文件路径标头的脚本(比如文件第一行是#!/usr/local/bin/perl的perl脚本)。 更多的信息请查看您系统的execve(2)手册。
args
args是一个要传递给程序的参数的字符串数组。
envs
envs是一个要传递给程序作为环境变量的字符串数组。这个数组是 key => value格式的,key代表要传递的环境变量的名称,value代表该环境变量值。
注意该方法的返回值比较特殊:当发生错误时返回 FALSE ,没有错误时没有返回,因为pcntl_exec调用成功,子进程就去运行新的程序 从父进程继承的代码段、数据段、堆、栈等信息全部被替换成新的,此时的pcntl_exec函数调用栈已经不存在了,所以也就没有返回了。代码示例:
<?php for($i = 0; $i < 3; $i++) { $pid = pcntl_fork(); if($pid == 0) { echo "子进程pid = " . posix_getpid() . PHP_EOL; $ret = pcntl_exec('/bin/ls'); //执行 ls 命令, 此处调用成功子进程将不会再回来执行下面的任何代码 var_dump($ret); // 此处的代码不会再执行 } } sleep(5); //睡眠5秒以确保子进程执行完毕,原因后面会说 exit( "主进程退出...\n");
运行结果:
[root@localhost process]# php pcntl_exec.php 子进程pid = 6728 子进程pid = 6729 子进程pid = 6727 pcntl_exec.php process.php pcntl_exec.php process.php pcntl_exec.php process.php 主进程退出... [root@localhost process]# ls pcntl_exec.php process.php
以上就是对PHP多进程开发的简单介绍,对于子进程不同的存续状态,引出孤儿进程和僵尸进程的概念,在linux系统中,init进程(1号进程)是所有进程的祖先,其他进程要么是该进程的子进程,要么是子进程的子进程,子进程的子进程的子进程...,linux系统中可以用 pstree 命令查看进程树结构:
在多进程程序中,如果父进程先于子进程退出,那么子进程将会被init进程收养,成为init进程的子进程,这种进程被称为孤儿进程,我们可以把上面的代码稍作修改来演示这种情况:
<?php $ppid = posix_getpid(); //记录父进程的进程号 for($i = 0; $i < 5; $i++) { $pid = pcntl_fork(); if ($pid == 0) { break; //由于子进程也会执行循环的代码,所以让子进程退出循环 } } if ($ppid == posix_getpid()) { //父进程直接退出,它的子进程都会成为孤儿进程 exit(0); } else { //子进程 for($i = 0; $i < 100; $i ++) { echo "子进程" . posix_getpid() . " 循环 $i ...\n"; sleep(1); } }
运行该程序,然后查看进程状态:
[root@localhost ~]# ps -ef | grep php root 2903 1 0 12:09 pts/0 00:00:00 php pcntl.fork.php root 2904 1 0 12:09 pts/0 00:00:00 php pcntl.fork.php root 2905 1 0 12:09 pts/0 00:00:00 php pcntl.fork.php root 2906 1 0 12:09 pts/0 00:00:00 php pcntl.fork.php root 2907 1 0 12:09 pts/0 00:00:00 php pcntl.fork.php root 2935 2912 0 12:10 pts/1 00:00:00 grep php
可以看到五个子进程的父进程号都是1了,并且这时控制台不再被程序占用,子进程转到了后台运行,这种孤儿进程被init进程收养的机制是实现后面将要介绍的守护进程的必要条件之一。
子进程还有一种状态叫僵尸进程,子进程结束时并不是完全退出,内核进程表中仍旧保有该进程的记录,这样做的目的是能够让父进程可以得知子进程的退出状态,以及子进程是自杀(调用exit或代码执行完毕)还是他杀(被信号终止),父进程可以调用pcntl_wait 或 pcntl_waitpid 方法来回收子进程(收尸),释放子进程占用的所有资源,并获得子进程的退出状态,如果父进程不做回收,则僵尸进程一直存在,如果这时父进程也退出了,则这些僵尸进程会被init进程接管并自动回收。
对于linux系统来说,一个长时间运行的多进程程序一定要回收子进程,因为系统的进程资源是有限的,僵尸进程会让系统的可用资源减少。
代码演示僵尸进程的产生:
<?php $ppid = posix_getpid(); //记录父进程的进程号 for($i = 0; $i < 5; $i++) { $pid = pcntl_fork(); if ($pid == 0) { break; //由于子进程也会执行循环的代码,所以让子进程退出循环 } } if ($ppid == posix_getpid()) { //父进程不退出,也不回收子进程 while(1) { sleep(1); } } else { //子进程退出,会成为僵尸进程 exit("子进程退出 $ppid ...\n"); }
运行之后查看进程状态:
[root@localhost ~]# ps -ef | grep php root 2971 2864 0 14:13 pts/0 00:00:00 php pcntl.fork.php root 2972 2971 0 14:13 pts/0 00:00:00 [php] <defunct> root 2973 2971 0 14:13 pts/0 00:00:00 [php] <defunct> root 2974 2971 0 14:13 pts/0 00:00:00 [php] <defunct> root 2975 2971 0 14:13 pts/0 00:00:00 [php] <defunct> root 2976 2971 0 14:13 pts/0 00:00:00 [php] <defunct> root 2978 2912 0 14:13 pts/1 00:00:00 grep php
僵尸进程会用
PHP的pcntl扩展提供了两个回收子进程的方法供我们调用:
int pcntl_wait ( int &$status [, int $options = 0 ] ) int pcntl_waitpid ( int $pid , int &$status [, int $options = 0 ] )
pcntl_wait函数挂起当前进程的执行直到一个子进程退出或接收到一个信号要求中断当前进程或调用一个信号处理函数。 如果一个子进程在调用此函数时已经退出(俗称僵尸进程),此函数立刻返回。子进程使用的所有系统资源将被释放。
关于wait在您系统上工作的详细规范请查看您系统的wait(2)手册。这个函数等同于以-1作为参数pid 的值并且没有options参数来调用pcntl_waitpid() 函数。
代码示例:
<?php $ppid = posix_getpid(); //记录父进程的进程号 for($i = 0; $i < 5; $i++) { $pid = pcntl_fork(); if ($pid == 0) { break; //由于子进程也会执行循环的代码,所以让子进程退出循环 } } if ($ppid == posix_getpid()) { //父进程循环回收收子进程 while(($id = pcntl_wait($status)) > 0) //如果没有子进程退出, pcntl_wait 会一直阻塞 { echo "回收子进程:$id, 子进程退出状态值: $status...\n"; } exit("父进程退出 $id....\n"); //当子进程全部结束 pcntl_wait 返回-1 } else { //子进程退出,会成为僵尸进程 sleep($i); exit($i); }
运行结果:
[root@localhost php]# php pcntl.fork.php 回收子进程:3043, 子进程退出状态值: 0... 回收子进程:3044, 子进程退出状态值: 256... 回收子进程:3045, 子进程退出状态值: 512... 回收子进程:3046, 子进程退出状态值: 768... 回收子进程:3047, 子进程退出状态值: 1024... 父进程退出 -1....
这里只是对PHP多进程编程做了基本的介绍,后面会结合 信号、进程间通信以及守护进程 做更进一步的介绍,欢迎大家关注后续文章。
PHP是世界上最好的语言 That's all :)
相关推荐:
위 내용은 PHP는 시스템 프로그래밍을 구현합니다: 다중 프로세스 프로그래밍과 고아 프로세스 및 좀비 프로세스 소개의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

PHP에서, 특성은 방법 재사용이 필요하지만 상속에 적합하지 않은 상황에 적합합니다. 1) 특성은 클래스에서 다중 상속의 복잡성을 피할 수 있도록 수많은 방법을 허용합니다. 2) 특성을 사용할 때는 대안과 키워드를 통해 해결할 수있는 방법 충돌에주의를 기울여야합니다. 3) 성능을 최적화하고 코드 유지 보수성을 향상시키기 위해 특성을 과도하게 사용해야하며 단일 책임을 유지해야합니다.

의존성 주입 컨테이너 (DIC)는 PHP 프로젝트에 사용하기위한 객체 종속성을 관리하고 제공하는 도구입니다. DIC의 주요 이점에는 다음이 포함됩니다. 1. 디커플링, 구성 요소 독립적 인 코드는 유지 관리 및 테스트가 쉽습니다. 2. 유연성, 의존성을 교체 또는 수정하기 쉽습니다. 3. 테스트 가능성, 단위 테스트를 위해 모의 객체를 주입하기에 편리합니다.

SplfixedArray는 PHP의 고정 크기 배열로, 고성능 및 메모리 사용이 필요한 시나리오에 적합합니다. 1) 동적 조정으로 인한 오버 헤드를 피하기 위해 생성 할 때 크기를 지정해야합니다. 2) C 언어 배열을 기반으로 메모리 및 빠른 액세스 속도를 직접 작동합니다. 3) 대규모 데이터 처리 및 메모리에 민감한 환경에 적합하지만 크기가 고정되어 있으므로주의해서 사용해야합니다.

PHP는 $ \ _ 파일 변수를 통해 파일 업로드를 처리합니다. 보안을 보장하는 방법에는 다음이 포함됩니다. 1. 오류 확인 확인, 2. 파일 유형 및 크기 확인, 3 파일 덮어 쓰기 방지, 4. 파일을 영구 저장소 위치로 이동하십시오.

JavaScript에서는 NullCoalescingOperator (??) 및 NullCoalescingAssignmentOperator (?? =)를 사용할 수 있습니다. 1. 2. ??= 변수를 오른쪽 피연산자의 값에 할당하지만 변수가 무효 또는 정의되지 않은 경우에만. 이 연산자는 코드 로직을 단순화하고 가독성과 성능을 향상시킵니다.

CSP는 XSS 공격을 방지하고 리소스로드를 제한하여 웹 사이트 보안을 향상시킬 수 있기 때문에 중요합니다. 1.CSP는 HTTP 응답 헤더의 일부이며 엄격한 정책을 통해 악의적 인 행동을 제한합니다. 2. 기본 사용법은 동일한 원점에서 자원을로드 할 수있는 것입니다. 3. 고급 사용량은 특정 도메인 이름을 스크립트와 스타일로드 할 수 있도록하는 것과 같은보다 세밀한 전략을 설정할 수 있습니다. 4. Content-Security Policy 보고서 전용 헤더를 사용하여 CSP 정책을 디버그하고 최적화하십시오.

HTTP 요청 방법에는 각각 리소스를 확보, 제출, 업데이트 및 삭제하는 데 사용되는 Get, Post, Put and Delete가 포함됩니다. 1. GET 방법은 리소스를 얻는 데 사용되며 읽기 작업에 적합합니다. 2. 게시물은 데이터를 제출하는 데 사용되며 종종 새로운 리소스를 만드는 데 사용됩니다. 3. PUT 방법은 리소스를 업데이트하는 데 사용되며 완전한 업데이트에 적합합니다. 4. 삭제 방법은 자원을 삭제하는 데 사용되며 삭제 작업에 적합합니다.

HTTPS는 HTTP를 기반으로 보안 계층을 추가하는 프로토콜로, 주로 암호화 된 데이터를 통해 사용자 개인 정보 및 데이터 보안을 보호합니다. 작업 원칙에는 TLS 핸드 셰이크, 인증서 확인 및 암호화 된 커뮤니케이션이 포함됩니다. HTTP를 구현할 때는 인증서 관리, 성능 영향 및 혼합 콘텐츠 문제에주의를 기울여야합니다.


핫 AI 도구

Undresser.AI Undress
사실적인 누드 사진을 만들기 위한 AI 기반 앱

AI Clothes Remover
사진에서 옷을 제거하는 온라인 AI 도구입니다.

Undress AI Tool
무료로 이미지를 벗다

Clothoff.io
AI 옷 제거제

AI Hentai Generator
AI Hentai를 무료로 생성하십시오.

인기 기사

뜨거운 도구

WebStorm Mac 버전
유용한 JavaScript 개발 도구

스튜디오 13.0.1 보내기
강력한 PHP 통합 개발 환경

SublimeText3 영어 버전
권장 사항: Win 버전, 코드 프롬프트 지원!

SublimeText3 Mac 버전
신 수준의 코드 편집 소프트웨어(SublimeText3)

DVWA
DVWA(Damn Vulnerable Web App)는 매우 취약한 PHP/MySQL 웹 애플리케이션입니다. 주요 목표는 보안 전문가가 법적 환경에서 자신의 기술과 도구를 테스트하고, 웹 개발자가 웹 응용 프로그램 보안 프로세스를 더 잘 이해할 수 있도록 돕고, 교사/학생이 교실 환경 웹 응용 프로그램에서 가르치고 배울 수 있도록 돕는 것입니다. 보안. DVWA의 목표는 다양한 난이도의 간단하고 간단한 인터페이스를 통해 가장 일반적인 웹 취약점 중 일부를 연습하는 것입니다. 이 소프트웨어는

뜨거운 주제



