ksjsb/tools/spoof_swipe.py
2026-07-30 20:25:56 +08:00

79 lines
2.9 KiB
Python

"""Frida 传感器伪造编排: 挂 nebula 主进程 -> (rpc.burst + adb swipe 同步).
用法 (用装了 frida 的 python 跑):
python tools/spoof_swipe.py testburst
挂上, 触发一次 760ms 爆发, 打印 INJECT 行 -> 验证注入路径(不需要验证码).
python tools/spoof_swipe.py swipe X1 Y1 X2 Y2 DUR_MS
arm burst + adb input swipe 同步触发 (滑动几何由调用方给, 落点用 solver 算).
python tools/spoof_swipe.py hold
挂上保持, 打印 handle 分类, 手动在 REPL 里用.
"""
from __future__ import annotations
import sys, time, subprocess
def adb(*a):
return subprocess.run(["adb", *a], capture_output=True, text=True, timeout=30,
encoding="utf-8", errors="replace").stdout
def main_pid():
out = adb("shell", r'for p in /proc/[0-9]*; do c=$(cat $p/cmdline 2>/dev/null | tr "\0" " " | sed "s/[[:space:]]*$//"); [ "$c" = "com.kuaishou.nebula" ] && { echo "$(basename $p)"; break; }; done')
out = out.strip()
return out.split()[0] if out else None
def on_msg_factory(tag="[f]"):
def on_msg(msg, data):
t = msg.get("type")
if t == "log":
print(tag, msg.get("payload", ""))
elif t == "error":
print(tag+"-err", msg.get("stack") or msg.get("description"))
elif t == "send":
print(tag, msg.get("payload"))
return on_msg
def main():
import frida
mode = sys.argv[1] if len(sys.argv) > 1 else "hold"
pid = main_pid()
if not pid:
print("[!] 没找到 com.kuaishou.nebula 主进程 — 先在手机上打开快手极速版")
return 1
print(f"[+] nebula main pid = {pid}")
dev = frida.get_usb_device(timeout=5)
session = dev.attach(int(pid))
with open("out/frida_sensor_spoof.js", encoding="utf-8") as f:
src = f.read()
script = session.create_script(src)
script.on("message", on_msg_factory())
script.load()
time.sleep(3.0) # 让 handle 分类跑完
api = script.exports_sync
print("[+] initial status:", api.status())
if mode == "testburst":
print("[+] 触发 test burst (760ms) -> 看下面 INJECT 行验证注入...")
api.burst()
time.sleep(2.0)
print("[+] final status:", api.status())
elif mode == "swipe":
if len(sys.argv) < 7:
print("[!] swipe 需要 X1 Y1 X2 Y2 DUR_MS"); return 2
x1, y1, x2, y2, dur = sys.argv[2:7]
print(f"[+] arm burst + adb swipe {x1},{y1}->{x2},{y2} dur={dur}ms (同步)")
api.burst()
subprocess.run(["adb", "shell", "input", "swipe", x1, y1, x2, y2, dur])
time.sleep(1.2)
print("[+] status:", api.status())
else:
print("[+] hold 模式: 挂着, Ctrl+C 退出.")
try:
while True: time.sleep(2)
except KeyboardInterrupt:
pass
try: session.detach()
except Exception: pass
return 0
if __name__ == "__main__":
raise SystemExit(main())