Files
live-hub-py/docs/dfpReport生成流程.md
T
yml2213 36b5d78050 docs(huya): 记录 dfpReport 零设备生成突破与生成器工具
- 破解进度: 服务端不校验 cw 内容, 随机 4146B cw 即可 200 + 签发新 t2/t5
- 生成流程: 零设备注册链 getDfpConfig->selectOperator->dfpReport 打法
- tools/dfp_gen.py: cw/body 构建器 (TAF 4226B 结构)
- tools/dfp_cli.py: 注册链 CLI
- evidence: cw JSON 段/collection 段抓取样本
2026-08-27 17:57:38 +08:00

96 lines
4.4 KiB
Markdown

# dfpReport 生成流程与逻辑(逆向推演总账)
> 目标:讲清楚 dfpReport 上报数据"每一步怎么生成"的完整链路。
> 已破解部分(黑纸白字)+ 待逆向部分(用 ⚠️ 标出)。
## 一、dfpReport 是什么
虎牙 huyaudb 风控的"设备行为上报"请求,POST 到 `wsapi.huya.com:443 /`,用腾讯 **taf/wup** 协议封装。
请求体(body)= taf 容器,内含若干 tag 字段,其中 **tag2 是核心密文区**(整个设备+行为报文的加密载荷)。
## 二、请求体生成的完整流程(逻辑推理)
### 第 1 步:准备明文 JSON(554B)——【已完全破解】
```json
{"appId":"5008","appVer":"13.4.22","appkey":"865a...cbb0e3",
"channel":"xiaomi","deviceId":"02df...9389","deviceName":"M2102J2SC",
"hdid":"7c5387...85ee","heightPixels":"2120",
"systemVer":"M2102J2SC,30,11","widthPixels":"1080", ...}
```
来源:
- `appId/appVer/sdkVer/channel` = App 编译期/运行期常量
- `deviceName/systemVer` = Android build props
- `widthPixels/heightPixels` = 屏幕分辨率(运行期查询)
- **`hdid` / `deviceId` / `appkey` = ⚠️ 设备三元组,这是核心待逆向项**(见第三节)
### 第 2 步:准备 collection ↓ 数据集(大 JSON,每轮变化)——【部分破解,算法待逆向】
一个 ~3400B 的大 JSON,含动态行为数据:
- `touch_events`(触摸事件时间/坐标)
- `net_intfs`(网络接口状态)
- `phoneInfo`(设备/系统信息汇总)
- `qimei16/36`(⚠️ 设备指纹 App 的标识,逆向目标)
- `risk_apps`(已安装的风险 App,如 magisk)
- `scanned_appname`(⚠️ ~2900B 二进制扫描结果)
- **`Poseidon_*` 反 frida 检测字段**(读 /proc/self/maps 等检测 hook)
⚠️ **collection 的构建逻辑(App 怎么采这些数据、怎么格式化)是"生成流程"里最大的一块未破解**,但注意:验证已证明 collection **不参与服务端设备身份匹配**(改它只影响"动态/静态"判定,不动 hdid)。
### 第 3 步:组合成明文平文本(pa)——【已知结构,精确边界待确认】
```
明文输入 ≈ JSON(554B) + collection(3420B) [顺序/分隔待最终确认]
```
### 第 4 步:XOR 加密(逐字节 keystream)——【算法已破解,种子待逆】
- `tag2 = [魔数 10B 57 18 82 cf 66 4b b3 94 01 ee] + [XOR密文]`
- keystream 逐字节 XOR 明文 → 密文
- **魔数恒定**(明文头 XOR 固定值)
- **keystream 每会话动态** → ⚠️ 种子(时间戳/会话随机+密钥)+ 生成函数待逆向
### 第 5 步:封装 taf/wup + 加密通信
body 各 tag 打包(taf 编码)→ `POST wsapi.huya.com:443 /`(TLS),`Content-Type: application/octet-stream`,`i-ver: 1`,`User-Agent: okhttp/3.14.9`
### 第 6 步:服务端校验(已通过差分实验定论)
- 服务端解密 tag2 → 解析明文 JSON 三元组(hdid/deviceId/appkey)+ collection
- **三元组在设备库 + collection 完整** → 回显设备 hdid(actionV)
- 否则 → 动态随机 token(拒绝)
## 三、核心待逆向项(按"生成流程"重要性排序)
### 3.1 设备三元组(hdid/deviceId/appkey)怎么来【最关键】
已知:
- 是真设备派生(`pm clear` 不变,跨会话稳定)
- 长度 40hex(hdid/deviceId)、32hex(appkey),像 hash 输出
- libhydeviceid.so 内有 MD5 实现(ror#7 @0xc37c0)+ SHA1 + hex 表
⚠️ 待逆向:
- 从哪些硬件/系统信息(AndroidID/IMEI/build/serial?)派生
- 用哪个 hash(MD5/SHA1/自实现)
- 掺什么盐/固定密钥
### 3.2 collection 的完整构建逻辑
- 哪些数据源、如何采集、如何序列化、顺序
### 3.3 keystream 的种子与生成函数
- 种子来源(时间戳?线程随机?会话 ID?)
- 生成器(自实现伪随机?流密码?)
## 四、验证里"能做什么"的现实
已确认(纯 Python 可做):
- `forge_replay.py`:任意帧真实 wire → XOR 差分改明文三元组 → 重放,HTTP 200(服务端接受,只是认不认设备问题)
- 捕获比:任何一帧真实 ks 即可加密任意伪造明文(不需要生成器)
## 五、逆向"生成流程"的推荐路径(hook 而非纯静态)
由于 libhydeviceid.so 是 OLLVM 混淆,纯静态难。推荐用 frida 在**生成点 hook**,抓真实输入输出:
1. **hook 三元组派生**:hook MD5(0xc37c0 附近)/ hex 表使用处,抓 hash 输入 → 反推三元组
2. **hook 加密函数入口**:抓 keystream 生成函数输入(种子)
3. **hook collection 构建函数**:抓各字段组装点
但 attach/spawn 反调试都强(已验证 attach 6/6 死,spawn 3-6s 死),给 hook 点逆向带来现实障碍