品茗施工资料制作与管理系统ver3.0.0.1180完全破解详细说明(内存补丁)
上次写的破解文章过于简单,存在许多漏洞,条理也不清楚,在了解了一些SEH后,
对破解有很大帮助,所以重写一篇以改正补遗。
[软件名称]:品茗施工资料制作与管理系统
[软件加密方式]:Armadilo2.5的壳+狗狗(?)
[解密工具]: softice(名牌),FrogsICE(隐藏ice),spy(在最后阶段用于查看窗口句柄)
[软件症状]:有4点疑症。
一. 程序启动一段时间Nag框后,自行退出程序,无法使用该程序。
(下面的3个问题是将第一个问题解决后引起的)
二. 无法新建工程。
三. 新建工程后,打印和预览菜单被灰化。
四. 无法退出程序。
[解决办法]:
一. 程序启动一段时间Nag框后,自行退出程序。
下断 bpx postquitmessage,来到下面关键处:
016F:00477DBC CALL 004107C8
016F:00477DC1 TEST AL,AL ;关键,条件判断语句(每20秒会来此一次)
016F:00477DC3 JNZ 00477DCC;不跳走就会调用下面的PostQuitMessage
016F:00477DC5 PUSH 00
016F:00477DC7 CALL USER32!PostQuitMessage
016F:00477DCC RET
做内存修改JZ 477DCC后,程序启动进入主用户界面,一切似乎正常。
但在操做过程中发现无法真正新建工程,这可是此软件的主要功能。还有,
程序无法正常退出,因为跳过了PostQuitMessage,所以windows发出退出
消息主程序无法收到。
请继续看下文。
二. 无法新建工程。
进入新建工程界面,下断bpx hmemcpy。来到下面:
程序有SEH处理,要避开引起SEH的程序段,否则就无法真正新建工程,
仔细查看跟踪调试,发现3处可疑。并找到正确的SEH结束。
016F:0067C10E CALL 00455EA4
016F:0067C113 MOV EAX,[ESI]
016F:0067C115 MOV AL,[EAX+00000330]
016F:0067C11B MOV [EBP-35],AL
016F:0067C11E MOV EAX,[ESI]
016F:0067C120 CALL 004041E8
016F:0067C125 XOR EDX,EDX
016F:0067C127 PUSH EBP
016F:0067C128 PUSH 0067C4E5 ;SEH安全地址
016F:0067C12D PUSH DWORD PTR FS:[EDX] ;SEH句柄
016F:0067C130 MOV FS:[EDX],ESP
016F:0067C133 LEA EAX,[EBP-18];1.会引起SEH的call,在此改为JMP 0067C1FA
016F:0067C136 CALL 00667A0C ;下面有很多引起结构异常的代码。
016F:0067C138 MOV EAX,C084FFFE
016F:0067C13D JNZ 0067C14C
016F:0067C13F XOR EAX,EAX
016F:0067C141 POP EDX
016F:0067C142 POP ECX
016F:0067C143 POP ECX
016F:0067C144 MOV FS:[EAX],EDX
016F:0067C147 JMP 0067C634
016F:0067C14C LEA EAX,[EBP-20]
016F:0067C14F PUSH EAX
016F:0067C150 MOV EAX,[EBP-18]
016F:0067C153 CALL 006678FC
016F:0067C158 LEA ECX,[EBP-1C]
016F:0067C15B MOV EDX,00000002
016F:0067C160 CALL 005DB194
016F:0067C165 TEST AL,AL
016F:0067C167 JNZ 0067C176
016F:0067C169 XOR EAX,EAX
016F:0067C16B POP EDX
016F:0067C16C POP ECX
016F:0067C16D POP ECX
016F:0067C16E MOV FS:[EAX],EDX
016F:0067C171 JMP 0067C634
016F:0067C176 MOV EAX,[EBP-18]
016F:0067C179 CALL 006678FC
016F:0067C17E LEA EDX,[EBP-24]
016F:0067C181 CALL 00667A30
016F:0067C186 TEST AL,AL
016F:0067C188 JNZ 0067C197
016F:0067C18A XOR EAX,EAX
016F:0067C18C POP EDX
016F:0067C18D POP ECX
016F:0067C18E POP ECX
016F:0067C18F MOV FS:[EAX],EDX
016F:0067C192 JMP 0067C634
016F:0067C197 PUSH 0067C6F4
016F:0067C19C PUSH DWORD PTR [EBP-1C]
016F:0067C19F PUSH 0067C704
016F:0067C1A4 LEA EAX,[EBP-50]
016F:0067C1A7 MOV EDX,00000003
016F:0067C1AC CALL 004052FC
016F:0067C1B1 MOV EAX,[EBP-50]
016F:0067C1B4 PUSH EAX
016F:0067C1B5 PUSH 0067C6F4
016F:0067C1BA MOV EAX,[EBP-24]
016F:0067C1BD CALL 0040A434
016F:0067C1C2 INC EAX
016F:0067C1C3 LEA EDX,[EBP-5C]
016F:0067C1C6 CALL 0040A394
016F:0067C1CB MOV EAX,[EBP-5C]
016F:0067C1CE LEA EDX,[EBP-58]
016F:0067C1D1 CALL 00667AF4
016F:0067C1D6 PUSH DWORD PTR [EBP-58]
016F:0067C1D9 PUSH 0067C704
016F:0067C1DE LEA EAX,[EBP-54]
016F:0067C1E1 MOV EDX,00000003
016F:0067C1E6 CALL 004052FC
016F:0067C1EB MOV EDX,[EBP-54]
016F:0067C1EE POP EAX
016F:0067C1EF CALL 00405380
016F:0067C1F4 JNZ 0067C31D
016F:0067C1FA MOV EBX,00000001
016F:0067C1FF MOV EAX,EBX
016F:0067C201 IMUL EBX
016F:0067C203 LEA EAX,[EAX*2+EAX]
016F:0067C206 MOV EDX,EBX
016F:0067C208 SHL EDX,03
016F:0067C20B SUB EDX,EBX
016F:0067C20D ADD EAX,EDX
016F:0067C20F ADD EAX,0D
016F:0067C212 MOV ESI,EAX
016F:0067C214 ADD EAX,000001BC
016F:0067C219 LEA EDX,[ESI+000001BC]
016F:0067C21F CMP EAX,EDX
016F:0067C221 JZ 0067C22F
016F:0067C223 MOV EAX,[006A0DAC]
016F:0067C228 MOV EAX,[EAX]
016F:0067C22A CALL 00477DBC
016F:0067C22F CMP EBX,00001613
016F:0067C235 JNZ 0067C30B
016F:0067C23B MOV EAX,EBX
016F:0067C23D IMUL EBX
016F:0067C23F LEA EAX,[EAX*2+EAX]
016F:0067C242 MOV EDX,EBX
016F:0067C244 SHL EDX,03
016F:0067C247 SUB EDX,EBX
016F:0067C249 ADD EAX,EDX
016F:0067C24B ADD EAX,0D
016F:0067C24E ADD EAX,000001A6
016F:0067C253 ADD ESI,000001A6
016F:0067C259 CMP EAX,ESI
016F:0067C25B JNZ 0067C30B
016F:0067C261 PUSH 0067C714
016F:0067C266 PUSH DWORD PTR [EBP-1C]
016F:0067C269 PUSH 0067C724
016F:0067C26E LEA EAX,[EBP-60]
016F:0067C271 MOV EDX,00000003
016F:0067C276 CALL 004052FC
016F:0067C27B MOV EAX,[EBP-60]
016F:0067C27E PUSH EAX
016F:0067C27F PUSH 0067C714
016F:0067C284 MOV EAX,[EBP-24]
016F:0067C287 CALL 0040A434 ;2. 会引起SEH的CALL 0040A434,
016F:0067C28C INC EAX ;占5个字节,用5个NOP代替
016F:0067C28D LEA EDX,[EBP-6C]
016F:0067C290 CALL 0040A394
016F:0067C295 MOV EAX,[EBP-6C]
016F:0067C298 LEA EDX,[EBP-68]
016F:0067C29B CALL 00667AF4
016F:0067C2A0 PUSH DWORD PTR [EBP-68]
016F:0067C2A3 PUSH 0067C724
016F:0067C2A8 LEA EAX,[EBP-64]
016F:0067C2AB MOV EDX,00000003
016F:0067C2B0 CALL 004052FC
016F:0067C2B5 MOV EDX,[EBP-64]
016F:0067C2B8 POP EAX
016F:0067C2B9 CALL 00405380
016F:0067C2BE JNZ 0067C30B ;3. 跳走就over,改为JZ
016F:0067C2C0 CALL 0040D1CC
016F:0067C2C5 FLD REAL10 PTR [0067C72C]
016F:0067C2CB FSUBP ST(1),ST
016F:0067C2CD FLD REAL10 PTR [0067C72C]
016F:0067C2D3 FSUBR REAL8 PTR [EBP-30]
016F:0067C2D6 FLD REAL10 PTR [0067C738]
016F:0067C2DC FADDP ST(1),ST
016F:0067C2DE FCOMPP
016F:0067C2E0 FSTSW AX
016F:0067C2E2 SAHF
016F:0067C2E3 JAE 0067C2F2
016F:0067C2E5 XOR EAX,EAX
016F:0067C2E7 POP EDX
016F:0067C2E8 POP ECX
016F:0067C2E9 POP ECX
016F:0067C2EA MOV FS:[EAX],EDX :SEH结束
016F:0067C2ED JMP 0067C634 ;安全结束
016F:0067C2F2 LEA EAX,[EDI+0000DCF5]
016F:0067C2F8 MOV EDX,[EBP-04]
016F:0067C2FB MOV [EDX+00000858],EAX
016F:0067C301 MOV EAX,EBX
016F:0067C303 SHL EAX,03
修改如下:
016F:0067C133 LEA EAX,[EBP-18] 改为JMP 0067C1FA
016F:0067C287 CALL 0040A434 用5个NOP
016F:0067C2BE JNZ 0067C30B 改为JZ 0067C30B
如此修改后,程序可以新建工程,好象一切正常。但又有问题,
表格处理中有二个菜单项被灰化了,无法打印和预览
三. enable被灰化的菜单项和enable其功能:打印和预览
bpx enablemenuitem,中断返回016F:004685B6后,往上看:
016F:0046854A MOV EAX,EAX
016F:0046854C PUSH EBX
016F:0046854D PUSH ESI
016F:0046854E PUSH EDI
016F:0046854F MOV EBX,EDX
016F:00468551 MOV ESI,EAX
016F:00468553 CMP BL,[ESI+39]
016F:00468556 JZ 004685BF ;改为jmp 4685BF
016F:00468558 MOV [ESI+39],BL ;避开EnableMenuItem
016F:0046855B MOV EAX,[006A1160] ;有个缺点,管理员和操作员。
016F:00468560 CMP DWORD PTR [EAX],02
016F:00468563 JNZ 00468570 ;菜单没有区别了
016F:00468565 MOV EAX,ESI
016F:00468567 CALL 00468620
016F:0046856C TEST EAX,EAX
016F:0046856E JNZ 0046857D
016F:00468570 MOV EDI,[ESI+64]
016F:00468573 TEST EDI,EDI
016F:00468575 JZ 00468588
016F:00468577 CMP DWORD PTR [EDI+6C],00
016F:0046857B JZ 00468588
016F:0046857D MOV DL,01
016F:0046857F MOV EAX,ESI
016F:00468581 MOV ECX,[EAX]
016F:00468583 CALL [ECX+3C]
016F:00468586 JMP 004685BF
016F:00468588 MOV EDI,[ESI+64]
016F:0046858B TEST EDI,EDI
016F:0046858D JZ 004685B6
016F:0046858F TEST BYTE PTR [ESI+1C],02
016F:00468593 JNZ 004685B6
016F:00468595 XOR EAX,EAX
016F:00468597 MOV AL,BL
016F:00468599 MOV EAX,[EAX*4+0069AE54]
016F:004685A0 OR EAX,00
016F:004685A3 PUSH EAX
016F:004685A4 MOVZX EAX,WORD PTR [ESI+50]
016F:004685A8 PUSH EAX
016F:004685A9 MOV EAX,EDI
016F:004685AB CALL 00466CE8
016F:004685B0 PUSH EAX
016F:004685B1 CALL USER32!EnableMenuItem
016F:004685B6 XOR EDX,EDX
016F:004685B8 MOV EAX,ESI
016F:004685BA MOV ECX,[EAX]
016F:004685BC CALL [ECX+3C]
016F:004685BF POP EDI
016F:004685C0 POP ESI
016F:004685C1 POP EBX
此时菜单没有被灰化,但没有功能调用,要找出其功能。
用spy找到窗口句柄,我的是a94,下断bmsg a94 wm_command,点击打印,
中断返回到:
016F:00463171 CMP BYTE PTR [EBX+6A],00
016F:00463175 JZ 0046318D
016F:00463177 CMP BYTE PTR [EBX+00000095],00
016F:0046317E JZ 0046318D
016F:00463180 MOV DL,[EBX+69]
016F:00463183 XOR DL,01
016F:00463186 MOV EAX,EBX
016F:00463188 CALL 00462C74
016F:0046318D CMP BYTE PTR [EBX+6A],00
016F:00463191 JZ 0046319E ;此处不要跳走就对了!
016F:00463193 MOV EAX,EBX
016F:00463195 CALL 004624EC
016F:0046319A TEST AL,AL
016F:0046319C JNZ 004631A2
016F:0046319E XOR EAX,EAX
016F:004631A0 JMP 004631A4
016F:004631A2 MOV AL,01
016F:004631A4 POP EBX
016F:004631A5 RET
但还有最后一个问题:当退出程序时,不能总强行中止吧。
用ctr+alt+del,这也太不专业了。:)
四. 无法正确退出程序。
用spy查看程序主窗口的句柄,我的是450,下断bmsg 450 wm_close,
按下窗口上的关闭X,拦下后,按F12返回很多次(我都记不清了,可能少于40次,
呵呵)。也可用bmsg 450 wm_command.
016F:004743E0 PUSH EBX
016F:004743E1 PUSH ESI
016F:004743E2 PUSH ECX
016F:004743E3 MOV EBX,EAX
016F:004743E5 TEST BYTE PTR [EBX+000002EC],08
016F:004743EC JZ 004743FD
016F:004743EE MOV DWORD PTR [EBX+0000024C],00000002
016F:004743F8 JMP 0047447D
016F:004743FD MOV EAX,EBX
016F:004743FF MOV EDX,[EAX]
016F:00474401 CALL [EDX+000000E0]
016F:00474407 TEST AL,AL
016F:00474409 JZ 0047447D
016F:0047440B CMP BYTE PTR [EBX+0000022F],01
016F:00474412 JNZ 00474429
016F:00474414 TEST BYTE PTR [EBX+00000228],02
016F:0047441B JZ 00474423
016F:0047441D MOV BYTE PTR [ESP],03
016F:00474421 JMP 0047442D
016F:00474423 MOV BYTE PTR [ESP],00
016F:00474427 JMP 0047442D
016F:00474429 MOV BYTE PTR [ESP],01
016F:0047442D MOV EDX,ESP
016F:0047442F MOV EAX,EBX
016F:00474431 MOV SI,FFB0
016F:00474435 CALL 004043E4
016F:0047443A CMP BYTE PTR [ESP],00
016F:0047443E JZ 0047447D
016F:00474440 MOV EAX,[006A2C34]
016F:00474445 CMP EBX,[EAX+44]
016F:00474448 JNZ 00474456
016F:0047444A MOV EAX,[006A2C34]
016F:0047444F CALL 00477DBC ;关键。
016F:00474454 JMP 0047447D
016F:00474456 CMP BYTE PTR [ESP],01
016F:0047445A JNZ 00474465
016F:0047445C MOV EAX,EBX
016F:0047445E CALL 00474580
016F:00474463 JMP 0047447D
016F:00474465 CMP BYTE PTR [ESP],03
016F:00474469 JNZ 00474476
016F:0047446B MOV DL,01
016F:0047446D MOV EAX,EBX
016F:0047446F CALL 004721B0
016F:00474474 JMP 0047447D
016F:00474476 MOV EAX,EBX
016F:00474478 CALL 0047461C
016F:0047447D POP EDX
016F:0047447E POP ESI
016F:0047447F POP EBX
016F:00474480 RET
找到关键:CALL 00477DBC,内有一条判断语句(见下),因为修改了在解决第一
个问题时,改JZ为JNZ所以就一直退不出程序了。在此用了一个技巧:
直接跳到477DC5处,
即用JMP 477DC5取代此CALL 00477DBC,
避开477DC3处的JNZ 00477DCC, 直接调用postquitmessage。
呵呵,成功退出。
016F:00477DBC CALL 004107C8
016F:00477DC1 TEST AL,AL
016F:00477DC3 JNZ 00477DCC
016F:00477DC5 PUSH 00
016F:00477DC7 CALL USER32!PostQuitMessage
016F:00477DCC RET
[总结]:4个问题的4处内存补丁。制做内存补丁机,用ppatcher。
格式:address=内存地址:原16进制:修改的16进制
1. 解决程序启动一段时间后,自行退出程序。
address=0x477dc3:0x74:0x75 ;将JZ改为JNZ ,不理会PostQuitMessage
2. 解决无法新建工程。
address=0x67c133:0x8d:0xe9 ;将67C133处改为JMP 67C1FA
address=0x67c134:0x45:0xc2
address=0x67c135:0xe8:0x00
address=0x67c136:0xe8:0x00
address=0x67c137:0xd1:0x00
address=0x67c287:0xe8:0x90 ;将CALL 0040A434用5个NOP
address=0x67c288:0xa8:0x90
address=0x67c289:0xe1:0x90
address=0x67c28a:0xd8:0x90
address=0x67c28b:0xff:0x90
address=0x67c2be:0x75:0x74 ;JNZ 改为JZ
3. 解决被灰化的菜单项和enable其功能
address=0x468556:74:EB JZ改为jmp
address=0x463191:74:75 JZ 改为JZN
4. 解决无法正确退出程序。
address=0x47444f:0xe8:0xe9 ;将CALL 00477DBC改为JMP 477DC5
address=0x474450:0x68:0x71 ;可以退出。直接调用PostQuitMessage
5. 相关系列软件可用同样思路。文中如有不正确和遗漏的地方,还欢迎各位大侠指正,以帮助我学习提高。
版权所有,1998-2005
[培训]内核驱动高级班,冲击BAT一流互联网大厂工作,每周日13:00-18:00直播授课