1.基本信息探查:
1.EXEinfo:
64位,无壳

2.运行一下:

2.IDA分析:
1.找思路:
搜索主函数看到main_main:
做这个题的时候确实很蒙,一开始想着F12看一下字符串(因为前面运行的时候有看到有个input flag),但是啥也没找到,索性就直接搜一下这些函数,抓着第一个函数搜了一下,发现这是GO语言的函数,之前确实没接触过这个语言的题,这里采用的办法是直接动调,选择在fmt_Fprintln函数和fmt_Fscanf的地方都下一个断点(没有为什么看一下输出和输入找找思路)

可以发现动调到
call fmt_Fprintln
就弹出了input flag,然后下面的scanf就是接收flag,这里随便乱输入一些东西
而紧接着就是调用main_check函数

这里F8步过

这里就是根据check函数会有个分支,左边为正确,右边为错误

这里退出来先分析main_check函数。
2.main_check函数分析:
搜一下这些函数,可以发现有个正则表达式的函数:
regexp_MustCompile
这里调用了一个函数,跟过去看看

这里按a注转一下:

注意这里有个正则表达式,这里基本可以确定check函数是判断输入的字符是否符合这个表达式。然后我们继续动调,sacnf时输入符合正则表达时的flag

这里就会跳转到左边的函数了,这次动调遇到跳转选择直接改ZF看一下哪些函数引发跳转

可以发现最后引发跳转在上图函数,先分析main___myCipher__Encrypt函数,这里面的核心代码为:
分析代码类似XXTEA,因为可以看到核心加密在第8行,但可能是ida的问题。加密算法有点奇怪
- 11行处的异或和正常思路一样只是有些步骤用变量代替,在做异或操作之前先赋好值,后面直接用
- 如
v19 = v15 + ((v15 >> 5) ^ (16 * v15))
- 17行处的异或a1相当于之前笔记的v1,我们大致将这个加密分为两块(异或的左右)
(v23 + ((v23 >> 5) ^ (16 * v23)))
和(sum + *(_DWORD *)(key + 4 * v24) + 305419896)
- 左边倒是中规中矩,
v23 * 16
就相当于v23<<4
,v23也就是笔记里的v0变量 - 右边就奇怪了,正常情况下代码为:
(sum + key[(sum>>11) & 3])
- 一开始还奇怪sum为什么还要在后面加一个0x12345678
- 但往上面发现正常情况下做完v0的加密后sum并没有进行累加,v0也用的不是sum进行加密而是用的v17,每个循环sum自己虽然没有累加delta值但是每次最开始都被v17赋值了,而v17在做完v0的加密后负责累加
到这里可以判断出这就是正常的XTEA加密,Delta的值为0x12345678,目前缺少的值为KEY和加密之后的数据。这里还是继续动调。
变量调整后的函数
3.寻找KEY值:
之前对加密函数分析知道,key的赋值在第50行:
这里在第51行下一个断点(这里重新调试了一下,做到后面忘记截图了,但重新反汇编的行数有不同)

F9运行

这里双击v20变量

这里转成double word(一个密钥32字节),得出key值:

4.获取加密后的数据:
直接在比较函数这里下断点:

跟进去先看一下流程图:(这样可以确认是通过那个比较进行跳转的)

直接在这个跳转地址下断点,我们要提取的值就在上面,但问题来了,不晓得要提取的是哪一个,这里的解决方案是调两次每次输入的flag不想同看哪个寄存器的值变了。
当flag为:
flag{12345678-1234-1234-1234-12345678abcd}
双击查看rsi的值:

双击查看rdi的值

当flag为:
flag{11111111-1111-1111-1111-111111111111}
双击查看rsi的值:

双击查看rdi的值:

这样一比对就可以发现加密后的数据存在了rdi内。
进入rdi的数据两次R,换成十六进制,然后提取数据。
3.EXP:
这里的exp直接在网上找的:

最后按照开始分析的flag的格式排列一下得到flag{3bbcf9ea-2918-4fee-8a2e-201b47dfcb4e}
最后贴上主函数内的函数作用: