欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  网络运营

破解CuteFTP 4.0的方法

程序员文章站 2022-04-26 23:11:26
CuteFTP早期的版本的保护还是比较厉害的,先是KeyFile,后来才改成注册码。它有个3.x版本被拿来作为HCU(High Cracking University)的strainer。4.0版本可以变成注册版,但是输入注... 08-10-08...
cuteftp早期的版本的保护还是比较厉害的,先是keyfile,后来才改成注册码。它有个3.x版本被拿来作为hcu(high cracking university)的strainer。4.0版本可以变成注册版,但是输入注册码之后它要连到其公司的服务器上去验证。输入注册码之后是可以跟出注册码来的,但是通不过联机验证则它不会将注册码保存起来,所以下次启动还是未注册版。可以从它启动时开始跟踪,找到注册码,实际上所有的软件都可以从启动时入手。
用regmon、filemon检查一下,发现有个注册表键叫做key1,里面放的是一些很长的乱七八糟的字符。可以用bpx regqueryvalueexa作断点,然后跟踪,但是这玩意儿读的注册表键太多,且softice的条件断点又不是很灵光(我用bpx regqueryvalueexa if *(esp 8)==’key1’作断点它不中断),所以改用w32dasm来寻找合适的断点。将其反汇编之后查找引用到"key1"这个字符串的地方,记下其地址作为断点,然后用symbol loader加载主程序,设好断点,发现在下面的地方读出该键值,但它要求key1串的长度小于等于20。

015f:00489074 mov esi,[advapi32!regqueryvalueexa]
015f:0048907a jnz 004890a9
015f:0048907c mov ecx,[esp 10]
015f:00489080 lea edx,[esp 14]
015f:00489084 push edx
015f:00489085 lea eax,[esp 20]
015f:00489089 push ebx
015f:0048908a push eax
015f:0048908b push 00
015f:0048908d push 0053e030 //key1
015f:00489092 push ecx
015f:00489093 call esi //读注册表
015f:00489095 test eax,eax
015f:00489097 jnz 004890a2
015f:00489099 mov edx,[esp 10]
015f:0048909d push edx
015f:0048909e call ebp
015f:004890a0 jmp 00489108

.........

015f:00489108 mov ecx,[esp 14] //key1串的长度
015f:0048910c cmp ecx,14 //长度小于等于0x14则继续检查
015f:0048910f jbe 0048911b
015f:00489111 pop edi
015f:00489112 pop esi
015f:00489113 pop ebp
015f:00489114 xor eax,eax //bag guy
015f:00489116 pop ebx
015f:00489117 add esp,10
015f:0048911a ret
015f:0048911b mov eax,[esp 28]
015f:0048911f test eax,eax
015f:00489121 jz 00489125
015f:00489123 mov [eax],ecx
015f:00489125 pop edi
015f:00489126 pop esi
015f:00489127 pop ebp
015f:00489128 mov eax,00000001
015f:0048912d pop ebx
015f:0048912e add esp,10
015f:00489131 ret

将key1串改成一个长度小于20的asciiz串,重新来一遍。等它读完key1后用bpr断点监视key1串,会看见它把key1转换成大写,并检查长度:

015f:004ab0f0 repnz scasb
015f:004ab0f2 not ecx
015f:004ab0f4 dec ecx
015f:004ab0f5 cmp ecx,0e
015f:004ab0f8 jnz 004ab16d

可见长度应为14个字符。接下来它检查key1的第一个字符是否为’a’,并计算注册码的其它位:

015f:00491828 cmp byte ptr [ebx],41 //key1的首字符
015f:0049182b jz 00491832
015f:0049182d pop edi
015f:0049182e xor eax,eax //bad guy
015f:00491830 pop ebx
015f:00491831 ret
015f:00491832 push esi //以下为计算过程
015f:00491833 mov esi,00000001
015f:00491838 mov al,[ebx esi]
015f:0049183b push eax
015f:0049183c call 004917d0
015f:00491841 shl edi,05
015f:00491844 add esp,04
015f:00491847 or edi,eax
015f:00491849 inc esi
015f:0049184a cmp esi,07
015f:0049184d jl 00491838
015f:0049184f mov cl,[ebx 07]
015f:00491852 push ecx
015f:00491853 call 004917d0
015f:00491858 add esp,04
015f:0049185b lea edx,[edi*4 00000000]
015f:00491862 shr eax,02
015f:00491865 pop esi
015f:00491866 pop edi
015f:00491867 or eax,edx
015f:00491869 pop ebx
015f:0049186a ret

计算完了之后就开始比较:

015f:004ab0f0 repnz scasb
015f:004ab0f2 not ecx
015f:004ab0f4 dec ecx
015f:004ab0f5 cmp ecx,0e //这是刚才判长度的地方
015f:004ab0f8 jnz 004ab16d
015f:004ab0fa push esi
015f:004ab0fb call 004b1b8a
015f:004ab100 push 0e
015f:004ab102 lea eax,[esp 20]
015f:004ab106 push esi
015f:004ab107 push eax
015f:004ab108 call 004af930
015f:004ab10d lea ecx,[esp 28]
015f:004ab111 mov byte ptr [esp 36],00
015f:004ab116 push ecx
015f:004ab117 call 00491820 //这是刚才计算的地方
015f:004ab11c mov esi,eax
015f:004ab11e push esi
015f:004ab11f call 00491510
015f:004ab124 lea edx,[esp 20]
015f:004ab128 mov edi,eax
015f:004ab12a push edx
015f:004ab12b push esi
015f:004ab12c mov byte ptr [esp 28],00
015f:004ab131 call 004916a0
015f:004ab136 lea eax,[esp 38]
015f:004ab13a push 0e //14个字符
015f:004ab13c lea ecx,[esp 2c]
015f:004ab140 push eax //真注册码
015f:004ab141 push ecx //假注册码
015f:004ab142 call 004b04d0 //比较
015f:004ab147 add esp,2c
015f:004ab14a test eax,eax
015f:004ab14c jnz 004ab15e
015f:004ab14e mov edx,[esp 2c]
015f:004ab152 or ax,ffff //good guy
015f:004ab156 mov [edx],edi
015f:004ab158 pop edi
015f:004ab159 pop esi
015f:004ab15a add esp,20
015f:004ab15d ret
015f:004ab15e mov eax,[esp 2c]
015f:004ab162 mov [eax],edi
015f:004ab164 pop edi
015f:004ab165 xor ax,ax //bad guy
015f:004ab168 pop esi
015f:004ab169 add esp,20
015f:004ab16c ret

至此就找出了注册码。根据上面的计算和比较过程可知注册码与名字什么的没有关系,所以它启动时不用读取用户名。用regmon监视一下它显示about对话框的时候的动作,发现它还读取regusername键,这显然是存放用户名的。
关键的健:
hkey_local_machine\software\globalscape inc.\cuteftp\key1
hkey_local_machine\software\globalscape inc.\cuteftp\regusername
hkey_classes_root\pfc
最后一个键是存放日期的,老版本的也在这里。