2020湖湘杯复盘(大概)

还是乐哥🐂🍺啊,差一点ak,甚至拿到一血,👴就只能做做签到异或,看看神仙打架🏄‍♂️🤸‍♂️🤺

easyre

这题啊,确实简单,但是👴汇编忘了不说,比赛中知道思路,但还是傻傻的不知道怎么做。赛后乐哥讲的OD中可以用ctrl+G跳到指定地址查看数据,👴才明白,下面来看题

拿到一个easyre.exe

用exeinfope分析发现没🐚

先来运行看看

1
2
Input your flag: 12344221331
Wrong length

很经典呐,对比字符串的题

这种题只要找到对比字符和算法就可以解出flag(👴还是太🥗了)

这题用OD调试

🔍一下关键字断点调试,发现了运算方法,同时知道字符串长度为24

image-20201106210414537

1
shl eax,0x3     ;逻辑左移指令 相当于<< 这里左移了3位
1
sar edx,0x5     ;逻辑右移指令 相当于>> 这里右移了5位
1
or eax,edx      ;将这两个字符进行或运算
1
xor eax,dword ptr ss:[ebp-0xC] ;将刚刚的结果异或当前的字符数组下标

借此可以推算出代码为 enflag[i] = ((flag[i]<<0x3)|(flag[(i+1)%24]>>0x5))^i

接着运行返回到另一个函数时发现对比字符串的位置

image-20201106213104057

1
2
3
4
5
6
7
8
# -*- coding:utf-8 -*-
from __future__ import print_function
s = "2B 08 A9 C8 97 2F FF 8C 92 F0 A3 89 F7 26 07 A4 DA EA B3 91 EF DC 95 AB"
s = s.split(" ")
print (len(s))
for i in s:
print ("0x" + i.lower(),end = ",")
#0x2b,0x08,0xa9,0xc8,0x97,0x2f,0xff,0x8c,0x92,0xf0,0xa3,0x89,0xf7,0x26,0x07,0xa4,0xda,0xea,0xb3,0x91,0xef,0xdc,0x95,0xab

4*6也是24长度,上脚本

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
#include <iostream>
#include <cstdio>
using namespace std;
int main()
{
unsigned char a[26] = {0x2b,0x08,0xa9,0xc8,0x97,0x2f,0xff,0x8c,0x92,0xf0,0xa3,0x89,0xf7,0x26,0x07,0xa4,0xda,0xea,0xb3,0x91,0xef,0xdc,0x95,0xab};
int i;
unsigned char flag = 0;
flag = (a[0] >> 3) | (a[23] << 5);
cout<<flag;
for(i = 1;i<23;i++)
{
//cout<<((((a[i] ^ i) >> 3) | ((a[i-1] ^ (i-1)) << 5))&0xff)<<endl;
flag = ((((a[i] ^ i) >> 3) | ((a[i-1] ^ (i-1)) << 5))&0xff);
cout<<flag;
}
flag = (a[23] >> 3) | ((a[22]^22) << 5);
cout<<flag;
return 0;
}

REMe

这题啊,图标就是python生成的exe文件,👴题还是做少了,没见过。比赛时👴用exeinfope分析

image-20201107165231582

好像是C++写的(被骗了💔)

后面好像说有一个什么.Zlib之类的东西

直接打开看看

image-20201107165604303

好像也是对比字符串什么的

用ida打开看看……

mian()中一堆函数调用🤷‍♂️,都看看,感觉不是用ida打开反汇编的,好像有一些python的相关字符(比赛时没反应过来🤪),直接去百度看看.Zlib是什么,是什么数据压缩的函式库,看不懂就放着了。没想到竟然是python反汇编(🍀生了出来)

那既然知道是python生成的exe,那就是一套老操作

python2 pyinstxtractor.py ReMe.exe解包

在那之中找到最像的 ReMe.pyc

uncompyle6 -o re.py ReMe.pyc转成py

pyc转py失败,用其他的试试,用struct.pyc反汇编成py成功了🙃

猜测可能是文件头损坏,用struct.pyc的文件头加上去

这里添加一份文件头大全

