吾爱破解 - LCG - LSG |安卓破解|病毒分析|www.52pojie.cn

 找回密码
 注册[Register]

QQ登录

只需一步,快速开始

查看: 10920|回复: 27
收起左侧

[原创] 看雪《加密与解密》第三版2-1TraceMe的学习体会

  [复制链接]
lizhirui 发表于 2018-1-15 11:23
本帖最后由 lizhirui 于 2018-1-15 11:25 编辑

该TraceMe.exe来源于看雪加密与解密第三版的2-1 ASCII版程序,我经过独立分析后,在这里向大家分享一些经验和体会:
首先我们打开程序:
1.jpg
经过尝试,输入的字符数至少为5个才行。
输入数目够了之后,这样提示:
2.jpg
我们使用OD将程序加载,然后搜索ASCII字符串,发现了大量特征字符串,不过这一次我不打算从这里入手。
由于该程序是VC++写成(可用PEID分析得到,或者分析该文件的导入表,可以看到msvcrt字样),该程序一般也就是用MFC实现的。
那么由于验证注册码是否正确必定要获取文本框内容,因此我们在GetDlgItemTextA下断(该程序是ASCII版程序,Unicode版则在GetDlgItemTextW下断,常用断点还有GetWindowTextA,GetWindowTextW等),我们在底部命令栏输入“bp GetDlgItemTextA”,运行程序,输入上面的用户名和序列号,点击Check按钮,程序中断在了user32.GetDlgItemTextA中:
3.jpg
从这个API的实现中我们可以看出,GetDlgItemTextA本身也调用了GetWindowTextA函数,因此在GetWindowTextA下断也是可以的。
我们按Ctrl+F9执行到返回,然后按F8返回程序领空:
4.jpg
我们看到了这样的代码,两个GetDlgItemTextA经过跟踪可以看出,第一个GetDlgItemTextA读入了用户名,而第二个则读入了序列号。
我们按Alt+B,在断点窗口中删除GetDlgItemTextA的断点,
紧接着不断F8到004011CA的地方,我们可以看到ss:[esp+0x4C]的地方正好是用户名的第一个字符,从该行开始往下三行检测用户名的第一个字节是否为0,也就是用户名是否为空,若不为空,继续往下走,
cmp ebx,0x5
jl short TraceMe.00401248
这两行的作用是判断用户名长度是否小于5,若不成立,继续往下走,
在004011DB处有一行push ebx,我们在004011C6处看到了一句mov ebx,eax,在API的调用约定中,eax是API函数返回值,我们这里看一下GetDlgItemTextA的MSDN解释:
-------------------------------------------------以下来自MSDN------------------------------------------------------------
GetDlgItemText function
Retrieves the title or text associated with a control in a dialog box.
Syntax
C++

UINT WINAPI GetDlgItemText(
  _In_  HWND   hDlg,
  _In_  int    nIDDlgItem,
  _Out_ LPTSTR lpString,
  _In_  int    nMaxCount
);

Parameters
hDlg [in]
Type: HWND
A handle to the dialog box that contains the control.
nIDDlgItem [in]
Type: int
The identifier of the control whose title or text is to be retrieved.
lpString [out]
Type: LPTSTR
The buffer to receive the title or text.
nMaxCount [in]
Type: int
The maximum length, in characters, of the string to be copied to the buffer pointed to by lpString. If the length of the string, including the null character, exceeds the limit, the string is truncated.
Return value
Type: UINT
If the function succeeds, the return value specifies the number of characters copied to the buffer, not including the terminating null character.
If the function fails, the return value is zero. To get extended error information, call GetLastError.
-------------------------------------------------以上来自MSDN------------------------------------------------------------
我们着重说一下返回值部分的含义,中文翻译过来大致意思是“如果函数执行成功,返回值是被写入到缓冲区中的字符串的长度(不包含最后的'\0'),若函数执行失败,返回值是0,为了获取更多的错误信息,请调用GetLastError”
因此该函数的返回值也就是文本框中输入的字符串长度
我们继续往下看:
5.jpg
很容易看出,那个004011E5处的call调用的就是注册验证程序,因为下方显而易见已经是根据判断结果输出不同信息的代码了。
这些代码出现了三次push,经过分析,该函数的第一个参数为序列号缓冲区地址,第二个参数为用户名缓冲区地址,第三个参数为用户名长度,
写成c格式大概是 :
int CheckCode(char *code,char *username,char *usernamelen)
我们跟入该函数,看到以下代码(每一行大致的含义我都已经注释出了):
6.jpg
那个00401358处的jle,00401374处的cmp和00401376处的jl,以及ecx,eax想要表达的含义如下:
for(ecx=3,eax=0;ecx < usernamelen;ecx++,eax++)
从00401359-00401376处就是该循环体内部,
我们可以看出这一部分代码计算出了注册码,而下面的一段代码:
7.jpg
将注册码直接转换为字符串,然后与用户输入的字符串比较,从而判断注册码是否正确。
这里我们还原一下注册码计算算法:
[C++] 纯文本查看 复制代码
int GenRegCode(TCHAR *username,int len)
{
        int i,j;
        int r = 0;
        char arr[]={0x0C,0x0A,0x13,0x09,0x0C,0x0B,0x0A,0x08};

        for(i = 3,j = 0;i < len;i++,j++)
        {
                if(j > 7)
                {
                        j = 0;
                }

                r += username[i] * arr[j];
        }

        return r;
}


