HackThisSite - Application Mission 4
Challenge
Press the Button. (easy)
按下按钮(easy)。
包内只有一个 app4win.exe(24
KB)。界面上有两个按钮,鼠标指到哪个,哪个就被置灰、另一个恢复可用,所以两个按钮都点不到。
Solution
Recon:
file app4win.exe→PE32 executable for MS Windows 4.00 (GUI), Intel i386, 3 sections。导入表里只有MSVBVM60.DLL一个 DLL,代码在.text(VA0x401000,大小0x2af8),没有 overlay。这是 VB6 编译成 native code 的程序,不是 p-code。- 导入表里直接能看到密码是怎么被拼出来的痕迹 —— 调用
rtcVarBstrFromAnsi(把 ANSI 字符转成 BSTR)和__vbaVarCat(拼接 Variant 字符串):
1 | $ objdump -x -M intel app4win.exe | sed -n '/The Import Tables/,$p' |
- 版本信息资源还留着编译时的工程名,确认真的是 VB6:
1 | $ strings -el app4win.exe | grep -iE 'challenge|project|app' |
- 密码不在字符串表里:
grep -a -c daytona app4win.exe→0,连Password这个词都搜不到。和同批 app1 一样,是运行时逐字符生成的,必须反汇编重建。
Step 1: VB6 事件分发表
VB6 native 程序给每个控件事件编一个 id,进入事件时用一长串
sub dword ptr [esp+4], id + jmp handler
分发。把这套 81 6c 24 04 <id> e9 <rel32>
模式扫出来:
1 | $ objdump -d -M intel app4win.exe > out/app4.asm |
核心分发在这几行(VA 0x40247c 起):
1 | 40247c: 81 6c 24 04 33 00 00 00 sub DWORD PTR [esp+0x4],0x33 |
event id 0x33 是建窗口,0x37
指上按钮、0x3b 指下按钮;每个按钮各有一对「MouseMove /
Click」处理函数。
Step 2: 确认「点不到」的原因
上按钮的 MouseMove 处理函数 0x402810
里,第一步就是对这个按钮自己调
EnableWindow(hwnd, FALSE):
1 | 40286d: 8b f8 mov edi,eax |
0x4029d0(下按钮
MouseMove)是镜像逻辑:禁用下按钮、启用上按钮。于是鼠标一进入某个按钮它就自我禁用,Click
永远触发不了。真正的密码逻辑在 Click 处理函数
0x402ad0 / 0x403170
里,不是被禁用的那一边。
Step 3: 从 Click 处理函数重建密码
0x402ad0 逐字符调用 rtcVarBstrFromAnsi
生成单字符 BSTR:
1 | 402b12: 8b 3d 54 10 40 00 mov edi,DWORD PTR ds:0x401054 ; rtcVarBstrFromAnsi |
每个字符的 immediate 按地址顺序连起来就是消息串。
1 | #!/usr/bin/env python3 |
1 | $ cd <hts-workspace> && uv run python challenges/hts-app/app4/extract_app4_password.py challenges/hts-app/app4/win/app4win.exe |
下按钮的 Click 处理函数 0x403170
建的是同一个串(push 0x50 … push 0x27,21
个字符),两条链互相印证。0x402cee 起的
__vbaVarCat 序列把这段 21 字符的串接起来,最后
__vbaNew2(0x401064)造出弹窗对象显示:
1 | 402d00: ff 15 64 10 40 00 call DWORD PTR ds:0x401064 ; __vbaNew2 |
Step 4: Patch 让鼠标「按下」上按钮
既然上按钮的
MouseMove(0x402810)会自我禁用,把分发表里指向它的那个
jmp 改成指向真正的 Click 处理函数 0x402ad0
即可 —— 鼠标一进按钮就等于按下了它。要改的指令在文件偏移
0x249e(VA 0x40249e):
1 | $ xxd -s 0x2496 -l 16 app4win.exe |
e9 6d 03 00 00 是
jmp 0x402810;rel32 相对指令末尾
0x4024a3 计算,新目标 0x402ad0 对应
rel = 0x402ad0 - 0x4024a3 = 0x62d。
1 | #!/usr/bin/env python3 |
1 | $ cd <hts-workspace> && uv run python challenges/hts-app/app4/patch_app4.py challenges/hts-app/app4/win/app4win.exe challenges/hts-app/app4/out/app4win_patched.exe |
反汇编验证补丁生效:
1 | $ objdump -d -M intel --start-address=0x402496 --stop-address=0x4024a3 app4win_patched.exe |