文件头大全

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
jpg: FF D8 FF
png: 89 50 4E 47
gif: 47 49 46 38
bmp: 42 4D
pyc: 03 F3 0D 0A
pyd: 4D 5A 90 00
zip: 50 4B 03 04 #ascii码部分是PK,可以直接根据PK判断是zip文件,也有可能是doc文件
rar: 52 61 72 21
7z: 37 7A BC AF 27 1C
xls/doc: D0 CF 11 E0
dwg: 41 43 31 30
psd: 38 42 50 53
rtf: 7B 5C 72 74 66
xml: 3C 3F 78 6D 6C
html: 68 74 6D 6C 3E
eml: 44 65 6C 69 76 65 72 79 2D 64 61 74 65 3A
dbx: CF AD 12 FE C5 FD 74 6F
pst: 21 42 44 4E
mdb: 53 74 61 6E 64 61 72 64 20 4A
wpd: FF 57 50 43
eps/ps: 25 21 50 53 2D 41 64 6F 62 65
pdf: 25 50 44 46 2D 31 2E
qdf: AC 9E BD 8F
pwl: E3 82 85 96
wav: 57 41 56 45
avi: 41 56 49 20
ram: 2E 72 61 FD
rm: 2E 52 4D 46
mpg: 00 00 01 BA or 00 00 01 B3
mov: 6D 6F 6F 76
asf: 30 26 B2 75 8E 66 CF 11
mid: 4D 54 68 64

直接将

1
00000000h: 42 0D 0D 0A 00 00 00 00 70 79 69 30 10 01 00 00 ; B.......pyi0....

覆盖第一行

1
00000010h: 03 F3 0D 0A 00 00 00 00 00 00 00 00 00 00 00 00 ; .?.............

就可以反汇编了,发现代码是将字符串中的字符逐个运算和一堆md5比较。

那就从32~127逐个枚举比对写出python暴力脚本。

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
# -*- coding:utf-8 -*-
import sys, hashlib
check = [
'e5438e78ec1de10a2693f9cffb930d23',
'08e8e8855af8ea652df54845d21b9d67',
'a905095f0d801abd5865d649a646b397',
'bac8510b0902185146c838cdf8ead8e0',
'f26f009a6dc171e0ca7a4a770fecd326',
'cffd0b9d37e7187483dc8dd19f4a8fa8',
'4cb467175ab6763a9867b9ed694a2780',
'8e50684ac9ef90dfdc6b2e75f2e23741',
'cffd0b9d37e7187483dc8dd19f4a8fa8',
'fd311e9877c3db59027597352999e91f',
'49733de19d912d4ad559736b1ae418a7',
'7fb523b42413495cc4e610456d1f1c84',
'8e50684ac9ef90dfdc6b2e75f2e23741',
'acb465dc618e6754de2193bf0410aafe',
'bc52c927138231e29e0b05419e741902',
'515b7eceeb8f22b53575afec4123e878',
'451660d67c64da6de6fadc66079e1d8a',
'8e50684ac9ef90dfdc6b2e75f2e23741',
'fe86104ce1853cb140b7ec0412d93837',
'acb465dc618e6754de2193bf0410aafe',
'c2bab7ea31577b955e2c2cac680fb2f4',
'8e50684ac9ef90dfdc6b2e75f2e23741',
'f077b3a47c09b44d7077877a5aff3699',
'620741f57e7fafe43216d6aa51666f1d',
'9e3b206e50925792c3234036de6a25ab',
'49733de19d912d4ad559736b1ae418a7',
'874992ac91866ce1430687aa9f7121fc']

def func(num):
result = []
while num != 1:
num = num * 3 + 1 if num % 2 else num // 2
result.append(num)

return result


if __name__ == '__main__':

flag = ""
for j in range(27):
for i in range(0x20,0x7f): #' '到'~' ASCII
ret_list = func(i)
s = ''
for idx in range(len(ret_list)):
s += str(ret_list[idx])
s += str(ret_list[(len(ret_list) - idx - 1)])

md5 = hashlib.md5()
md5.update(s.encode('utf-8'))
if md5.hexdigest() == check[j]:
flag+=chr(i)
print(flag)

md5 = hashlib.md5()
md5.update(flag.encode('utf-8'))
print('You win!')
print('flag{' + md5.hexdigest() + '}')

easy_c++

逆向签到题(👴终于有会做的了)用ida打开找到运算函数,直接做与运算就行

image-20201108191655442

有一点要注意的是在c++中 \“ 是代表

1
2
3
4
5
6
7
8
9
flag = ""
s = str(r'7d21e<e3<:3;9;ji t r#w"$*{*+*$|,')
print(s)
for i in range(0,32):
b = s[i]
flag+=chr(ord(b)^i)
print(ord(b)^i,s[i])
print(s)
print(flag)

easyZ

发现文件并不能用ida调试,分析无果后思路断了暂无思路,看wp也有些😵,先放着巩固一下知识再来回顾。