-
-
[原创]看雪CTF2017第二题 Fpc-CrackMe WriteUp
-
发表于: 2017-10-27 14:13 2998
-
相关工具:OD,IDA
拖进IDA
解方程失败后,重新思考了几个问题
1、CrackMe没有验证sn的长度,也就是说,若XXXXXXXX满足条件,那么XXXXXXXX后面接上任意字符都满足条件。作者不会如此大意。
2、阅读汇编代码,发现sn是被分配在栈上的。
看来这是一道溢出题,我们可以控制第一个call的返回地址,那么应该跳到哪里去呢?
sn必须为字母或数字,而且scanf输入的sn是以0x00结尾的。作者设计的地址应该是0x00410000往上。
IDA进入text view,发现如下数据:
一道很有意思的CrackMe,作者精心构造了栈溢出和花指令,并且给选手挖了一个解方程的大坑。。。
.text:0040100D mov dword_41B034, 2 .text:00401017 call sub_401050 .text:0040101C call sub_401090 .text:00401021 call sub_4010E0 .text:00401026 mov eax, dword_41B034 .text:0040102B test eax, eax .text:0040102D jnz short loc_40103F
看上去CrackMe的流程很简单
dword_41b034被初始化为2
第一个call调用scanf读取sn
后两个call验证sn,验证通过则将dword_41B034减1
dword_41b034被减为0后,输出You get it!的成功字符串。
整理后两个call里的算法,得出4个二元一次方程:
5(x-y)+x=0x8F503A42 13(x-y)+y=0xEF503A42 17*(x-y)+x=0xF3A94883 7*(x-y)+y=0x33A94883
算了很久发现无解。。。
甚至写了穷举代码。。。
#include <windows.h> #pragma comment(lib,"kernel32.lib") #pragma comment(lib,"user32.lib") int __declspec(naked)check() { _asm{ mov ecx,ds:[0x409900] mov edx,ds:[0x409904] mov eax,edx sub eax,ecx imul eax,5 add ecx,eax cmp ecx,0x8f503a42 jnz error mov eax,edx sub eax,ecx imul eax,13 add edx,eax cmp edx,0xef503a42 jnz error mov eax,edx sub eax,ecx imul eax,17 add edx,eax cmp edx,0xf3a94883 jnz error mov eax,edx sub eax,ecx imul eax,7 add edx,eax cmp edx,0x33a94883 jnz error mov eax,1 ret error: mov eax,0 ret } } char s[9]={0}; void main() { int i1; int i2; int i3; int i4; int i5; int i6; int i7; int i8; int x; int y; char ch[62]={'0','1','2','3','4','5','6','7','8','9', 'a','b','c','d','e','f','g','h','i','j','k','l','m', 'n','o','p','q','r','s','t','u','v','w','x','y','z', 'A','B','C','D','E','F','G','H','I','J','K','L','M', 'N','O','P','Q','R','S','T','U','V','W','X','Y','Z'}; for(i1=0;i1<62;i1++){ for(i2=0;i2<62;i2++){ for(i3=0;i3<62;i3++){ for(i4=0;i4<62;i4++){ printf("ch[i4]=%c\n",ch[i4]); for(i5=0;i5<62;i5++){ for(i6=0;i6<62;i6++){ for(i7=0;i7<62;i7++){ for(i8=0;i8<62;i8++){ sprintf(s,"%c%c%c%c%c%c%c%c",ch[i1],ch[i2],ch[i3],ch[i4],ch[i5],ch[i6],ch[i7],ch[i8]); if(check()) { printf("%s",s); getchar(); } } } } } } } } } getchar(); return; }
估算了一下时间,需要855天。。。。。,遂放弃。
二、整理思路,柳暗花明又一村
解方程失败后,重新思考了几个问题
1、CrackMe没有验证sn的长度,也就是说,若XXXXXXXX满足条件,那么XXXXXXXX后面接上任意字符都满足条件。作者不会如此大意。
2、阅读汇编代码,发现sn是被分配在栈上的。
看来这是一道溢出题,我们可以控制第一个call的返回地址,那么应该跳到哪里去呢?
sn必须为字母或数字,而且scanf输入的sn是以0x00结尾的。作者设计的地址应该是0x00410000往上。
IDA进入text view,发现如下数据:
.text:0040112B db 5 dup(90h) .text:00401130 dd 4800h dup(0) .text:00413130 ; --------------------------------------------------------------------------- .text:00413130 retn .text:00413130 ; --------------------------------------------------------------------------- .text:00413131 db 83h, 0C4h, 0F0h .text:00413134 dd 20712A70h, 0F1C75F2h, 28741C71h, 2E0671DDh, 870F574h .text:00413134 dd 74F17169h, 0DC167002h, 0EA74C033h, 0DC261275h, 0F471E771h .text:00413134 dd 6903740Fh, 0EB75EB70h, 0FDF7069h, 22712C70h, 0B8261F7Dh .text:00413134 dd 2B741E71h, 3E067169h, 870F57Ch, 7CF17169h, 0DC197002h .text:00413134 dd 41B034A3h, 75E77400h, 0E571DC12h, 7CDCF271h, 0E9706903h .text:00413134 dd 6965E97Dh, 70B8DC70h, 3E1D7127h, 710F1971h, 0DD257019h .text:00413134 dd 0F6700571h, 71DD0870h, 700270F2h, 70580F14h, 0F1171ECh .text:00413134 dd 0F671EA71h, 0DD03700Fh, 0ED71ED70h, 0FE170DDh, 7F36217Eh .text:00413134 dd 671A7D27h, 1D2A74B8h, 65690D7Eh, 67C067Fh, 1D361C7Eh .text:00413134 dd 8BDC0E7Fh, 75EA74C8h, 7E69DC14h, 0C1F47FEFh, 0F97CFB7Fh .text:00413134 dd 0EA7DE27Fh, 0D87E6965h, 772076B8h, 2E1A7F27h, 0DD2978B8h
前面大量重复的数据,到0x00413131变得杂乱无章。而且0x413131="11A",这就是要跳转到的新世界?
构造溢出数据:44443333222211A,程序居然没有崩溃,并且输出"Bad register-code",说明地址找对了。
上OD动态跟踪,各种各样的跳转,看得头都晕了,反复跟了几次,终于整理出了算法:
4(a-b)+a+c=0xeaf917e2 2(a-b)+(a-b)+a+c=0xe8f508c8 2(a-b)+(a-b)+a-c=0xc0a3c68
利用python,手算就可出结果:
a=0x74737543 b=0x726f6630 c=0x6e756630
sn:Just0for0fun11A
总结:
一道很有意思的CrackMe,作者精心构造了栈溢出和花指令,并且给选手挖了一个解方程的大坑。。。
5(x-y)+x=0x8F503A42 13(x-y)+y=0xEF503A42 17*(x-y)+x=0xF3A94883 7*(x-y)+y=0x33A94883
5(x-y)+x=0x8F503A42 13(x-y)+y=0xEF503A42 17*(x-y)+x=0xF3A94883 7*(x-y)+y=0x33A94883
[注意]传递专业知识、拓宽行业人脉——看雪讲师团队等你加入!
赞赏
他的文章
看原图
赞赏
雪币:
留言: