首页
社区
课程
招聘
[原创] KCTF2020 秋季赛 第二题 异常信号
2020-12-15 00:10 6019

[原创] KCTF2020 秋季赛 第二题 异常信号

2020-12-15 00:10
6019

程序直接打开就是一个巨大的函数,trace一下看看,有看到

1
2
3
4
~~1120~~ Cabinet.dll!Decompress
    arg 0: 0x00c14a38
    arg 1: 0x000500ba
    and return to module id:0, offset:0x59026

又回头看看有一个space的段没有内容,那大概是运行的时候把什么东西解压到这个space段?

 

那就运行一下,然后Attach。在几个Crackme的线程上打上断点,走几步,就可以看到space填充好内容了。这个时候把程序dump下来看看,找到主要逻辑 sub_2312B0。

 

算法逻辑最核心是要求找到一个长度为12的数组,然后数字之间两两的差都不同,最大数字是不超过90,最小的是0,还有一些小的限制。

 

然后写个脚本加点小限制条件来爆破一下。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
#include<stdio.h>
int diff[100];
int is_valid(int * arr, int len) {
    for(int i = 0; i <= 90; i++) {
        diff[i] = 0;
    }
    for(int j = 0; j < len; j++) {
        for(int k = 0; k < len; k++) {
            if (arr[j] > arr[k]) {
                if(diff[arr[j] - arr[k]] == 0) {
                    diff[arr[j] - arr[k]] = 1;
                } else {
                    return 0;
                }
            }
        }
    }
    return 1;
}
int arr[20];
 
int max_d = 35;
int main() {
    for(int i0 = 0; i0 < 90; i0++) {
        for(int i1 = i0 + 1; i1 < 90; i1++) {
            if(i1 - i0 > max_d) break;
            arr[1] = i1;
            if(!is_valid(arr, 2)) continue;
            /*
            if(i1 == 2) {
                printf("----\n");
            }
            */
            for(int i2 = i1 + 1; i2 < 90; i2++) {
                if(i2 - i1 > max_d) break;
                arr[2] = i2;
                if(!is_valid(arr, 3)) continue;
                for(int i3 = i2 + 1; i3 < 90; i3++) {
                    if(i3 - i2 > max_d) break;
                    arr[3] = i3;
                    if(!is_valid(arr, 4)) continue;
                    for(int i4 = i3 + 1; i4 < 90; i4++) {
                        if(i4 - i3 > max_d) break;
                        arr[4] = i4;
                        if(!is_valid(arr, 5)) continue;
                        for(int i5 = i4 + 1; i5 < 90; i5++) {
                            if(i5 - i4 > max_d) break;
                            arr[5] = i5;
                            if(!is_valid(arr, 6)) continue;
                            for(int i6 = i5 + 1; i6 < 90; i6++) {
                                if(i6 - i5 > max_d) break;
                                arr[6] = i6;
                                if(!is_valid(arr, 7)) continue;
                                for(int i7 = i6 + 1; i7 < 90; i7++) {
                                    if(i7 - i6 > max_d) break;
                                    arr[7] = i7;
                                    if(!is_valid(arr, 8)) continue;
                                    for(int i8 = i7 + 1; i8 < 90; i8++) {
                                        if(i8 - i7 > max_d) break;
                                        arr[8] = i8;
                                        if(!is_valid(arr, 9)) continue;
                                        for(int i9 = i8 + 1; i9 < 90; i9++) {
                                            if(i9 - i8 > max_d) break;
                                            arr[9] = i9;
                                            if(!is_valid(arr, 10)) continue;
                                            for(int i10 = i9 + 1; i10 < 90; i10++) {
                                                if(i10 - i9 > max_d) break;
                                                arr[10] = i10;
                                                if(!is_valid(arr, 11)) continue;
                                                    /*
                                                    for(int z = 0; z < 11; z++) {
                                                        printf("%d, ", arr[z]);
                                                    }
                                                    puts("");
                                                    */
                                                for(int i11 = i10 + 1; i11 < 90; i11++) {
                                                    if(i11 - i10 > max_d) break;
                                                    arr[11] = i11;
                                                    if(!is_valid(arr, 12)) continue;
                                                    for(int z = 0; z < 12; z++) {
                                                        printf("%d ", arr[z]);
                                                    }
                                                    return 0;
 
                                                }
                                            }
 
                                        }
 
                                    }
 
                                }
 
                            }
 
                        }
 
                    }
 
                }
 
            }
 
        }
 
    }
    return 0;
}

跑出结果

1
0 2 6 24 29 40 43 55 68 75 76 85

然后套上题目的随机数逻辑,就可以得到最终答案。


[培训]《安卓高级研修班(网课)》月薪三万计划,掌握调试、分析还原ollvm、vmp的方法,定制art虚拟机自动化脱壳的方法

收藏
点赞1
打赏
分享
最新回复 (0)
游客
登录 | 注册 方可回帖
返回