BUUCTF-[2019红帽杯]easyRE
1.信息收集:无加壳,64位文件
2.IDA64位,搜索关键代码,如下
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 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166
| signed __int64 sub_4009C6() { char *v0; char *v1; __int64 v2; signed __int64 result; unsigned __int64 v4; __int64 v5; __int64 v6; __int64 v7; __int64 v8; __int64 v9; __int64 v10; __int64 v11; __int64 v12; __int64 v13; __int64 v14; __int64 v15; int i; char v17; char v18; char v19; char v20; char v21; char v22; char v23; char v24; char v25; char v26; char v27; char v28; char v29; char v30; char v31; char v32; char v33; char v34; char v35; char v36; char v37; char v38; char v39; char v40; char v41; char v42; char v43; char v44; char v45; char v46; char v47; char v48; char v49; char v50; char v51; char v52; char v53[32]; int v54; char v55; char v56; char v57; char v58; unsigned __int64 v59;
v59 = __readfsqword(0x28u); v17 = 73; v18 = 111; v19 = 100; v20 = 'l'; v21 = '>'; v22 = 'Q'; v23 = 'n'; v24 = 'b'; v25 = '('; v26 = 'o'; v27 = 'c'; v28 = 'y'; v29 = ''; v30 = 'y'; v31 = '.'; v32 = 'i'; v33 = ''; v34 = 'd'; v35 = '`'; v36 = '3'; v37 = 'w'; v38 = '}'; v39 = 'w'; v40 = 'e'; v41 = 'k'; v42 = '9'; v43 = '{'; v44 = 'i'; v45 = 'y'; v46 = '='; v47 = '~'; v48 = 'y'; v49 = 'L'; v50 = '@'; v51 = 'E'; v52 = 'C'; memset(v53, 0, sizeof(v53)); v54 = 0; v55 = 0; v0 = v53; sub_4406E0(0LL, v53, 37LL); v55 = 0; v1 = v53; LODWORD(v2) = sub_424BA0((const __m128i *)v53); if ( v2 == 36 ) { for ( i = 0; ; ++i ) { v1 = v53; LODWORD(v4) = sub_424BA0((const __m128i *)v53); if ( i >= v4 ) break; if ( (unsigned __int8)(v53[i] ^ i) != *(&v17 + i) ) { result = 4294967294LL; goto LABEL_13; } } sub_410CC0("continue!"); memset(&v56, 0, 0x40uLL); v58 = 0; v0 = &v56; sub_4406E0(0LL, &v56, 64LL); v57 = 0; v1 = &v56; LODWORD(v5) = sub_424BA0((const __m128i *)&v56); if ( v5 == 39 ) { v6 = sub_400E44(&v56); v7 = sub_400E44(v6); v8 = sub_400E44(v7); v9 = sub_400E44(v8); v10 = sub_400E44(v9); v11 = sub_400E44(v10); v12 = sub_400E44(v11); v13 = sub_400E44(v12); v14 = sub_400E44(v13); v15 = sub_400E44(v14); v0 = off_6CC090; v1 = (char *)v15; if ( !(unsigned int)sub_400360(v15, off_6CC090) ) { sub_410CC0("You found me!!!"); v1 = "bye bye~"; sub_410CC0("bye bye~"); } result = 0LL; } else { result = 4294967293LL; } } else { result = 0xFFFFFFFFLL; } LABEL_13: if ( __readfsqword(0x28u) != v59 ) sub_444020(v1, v0); return result; }
|
所有分析在注释当中
首先我们再异或得出保存的数据的意思,简单得出:Info:The first four chars are flag
再看sub_400E44
,点开里面可以发现有一个方法保存的字符串是ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/
即可明白这是base64加密,还进行了10次加密。
然后把加密后的结果与off_6CC090
中保存的字符串比较。
解密过后得:https://bbs.pediy.com/thread-254172.htm,查询发现被耍了。
实际上在off_6CC090
里,下面还有一节字符串
跟进它的地址,就是解密过程(这一段蛮难的)
24行中,byte_6CC0A0就是存储的字符串,byte_6CC0A3 也就是byte_6CC0A0[3]
HIBYTE(v8)=HIBYTE(v4)=(*((_BYTE)&(V4)+1)) 属于未知
解密过程为byte_6CC0A0与v8对应位(四位一循环)异或
由于flag开头是flag
,我们明白前四位与byte_6CC0A0异或后等于”flag”
存储的字符串要与v8对应位进行异或,v8要四位进行循环遍历,可根据开头flag
得出v8.
于是就可以再异或得出flag了
于是写脚本:
1 2 3 4 5 6 7 8 9 10 11 12
| s = [0x40, 0x35, 0x20, 0x56, 0x5D, 0x18, 0x22, 0x45, 0x17, 0x2F, 0x24, 0x6E, 0x62, 0x3C, 0x27, 0x54, 0x48, 0x6C, 0x24, 0x6E, 0x72, 0x3C, 0x32, 0x45, 0x5B] s1 = 'flag' flag = '' key = '' for i in range(4): key += chr(s[i] ^ ord(s1[i])) for i in range(len(s)): flag += chr(s[i] ^ ord(key[i % 4])) print(flag)
|
得flag{Act1ve_Defen5e_Test}
搞定!
红帽杯的题还蛮难的
经验:memset与输入有关
byte_6CC0A3 也就是byte_6CC0A0[3]
HIBYTE(v8)=HIBYTE(v4)=(*((_BYTE)&(V4)+1))
一般从最后面看起,明白最终结果是什么,再逆着推导,更好理清逻辑,明白关键代码。