首页 > 其他 > 详细

网鼎杯2020 joker逆向

时间:2020-05-10 21:47:03      阅读:114      评论:0      收藏:0      [点我收藏+]

gcc编译,无壳:

技术分享图片技术分享图片技术分享图片

 

看一下程序结构:

程序有函数分析错误,堆栈的原因,我就没改它了,因为汇编也简单,上手就撸:

技术分享图片技术分享图片

 

 

第一个关键块:

技术分享图片技术分享图片

4017DD就是一个字符串拷贝函数,动态可见,然后4017EB是第一个无用函数,看一下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
char *__cdecl wrong(char *a1)
{
  char *result; // eax
  signed int i; // [esp+Ch] [ebp-4h]
 
  for ( i = 0; i <= 23; ++i )
  {
    if ( i & 1 )
    {
      result = &a1[i];
      a1[i] -= i;
    }
    else
    {
      result = &a1[i];
      a1[i] ^= i;
    }
  }
  return result;
}

a1就是输入的flag,简单操作之后到4017F9函数判断:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
int __cdecl omg(char *a1)
{
  int result; // eax
  int v2[24]; // [esp+18h] [ebp-80h]
  int i; // [esp+78h] [ebp-20h]
  int v4; // [esp+7Ch] [ebp-1Ch]
 
  v4 = 1;
  qmemcpy(v2, byte_4030C0, sizeof(v2));
  for ( i = 0; i <= 23; ++i )
  {
    if ( a1[i] != v2[i] )
      v4 = 0;
  }
  if ( v4 == 1 )
    result = puts("hahahaha_do_you_find_me?");
  else
    result = puts("wrong ~~ But seems a little program");
  return result;
}

byte_4030C0是硬编码字符,大概逆一下得到虚假flag:

byte_4030c0=[0x66, 0x6B, 0x63, 0x64, 0x7F, 0x61,  0x67, 0x64, 0x3B, 0x56, 0x6B, 0x61, 0x7B, 0x26, 0x3B, 0x50, 0x63, 0x5F, 0x4D, 0x5A, 0x71, 0x0C, 0x37, 0x66]

flag=""

for i in range(23):

    if i &1:

        byte_4030c0[i]+=i

    else:

        byte_4030c0[i]^=i

 

for i in range(23):

    flag+=chr(byte_4030c0[i])

print(flag)

 

flag{fak3_alw35_sp_me!!

 

肯定是不对的,然后下面这块吸引我的注意:

技术分享图片技术分享图片

 

有smc操作,而且代码中确实有很多没有解释的byte,解密函数很简单,写idc也行,我直接动态调试:

虚假函数nop掉:

技术分享图片技术分享图片技术分享图片

这就是刚刚的fake函数,nop掉就行:

下面就是自解密函数:

技术分享图片技术分享图片

解密位置是401500,断在182D,然后过掉看结果:

技术分享图片技术分享图片

 

之后就是调用这块代码了:

跟进去,单步可以看得到懂逻辑的:

 

技术分享图片技术分享图片

 

大概意思就是输入的位数,和hahahaha_do_you_find_me?这个字符串异或之后,等于3040位置的硬编码值

意思很简单,单步就ok

 

然后解密得到前部分flag:

str=[0x0E,0x0D,0x09,0x06,0x13,0x05,0x58,0x56,0x3E,0x06,0x0C,0x3C,0x1F,0x57,0x14,0x6B,0x57,0x59,0x0D]

str2="hahahaha_do_you_find_me?"

flag=""

for i in range(19):

    flag+=chr(str[i]^ ord(str2[i]))

print(flag)

 

flag{d07abccf8a410c

 

但是位数明显不够,少5位,还有一个finall函数:

技术分享图片技术分享图片

 

动态的时候这一步改jmp,或者z=0过掉:

技术分享图片技术分享图片

 

进入final函数:

技术分享图片技术分享图片

 

如果是字节强制分析就成:

时间函数过滤,没用:

技术分享图片技术分享图片

 

会得到%tp&:  五个字符,后面竟然和前面的flag{做比较

技术分享图片技术分享图片

 

所以忙猜这是flag最后的五个字节,:就是 }的异或答案,那么:答案就是b37a}

 

所以

flag{d07abccf8a410cb37a}

 

 

 

总结:感染函数,自解密很到位,但最后的函数确实有点无脑,这样盲猜不适合大型比赛,不行就好好整算法题目像kctf一样(手动狗头.jpg)

网鼎杯2020 joker逆向

原文:https://www.cnblogs.com/jentleTao/p/12865189.html

(0)
(0)
   
举报
评论 一句话评论(0
关于我们 - 联系我们 - 留言反馈 - 联系我们:wmxa8@hotmail.com
© 2014 bubuko.com 版权所有
打开技术之扣,分享程序人生!