初练160个CrakeMe程序之003
本帖最后由 海天一色001 于 2017-4-24 17:15 编辑AfKayAs.2,先运行,看看具体情况:
要求是杀掉NAG窗口,并找到注册码。第一个启动的窗口感觉停留的时间还挺长,要求是杀掉它,但是现在对它还是无能为力,先完成下一个要求,找到注册码吧。用户名清空,点“OK”,弹出错误信息框,说明用户名不能为空:
再输入用户名:www.52pojie.cn,下面的注册码先不输入,点“OK”,弹出错误信息框,再点“确定”程序退出了。注册码再随意填写其他内容,同样弹出这个信息框。
类型不匹配?正确的类型又是什么呢?
反复试验,原来是注册码数字之外的字符都要报错!可是如果只是这个类型不匹配范围太大了点吧!查看一下这里也浪费了不少时间。待会从OD里查找一下是哪里在判断类型的地方。(找了很多遍,还是没找到在哪里!在网上查到了一个VB6函数VarType(varname) ,这个函数返回一个整数:还有一个是TypeName(varname)函数,返回变量类型的名称,返回值为字符串类型,但从程序中也没找到)。
先爆破再算注册码,最后去弹窗。
OD载入,智能查找字符串,只有这么几个,明显是弹出对话框的内容,和CrackMe002一样,应该爆破点和算法都一样吧。继续下去:
随意双击一个错误的提示进入CPU界面:
很熟悉的地方,向上找到了跳过失败的jmp,以及让这个jmp没有运行的另一个跳转的地方。
顺着红线向上找到了地址:00408677处,命令是je XAfKayAs_.004086DB;跳过了成功,那么F2下断点,再用nop改掉这一句,
再f9运行,输入用户名“www.52pojie.cn”,注册码一长串的“1”,点击“OK”,程序断在了这里,继续F9,如图成功爆破。程序另存为一个新文件即可。
按照上一个程序的思路,注册算法在这个段内,向上找段首,还是很长很长的一段!来到了这里,
004080F0 > \55 push ebp ;计算判断注册码的段首
004080F1 .8BEC mov ebp,esp
004080F3 .83EC 0C sub esp,0xC
004080F6 .68 56104000 push <jmp.&MSVBVM50.__vbaExceptHandler>;SE 处理程序安装
对004080F0下断,然后重载程序,F9运行,暂停后单步向下,很快就看到了可疑字符串“1244551”,先复制下来;继续向下,怎么又出来一个“1244553”?再复制下来;继续单步运行,这个“3733657”是怎么回事?还有一个“3733672”又是怎么来的?继续单步走,终于来到了关键跳处,跳过了成功。严重怀疑最后一个字符串是正确的注册码,复制粘贴,点“OK”,成功。看来是得到“1244551”后又经一堆的VB函数运算才得到了这个结果,只能再返回去单步走了。经过多次重复,才勉强弄明白了,原来这个程序利用了浮点运算使计算过程增加了许多,也逼着我对汇编语言进行了一定地学习和熟悉。
这个注册算法大概分了四部分:
第一部分:004081E9 > \8B95 50FFFFFF mov edx,dword ptr ss:
004081EF .8B45 E4 mov eax,dword ptr ss: ;取用户名
004081F2 .50 push eax ; /String=”www.52pojie.cn”
004081F3 .8B1A mov ebx,dword ptr ds: ; |
004081F5 .FF15 F8B04000 call dword ptr ds:[<&MSVBVM50.__vbaLenBs>; \取用户名长度,存入eax中 eax=0x0000000E
004081FB .8BF8 mov edi,eax
004081FD .8B4D E8 mov ecx,dword ptr ss:
00408200 .69FF 385B0100 imul edi,edi,0x15B38 ;edi=edi*0x15b38=0x0012FD10
00408206 .51 push ecx ; /String=”w”
00408207 .0F80 B7050000 jo AfKayAs_.004087C4 ; |溢出则跳
0040820D .FF15 0CB14000 call dword ptr ds:[<&MSVBVM50.#516>] ; \得到用户名第一个字的ansi值,存入ax ax=0x77
00408213 .0FBFD0 movsx edx,ax
00408216 .03FA add edi,edx ;edi=edi+edx(edx即用户名第一个字的ansi值)= 0x0012FD87
00408218 .0F80 A6050000 jo AfKayAs_.004087C4 ;溢出则跳
0040821E .57 push edi
0040821F .FF15 F4B04000 call dword ptr ds:[<&MSVBVM50.__vbaStrI4>;edi结果转换成10进制数“1244551”,存入eax中
第二部分:
004082DD > \8B8D 58FFFFFF mov ecx,dword ptr ss:
004082E3 .8B55 E8 mov edx,dword ptr ss: ; 取字符串1244551
004082E6 .52 push edx
004082E7 .8B19 mov ebx,dword ptr ds:
004082E9 .FF15 74B14000 call dword ptr ds:[<&MSVBVM50.__vbaR8Str>;将字符串转成浮点型(8个字节)的数值形式
004082EF .D905 08104000 fld dword ptr ds: ;把ecx指向的数据当作浮点数载入浮点堆栈中
004082F5 .833D 00904000>cmp dword ptr ds:,0x0 ;比较0与堆栈中的值大小
004082FC .75 08 jnz XAfKayAs_.00408306
004082FE .D835 0C104000 fdiv dword ptr ds: ;浮点除法:st=st/ds=10/5=2
00408304 .EB 0B jmp XAfKayAs_.00408311
00408306 >FF35 0C104000 push dword ptr ds:
0040830C .E8 578DFFFF call <jmp.&MSVBVM50._adj_fdiv_m32>
00408311 >83EC 08 sub esp,0x8
00408314 .DFE0 fstsw ax ;把状态寄存器的值传送给AX
00408316 .A8 0D test al,0xD
00408318 .0F85 A1040000 jnz AfKayAs_.004087BF
0040831E .DEC1 faddp st(1),st ;st(0) = st(1) + st(0)=1244553
00408320 .DFE0 fstsw ax ;把状态寄存器的值传送给AX
00408322 .A8 0D test al,0xD
00408324 .0F85 95040000 jnz AfKayAs_.004087BF
0040832A .DD1C24 fstp qword ptr ss: ;把ST(0)中的值作为浮点数 保存到 SS段地址为ebp-0xE4处
0040832D .FF15 48B14000 call dword ptr ds:[<&MSVBVM50.__vbaStrR8>;MSVBVM50.__vbaStrR8 将实数转化成字符串存入eax中eax=1244553
00408333 .8BD0 mov edx,eax
00408335 .8D4D E4 lea ecx,dword ptr ss:
00408338 .FF15 94B14000 call dword ptr ds:[<&MSVBVM50.__vbaStrMo>;MSVBVM50.__vbaStrMove 移动字符串
第三部分:
004083E9 > \8B8D 58FFFFFF mov ecx,dword ptr ss:
004083EF .8B55 E8 mov edx,dword ptr ss: 取字符串1244553
004083F2 .52 push edx
004083F3 .8B19 mov ebx,dword ptr ds:
004083F5 .FF15 74B14000 call dword ptr ds:[<&MSVBVM50.__vbaR8Str>;MSVBVM50.__vbaR8Str将字符串转为浮点型(8个字节)的数值形式
004083FB .DC0D 10104000 fmul qword ptr ds: ;st(0)=st*ds:=1244553*3=3733659
00408401 .83EC 08 sub esp,0x8
00408404 .DC25 18104000 fsub qword ptr ds: ;st(0)=st(0)-ds:=3733659-2=3733657
0040840A .DFE0 fstsw ax
0040840C .A8 0D test al,0xD
0040840E .0F85 AB030000 jnz AfKayAs_.004087BF
第四部分:
004084D3 > \8B8D 58FFFFFF mov ecx,dword ptr ss:
004084D9 .8B55 E8 mov edx,dword ptr ss: ;取字符串3733657
004084DC .52 push edx
004084DD .8B19 mov ebx,dword ptr ds:
004084DF .FF15 74B14000 call dword ptr ds:[<&MSVBVM50.__vbaR8Str>;MSVBVM50.__vbaR8Str
004084E5 .DC25 20104000 fsub qword ptr ds: ;st(0)=st(0)-(-15)=st(0)+15=3733672
004084EB .83EC 08 sub esp,0x8
004084EE .DFE0 fstsw ax
004084F0 .A8 0D test al,0xD
004084F2 .0F85 C7020000 jnz AfKayAs_.004087BF
注册算法出来了:先得到用户名的长度,乘以0x15B38,再加上用户名第一个字符的16进制ansi值,转换成10进制值后,加2,乘3,减2,加15。也可以先转成10进制再运算,更简单一些。
注册机仍用VB编写:
Private Sub Command1_Click()
Dim str1, lend, str2, str3
If Text1.Text <> "" Then
str1 = (Text1.Text)
lend = Len(str1)
str2 = lend * 88888
str3 = (Asc(str1) + str2 + 2) * 3 + 13
Text2.Text = str3
Else: MsgBox ("用户名不能为空!")
End If
End Sub
4/18/2017 5:06:53 PM
该去弹窗了!
4/19/2017 2:30:10 PM
折腾了很多遍,总是不成功!盼有大神指点啊!!!
我的思路:两个窗体,程序启动时先加载第一个,7秒后卸载自己,再装载第二个,这两个窗体之间没有参数传递之类的,只是一个显示顺序(一个加载一个不加载)的问题,可以更改启动顺序或者是直接启动第二个窗体,不启动第一个窗体。想法很美好,现实很残酷,在OD中我无法实现自己的想法!参考其他人类似的方法,都是修改timer控件的时间参数7000为1,窗体改小,或者窗体出现的位置设到屏幕外等,这些方法只能说是半成功吧,毕竟窗还是运行了,而不是不再运行这个窗体了。
自己想直接调用第二个窗体,怎么弄都不行。确实是没有办法了。
无奈之下,想到自己用VB仿一个程序出来,再反汇编一下,看看情况,还是傻眼了:自己编的程序,只是编写了两个空窗体(form1和form2),什么东西都没有,只能在VB中工程属性里更改启动顺序,一旦编译成exe文件,在OD中一样找不到在什么地方可以更改窗体显示顺序或者NAG干掉!
再次呼唤大神的帮助!
汉化:汉化过程也是很无奈。
首先用OD查找字符串,很容易就看到了上方的界面,随意双击了“You Get It”后进入CPU窗口,Push后面有一个地址,这个地址明显是.text里面的,说明是固定的,可以修改。那么其他的有这样特征的字符串应该都能很轻松地修改吧。试试。
双击任一字符串进入CPU窗口,右键到立即数,下方的数据窗口即到了这些地址,可以进行修改了。
可以看出这些是Unicode码,用二进制进行编辑(Ctrl+E),修改时也是在UNICODE那一栏中进行修改,然后保存到可执行文件,一切都很顺利,等到一运行,不对了!!!
汉字没了,一堆乱码????????
在这里是可以改的啊!为什么出错????又上网查,看视频,仍然没找到在OD中进行修改的解决办法。无奈之下,使用了GetVBRes这个工具才修改了部分英文。
由此可见,自己仍是菜鸟级别,此次练习003的过程中最后两个问题(去弹窗和汉化)太令人头疼了,希望能得到论坛中各位的帮助啊。
附件是源程序及自己部分汉化的程序及注册程序,在百度网盘上也有:
链接: http://pan.baidu.com/s/1nviCB7F 密码: 2cfb 厉害厉害,,,。 感谢分享,共同成长{:17_1060:} 666666666666666666 学习了!感谢搂住的经验心得 学习了,谢谢啊 弹窗我也没去掉{:1_923:} 弹窗我也没去掉.... 感谢大佬给入门的菜鸡提供资源和帮助
页:
[1]