[XCTF-Reverse] 62 XCTF 4th-QCTF-2018_asong

这是个比较正规的逆向题

主程序先读入flag然后打开一个文档并统计字频然后加密输出到out文件

__int64 __fastcall main(__int64 a1, char **a2, char **a3)
{
  void *v3; // ST00_8
  const char *v4; // ST08_8

  v3 = malloc(0xBCuLL);
  v4 = (const char *)malloc(0x50uLL);
  init_0();
  read_flag((__int64)v4);
  sub_400C02((__int64)v4);                      // 去皮
  sub_400AAA("that_girl", (__int64)v3);         // v3统计字频
  sub_400E54(v4, (__int64)v3);                  // 加密输出
  return 0LL;
}

加密输入这块先转码再重排序然后整串循环向左移3位

unsigned __int64 __fastcall sub_400E54(const char *a1, __int64 a2)
{
  int i; // [rsp+18h] [rbp-48h]
  int v4; // [rsp+1Ch] [rbp-44h]
  char v5[56]; // [rsp+20h] [rbp-40h]
  unsigned __int64 v6; // [rsp+58h] [rbp-8h]

  v6 = __readfsqword(0x28u);
  v4 = strlen(a1);
  for ( i = 0; i < v4; ++i )
    v5[i] = *(_DWORD *)(4LL * (signed int)trancode(a1[i]) + a2);
  sub_400D33((unsigned __int8 *)v5);            // 交换顺序
  sub_400DB4(v5, v4);                           // 前3后5交错
  write_file((__int64)v5, "out", v4);
  return __readfsqword(0x28u) ^ v6;
}

转码部分,这块由于不知道flag用的字符是哪些,这个转码并不是所有转码都正确(仅有用的字符正确)但逆向时就麻烦了,所以在这里需要改一下再逆。

__int64 __fastcall trancode(char a1)
{
  __int64 result; // rax

  result = (unsigned int)(a1 - 10);
  switch ( a1 )
  {
    case 10:
      result = (unsigned int)(a1 + 35);
      break;
    case 32:
    case 33:
    case 34:
      result = (unsigned int)(a1 + 10);
      break;
    case 39:
      result = (unsigned int)(a1 + 2);
      break;
    case 44:
      result = (unsigned int)(a1 - 4);
      break;
    case 46:
      result = (unsigned int)(a1 - 7);
      break;
    case 58:
    case 59:
      result = (unsigned int)(a1 - 21);
      break;
    case 63:
      result = (unsigned int)(a1 - 27);
      break;
    case 95:
      result = (unsigned int)(a1 - 49);
      break;
    default:
      if ( a1 <= 47 || a1 > 48 )
      {
        if ( a1 <= 64 || a1 > 90 )
        {
          if ( a1 > 96 && a1 <= 122 )
            result = (unsigned int)(a1 - 87);
        }
        else
        {
          result = (unsigned int)(a1 - 55);
        }
      }
      else
      {
        result = (unsigned int)(a1 - 48);
      }
      break;
  }
  return result;
}

交换位置这块看起来先绕,不过想想快排啥的,大意就是按一个顺序表重排

__int64 __fastcall sub_400D33(unsigned __int8 *a1)
{
  __int64 result; // rax
  _BYTE v2[5]; // [rsp+13h] [rbp-5h]

  v2[4] = 0;
  *(_DWORD *)v2 = *a1;
  while ( dword_6020A0[*(signed int *)&v2[1]] )
  {
    a1[*(signed int *)&v2[1]] = a1[dword_6020A0[*(signed int *)&v2[1]]];
    *(_DWORD *)&v2[1] = dword_6020A0[*(signed int *)&v2[1]];
  }
  result = v2[0];
  a1[*(signed int *)&v2[1]] = v2[0];
  return result;
}

整体循环错3位这块,理解起来还不难

_BYTE *__fastcall sub_400DB4(_BYTE *a1, int a2)
{
  _BYTE *result; // rax
  char v3; // [rsp+17h] [rbp-5h]
  int i; // [rsp+18h] [rbp-4h]

  v3 = *a1 >> 5;
  for ( i = 0; a2 - 1 > i; ++i )
    a1[i] = 8 * a1[i] | (a1[i + 1] >> 5);
  result = &a1[i];
  *result = 8 * *result | v3;
  return result;
}

这里换顺序这块可以后作,都是单个字节处理所以后两步不影响顺序,当flag的字符都出来后换顺序可以很容易验证

第1步先循环右移3位

第2步恢复原来的字符

第3步再恢复原来的顺序,表里的序号就是字符在原串中的位置

v3的词频转码表可以gdb中得到,dword_6020a0在程序里有

转换表不区分大小写,大概可以接数字0-9,字母1-35,然后是一堆符号,不能直接用原程序转。

#v3 词频转码表
v3 = [0,0,0,0,0,0,0,0,0,0,104,30,15,29,169,19,38,67,60,0,20,39,28,118,165,26,0,61,51,133,45,7,34,0,62,0,0,0,0,0,0,40,71,0,0,66,245,0,0,0,97,0]
#dword_6020a0 顺序表
dword_6020a0 = [22,0,6,2,30,24,9,1,21,7,18,10,8,12,17,23,13,4,3,14,19,11,20,16,15,5,25,36,27,28,29,37,31,32,33,26,34,35]

#1 循环向右移3位(尾3位移到头)
a = open('out', 'rb').read()
b = ''
for i in a:
    b += bin(i)[2:].rjust(8, '0')
