=Start=
缘由:
现在自用的Linux主机系统我都是选的CentOS 7,用的PHP版本也升级到了PHP 7。在之前的主机、博客维护过程中已经出过不少问题,这次又碰到了一个问题——在主机因维护而重启后php-fpm没有正确启动导致博客无法正常访问,解决办法和之前的不太一样,所以在此记录一下,方便以后查阅、参考。
正文:
参考解答:
0、一些辅助命令
# ls -lt /etc/systemd/system/multi-user.target.wants/ # find / -type f -iname "php-fpm.conf" | xargs ls -lt # grep -v '^;' /etc/opt/remi/php71/php-fpm.d/www.conf | grep 'listen' # nginx -t # grep "fastcgi_pass" /etc/nginx/nginx.conf
1、systemd的系统启动项
应该是从CentOS 7开始,Linux服务管理器开始用systemd来替换之前的SysVinit,很多命令和之前不太一样,具体的可以参考之前记录的一篇文章「Linux的systemd相关知识学习」,这里只提一点:
# systemd里面的.service文件一般是放在下面这个目录下,当不记得服务名称了,可以去目录里看看 # ls -lt /usr/lib/systemd/system/ # cat /usr/lib/systemd/system/php71-php-fpm.service
&
# 查看当前系统上现在有哪些开机启动项,如果不在的话使用enable进行添加 # ls -lt /etc/systemd/system/multi-user.target.wants/ # systemctl enable nginx # systemctl enable php71-php-fpm # systemctl enable mysqld
2、php-fpm启动失败的原因
● php71-php-fpm.service - The PHP FastCGI Process Manager Loaded: loaded (/usr/lib/systemd/system/php71-php-fpm.service; disabled; vendor preset: disabled) Active: failed (Result: exit-code) since Wed 2018-05-05 10:38:32 CST; 36s ago Process: 5500 ExecStart=/opt/remi/php71/root/usr/sbin/php-fpm --nodaemonize (code=exited, status=78) Main PID: 5500 (code=exited, status=78) May 05 10:38:32 ixyzero-centos systemd[1]: Starting The PHP FastCGI Process Manager... May 05 10:38:32 ixyzero-centos php-fpm[5500]: [02-May-2018 10:38:32] ERROR: unable to bind listening socket for address '/var/run/php-fpm/php-fpm.sock': No such file or directory (2) May 05 10:38:32 ixyzero-centos php-fpm[5500]: [02-May-2018 10:38:32] ERROR: FPM initialization failed May 05 10:38:32 ixyzero-centos systemd[1]: php71-php-fpm.service: main process exited, code=exited, status=78/n/a May 05 10:38:32 ixyzero-centos systemd[1]: Failed to start The PHP FastCGI Process Manager. May 05 10:38:32 ixyzero-centos systemd[1]: Unit php71-php-fpm.service entered failed state. May 05 10:38:32 ixyzero-centos systemd[1]: php71-php-fpm.service failed.
即,没有 `/var/run/php-fpm/php-fpm.sock` 这个文件,导致无法绑定监听端口/文件,初始化失败。
之前出现这种问题,一般是以下原因之一:
- php-fpm的配置文件里的listen.owner/group和Nginx配置文件里的user/group不匹配,导致权限不够;
- php-fpm的配置文件里的listen和Nginx配置文件里的fastcgi_pass不匹配,导致监听和读取的不是同一个socket文件;
3、临时解决办法
但这次不是,这次的上面2个配置都是对的,但就是 `/var/run/php-fpm/php-fpm.sock` 这个文件不存在,解决办法也很简单,就是:
# sudo mkdir -p /var/run/php-fpm/ # sudo touch /var/run/php-fpm/php-fpm.sock # sudo systemctl start php71-php-fpm
不过,一旦机器重启,`/var/run/php-fpm/php-fpm.sock` 这个文件就又没了,而且 `/var/run/php-fpm/` 这个目录也没了,所以,这种手工创建目录、文件的方式只能临时生效。
4、长期解决办法
如果想要找到一个长期有效的办法,那就需要定位问题以及其背后的原因,否则问题还是会一直存在。
# 看 /var/run/ 目录权限 [zero@ixyzero-centos ~]$ ls -lt /var/ | grep "run" lrwxrwxrwx. 1 root root 11 2月 3 2017 lock -> ../run/lock lrwxrwxrwx. 1 root root 6 2月 3 2017 run -> ../run [zero@ixyzero-centos ~]$ [zero@ixyzero-centos ~]$ ls -lt / | grep "run" drwxr-xr-x 22 root root 620 5月 2 16:30 run # 从上面的信息可以看出, /var/run 这个目录只有root才有「写」权限,而php-fpm的执行用户是和Nginx一样的低权限用户,所以无法创建 /var/run/php-fpm/ 子目录,从而也就无法创建 /var/run/php-fpm/php-fpm.sock 文件 # 目录 /var/run 有点「内存盘」的感觉,就是说它不是一直稳定存在的,而是只存在于内存中(网上有说法是这样会提高速度),当系统重启时,/var 下的目录便会消失,需要重新创建
综上,我将原先php-fpm的配置文件里的listen和Nginx配置文件里的fastcgi_pass都改成了 `/var/run/php-fpm.sock` ,然后将php-fpm和Nginx服务都加入系统启动项,重启系统,一切OK。
参考链接:
=END=
《 “CentOS 7上php-fpm无法启动的问题处理” 》 有 11 条评论
502错误,让你进一步明白nginx和php-fpm之间的关系
https://mp.weixin.qq.com/s/keJuNwnZu2ejnZqCvXxy3A
什么是SAPI,FastCGI,PHP-FPM?学习PHP的必备知识
https://mp.weixin.qq.com/s?__biz=MzAwOTU4NzM5Ng==&mid=2455770169&idx=1&sn=68670208eab3a6f93c528f3d2f14317a
如何通过nginx、php-fpm、php的日志调试程序
https://mp.weixin.qq.com/s/CPsjXITMHfpIWV2ylxknrA
`
在这四个层面(nginx、php-fpm主进程、php-fpm pool工作进程、php)都有与日志有关的指令,接下去分别描述。
php.ini
每一个php解析器都有一个php.ini,该文件定义了很多php的默认行为,从日志的角度看,有三个指令很重要。
error_reporting = E_ALL & ~E_DEPRECATED & ~E_STRICT
display_errors=off
error_log=/var/log/phperror.log
nginx.conf
对于nginx来说,可以通过以下指令控制访问日志和错误日志,非常的简单:
access_log logs/access.log main;
error_log logs/error.log;
php-fpm pool 日志
比如:
fpm/pool.d/www.test.com.conf
fpm/pool.d/www.test.cn.conf
php-fpm 日志
暂时可以忽略
`
2018年12月31日 PHP 5.6.x 的安全支持将正式停止,大约 62% 的互联网站点将运行不受支持的 PHP 版本
https://www.zdnet.com/article/around-62-of-all-internet-sites-will-run-an-unsupported-php-version-in-10-weeks/
php-fpm环境的一种后门实现
https://www.anquanke.com/post/id/163197?from=timeline
`
简介
测试环境
php-fpm文件句柄泄露
文件句柄泄露的利用
一个另类的利用方法
利用限制
总结
`
PHP远程代码执行漏洞预警(CVE-2019-11043)
https://www.4hou.com/vulnerable/21160.html
CVE-2019-11043: PHP 7 RCE漏洞分析
https://www.4hou.com/vulnerable/21195.html
https://thehackernews.com/2019/10/nginx-php-fpm-hacking.html
`
# 建议
虽然漏洞利用只在PHP 7+版本上工作,但该漏洞本身存在于之前的版本中。很长时间内,php-fpm都不会限制脚本的扩展,比如/avatar.png/some-fake-shit.php可以将 avatar.png 作为php脚本执行。
GitHub上的PoC脚本可以通过发送特殊伪造的请求来查询目标web服务器来识别是否受到该漏洞的影响。识别了有漏洞的目标后,攻击者可以在URL中加上’?a=’并发送伪造的请求到有漏洞的web服务器。
因为PoC漏洞利用已经在GitHub上公布了,虽然补丁已经发布了,但是黑客可能已经利用该漏洞了。研究人员建议用户更新PHP到最新的PHP 7.3.11 或PHP 7.2.24。
`
CVE-2019-11043 exposes Web servers using nginx and PHP-FPM to hack
https://securityaffairs.co/wordpress/92997/hacking/cve-2019-11043-php7-flaw.html
PHP7 被曝出一个远程执行代码漏洞
https://www.infoq.cn/article/gB5J27dSA6SBcrtepsT5
Exploit for CVE-2019-11043
https://github.com/neex/phuip-fpizdam
PHP-fpm 远程代码执行漏洞(CVE-2019-11043)分析
https://paper.seebug.org/1063/
https://blog.knownsec.com/2019/10/php-fpm-%E8%BF%9C%E7%A8%8B%E4%BB%A3%E7%A0%81%E6%89%A7%E8%A1%8C%E6%BC%8F%E6%B4%9Ecve-2019-11043%E5%88%86%E6%9E%90/
https://github.com/vulhub/vulhub/tree/master/php/CVE-2019-11043
【漏洞通告】PHP远程代码执行漏洞(CVE-2019-11043)
https://mp.weixin.qq.com/s/iFtnfEyL2u4skA2DY7d6yA
`
2.漏洞概述
漏洞类型:远程代码执行漏洞
危险等级:高危
利用条件:nginx配置了fastcgi_split_path_info
受影响系统:PHP 5.6-7.x,Nginx>=0.7.31
3.漏洞编号
CVE-2019-11043 PHP远程代码执行漏洞
4.漏洞描述
Nginx 与 php-fpm 服务器上存在远程代码执行漏洞,由于Nginx的fastcgi_split_path_info模块在处理带 %0a 的请求时,对换行符 \n 处置不当使得将 PATH_INFO 值置为空,从而导致 php-fpm 组件在处理 PATH_INFO 时存在漏洞,攻击者通过精心的构造和利用,可以导致远程代码执行。
5.修复建议
1).补丁包修复方案:
目前官方尚未发布修复漏洞的补丁包,将于当地时间24日进行发布,请随时关注并进行升级。
2).源码修复方案:
https://bugs.php.net/patch-display.php?bug_id=78599&patch=0001-Fix-bug-78599-env_path_info-underflow-can-lead-to-RC.patch&revision=latest
3).临时修复方案:
Nginx 配置文件中location添加如下配置:
try_files $uri =404
`
漏洞预警 | PHP 远程代码执行漏洞 (CVE-2019-11043)
https://mp.weixin.qq.com/s/NFPVPSUHJKr4ghfa0ofoWQ
CVE-2019-11043 PHP远程代码执行漏洞复现
https://mp.weixin.qq.com/s/senNnIrw1cm4ND66qFWyRw
`
# 复现总结
(1)利用条件苛刻,因为触发漏洞的配置不是默认配置。
(2)即使是触发漏洞的配置,仍有失败的机率,执行命令时成功率50%的样子。
`
https://www.hostwinds.com/guide/install-php-modules-centos-7/
`
# 为PHP7安装zip模块
yum search php73
sudo yum install -y php73-php-pecl-zip
sudo systemctl status php73-php-fpm
sudo systemctl reload php73-php-fpm
`
Centos7 安装zipArchive及libzip 版本更新
https://www.uedbox.com/post/9253/
lnmp centos7 安装 php7.3 nginx1.4 部署 并安装wordpress
https://blog.csdn.net/weixin_37377511/article/details/81537194
PHP-fpm 远程代码执行漏洞(CVE-2019-11043)分析
https://lorexxar.cn/2019/10/25/php-fpm-rce/
question:
php-fpm.conf 配置文件如何被nginx识别和读取?
answer:
Nginx 本身**不会直接读取或解析** `php-fpm.conf` 文件。这个文件是 **PHP-FPM (FastCGI Process Manager)** 的主配置文件,由 PHP-FPM 进程自己读取和管理。
Nginx 与 PHP-FPM 的协作是通过 **FastCGI 协议**进行的,它们之间的“桥梁”是 Nginx 配置文件中的 `fastcgi_pass` 指令。
以下是详细的协作流程和配置说明:
—
### 1. PHP-FPM 的配置 (`php-fpm.conf` 和 `www.conf`)
– **`php-fpm.conf`**: 这是 PHP-FPM 的主配置文件,通常位于 `/etc/php-fpm.conf` 或 `/etc/php/8.x/fpm/php-fpm.conf`。它定义了全局设置,如进程管理、日志位置、PID 文件等。
– **`www.conf`**: 通常位于 `/etc/php-fpm.d/www.conf` 或 `/etc/php/8.x/fpm/pool.d/www.conf`。这个文件定义了“进程池”(pool),其中最关键的是 `listen` 指令。
#### 关键配置项(在 `www.conf` 中):
“`ini
[www]
; PHP-FPM 监听的地址和端口(或 Unix Socket)
listen = 127.0.0.1:9000
; 或者使用 Unix Socket(性能更好)
; listen = /run/php/php8.3-fpm.sock
; 允许连接的地址(如果使用 TCP)
listen.allowed_clients = 127.0.0.1
“`
当 PHP-FPM 服务启动时,它会读取 `php-fpm.conf` 和 `pool.d/` 目录下的配置文件(如 `www.conf`),然后根据 `listen` 指令在指定的地址(如 `127.0.0.1:9000` 或 `/run/php/php8.3-fpm.sock`)上**启动一个监听服务**。
—
### 2. Nginx 的配置 (`nginx.conf` 或站点配置文件)
Nginx 需要知道将 PHP 请求转发到哪里。这通过 `fastcgi_pass` 指令实现。
#### 示例 Nginx 配置:
“`nginx
server {
listen 80;
server_name example.com;
root /var/www/html;
index index.php index.html;
location ~ \.php$ {
# 将 PHP 请求传递给 PHP-FPM 监听的地址
fastcgi_pass 127.0.0.1:9000;
# 如果 PHP-FPM 使用 Unix Socket,则:
# fastcgi_pass unix:/run/php/php8.3-fpm.sock;
fastcgi_index index.php;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
include fastcgi_params;
}
}
“`
—
### 3. 协作流程
1. **PHP-FPM 启动**:
– 读取 `php-fpm.conf` 和 `www.conf`。
– 在 `listen` 指定的地址(如 `127.0.0.1:9000`)上启动监听。
2. **Nginx 启动**:
– 读取自己的配置文件(如 `/etc/nginx/nginx.conf` 和 `/etc/nginx/sites-available/default`)。
– 当收到一个 PHP 请求(如 `index.php`)时,Nginx 根据 `location ~ \.php$` 块中的 `fastcgi_pass` 指令,将请求**转发**到 `127.0.0.1:9000`。
3. **数据交换**:
– Nginx 通过 FastCGI 协议将请求数据(如 URL、POST 数据、HTTP 头等)发送给 PHP-FPM。
– PHP-FPM 执行 PHP 脚本,生成 HTML 响应。
– PHP-FPM 将响应通过同一连接返回给 Nginx。
– Nginx 再将响应发送给客户端(浏览器)。
—
### 总结
| 组件 | 配置文件 | 职责 |
|——|———-|——|
| **PHP-FPM** | `php-fpm.conf`, `www.conf` | 读取这些文件,启动并监听在 `listen` 指定的地址上。 |
| **Nginx** | `nginx.conf`, 站点配置 | 通过 `fastcgi_pass` 指令,将 PHP 请求转发到 PHP-FPM 监听的地址。 |
**简单来说:**
– `php-fpm.conf` 是给 **PHP-FPM** 看的。
– `fastcgi_pass` 是给 **Nginx** 看的,告诉它“PHP-FPM 在哪里等着”。
只要 Nginx 的 `fastcgi_pass` 地址与 PHP-FPM 的 `listen` 地址**完全匹配**,两者就能成功通信。
===
要让 Nginx 使用特定版本或路径的 PHP-FPM,您需要在 Nginx 的配置文件中,通过 `fastcgi_pass` 指令精确指向该 PHP-FPM 实例的监听地址(可以是 TCP 端口或 Unix Socket)。关键在于 **PHP-FPM 的 `listen` 配置** 和 Nginx 的 `fastcgi_pass` 配置必须**匹配**。