首页
社区
课程
招聘
[原创]KCTF2022秋季赛 第二题 盗贼作乱 题解
发表于: 2022-11-30 12:26 8813

[原创]KCTF2022秋季赛 第二题 盗贼作乱 题解

2022-11-30 12:26
8813

根据调试,确定函数的功能

首先通过第一个if条件进入while 1循环后,进入第一个函数调试,会发现程序会有一个大数结构

那么前面的函数的功能也可以据此bignum推测出来了。

此时main函数的比较部分整理出来如下:

难搞的是sbf1sbf2函数,因为此函数多次引用了main函数里面的全局变量,而且包含多个if条件,在乘法计算完后有这些操作

而这些函数里面又有类似sbf1的操作

理性分析一下会发现一个问题:
sbf1sbf2函数改了哪些变量呢?

改了图里的firststagenumbersecondstageNumber

这两个变量在执行compare 比较之前会被重新赋值,没有问题

还有在特殊条件下有一个条件会改example->data的值

这个example->data是前面用来取模的数

这个特殊条件又是写死的。

example->data + 32 == 32时,即在内存布局中

i == 32时,example->data + 36 (succ) += 4;

说人话即是

计算方程

的两个解

这里直接z3解

 
 
struct bignum{
    int len;
    uint8_t data[32];
}
struct bignum{
    int len;
    uint8_t data[32];
}
 
if ( v3 > 0
   && (v6 = v4 - v3, v4 - v3 > 0)
   && frombase62(first, &a2, v3, table) > 0
   && frombase62(&second, &v10[v3], v6 - 1, table) > 0
   && (frombase62(&example, "IRtzloZ6iuB", strlen("IRtzloZ6iuB"), table),
       init(firstop, 0),
       init(secondop, 0),
       compare((char *)first, (char *)&second) < 0)
   && compare((char *)first, (char *)&example) < 0
   && compare((char *)&second, (char *)&example) < 0 )
 {
   v7 = 0;
   while ( 1 )
   {
     i = v7 + 1;
     plus(firstop, firstop, first);
     plus(secondop, secondop, &second);
     mod((unsigned int *)firstop, (char *)firstop, (char *)&example);
     mod((unsigned int *)secondop, (char *)secondop, (char *)&example);
     init(&firststageNumber, 1);
     sub(&firststageNumber, firstop, &firststageNumber);
     if ( !compare((char *)&firststageNumber, (char *)first) )
     {
       ++succ;
       sbf1(&firststageNumber, &firststageNumber, first);// sbf1唯一的作用就是当i==32时,succ+=4
     }
     init(&secondStageNumber, 1);
     plus(&secondStageNumber, secondop, &secondStageNumber);
     if ( !compare((char *)&secondStageNumber, (char *)&second) )
     {
       ++succ;
       sbf2(&secondStageNumber, (char *)&example, (char *)&second);// sbf2唯一的作用就是当i==32时,succ+=4
     }
     if ( succ == 10 )
       break;
     v7 = i;
     if ( i >= 2097152 )
       goto LABEL_20;
   }
   sub_40284A((int)aSuccess);
   return 0;
 }
if ( v3 > 0
   && (v6 = v4 - v3, v4 - v3 > 0)
   && frombase62(first, &a2, v3, table) > 0
   && frombase62(&second, &v10[v3], v6 - 1, table) > 0
   && (frombase62(&example, "IRtzloZ6iuB", strlen("IRtzloZ6iuB"), table),
       init(firstop, 0),
       init(secondop, 0),
       compare((char *)first, (char *)&second) < 0)
   && compare((char *)first, (char *)&example) < 0
   && compare((char *)&second, (char *)&example) < 0 )
 {
   v7 = 0;
   while ( 1 )
   {
     i = v7 + 1;
     plus(firstop, firstop, first);
     plus(secondop, secondop, &second);
     mod((unsigned int *)firstop, (char *)firstop, (char *)&example);
     mod((unsigned int *)secondop, (char *)secondop, (char *)&example);
     init(&firststageNumber, 1);
     sub(&firststageNumber, firstop, &firststageNumber);
     if ( !compare((char *)&firststageNumber, (char *)first) )
     {
       ++succ;
       sbf1(&firststageNumber, &firststageNumber, first);// sbf1唯一的作用就是当i==32时,succ+=4
     }
     init(&secondStageNumber, 1);
     plus(&secondStageNumber, secondop, &secondStageNumber);
     if ( !compare((char *)&secondStageNumber, (char *)&second) )
     {
       ++succ;
       sbf2(&secondStageNumber, (char *)&example, (char *)&second);// sbf2唯一的作用就是当i==32时,succ+=4
     }
     if ( succ == 10 )
       break;
     v7 = i;
     if ( i >= 2097152 )
       goto LABEL_20;
   }
   sub_40284A((int)aSuccess);
   return 0;
 }
arrAnd(&firststageNumber, firstop, secondop);
    if ( compare((char *)&firststageNumber, (char *)&secondStageNumber) > 0 && succ > 0 )
    {
      maybe_div2(&firststageNumber, &firststageNumber, i);
      plus(&secondStageNumber, first, second);
      sub(&firststageNumber, &firststageNumber, &secondStageNumber);
    }
    init(&firststageNumber, 4);
    shlarg3(&secondStageNumber, &firststageNumber, 3);
    if ( succ > 0
      && *(int *)((char *)&examplerawNumber + (unsigned __int8)SecondStageNumber) == (unsigned __int8)SecondStageNumber )// i == 32
    {
      plus(&firststageNumber, &firststageNumber, &secondStageNumber);
      v13 = GetModImm(&firststageNumber, i);
      *((_BYTE *)&examplerawNumber + *((unsigned __int8 *)&firststageNumber + 4)) += 4;
      shlarg3(&firststageNumber, &firststageNumber, v13);
      sub(&secondStageNumber, &firststageNumber, &secondStageNumber);
    }
arrAnd(&firststageNumber, firstop, secondop);

[注意]传递专业知识、拓宽行业人脉——看雪讲师团队等你加入!

收藏
免费 2
支持
分享
最新回复 (0)
游客
登录 | 注册 方可回帖
返回
//