b = b[-3:]+b[:-3]
c = b''
for i in range(0, len(b), 8):
    c += bytes([int(b[i:i+8], 2)])
b = c
print(b)

def trancode(a):
    if a==10:
        return a+35
    elif (a==32) or (a==33) or (a==34):
        return a+10
    elif a==39:
        return a+2
    elif a==44:
        return a-4
    elif a==46:
        return a-7
    elif (a==58) or (a==59):
        return a-21
    elif a==63:
        return a-27
    elif a==95:
        return a-49
    else:
        if a <48 or a>57:   #数字
            if (a<=64) or (a>90):
                if (a>96) and (a<=122):
                    return a-87  #大写字母 不区分
                else:
                    return -1
            else:
                return a-55  #小写字母
        else:
            return a-48  #0-9
    return a-10

code = [0]*256
for i in range(256):
    code[i] = (256+trancode(i))%256
#print(code)
c = ''
for i in b:
    t1 = v3.index(i)
    t2 = code.index(t1)
    c += chr(t2)
    #print(i, t1, t2)
print(c)

a = list(c) 
for i,v in enumerate(dword_6020a0):
    a[v]=c[i]
print(''.join(a))
#THAT_GIRL_SAYING_NO_FOR_YOUR_VINDICATE
#QCTF{that_girl_saying_no_for_your_vindicate}

最后提交的时候加上包裹,由于转码程序不分大小写,大写提交不成改小写成功。

### 回答1: pure_color xctf是一个CTF比赛平台,致力于举办和推广网络安全竞赛。 pure_color xctf的目标是为安全爱好者和专业人士提供一个学习、切磋和交流的平台。这个平台上举办的比赛覆盖了各种网络安全领域,包括但不限于网络攻防、密码学、逆向工程等。通过参与这些比赛,参赛者可以提升自己的技能,了解最新的安全威胁和攻击技术,锻炼解决问题的能力。 pure_color xctf的比赛模式多样,可以是个人或团队参与。参赛者需要在限定的时间内完成一系列的题目,这些题目可能包含漏洞分析、编程挑战、数据分析等。比赛过程中,参赛者需要运用各种技术手段,如渗透测试、代码审计、漏洞利用等,解决题目的要求。参赛者不仅需要具备网络安全相关的知识,还需要具备良好的团队合作和解决问题的能力。 此外,pure_color xctf也为参赛者提供了一个交流平台。比赛期间,参赛者可以在平台上与其他选手交流经验、讨论解题思路。参赛者也可以通过竞赛结果来评估自己的能力,并与其他选手进行切磋比拼。 总之,pure_color xctf是一个举办网络安全竞赛的平台,旨在为安全爱好者和专业人士提供学习和交流的机会,促进网络安全技术的发展。 ### 回答2: pure_color xctf 是一项竞技性的网络安全挑战赛。XCCTF 是全球知名的网络安全竞赛组织之一,而 pure_color 是该竞赛组织内的一项赛事。该赛事旨在提升参赛者的网络安全技能和知识,让他们在一个仿真的网络环境中进行攻防对抗。 在 pure_color xctf 中,参赛队伍将根据题目要求进行网络攻击和防御。这些题目有不同的难度级别,并涵盖了各种不同的网络安全技术和攻击类型。参赛队伍将需要利用他们的知识和技能,像真实的黑客一样去攻击系统漏洞,获取目标系统内的敏感信息或是直接控制目标系统。同时,他们也需要通过搭建防御策略和系统来保护自己的系统免受攻击。 pure_color xctf 不仅仅是一个交流学习的平台,也是一个展示能力的舞台。优胜的参赛队伍将会被邀请参加更高级别的网络安全竞赛和会议,进一步提升他们的技能并扩展职业网络。此外,pure_color xctf 也为参赛者提供了一个找到职业机会的平台,很多安全公司和组织会在赛事期间招聘优秀的选手。 总而言之,pure_color xctf 是一个有挑战性的网络安全竞赛,旨在通过攻击和防御对抗提升参赛者的技能,并为他们提供职业发展和展示的机会。同时,这个赛事也在促进网络安全领域的交流和合作,为提升整个网络安全行业的水平做出贡献。 ### 回答3: pure_color xctf 是一个CTF(Capture The Flag,夺旗赛)竞赛平台。CTF是一种网络安全竞赛,旨在让参赛者通过解决一系列的密码学、逆向工程、漏洞利用等问题来获取旗标,比赛者可以通过这些旗标来获取积分并竞争排名。 pure_color xctf 平台是一个为CTF竞赛提供的一个在线环境,类似于一个实验室,用于举办CTF比赛。在这个平台上,参赛者可以注册账号并加入已经发布的CTF赛事中。赛事中的题目被分为不同的难度级别,涵盖了各种安全领域的知识。参赛者需要通过解决题目中的任务来获取旗标,并将其提交到平台上进行验证。在比赛结束后,将根据参赛者解决的题目数量、用时、积分等因素来计算最终排名,并颁发奖励给获胜者。 pure_color xctf 提供了逼真的仿真环境,使得参赛者能够在一个安全的网络环境下进行实时的攻防演练。平台上的题目多样化且具有挑战性,旨在让参赛者将所学的理论知识应用到实际场景中去,并培养解决问题和团队合作的能力。同时,pure_color xctf 还为参赛者提供了交流平台,方便他们在比赛过程中与其他参赛者交流经验、技巧以及解题思路。 总之,pure_color xctf 是一个提供CTF竞赛平台的在线环境,旨在鼓励参赛者在安全领域中深入学习和实践,并通过解决各种挑战赛题目来提升技能和知识水平。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值