Lycou' Blog

Lycou' Blog

IT博客 首页 新随笔 联系 聚合 管理
  0 Posts :: 15 Stories :: 0 Comments :: 0 Trackbacks
逆向分析看人家怎么保护版权
作者:asm[C.R.S.T]  来源:邪恶八进制信息安全团队  发布时间:2007-2-1 0:47:18  发布人:黑客动画吧

减小字体 增大字体

不知道大家写程序是怎么保护版权的。不过最近偶碰到两种思路比较好的,偶通过逆向分析把它们弄出来和大家分享 ^_^
    第一种是保护方式是明小子旁注工具里面的。它的标题是:"旁注WEB检测综合利用工具 [黑客动画吧出品 - 明小子]。改过版权的人都会知道怎么去修改这样的东东。利用VC资源编辑器选择二进制的方式打开文件,然后查找要修改的字符,把自己喜好的文字填进去就行了。但是你们是否发现,无论怎么弄,后面的“[黑客动画吧出品 - 明小子]”总是无法修改,一改,旁注工具一运行,就自己退出了。不知道改过这个工具的人有无注意。现在我们来看一下其中的猫腻。先把它的壳给扒了(壳是UPX,很容易扒的),用IDA载入查看。等等,我们先设想一下,旁注工具是怎么样保护这几个字符不被修改:先在一个缓冲区保存“[黑客动画吧出品 - 明小子]”,待启动工具后,对比一下标题部分是否和这个缓冲区里保存的字符等于,如果等,继续执行,如果不等,就out。这个是偶设想的,现在就来看看IDA里吧,我们快速通过IDA查找文本找是否发现这些字符。查看反汇编代码:
  
CODE:

CODE:005A55D6           mov   eax, [ebp-14h]
CODE:005A55D9           push   eax
CODE:005A55DA           mov   edx, offset s_VwebTVer3_5C0 ; "旁注WEB综合检测程序 Ver3.5正式版 (05.7."...
CODE:005A55DF           pop   eax
CODE:005A55E0           call   sub_404758
CODE:005A55E0
CODE:005A55E5           jnz   short loc_5A5603
CODE:005A55E5
CODE:005A55E7           lea   edx, [ebp-18h]
CODE:005A55EA           mov   eax, [ebp-4]
CODE:005A55ED           call   sub_476D74
CODE:005A55ED
CODE:005A55F2           mov   edx, [ebp-18h]
CODE:005A55F5           mov   eax, offset s_PN-B ; "黑客动画吧出品 - 明小子"
CODE:005A55FA           call   sub_404950    
CODE:005A55FA
CODE:005A55FF           test   eax, eax
CODE:005A5601           jnz   short loc_5A5633
[Copy to clipboard]


  看到没,"黑客动画吧出品 - 明小子"的字符已经保存到eax中。接着调用sub_404950来检测是否一样,eax是否等于零,也就是字符串是否相同,如果是,就继续执行。如果比较失败,那么就跳到loc_5A5633处。现在来看一下loc_5A5633这个地址处的代码:
CODE:

CODE:005A5633 loc_5A5633:                   ; CODE XREF: CODE:005A5601j
CODE:005A5633           xor   eax, eax
CODE:005A5635           pop   edx
CODE:005A5636           pop   ecx
CODE:005A5637           pop   ecx
CODE:005A5638           mov   fs:[eax], edx
CODE:005A563B           push   offset loc_5A5662
[Copy to clipboard]


  很明显,它在为退出做准备,恢复了积存器的值。现在我们来总结一下,它的执行流程是:把 "黑客动画吧出品 - 明小子"字符串存到eax,然后调用sub_404758来查询。当eax等于0的时候,查询成功;不等于0的时候,就到 loc_5A5633恢复所有堆栈。到这里,就很明显,我们可以这样来完全改掉它的版权。把jnz   short loc_5A5633改成 je   short loc_5A5633。查询失败,照样去执行。下面根据这种保护版权的方式,偶给个简单的直观的模拟代码:

CODE:

;*******************************************************************
;程序编写by Asm
;日期:2007-1-24日
;出处:http://www.wolfexp.net/(红狼安全小组)
;注意事项:如欲转载,请保持本程序的完整,并注明:
;转载自 红狼安全小组(http://www.wolfexp.net/)
;*******************************************************************
.386
.model flat,stdcall
option casemap:none
include windows.inc
include user32.inc
includelib     user32.lib
include kernel32.inc
includelib     kernel32.lib
.data
szText           db 'asm是好男人 ^_^ 测试一下',0
szCaption       db '[这里你就不能乱来了]',0
szFileText       db   '[这里你就不能乱来了]',0
.code
start:
  jz Vstart
  jnz Vstart
  db 0E8h
Vstart:
  lea ebx, szCaption
  lea ecx, szFileText
  invoke lstrcmp,ecx,ebx
    .if eax == NULL
invoke MessageBox,NULL,addr szText,ebx,MB_OK
invoke ExitProcess,NULL
.elseif
invoke ExitProcess,NULL
.endif
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
end start
[Copy to clipboard]


    下面再来看一下QQ是怎么对自己进行保护的。首先我们得发现问题,比如2006年最新版本的QQ,是不允许改名,如果你把QQ.EXE改成11111111.exe,QQ会无情地提示:“QQ程序出错,请重新安装”够叼吧?改个名字都不行,更别说要对QQ本身进行数据修改。按照第一种破解方法的提示,我们是否要寻找:“QQ程序出错,请重新安装”这个字符串?当初我也是这么认为,不过用IDA查找之后才发现,那是没用的。这个字符本身就存在文件本身,但是反汇编后就找不到。所以我猜想,QQ还有另外一种保护方法,那是什么捏?你问我,我问谁去?既然改了QQ,就执行不了,那么,是否和"QQ.exe"这个字符串有关系捏?在IDA里找了一下,找到两处地方是"QQ.exe",其中这里最有价值:

CODE:

.text:0040187A           push   offset s_Qq_exe ; "QQ.exe"
.text:0040187F           push   eax
.text:00401880           lea   eax, [ebp-28h]
.text:00401883           xor   edi, edi
.text:00401885           push   eax
.text:00401886           mov   [ebp-4], edi
.text:00401889           call   operator+(CString const &,char const *)
.text:00401889
.text:0040188E           lea   ecx, [ebp-30h]
.text:00401891           mov   byte ptr [ebp-4], 2
.text:00401895           call   CString::~CString(void)
.text:00401895
.text:0040189A           push   dword ptr [ebp-28h]
.text:0040189D           mov   ecx, esi
.text:0040189F           call   sub_4030D9 ;调用这个地址处的函数判断
.text:0040189F
.text:004018A4           test   eax, eax ;是不是很熟悉?
.text:004018A6           jnz   short loc_4018C0 ;开始判断QQ执行程序的名字是否QQ.exe
[Copy to clipboard]

  如果这里,eax不等于0,就执行成功,来到loc_4018C0。也就是对比程序名字一样的时候,就到这里了:
CODE:

loc_4018C0:
movzx   ebx, byte ptr [esi+0CEh]
movzx   eax, byte ptr [esi+0CFh]
imul   ebx, 64h
lea   ecx, [ebp-38h]
add   ebx, eax
call   CString::CString(void)
lea   eax, [ebp-30h]
mov   byte ptr [ebp-4], 3
push   eax
call   ds:GetExeFolder(void)
mov   [esp+7Ch+var_7C], offset s_Qqliveupdate_ ; "QQLiveUpdate.exe"
push   dword ptr [eax]
lea   eax, [ebp-38h]
mov   byte ptr [ebp-4], 4
push   offset s_SS   ; "%s%s"
push   eax
call   CString::Format(char const *,...)
[Copy to clipboard]


  到这里后,它会判断是否已经升级,如果没有,就执行QQLiveUpdate.exe程序进行升级。好,现在我们来看若是QQ名不一样的时候,它会怎么做:

CODE:

push   0FFFFFFFFh
push   edi
push   4
call   AfxMessageBox(uint,uint,uint) ;该死的,在这里提示QQ程序错误,请重新安装!
mov   eax, [ebp+8]
mov   dword ptr [eax], 1

loc_401F8C:
mov   ecx, [ebp-0Ch]
pop   edi     ;恢复积存器准备退出了。这个家伙!
pop   esi
pop   ebx
mov   large fs:0, ecx
leave
retn   4
sub_40184A endp ; sp = 4
[Copy to clipboard]

  目前为止,偶已经明白了QQ是通过判断程序名字来决定是否启动QQ。够叼!就是这个害我搞了一个晚上,AV都木得看,日!废话少说,它不是eax不等于0就代码程序名字一样,就跳到loc_4018C0么,我们把指令改成,当eax等于0的时候,也就是程序名字不一样的时候,也跳到loc_4018C0。破戒的人都知道,把JNZ改成JE就行了,多简单呀 ^_^ 下面是模拟它这种保护方法的一个简单的汇编代码:
CODE:

;*******************************************************************
;程序编写by Asm
;日期:2007-1-24日
;出处:http://www.wolfexp.net/(红狼安全小组)
;注意事项:如欲转载,请保持本程序的完整,并注明:
;转载自 红狼安全小组(http://www.wolfexp.net/)
;*******************************************************************
.386
.model flat,stdcall
option casemap:none
include windows.inc
include user32.inc
includelib user32.lib
include kernel32.inc
includelib kernel32.lib
.data
FileNameOfAsm db 156 dup(0)
FileName db 156 dup(0)
lpBuffer db 156 dup(0)
szFile db '\asm.exe',0
szText db '当你看到这里,说明程序的名字和原来一样',0
.data?
dwSize DWORD ?
lpLength DWORD ?
.code
start:
invoke GetModuleFileName,NULL,addr FileName,addr dwSize
invoke GetCurrentDirectory,addr lpLength,addr lpBuffer
invoke lstrcat,addr FileNameOfAsm,addr lpBuffer
invoke lstrcat,addr FileNameOfAsm,addr szFile
invoke lstrcmp,addr FileNameOfAsm,addr FileName
.if eax == NULL
invoke MessageBox,NULL,addr szText,ebx,MB_OK ;查询程序名字正确,这里开始程序运行。
invoke ExitProcess,NULL
.elseif
invoke ExitProcess,NULL
.endif
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
end start
posted on 2007-02-01 15:49 Lycou' Blog 阅读(90) 评论(0)  编辑 收藏 引用 所属分类: 技术无底
只有注册用户登录后才能发表评论。