ISCC2024_revrese_Badcode

2>Badcode

下载附件,查壳,无壳32位

将文件拖入ida中,发现主函数_main,我们点进去吧

F5反汇编出伪c代码,看重点

     28行始

  1. v3 = rand();: 生成一个随机数。
  2. v18 = sub_4016F0(v3 % 100);: 调用sub_4016F0函数,并用随机数的百位数作为参数,结果存储在v18
  3. 接下来的for循环执行100次,看起来像是一个测试循环,因为循环变量iv18的值在循环中没有被进一步使用。
  4. 如果v18等于123456,将输出"This will never happen.",这似乎是一个不可能发生的情况,可能是用于调试或测试。

看下一个循环,40行始

这个for循环遍历v17数组,对每个字符进行变换。如果索引j是偶数,字符ASCII值加2;如果是奇数,字符ASCII值减3。

 接下来看下个循环,50行始

1.循环使用变量k作为索引,从0开始,直到字符串v17的长度(由unknown_libname_3(v17)给出)。

2.对于v17中的每个字符,通过sub_401B60(k)获取其内存地址,并进行处理。

3.尝试将字符转换为其对应的整数值(如果字符是数字)。这是通过从字符的ASCII值中减去48来实现的,因为数字字符'0'到'9'的ASCII值是连续的,范围从48到57。

4.对每个字符的原始值v9和转换后的整数值进行异或操作。这个操作通常用于加密或数据变换,可以改变字符的原始值。

5.将异或操作的结果v10写回v17字符串的相应位置,从而修改原始字符串。

接下来看63行,这里将之前处理过的数组传进去这个函数了,我们点开这个函数

通过观察我们可以发现这是XTEA加密,具体了解可以看这篇文章TEA XTEA XXTEA-CSDN博客icon-default.png?t=N7T8https://blog.csdn.net/m0_51713041/article/details/115535776

DELTA是 -1640531527(-0x61C88647),密钥在&unk_407018,4个密钥分别为0x12345678, 0x9ABCDEF0, 0xFEDCBA98, 0x76543210

 那我们接下来就可以写解密脚本了

#include <stdio.h>
#include <stdint.h>
#include <iostream>
#include <string>
#include <cstdlib>
#include <ctime>

#define DELTA -0x61C88647
#define MX (((z >> 5 ^ y << 2) + (y >> 3 ^ z << 4)) ^ ((sum ^ y) + (key[(p & 3) ^ e] ^ z)))

using namespace std;

void btea(uint32_t *v, int n, uint32_t const key[4]) {
    uint32_t y, z, sum;
    unsigned p, rounds, e;

    if (n > 1) {
        rounds = 6 + 52 / n;
        sum = 0;
        z = v[n - 1];

        do {
            sum -= DELTA;
            e = (sum >> 2) & 3;
            for (p = 0; p < n - 1; p++) {
                y = v[p + 1];
                z = v[p] += MX;
            }
            y = v[0];
            z = v[n - 1] += MX;
        } while (--rounds);
    } else if (n < -1) {
        n = -n;
        rounds = 6 + 52 / n;
        sum = rounds * DELTA;
        y = v[0];

        do {
            e = (sum >> 2) & 3;
            for (p = n - 1; p > 0; p--) {
                z = v[p - 1];
                y = v[p] -= MX;
            }
            z = v[n - 1];
            y = v[0] -= MX;
            sum -= DELTA;
        } while (--rounds);
    }
}

int main() {
    uint32_t key[4] = {0x12345678, 0x9ABCDEF0, 0xFEDCBA98, 0x76543210};
    uint32_t v[] = {0x3881C7CA, 0x5AEA661A, 0xC0E1397D, 0x3C415BB1, 0xDC546CB9, 0x5DC6BE6};
    btea(v, -6, key);

    // 将uint32_t数组转换为char数组
    string a(reinterpret_cast<char*>(v), sizeof(v));

    srand(static_cast<unsigned>(time(NULL)));

    int v16[24];
    for (int i = 0; i < 24; ++i) {
        v16[i] = rand() % 10 + '0'; // 生成0-9之间的随机数并转换为字符
    }

    for (int k = 0; k < 24; ++k) {
        a[k] ^= static_cast<char>(v16[k] - '0'); // 异或操作
    }

    for (int j = 0; j < 24; ++j) {
        if (j % 2) {
            a[j] -= 2;
        } else {
            a[j] += 3;
        }
    }

    // 输出结果字符串
    for (int i = 0; i < 24; i++) {
        cout << a[i];
    }
    cout << endl;

    return 0;
}

  • 29
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值