4.3 解密技术中的相关问题
学习解密技术的过程中涉及一些常见问题,用户只有理解这些问题的内涵才能更进一步地学习。下面就详细介绍一下在解密过程中经常涉及的几个问题。
4.3.1 软件的破解方式
通常将软件破解方式分为两种:完全破解和暴力破解。
所谓完全破解主要是针对那些需要输入注册码或密码等的软件来说的,如果能通过对程序的跟踪找到正确的注册码,通过软件本身的注册功能正常注册了软件,这样的破解称为完全破解。
如果有些软件本身没有提供注册功能,只是提供试用(DEMO)或注册不能通过软件本身进行(例如需要获取另外一个专用的注册程序,通过Internet的注册等),或软件本身的加密技术比较复杂,软件破解者的能力、精力、时间有限,不能直接得到正确的注册码,此时需要去修改软件本身的程序码,即人为改变软件的运行方向,这样的破解称为暴力破解。
4.3.2 破解教程中程序代码地址问题
破解教程中通常都会放上一部分程序代码,以帮助讲解程序的分析方法,例如,下面的一段程序代码。
... 0167:00408033 PUSH 00 0167:00408035 PUSH EBX 0167:00408036 CALL [USER32! EndDialog] 0167:0040803C JMP 0040812C ...
在这里程序中的代码地址如0167:00408033,其代码段的值(即0167)有可能根据不同的计算机而有所区别,不一定会一模一样,但偏移值应该是固定的(即00408033不变)。因此,如果看到破解文章中程序代码的地址值和自己计算机里的不一样,千万不要以为自己搞错地方了,只要程序代码正确就不会有问题。
4.3.3 如何设置断点的问题
正确恰当地设置好断点对于快速有效地解密非常重要,好的断点设置可以迅速找到关键的程序段,而不恰当的断点则会对解密造成不必要的精力消耗,甚至根本就不能拦截到程序的运行。
但具体什么时候用什么断点比较合适很难说,这需要自己用经验去累积。总的说来,Bpx Hmemcpy这个万能断点对大多数注册码方式的软件都有用。
对于那些需要暴力破解的非注册码方式的软件,通常应该拦截对话框(如Bpx DialogBox)和消息框(如Bpx MessageBox(A))等。不论对于哪一类软件,当设置的断点均没有效果时,可以试一下Bpx Lockmytask,这个断点的作用是拦截任何一个按键的动作。
另外,在注册码的破解中通常需要输入用户名和注册码,一般说来用户名和密码都可以随意输入。但根据经验,很多软件对于注册码都会逐位地进行处理,假如输入“78787878”这串数字,那么在跟踪程序时就无法知道当时所看到的“78”到底是哪一个“78”,所以比较喜欢用“12345678”这样的注册码输入方式,这样就能知道程序是在对注册码的哪一位进行运算。
同样,对于那些需要输入较长序列号的软件,输入类似“12345-67890-ABCDEF”这样的序列号较好。
不过有一点需要特别注意。
注册码输入方式“12345678”是针对拦截Win32 API函数而言的,假如有些时候直接拦截Win32 API函数难以找到程序的突破口,而要借助于“S”指令在内存中寻找输入的用户名或注册码时,就最好不要采用“12345678”作为注册码,因为内存中很可能有许多的“12345678”字符串,这样就没有办法知道到底要破解的程序使用的是哪一个“12345678”,所以应该选择一个不易和内存数据相同的注册码。
具体用什么样的输入形式可以根据本人的爱好、习惯来定,不必拘泥于某一固定的模式。
4.3.4 如何跟踪程序的问题
初学者在开始学习解密时往往不知道怎样去跟踪程序,当面对长长的一堆程序代码时往往显得不知所措。
通常,软件的程序内部都会利用一个子程序(即CALL ********)去验证输入的注册码正确与否,对于注册码显式存在的程序,一般都会将所输入的注册码和正确的注册码放进寄存器,然后调用验证子程序进行判断,将结果返回,应用程序根据子程序返回的结果决定是否注册成功,这样的程序经常具有如下形式。
****:******** MOV EAX, [********](或PUSH EAX等形式) ****:******** MOV EDX, [********](或PUSH EDX等形式) ****:******** CALL ******** ****:******** TEST EAX, EAX(或TEST AL, AL,或是没有这一句等形式) ****:******** JNZ ********(或JZ ********等形式)
其中EAX和EDX指向的内存区域就是输入的注册码和正确的注册码,这里的寄存器EAX和EDX是随意写的,也可以是ECX、EBX、EDI、ESI等。
对于注册码隐式存在的程序,虽然不能直接看到正确的注册码,但通常也是先将所输入的注册码地址放进某个寄存器,然后调用子程序去验证,破解时就需要进入子程序去分析注册算法。
总之,看到子程序(call ********)后面跟着跳转指令(JNZ ********或JZ ********)的地方就应该提高警惕,多用D EAX(或EBX、ECX、EDX、EDI、ESI等)去看看寄存器指向的内存区域藏着什么东西。
看见程序中使用GetDlgItenInt函数时要注意,这个API函数的作用是将输入的文本转化为整数,所以这类程序中是不会显示存在注册码的,因为注册码被转换为整数了,程序通常会用CMP ECX、EDX这种类型的指令去验证注册码的正确性。这里ECX和EDX中存储的就是所输入注册码和正确注册码的整数形式,此时可以用 ? edx和 ? ecx查看其十进制形式,即输入的形式。
4.3.5 软件的反安装问题
经常使用某些软件时都会遇到一个问题,就是共享软件过期之后,即使删掉原程序重新安装,程序依然不能用,还是一样提醒试用期已过请注册;或者是已经破解了某个软件,但还想继续研究它,却因为软件已经注册好而没有了注册选项,这时即使彻底删掉程序再重新安装软件,结果程序运行后还是注册过的。
之所以会出现这样的情况,其实原因很简单,因为程序将注册或过期信息存在了系统注册表中,所以简单地重新安装软件是无济于事的。
解决的办法就是自己删掉注册表中有关的信息,但因为注册表是Windows系统工作的基础,如果不小心很可能会因损坏它而引起系统异常。因此,如果对注册表不是很熟,最好在修改之前备份一下。
不论是修改还是备份注册表,都可以使用Windows系统下的注册表管理工具“REGEDIT”来进行,大部分的应用软件都会将自己的信息存在如下的路径中:HKEY_LOCAL_ MACH INE\Software、HKEY_LOCAL_MACHINE\Software\Microsoft、HKEY_CURRENT_USER\Soft ware\HKEY_CURRENT_USER\Software\Microsoft或HKEY_USERS\.DEFAULT\Software分支下,具体是哪个地方依据不同的程序而有所不同,只要按上面的顺序,肯定能找到有关应用程序的键,然后将和用户名及注册码有关的键值删掉就可以了。