首页
社区
课程
招聘
未解决 [原创] 关于第7题的一些疑问
发表于: 2019-6-17 21:22 1256

未解决 [原创] 关于第7题的一些疑问

2019-6-17 21:22
1256

算法

这个程序存在非常多的反调试与SMC,经过一番分析,还原出来的算法代码大致如下:

unsigned int a;
unsigned int b;

unsigned char map[] = {
  0xDE, 0x93, 0xAB, 0x71, 0xE4, 0x6A, 0xA8, 0x2F, 0xC5, 0xAC, 
  0x6D, 0x7B, 0x53, 0xF8, 0xEF, 0x04, 0xC6, 0xB0, 0xD6, 0x65, 
  0xA5, 0x4F, 0x81, 0x0E, 0xEA, 0xFC, 0x4A, 0x82, 0x61, 0x5F, 
  0x0B, 0xC4, 0x15, 0xDD, 0xCD, 0x6B, 0x46, 0x9A, 0x49, 0xFE, 
  0x68, 0x97, 0xC6, 0x37, 0x18, 0x2F, 0x61, 0x09, 0xB9, 0x66, 
  0x7C, 0xE8, 0x80, 0x9B, 0xB4, 0x3C, 0xF3, 0xA3, 0xCD, 0xBF, .....
} //  一张很大的表格, 256*32

int count_step(unsigned char * buf) {
    char step = 0;
    int i;
    char map[] = { 0x00, 0x01, 0x01, 0x02, 0x01, 0x02, 0x02, 0x03, 0x01, 0x02, 
  0x02, 0x03, 0x02, 0x03, 0x03, 0x04, 0x01, 0x02, 0x02, 0x03, 
  0x02, 0x03, 0x03, 0x04, 0x02, 0x03, 0x03, 0x04, 0x03, 0x04, 
  0x04, 0x05, 0x01, 0x02, 0x02, 0x03, 0x02, 0x03, 0x03, 0x04, 
  0x02, 0x03, 0x03, 0x04, 0x03, 0x04, 0x04, 0x05, 0x02, 0x03, 
  0x03, 0x04, 0x03, 0x04, 0x04, 0x05, 0x03, 0x04, 0x04, 0x05, 
  0x04, 0x05, 0x05, 0x06, 0x01, 0x02, 0x02, 0x03, 0x02, 0x03, 
  0x03, 0x04, 0x02, 0x03, 0x03, 0x04, 0x03, 0x04, 0x04, 0x05, 
  0x02, 0x03, 0x03, 0x04, 0x03, 0x04, 0x04, 0x05, 0x03, 0x04, 
  0x04, 0x05, 0x04, 0x05, 0x05, 0x06, 0x02, 0x03, 0x03, 0x04, 
  0x03, 0x04, 0x04, 0x05, 0x03, 0x04, 0x04, 0x05, 0x04, 0x05, 
  0x05, 0x06, 0x03, 0x04, 0x04, 0x05, 0x04, 0x05, 0x05, 0x06, 
  0x04, 0x05, 0x05, 0x06, 0x05, 0x06, 0x06, 0x07, 0x01, 0x02, 
  0x02, 0x03, 0x02, 0x03, 0x03, 0x04, 0x02, 0x03, 0x03, 0x04, 
  0x03, 0x04, 0x04, 0x05, 0x02, 0x03, 0x03, 0x04, 0x03, 0x04, 
  0x04, 0x05, 0x03, 0x04, 0x04, 0x05, 0x04, 0x05, 0x05, 0x06, 
  0x02, 0x03, 0x03, 0x04, 0x03, 0x04, 0x04, 0x05, 0x03, 0x04, 
  0x04, 0x05, 0x04, 0x05, 0x05, 0x06, 0x03, 0x04, 0x04, 0x05, 
  0x04, 0x05, 0x05, 0x06, 0x04, 0x05, 0x05, 0x06, 0x05, 0x06, 
  0x06, 0x07, 0x02, 0x03, 0x03, 0x04, 0x03, 0x04, 0x04, 0x05, 
  0x03, 0x04, 0x04, 0x05, 0x04, 0x05, 0x05, 0x06, 0x03, 0x04, 
  0x04, 0x05, 0x04, 0x05, 0x05, 0x06, 0x04, 0x05, 0x05, 0x06, 
  0x05, 0x06, 0x06, 0x07, 0x03, 0x04, 0x04, 0x05, 0x04, 0x05, 
  0x05, 0x06, 0x04, 0x05, 0x05, 0x06, 0x05, 0x06, 0x06, 0x07, 
  0x04, 0x05, 0x05, 0x06, 0x05, 0x06, 0x06, 0x07, 0x05, 0x06, 
  0x06, 0x07, 0x06, 0x07, 0x07, 0x08};
    a = 0;
    for(i = 0;i < 32; i++) {
        a += map[buf[i]];
    }
    return a;
}

void geniv(int * prev_iv,char * buf) {
    a = (prev_iv[0] ^ prev_iv[1] ^ prev_iv[2] ^ prev_iv[3]) + 0x1234567;
    b = (prev_iv[7] ^ prev_iv[4] ^ prev_iv[5] ^ prev_iv[6]) - 0x1234568;
    // printf("%x %x\n",a,b); //0x0124292B 0xfedcba98
    unsigned int x,y;
    int i;

    x = a;
    y = b;

    for(i = 0;i < 32; i++) {
        y = 0x9069 * (unsigned short)y + (y >> 16);
        x = 0x4650 * (unsigned short)x + (x >> 16);
        buf[i] = x ^ *((char *)prev_iv + i);
    }

    a = x;
    b = y;
}
int check(unsigned char * input,unsigned int len) {
    int i,T;
    unsigned char buf[32] = {0};
    unsigned char iv[32] = {0xC4, 0xE3, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 
        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 
        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 
        0x00, 0x00};
    for(T = 0;T < len; T++) { //循环次数为input长度
        unsigned char * part_map = &map[input[T] * 32];
        memset(buf,0,32);
        geniv((int *)iv,buf);

        memcpy(iv,buf,0x20);
    }
    for(i = 0;i < 32;i++) {
        buf[i] ^= part_map[i];
    }
    return count_step(buf);
}

这个genIv函数中用到的实际上是一个随机数生成器Marsaglia’s MWC algorithm,只用到了半个,周期大约为5亿多。
算法用图示如下:

(图里写错了,第二个应该是map[Input[1]])
Input长度未知,只知道大于2bytes小于等于32bytes,需要最后产生的结果全为0.

 

============================================================

 

看了出题人的Writeup,使用随机性测试进行求解
还是脑洞不够大,gg
(不过在数据中放漏洞真的没问题吗


[招生]科锐逆向工程师培训(2024年11月15日实地,远程教学同时开班, 第51期)

最后于 2019-6-24 14:24 被acdxvfsvd编辑 ,原因: 太菜了
收藏
免费 0
支持
分享
最新回复 (0)
游客
登录 | 注册 方可回帖
返回
//