逆向攻防世界CTF系列9-no-strings-attached

image-20241014144159264

image-20241014144251583

image-20241014144404342

wsccmp:应该是个比较函数,相同为0,输出“Success! Welcome back!”,点进unk,从上往下看的车。

不知道decrypt是个什么,查了下,是解密的意思。

image-20241014150734763

解法1:

选中shift+e

image-20241014160153421

把s和A2转出,目标程序是 32 位 Ubuntu ,所以 wchar_t 表示 \0 占 4 字节,后面 4 个是截止符,不代入计算。(64位也是4字节)

#include <stdio.h>

int main() {
    unsigned char s[] =
    {
       58,  20,   0,   0,  54,  20,   0,   0,  55,  20,
        0,   0,  59,  20,   0,   0, 128,  20,   0,   0,
      122,  20,   0,   0, 113,  20,   0,   0, 120,  20,
        0,   0,  99,  20,   0,   0, 102,  20,   0,   0,
      115,  20,   0,   0, 103,  20,   0,   0,  98,  20,
        0,   0, 101,  20,   0,   0, 115,  20,   0,   0,
       96,  20,   0,   0, 107,  20,   0,   0, 113,  20,
        0,   0, 120,  20,   0,   0, 106,  20,   0,   0,
      115,  20,   0,   0, 112,  20,   0,   0, 100,  20,
        0,   0, 120,  20,   0,   0, 110,  20,   0,   0,
      112,  20,   0,   0, 112,  20,   0,   0, 100,  20,
        0,   0, 112,  20,   0,   0, 100,  20,   0,   0,
      110,  20,   0,   0, 123,  20,   0,   0, 118,  20,
        0,   0, 120,  20,   0,   0, 106,  20,   0,   0,
      115,  20,   0,   0, 123,  20,   0,   0, 128,  20,
        0,   0
    };
    unsigned char a2[] = {
        1, 20, 0, 0, 2, 20, 0, 0, 3, 20,
        0, 0, 4, 20, 0, 0, 5, 20, 0, 0
    };
    int v4 = 0;
    int v6 = sizeof(s) / sizeof(unsigned char);
    int v7 = sizeof(a2) / sizeof(unsigned char);
    while (v4 < v6) {
        for (int i = 0; i < v7 && v4 < v6; ++i) {
            printf("%c", s[v4++] - a2[i]);
        }
    }
    return 0;

}

输出9447{you_are_an_international_mystery}

解法2:

image-20241014165115685

得a2=[0x1401,0x1402,0x1403,0x1404,0x1405],同理可得s,再修改上面的代码也行

解法3:

脚本查看

运行脚本,ida中,file,script file,选择脚本,查看地址,最后的0L要舍去

这里的39我猜测是尾项地址-0x08048AA8/4算出来,填>39的也没事,0L处截断就行

addr=0x08048AA8
arr = []
for i in range(39):
    arr.append(Dword(addr+4* i))
print(arr)

image-20241014165316760

s = [5178, 5174, 5175, 5179, 5248, 5242, 5233, 5240, 5219, 5222, 5235, 5223, 5218, 5221, 5235, 5216, 5227, 5233, 5240, 5226, 5235, 5232, 5220, 5240, 5230, 5232, 5232, 5220, 5232, 5220, 5230, 5243, 5238, 5240, 5226, 5235, 5243, 5248]
a = [5121, 5122, 5123, 5124, 5125]
v6 = len(s)
v7 = len(a )
v2 = len(s)

v4=0
while v4<v6:

    for i in range(0,5):
        if(i<v7 and v4<v6):
            s[v4]-=a[i]
            v4 += 1
        else:
            break
for i in range (38):
    print(chr(s[i]),end="")

解法4:

动态分析

此时我们需要转变一下思维:之前我们都是各种找、各种逻辑推断正确输入。但是我们忽略了一件事,那个与输入的比较的正确答案,一定是加载到内存里面之后,才与输入比较。要是我们能跟踪到这个正确答案储存在内存的位置然后把他拿出来,也行

参考[CTF-攻防世界 Reverse新手练习解析_ctf中的rev题-CSDN博客](https://blog.csdn.net/weixin_42621117/article/details/99768988#:~:text=XCTF 攻防世界)这篇文章