该函数返回的数值就是注册码

8.jpg
我们输入试验一下:
9.jpg
可见注册成功。
由于Windows是事件驱动的操作系统,所以除了以上方法以外,我们还要实验另一种定位注册代码的方法:消息定位法。
我们知道,按下按钮操作系统必定会传递WM_LBUTTONDOWN和WM_LBUTTONUP事件到窗口消息循环队列中。
那么按钮使用的是哪个事件呢?我们可以试验一下,我们按下按钮,发现什么都没有发生,然后放开按钮,出现了提示框,因此我们断定,按钮使用的必然是WM_LBUTTONUP事件。
我们用OD加载程序并运行,按Alt+W打开窗口句柄窗口,右键点击刷新,可以看到所有的窗口,我们在按钮“Check”上设置消息断点:
10.jpg
我们可以点击下面的“根据名称排列消息”,这样从上面的列表中找消息更容易一些。
现在我们点击“Check”按钮,程序中断了下来,我们看堆栈窗口:
11.jpg
很明显已经中断了下来,由于事件处理需要经过操作系统传递,用Ctrl+F9难以跟踪,因此我们按Alt+M,打开内存映射窗口,在TraceMe的.text上按F2下断,按F9运行程序,中断在了这里:
12.jpg
我们按F8跟踪,
慢慢的又回到了user32内存空间,我们再一次在.text上下断,运行程序,再一次返回到了这里,
我们按F8跟踪,发现我们到了这里:
13.jpg
这是从上面的一个较远的跳转跳过来的,因此我们在这个地方调试的时候如果发现远距离跳转,一般就是进入了用户真正的事件处理程序。
至此,程序跟踪完成,以上是我的一些体会,这是我第一次使用事件跟踪和人工逆向非爆破的方式解决这个crackme,从中获得了大量的经验和体会。
以下是TraceMe:
TraceMe.rar (9.73 KB, 下载次数: 106)

免费评分

参与人数 7威望 +1 吾爱币 +16 热心值 +6 收起 理由
海天一色001 + 1 + 1 谢谢@Thanks!
Hmily + 1 + 10 + 1 用心讨论,共获提升!
心痛不如行动 + 1 + 1 热心回复!
Liamemp + 1 谢谢@Thanks!
h1825052587 + 1 + 1 用心讨论,共获提升!
SKnight + 1 + 1 谢谢@Thanks!
136136 + 1 + 1 用心讨论,共获提升!

查看全部评分

本帖被以下淘专辑推荐:

发帖前要善用论坛搜索功能,那里可能会有你要找的答案或者已经有人发布过相同内容了,请勿重复发帖。

wuyusen 发表于 2018-1-15 12:26
学习了,谢谢。
dirisyou 发表于 2018-1-15 14:00
能反,能正。。我们就是需要你这样的,真正懂汇编的大神。 算法分析的头头是道。
仰头深呼吸 发表于 2018-1-15 16:29
东仔东 发表于 2018-1-15 21:49
接着学习下先
tydzjing 发表于 2018-1-16 11:05
图文并茂,条理明晰,学习了
duanlai 发表于 2018-1-16 12:46
学习了,谢谢。
Liamemp 发表于 2018-1-16 13:02
楼主这个很详细!!!
evill 发表于 2018-1-16 14:17
mark
学习一下。。。
头像被屏蔽
my20889938 发表于 2018-1-16 18:18 来自手机
提示: 作者被禁止或删除 内容自动屏蔽
您需要登录后才可以回帖 登录 | 注册[Register]

本版积分规则 警告:本版块禁止灌水或回复与主题无关内容,违者重罚!

快速回复 收藏帖子 返回列表 搜索

RSS订阅|小黑屋|处罚记录|联系我们|吾爱破解 - LCG - LSG ( 京ICP备16042023号 | 京公网安备 11010502030087号 )

GMT+8, 2024-4-24 22:10

Powered by Discuz!

Copyright © 2001-2020, Tencent Cloud.

快速回复 返回顶部 返回列表