在 Web 安全领域,文件包含漏洞(File Inclusion Vulnerability)一直是高危漏洞中的常客。其中,本地文件包含(LFI)虽然本身只能读取服务器本地文件,但当攻击者将其与日志投毒、文件上传、PHP 伪协议等技巧结合时,往往能实现从 LFI 到远程代码执行(RCE)的华丽提权。本文将系统梳理多种 LFI 到 RCE 的利用路径,并分析其原理与防御思路。

一、LFI 漏洞基础回顾
LFI 通常出现在 PHP 等动态语言中,当程序使用用户可控的输入拼接进 include、require 等函数时,攻击者可以构造路径遍历(如 ../../etc/passwd)读取任意文件。例如:
<?php
$file = $_GET['page'];
include($file);
?>
访问 ?page=../../../../etc/passwd 即可读取系统文件。但读取文件并非终点,真正的威胁在于如何将“读”升级为“写”或“执行”。
二、路径一:日志投毒 + 文件包含
这是最经典的 LFI 到 RCE 手法。Web 服务器(如 Apache、Nginx)会将每个 HTTP 请求记录到访问日志中。攻击者可以构造包含 PHP 代码的请求头(如 User-Agent),使恶意代码写入日志文件,再通过 LFI 包含该日志文件,从而触发代码执行。
利用步骤:
- 确认 LFI 点,尝试读取
/var/log/apache2/access.log或/var/log/nginx/access.log。 - 发送一个带有恶意 PHP 代码的请求,例如:
curl -A "<?php system($_GET['cmd']); ?>" http://target.com/ - 通过 LFI 包含日志文件:
?page=/var/log/apache2/access.log&cmd=id
注意点: 日志路径因系统而异,常见路径包括 /var/log/apache2/access.log、/var/log/httpd/access_log、/var/log/nginx/access.log 等。若日志被截断或编码,可能需要调整 payload 长度或使用其他注入点。
三、路径二:PHP 伪协议与 php://filter
PHP 提供了多种流包装器,其中 php://filter 可用于读取文件源码,而 php://input 和 data:// 则可能直接执行代码。
1. php://input 执行代码
若 allow_url_include 开启,可通过 POST 数据提交 PHP 代码:
?page=php://input
POST: <?php system('id'); ?>
2. data:// 协议
同样需要 allow_url_include=On:
?page=data://text/plain,<?php system('id'); ?>
3. php://filter 链
php://filter 本身不直接执行代码,但可结合 convert.base64-decode 等过滤器,将恶意内容解码后写入文件,或配合文件包含实现代码执行。例如,利用 php://filter/convert.base64-decode/resource=shell.php 将 Base64 内容解码写入 shell.php,再包含该文件。这通常需要配合文件上传或日志写入。
四、路径三:Session 文件包含
PHP 默认将 Session 数据存储在 /var/lib/php/sessions/ 或 /tmp/ 下,文件名格式为 sess_<sessionid>。如果攻击者能控制 Session 中的某个值(如用户名),即可将 PHP 代码写入 Session 文件,再通过 LFI 包含。
利用步骤:
- 在登录或留言处提交包含 PHP 代码的用户名,如
<?php system($_GET['cmd']); ?>。 - 获取当前 Session ID(通常在 Cookie 中)。
- 通过 LFI 包含 Session 文件:
?page=/var/lib/php/sessions/sess_<sessionid>&cmd=id
注意点: Session 存储路径可通过 phpinfo() 或读取 /etc/php/7.4/apache2/php.ini 获取。若 Session 内容被序列化或编码,可能需要调整 payload。
五、路径四:文件上传 + 文件包含
如果目标存在文件上传功能,即使上传的文件被重命名或限制后缀,也可结合 LFI 实现 RCE。例如:
- 上传一个包含 PHP 代码的图片文件(如
shell.jpg),内容为<?php system($_GET['cmd']); ?>。 - 通过 LFI 包含该图片文件:
?page=uploads/shell.jpg&cmd=id
绕过技巧: 若上传目录有执行限制,可通过 LFI 包含即可绕过。若文件内容被 getimagesize() 检查,可在图片末尾附加 PHP 代码。
六、路径五:/proc/self/environ 包含
在 Linux 系统中,/proc/self/environ 文件包含当前进程的环境变量。如果 Web 服务器将 User-Agent 等请求头写入环境变量(某些配置下),攻击者可通过 LFI 包含该文件并注入代码。
利用步骤:
- 尝试读取
/proc/self/environ,确认是否包含可控内容。 - 发送带有 PHP 代码的 User-Agent 请求。
- 包含
/proc/self/environ执行代码。
注意点: 现代系统通常不会将请求头写入环境变量,此方法成功率较低,但在特定容器或旧版本中仍可能有效。
七、路径六:临时文件包含
PHP 在处理文件上传时,会将上传的临时文件存储在 /tmp/ 下,文件名随机(如 phpXXXXXX)。攻击者可通过 LFI 包含该临时文件,但需要竞争条件(Race Condition)——在上传后、删除前完成包含。
利用工具: 可使用 phpinfolfi.py 等脚本自动化竞争,通过大量请求提高成功率。
八、防御与修复建议
- 避免动态包含:尽量使用白名单机制,限制可包含的文件。
- 关闭危险配置:设置
allow_url_include = Off,allow_url_fopen = Off。 - 路径规范化:使用
realpath()和basename()过滤用户输入,防止路径遍历。 - 日志安全:对日志文件设置严格权限,避免 Web 用户可读。
- Session 安全:设置
session.save_path到非 Web 目录,并对 Session 内容进行过滤。 - WAF 与 RASP:部署 Web 应用防火墙,检测并拦截包含攻击。
九、总结
LFI 到 RCE 的提权路径多样,核心思路是“将恶意代码写入服务器可读文件,再通过 LFI 包含执行”。日志投毒、Session 包含、文件上传、伪协议等手法各有适用场景,攻击者往往会组合使用。作为防御方,应从代码审计、配置加固、权限控制等多层面入手,彻底切断 LFI 的利用链。只有深入理解攻击路径,才能构建更有效的防御体系。
未经允许不得转载:任鹏个人博客 » 文件包含漏洞利用:LFI 到 RCE 的多种提权路径详解

