[XCTF-Reverse] 51 2019_UNCTF_BabyXor

"本文详细讲述了如何通过exeinfo和通用脱壳工具处理带有壳层的程序,揭示了主程序分为三段加密的复杂逻辑,包括字符操作和字符串拼接加密。最后揭示了flag:flag{2378b077-7d6e-4564-bdca-7eec8eede9a2}
摘要由CSDN通过智能技术生成

一打开看程序有壳,通过exeinfo查不到,用通用脱壳机脱成功。

主程序分3段加密

int main_0()
{
  int v0; // ST5C_4
  char *v1; // ST6C_4
  const char *v2; // ST68_4
  void *v3; // ST64_4
  size_t v4; // eax
  char *v5; // ST60_4

  sub_4010B4((int)dword_4395F0, dword_432020);
  sub_40107D((int)sub_40102D);
  if ( --stru_436270._cnt < 0 )
  {
    _filbuf(&stru_436270);
  }
  else
  {
    v0 = (unsigned __int8)*stru_436270._ptr;
    ++stru_436270._ptr;
  }
  v1 = sub_40108C((int)dword_435DC0, 56);
  v2 = sub_401041((int)dword_435DC0, (int)&dword_435DF8, 0x38u);// a1[i]^a2[i]^a1[i-1] v5[0] = a2[0] 14
  v3 = malloc(0x64u);
  v4 = strlen(v2);
  memcpy(v3, v2, v4);
  v5 = sub_4010C3((int)dword_435DC0, (int)v2, (int)&dword_435E30, 56);
  sub_40101E((int)v1, (int)v2, (int)v5);        // 3个串连一起
  return 0;
}
//第1段
char *__cdecl sub_401190(int a1, unsigned int a2)
{
  char *v3; // [esp+4Ch] [ebp-Ch]
  signed int i; // [esp+54h] [ebp-4h]

  v3 = (char *)malloc(a2 >> 2);
  for ( i = 0; i < (signed int)(a2 >> 2); ++i )
    sprintf(&v3[i], "%c", i ^ *(_DWORD *)(a1 + 4 * i));
  return v3;
}
//第2段
char *__cdecl sub_401240(int a1, int a2, size_t a3)
{
  signed int i; // [esp+4Ch] [ebp-Ch]
  char *v5; // [esp+50h] [ebp-8h]

  v5 = (char *)malloc(a3);
  sprintf(v5, "%c", *(_DWORD *)a2);
  for ( i = 1; i < (signed int)(a3 >> 2); ++i )
    sprintf(&v5[i], "%c", *(_DWORD *)(a1 + 4 * i) ^ *(_DWORD *)(a2 + 4 * i) ^ *(_DWORD *)(a1 + 4 * i - 4));
  return v5;
}
//第3段
char *__cdecl sub_401320(int a1, int a2, int a3, unsigned int a4)
{
  int i; // [esp+4Ch] [ebp-10h]
  char *v6; // [esp+50h] [ebp-Ch]
  char *v7; // [esp+54h] [ebp-8h]

  v7 = (char *)malloc(a4 - 1);
  v6 = (char *)malloc(4 * a4 - 1);
  for ( i = 0; i < (signed int)((a4 >> 2) - 1); ++i )
  {
    sprintf(&v6[i], "%c", *(_DWORD *)(a3 + 4 * i + 4) ^ *(char *)(i + a2));
    sprintf(&v7[i], "%c", i ^ v6[i]);
  }
  sprintf(&byte_439558, "%c", 45);
  strcat(&byte_439558, v7);
  return &byte_439558;
}

每一段都不绕,但小细节挺讨厌,中间要加个'-' 想半天

a = [0x66, 0x6D, 0x63, 0x64, 0x7F, 0x37, 0x35, 0x30, 0x30, 0x6B, 0x3A, 0x3C, 0x3B, 0x20]
b = [0x37, 0x6F, 0x38, 0x62, 0x36, 0x7C, 0x37, 0x33, 0x34, 0x76, 0x33, 0x62, 0x64, 0x7a]
c = [0x1a,    0,    0, 0x51, 5,    0x11, 0x54, 0x56, 0x55, 0x59, 0x1D,    9, 0x5D, 0x12, 0]

#a[i]^i
v1 = bytes([i^a[i] for i in range(14)])

#a1[i]^a2[i]^a1[i-1] v5[0] = a2[0] 14
v2 = bytes([b[0]])
v2 += bytes([a[i]^b[i]^a[i-1] for i in range(1,14)])

#- c[i+1]^v2[i]^i 
v6 = b'-'+bytes([c[i+1]^v2[i]^i for i in range(14)])

print(v1+v2+v6)
#b'flag{2378b077-7d6e-4564-bdca-7eec8eede9a2}l'
#flag{2378b077-7d6e-4564-bdca-7eec8eede9a2}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值