BUUCTF reverse wp 65 - 70

news2024/11/26 4:22:45

[SWPU2019]ReverseMe

在这里插入图片描述

反编译的伪码看不明白, 直接动调
在这里插入图片描述

这里显示"Please input your flag", 然后接受输入, 再和32进行比较, 应该是flag长度要求32位, 符合要求则跳转到loc_E528EE分支继续执行

动调之后伪码可以读了

int __cdecl main(int argc, const char **argv, const char **envp)
{
  int v3; // ecx
  int *v4; // eax
  int v5; // ecx
  int *v6; // eax
  char *v7; // esi
  int i; // edi
  unsigned int xor_len; // kr00_4
  void **v10; // ecx
  __int128 *v11; // ecx
  char *checkval; // ecx
  __int128 *buf; // edx
  unsigned int v14; // edi
  int checkarr; // eax
  int v16; // eax
  bool v17; // cf
  unsigned __int8 v18; // al
  unsigned __int8 v19; // al
  unsigned __int8 v20; // al
  const char *output; // edx
  int *v22; // eax
  char *v23; // eax
  int v25; // [esp-14h] [ebp-D8h]
  int v26; // [esp-10h] [ebp-D4h]
  void *input[4]; // [esp+24h] [ebp-A0h] BYREF
  int length; // [esp+34h] [ebp-90h]
  unsigned int v29; // [esp+38h] [ebp-8Ch]
  __int128 processed[2]; // [esp+3Ch] [ebp-88h] BYREF
  int v31; // [esp+5Ch] [ebp-68h]
  __int128 v32; // [esp+60h] [ebp-64h] BYREF
  __int128 v33; // [esp+70h] [ebp-54h]
  int v34; // [esp+80h] [ebp-44h]
  char xorval[16]; // [esp+84h] [ebp-40h] BYREF
  char v36[32]; // [esp+94h] [ebp-30h] BYREF
  int v37; // [esp+C0h] [ebp-4h]

  length = 0;
  v29 = 15;
  LOBYTE(input[0]) = 0;
  v37 = 1;
  v4 = sub_E52DA0(v3, "Please input your flag: ");
  sub_E53050(v4);
  sub_E537B0((int)&dword_E80068, input);
  strcpy(xorval, "SWPU_2019_CTF");
  if ( length == 32 )
  {
    *(_DWORD *)&v36[16] = -1173078761;
    *(_DWORD *)&v36[20] = 494076752;
    *(_DWORD *)&v36[24] = -1811652486;
    *(_DWORD *)&v36[28] = 688582768;
    i = 0;
    v32 = 0i64;
    v34 = 0;
    v33 = 0i64;
    xor_len = strlen(xorval);
    do                                          // xor
    {
      v10 = input;
      if ( v29 >= 0x10 )
        v10 = (void **)input[0];
      *((_BYTE *)v10 + i) ^= xorval[i % xor_len];
      ++i;
    }
    while ( i < 32 );
    v11 = (__int128 *)input;
    v7 = (char *)input[0];
    if ( v29 >= 0x10 )
      v11 = (__int128 *)input[0];
    v31 = 0;
    memset(processed, 0, sizeof(processed));
    v32 = *v11;
    v33 = v11[1];
    sub_E525C0(v25, v26, 256, (unsigned int)&v32, (unsigned int)processed);// ?
    *(_DWORD *)v36 = 4161746867;
    *(_DWORD *)&v36[4] = 1571732668;
    checkval = v36;
    *(_DWORD *)&v36[8] = -2041750854;
    buf = processed;
    *(_DWORD *)&v36[12] = -748513468;
    v14 = 28;
    *(_DWORD *)&v36[16] = 371505743;
    *(_DWORD *)&v36[20] = 443719435;
    *(_DWORD *)&v36[24] = 644704357;
    *(_DWORD *)&v36[28] = 1741188026;
    while ( 1 )
    {
      checkarr = *(_DWORD *)checkval;
      if ( *(_DWORD *)checkval != *(_DWORD *)buf )
        break;
      checkval += 4;
      buf = (__int128 *)((char *)buf + 4);
      v17 = v14 < 4;
      v14 -= 4;
      if ( v17 )
      {
        v16 = 0;
        goto LABEL_19;
      }
    }
    v17 = (unsigned __int8)checkarr < *(_BYTE *)buf;// v15 < v13
    if ( (_BYTE)checkarr == *(_BYTE *)buf
      && (v18 = checkval[1], v17 = v18 < *((_BYTE *)buf + 1), v18 == *((_BYTE *)buf + 1))
      && (v19 = checkval[2], v17 = v19 < *((_BYTE *)buf + 2), v19 == *((_BYTE *)buf + 2))
      && (v20 = checkval[3], v17 = v20 < *((_BYTE *)buf + 3), v20 == *((_BYTE *)buf + 3)) )
    {
      v16 = 0;
    }
    else
    {
      v16 = v17 ? -1 : 1;                       // v17 should be True
    }
LABEL_19:
    if ( v16 )                                  // v16 should be 0
      output = "Try again!\r\n";
    else
      output = "Congratulations! I always knew you could do it.";
    v22 = sub_E52DA0((int)checkval, output);
    sub_E53050(v22);
    sub_E5ADBE("pause");
  }
  else
  {
    v6 = sub_E52DA0(v5, "Try again!\r\n");
    sub_E53050(v6);
    sub_E5ADBE("pause");
    v7 = (char *)input[0];
  }
  if ( v29 >= 0x10 )
  {
    v23 = v7;
    if ( v29 + 1 >= 0x1000 )
    {
      v7 = (char *)*((_DWORD *)v7 - 1);
      if ( (unsigned int)(v23 - v7 - 4) > 0x1F )
        _invalid_parameter_noinfo_noreturn();
    }
    sub_E564DE(v7);
  }
  return 0;
}

checkval可以直接动调出来, 和input处理过后的值进行比较, 全部通过就是congratulation, 需要逆sub_E525C0这个函数, 动调一下猜测是某种加密函数, Findcrypt一下没有明确结果, 继续读一下伪码

void __cdecl sub_E525C0(int a1, int a2, int a3, unsigned int input, unsigned int processed)
{
  unsigned __int8 *v5; // ecx
  unsigned int process_tmp; // ebx
  unsigned __int8 *v7; // esi
  unsigned int v8; // edi
  unsigned int v9; // esi
  unsigned int v10; // edx
  unsigned int v11; // esi
  _DWORD *v12; // ecx
  int v13; // eax
  unsigned int v14; // ebx
  char *v15; // esi
  __m128i v16; // xmm0
  __m128i v17; // xmm1
  __m128i v18; // xmm0
  __m128i v19; // xmm1
  __m128i v20; // xmm0
  __m128i v21; // xmm1
  __m128i v22; // xmm0
  __m128i v23; // xmm1
  int v24; // ebx
  unsigned int v25; // eax
  char *v26; // esi
  unsigned int v27; // edi
  int v28; // ecx
  signed int v29; // [esp+20h] [ebp-20h]
  int v30; // [esp+24h] [ebp-1Ch]
  _DWORD *Block; // [esp+28h] [ebp-18h]
  int v32[4]; // [esp+2Ch] [ebp-14h] BYREF

  process_tmp = processed;
  v7 = v5;
  v8 = (unsigned int)(a3 + 31) >> 5;
  v30 = 4 * v8;
  Block = malloc(4 * v8);
  v32[0] = -1839987866;
  v32[1] = 120;
  v32[2] = -1839987866;
  v32[3] = 120;
  sub_E52270(v7, (unsigned __int8 *)v32);
  sub_E520E0();
  sub_E52150();
  sub_E51F80();
  v29 = 0;
  if ( v8 )
  {
    do
    {
      dword_E80D94 = (2 * dword_E80DA4) ^ (unsigned __int16)(dword_E80DBC ^ (2 * dword_E80DA4));
      dword_E80D78 = (dword_E80DB8 << 16) | ((unsigned int)dword_E80DAC >> 15);
      v9 = (dword_E80D70 << 16) | ((unsigned int)dword_E80D90 >> 15);
      dword_E80D8C = (dword_E80D68 << 16) | ((unsigned int)dword_E80D84 >> 15);
      dword_E80D7C = v9;
      Block[v29] = v9 ^ sub_E52150();
      sub_E51F80();
      ++v29;
    }
    while ( v29 < (int)v8 );
    process_tmp = processed;
  }
  v10 = 0;
  if ( v8 )
  {
    v11 = input;
    if ( v8 < 0x10 || process_tmp <= input + v30 - 4 && process_tmp + v30 - 4 >= input )
    {
      v12 = Block;
    }
    else
    {
      v12 = Block;
      if ( process_tmp > (unsigned int)&Block[v8 - 1] || process_tmp + v30 - 4 < (unsigned int)Block )
      {
        v13 = input + 16;
        v12 = Block;
        v14 = process_tmp + 32;
        v15 = (char *)Block - input;
        do
        {
          v16 = *(__m128i *)(v13 - 16);
          v13 += 64;
          v14 += 64;
          v17 = _mm_xor_si128(*(__m128i *)&Block[v10], v16);
          v18 = *(__m128i *)(v13 - 64);
          *(__m128i *)(v14 - 96) = v17;
          v19 = _mm_xor_si128(*(__m128i *)&v15[v13 - 64], v18);
          v20 = *(__m128i *)(v13 - 48);
          *(__m128i *)(processed - input + v13 - 64) = v19;
          v15 = (char *)Block - input;
          v21 = _mm_xor_si128(*(__m128i *)((char *)Block + v14 - processed - 64), v20);
          v22 = *(__m128i *)(v13 - 32);
          *(__m128i *)(v14 - 64) = v21;
          v23 = *(__m128i *)&Block[v10 + 12];
          v10 += 16;
          *(__m128i *)(v14 - 48) = _mm_xor_si128(v23, v22);
        }
        while ( v10 < (v8 & 0xFFFFFFF0) );
        process_tmp = processed;
        v11 = input;
      }
    }
    if ( v10 < v8 )
    {
      v24 = process_tmp - input;
      v25 = v11 + 4 * v10;
      v26 = (char *)v12 - input;
      v27 = v8 - v10;
      do
      {
        v28 = *(_DWORD *)&v26[v25];
        v25 += 4;
        *(_DWORD *)(v24 + v25 - 4) = *(_DWORD *)(v25 - 4) ^ v28;
        --v27;
      }
      while ( v27 );
    }
  }
  free(Block);
}

发现processed在前面一大段操作里并没有作为左值进行, 只有最后一段进行了相关的赋值操作, 所以processed的值只在这一段指令之后确定

在这里插入图片描述

伪码不清不楚, 直接读汇编, 结合动调的数值进行对比, 得知[esi + eax]存的就是与input处理之后数值xor的数组
在这里插入图片描述

shift+E导出, 两次xor处理, 逆回去就是flag

xorval = 'SWPU_2019_CTF'

checkval = [
    0xB3, 0x37, 0x0F, 0xF8, 0xBC, 0xBC, 0xAE, 0x5D, 0xBA, 0x5A, 
    0x4D, 0x86, 0x44, 0x97, 0x62, 0xD3, 0x4F, 0xBA, 0x24, 0x16, 
    0x0B, 0x9F, 0x72, 0x1A, 0x65, 0x68, 0x6D, 0x26, 0xBA, 0x6B, 
    0xC8, 0x67
]
# print(len(xorval))

process = [
    0x86, 0x0C, 0x3E, 0xCA, 0x98, 0xD7, 0xAE, 0x19, 0xE2, 0x77, 
    0x6B, 0xA6, 0x6A, 0xA1, 0x77, 0xB0, 0x69, 0x91, 0x37, 0x05, 
    0x7A, 0xF9, 0x7B, 0x30, 0x43, 0x5A, 0x4B, 0x10, 0x86, 0x7D, 
    0xD4, 0x28
]

tmp = [0 for _ in range(32)]
for i in range(32):
    tmp[i] = process[i] ^ checkval[i]

for i in range(32):
    tmp[i] ^= ord(xorval[i % len(xorval)])
    tmp[i] = chr(tmp[i])

flag = ''.join(tmp)
print(flag)

[羊城杯 2020]login

在这里插入图片描述

pyinstaller, 解包工具 https://github.com/extremecoders-re/pyinstxtractor

>python pyinstxtractor.py attachment.exe
[+] Processing attachment.exe
[+] Pyinstaller version: 2.1+
[+] Python version: 3.6
[+] Length of package: 6021662 bytes
[+] Found 59 files in CArchive
[+] Beginning extraction...please standby
[+] Possible entry point: pyiboot01_bootstrap.pyc
[+] Possible entry point: login.pyc
[!] Warning: This script is running in a different Python version than the one used to build the executable.
[!] Please run this script in Python 3.6 to prevent extraction errors during unmarshalling
[!] Skipping pyz extraction
[+] Successfully extracted pyinstaller archive: attachment.exe

You can now use a python decompiler on the pyc files within the extracted directory

uncompyle6进行反编译, 拿到源码

# uncompyle6 version 3.9.0
# Python bytecode version base 3.6 (3379)
# Decompiled from: Python 3.6.13 |Anaconda, Inc.| (default, Mar 16 2021, 11:37:27) [MSC v.1916 64 bit (AMD64)]
# Embedded file name: login.py
import sys
input1 = input('input something:')
if len(input1) != 14:
    print('Wrong length!')
    sys.exit()
else:
    code = []
    for i in range(13):
        code.append(ord(input1[i]) ^ ord(input1[i + 1]))

    code.append(ord(input1[13]))
    a1 = code[2]
    a2 = code[1]
    a3 = code[0]
    a4 = code[3]
    a5 = code[4]
    a6 = code[5]
    a7 = code[6]
    a8 = code[7]
    a9 = code[9]
    a10 = code[8]
    a11 = code[10]
    a12 = code[11]
    a13 = code[12]
    a14 = code[13]
    if (a1 * 88 + a2 * 67 + a3 * 65 - a4 * 5 + a5 * 43 + a6 * 89 + a7 * 25 + a8 * 13 - a9 * 36 + a10 * 15 + a11 * 11 + a12 * 47 - a13 * 60 + a14 * 29 == 22748) & \
    (a1 * 89 + a2 * 7 + a3 * 12 - a4 * 25 + a5 * 41 + a6 * 23 + a7 * 20 - a8 * 66 + a9 * 31 + a10 * 8 + a11 * 2 - a12 * 41 - a13 * 39 + a14 * 17 == 7258) & \
    (a1 * 28 + a2 * 35 + a3 * 16 - a4 * 65 + a5 * 53 + a6 * 39 + a7 * 27 + a8 * 15 - a9 * 33 + a10 * 13 + a11 * 101 + a12 * 90 - a13 * 34 + a14 * 23 == 26190) & \
    (a1 * 23 + a2 * 34 + a3 * 35 - a4 * 59 + a5 * 49 + a6 * 81 + a7 * 25 + (a8 << 7) - a9 * 32 + a10 * 75 + a11 * 81 + a12 * 47 - a13 * 60 + a14 * 29 == 37136) & \
    (a1 * 38 + a2 * 97 + a3 * 35 - a4 * 52 + a5 * 42 + a6 * 79 + a7 * 90 + a8 * 23 - a9 * 36 + a10 * 57 + a11 * 81 + a12 * 42 - a13 * 62 - a14 * 11 == 27915) & \
    (a1 * 22 + a2 * 27 + a3 * 35 - a4 * 45 + a5 * 47 + a6 * 49 + a7 * 29 + a8 * 18 - a9 * 26 + a10 * 35 + a11 * 41 + a12 * 40 - a13 * 61 + a14 * 28 == 17298) & \
    (a1 * 12 + a2 * 45 + a3 * 35 - a4 * 9 - a5 * 42 + a6 * 86 + a7 * 23 + a8 * 85 - a9 * 47 + a10 * 34 + a11 * 76 + a12 * 43 - a13 * 44 + a14 * 65 == 19875) & \
    (a1 * 79 + a2 * 62 + a3 * 35 - a4 * 85 + a5 * 33 + a6 * 79 + a7 * 86 + a8 * 14 - a9 * 30 + a10 * 25 + a11 * 11 + a12 * 57 - a13 * 50 - a14 * 9 == 22784) & \
    (a1 * 8 + a2 * 6 + a3 * 64 - a4 * 85 + a5 * 73 + a6 * 29 + a7 * 2 + a8 * 23 - a9 * 36 + a10 * 5 + a11 * 2 + a12 * 47 - a13 * 64 + a14 * 27 == 9710) & \
    (a1 * 67 - a2 * 68 + a3 * 68 - a4 * 51 - a5 * 43 + a6 * 81 + a7 * 22 - a8 * 12 - a9 * 38 + a10 * 75 + a11 * 41 + a12 * 27 - a13 * 52 + a14 * 31 == 13376) & \
    (a1 * 85 + a2 * 63 + a3 * 5 - a4 * 51 + a5 * 44 + a6 * 36 + a7 * 28 + a8 * 15 - a9 * 6 + a10 * 45 + a11 * 31 + a12 * 7 - a13 * 67 + a14 * 78 == 24065) & \
    (a1 * 47 + a2 * 64 + a3 * 66 - a4 * 5 + a5 * 43 + a6 * 112 + a7 * 25 + a8 * 13 - a9 * 35 + a10 * 95 + a11 * 21 + a12 * 43 - a13 * 61 + a14 * 20 == 27687) & \
    (a1 * 89 + a2 * 67 + a3 * 85 - a4 * 25 + a5 * 49 + a6 * 89 + a7 * 23 + a8 * 56 - a9 * 92 + a10 * 14 + a11 * 89 + a12 * 47 - a13 * 61 - a14 * 29 == 29250) & \
    (a1 * 95 + a2 * 34 + a3 * 62 - a4 * 9 - a5 * 43 + a6 * 83 + a7 * 25 + a8 * 12 - a9 * 36 + a10 * 16 + a11 * 51 + a12 * 47 - a13 * 60 - a14 * 24 == 15317):
        print('flag is GWHT{md5(your_input)}')
        print('Congratulations and have fun!')
    else:
        print('Sorry,plz try again...')
# okay decompiling login.pyc

z3解方程组

from z3 import *


a1 = Int('a1')
a2 = Int('a2')
a3 = Int('a3')
a4 = Int('a4')
a5 = Int('a5')
a6 = Int('a6')
a7 = Int('a7')
a8 = Int('a8')
a9 = Int('a9')
a10 = Int('a10')
a11 = Int('a11')
a12 = Int('a12')
a13 = Int('a13')
a14 = Int('a14')

solver = Solver()
solver.add(a1 * 88 + a2 * 67 + a3 * 65 - a4 * 5 + a5 * 43 + a6 * 89 + a7 * 25 + a8 * 13 - a9 * 36 + a10 * 15 + a11 * 11 + a12 * 47 - a13 * 60 + a14 * 29 == 22748)
solver.add(a1 * 89 + a2 * 7 + a3 * 12 - a4 * 25 + a5 * 41 + a6 * 23 + a7 * 20 - a8 * 66 + a9 * 31 + a10 * 8 + a11 * 2 - a12 * 41 - a13 * 39 + a14 * 17 == 7258)
solver.add(a1 * 28 + a2 * 35 + a3 * 16 - a4 * 65 + a5 * 53 + a6 * 39 + a7 * 27 + a8 * 15 - a9 * 33 + a10 * 13 + a11 * 101 + a12 * 90 - a13 * 34 + a14 * 23 == 26190)
solver.add(a1 * 23 + a2 * 34 + a3 * 35 - a4 * 59 + a5 * 49 + a6 * 81 + a7 * 25 + a8 * 128 - a9 * 32 + a10 * 75 + a11 * 81 + a12 * 47 - a13 * 60 + a14 * 29 == 37136)
solver.add(a1 * 38 + a2 * 97 + a3 * 35 - a4 * 52 + a5 * 42 + a6 * 79 + a7 * 90 + a8 * 23 - a9 * 36 + a10 * 57 + a11 * 81 + a12 * 42 - a13 * 62 - a14 * 11 == 27915)
solver.add(a1 * 22 + a2 * 27 + a3 * 35 - a4 * 45 + a5 * 47 + a6 * 49 + a7 * 29 + a8 * 18 - a9 * 26 + a10 * 35 + a11 * 41 + a12 * 40 - a13 * 61 + a14 * 28 == 17298)
solver.add(a1 * 12 + a2 * 45 + a3 * 35 - a4 * 9 - a5 * 42 + a6 * 86 + a7 * 23 + a8 * 85 - a9 * 47 + a10 * 34 + a11 * 76 + a12 * 43 - a13 * 44 + a14 * 65 == 19875)
solver.add(a1 * 79 + a2 * 62 + a3 * 35 - a4 * 85 + a5 * 33 + a6 * 79 + a7 * 86 + a8 * 14 - a9 * 30 + a10 * 25 + a11 * 11 + a12 * 57 - a13 * 50 - a14 * 9 == 22784)
solver.add(a1 * 8 + a2 * 6 + a3 * 64 - a4 * 85 + a5 * 73 + a6 * 29 + a7 * 2 + a8 * 23 - a9 * 36 + a10 * 5 + a11 * 2 + a12 * 47 - a13 * 64 + a14 * 27 == 9710)
solver.add(a1 * 67 - a2 * 68 + a3 * 68 - a4 * 51 - a5 * 43 + a6 * 81 + a7 * 22 - a8 * 12 - a9 * 38 + a10 * 75 + a11 * 41 + a12 * 27 - a13 * 52 + a14 * 31 == 13376)
solver.add(a1 * 85 + a2 * 63 + a3 * 5 - a4 * 51 + a5 * 44 + a6 * 36 + a7 * 28 + a8 * 15 - a9 * 6 + a10 * 45 + a11 * 31 + a12 * 7 - a13 * 67 + a14 * 78 == 24065)
solver.add(a1 * 47 + a2 * 64 + a3 * 66 - a4 * 5 + a5 * 43 + a6 * 112 + a7 * 25 + a8 * 13 - a9 * 35 + a10 * 95 + a11 * 21 + a12 * 43 - a13 * 61 + a14 * 20 == 27687)
solver.add(a1 * 89 + a2 * 67 + a3 * 85 - a4 * 25 + a5 * 49 + a6 * 89 + a7 * 23 + a8 * 56 - a9 * 92 + a10 * 14 + a11 * 89 + a12 * 47 - a13 * 61 - a14 * 29 == 29250)
solver.add(a1 * 95 + a2 * 34 + a3 * 62 - a4 * 9 - a5 * 43 + a6 * 83 + a7 * 25 + a8 * 12 - a9 * 36 + a10 * 16 + a11 * 51 + a12 * 47 - a13 * 60 - a14 * 24 == 15317)

if solver.check():
    model = solver.model()
    print(model)

'''
[a13 = 88,
 a3 = 10,
 a4 = 7,
 a10 = 108,
 a12 = 74,
 a1 = 119,
 a7 = 28,
 a6 = 43,
 a9 = 52,
 a14 = 33,
 a5 = 104,
 a8 = 91,
 a2 = 24,
 a11 = 88]
'''

提取置换表, 然后xor逆回去

'''
[a13 = 88,
 a3 = 10,
 a4 = 7,
 a10 = 108,
 a12 = 74,
 a1 = 119,
 a7 = 28,
 a6 = 43,
 a9 = 52,
 a14 = 33,
 a5 = 104,
 a8 = 91,
 a2 = 24,
 a11 = 88]

a1 = code[2]
a2 = code[1]
a3 = code[0]
a4 = code[3]
a5 = code[4]
a6 = code[5]
a7 = code[6]
a8 = code[7]
a9 = code[9]
a10 = code[8]
a11 = code[10]
a12 = code[11]
a13 = code[12]
a14 = code[13]
'''

flag = [0 for _ in range(14)]

table = [2, 1, 0, 3, 4, 5, 6, 7, 9, 8, 10, 11, 12, 13]
sols = [119, 24, 10, 7, 104, 43, 28, 91, 52, 108, 88, 74, 88, 33]
table_sols = [0 for _ in range(14)]

for i in range(14):
    table_sols[i] = sols[table[i]]

flag[13] =  table_sols[13]
for i in range(12, -1, -1):
    flag[i] = table_sols[i] ^ flag[i + 1]

for i in range(14):
    flag[i] = chr(flag[i])

flag = ''.join(flag)
print(flag)

[QCTF2018]Xman-babymips

在这里插入图片描述

在这里插入图片描述

在这里插入图片描述

注意python进行移位操作, 需要& 0xff确保不溢出

checklist = [
   82, 253,  22, 164, 137, 189, 146, 128,  19,  65, 
   84, 160, 141,  69,  24, 129, 222, 252, 149, 240, 
   22, 121,  26,  21,  91, 117,  31,   0
]

checkfirst = [81, 124, 106, 123, 103]

flag = ''

# first 5 bytes
for i in range(len(checkfirst)):
    flag += chr(checkfirst[i] ^ (32 - i))

# last bytes
for i in range(5, 32):
    checkval = checklist[i - 5]
    for j in range(128):
        tmp = j
        if i % 2 == 1: # odd
            v1 = ((tmp >> 2) & 0xff) | ((tmp << 6) & 0xff)
        else: # even
            v1 = ((tmp << 2) & 0xff) | ((tmp >> 6) & 0xff)
        
        if v1 == checkval:
            tmp ^= 32 - i
            flag += chr(tmp)
            print(i, chr(j))
            break

print(flag)

[UTCTF2020]babymips

在这里插入图片描述

int __cdecl main(int argc, const char **argv, const char **envp)
{
  int v3; // $v0
  char input[24]; // [sp+18h] [+18h] BYREF
  char flag[24]; // [sp+30h] [+30h] BYREF
  char checklist[84]; // [sp+48h] [+48h] BYREF

  std::string::basic_string(input, argv, envp);
  v3 = std::operator<<<std::char_traits<char>>(&std::cout, "enter the flag");
  std::ostream::operator<<(v3, &std::endl<char,std::char_traits<char>>);
  std::operator>><char>(&std::cin, input);
  memcpy(checklist, &checkval, sizeof(checklist));
  std::string::basic_string(flag, input);
  check((int)checklist, (int)flag);
  std::string::~string(flag);
  std::string::~string(input);
  return 0;
}

int __fastcall check(int checklist, int flag)
{
  int v2; // $v0
  int v4; // $v0
  unsigned int i; // [sp+1Ch] [+1Ch]

  if ( std::string::size(flag) != 78 )
  {
LABEL_2:                                        // wrong
    v2 = std::operator<<<std::char_traits<char>>(&std::cout, "incorrect");
    return std::ostream::operator<<(v2, &std::endl<char,std::char_traits<char>>);
  }
  else
  {
    for ( i = 0; i < std::string::size(flag); ++i )
    {
      if ( (*(char *)std::string::operator[](flag, i) ^ (i + 23)) != *(char *)(checklist + i) )
        goto LABEL_2;
    }                                           // correct
    v4 = std::operator<<<std::char_traits<char>>(&std::cout, "correct!");
    return std::ostream::operator<<(v4, &std::endl<char,std::char_traits<char>>);
  }
}
checklist = [
   98, 108, 127, 118, 122, 123, 102, 115, 118,  80, 
   82, 125,  64,  84,  85, 121,  64,  73,  71,  77, 
  116,  25, 123, 106,  66,  10,  79,  82, 125, 105, 
   79,  83,  12, 100,  16,  15,  30,  74, 103,   3, 
  124, 103,   2, 106,  49, 103,  97,  55, 122,  98, 
   44,  44,  15, 110,  23,   0,  22,  15,  22,  10, 
  109,  98, 115,  37,  57, 118,  46,  28,  99, 120, 
   43, 116,  50,  22,  32,  34,  68,  25,   0,  
]

flag = ''

for i in range(len(checklist) - 1):
    flag += chr(checklist[i] ^ (23 + i))

print(flag)

[GKCTF 2021]QQQQT

在这里插入图片描述

搜一下Enigma VB, 找到一个现有的解包工具 https://www.52pojie.cn/thread-1575691-1-1.html

shift+F12 没有明显的字符串, 那就一个个函数看(只需要考虑用户代码, 忽略框架代码), 找到可能的关键逻辑, 注释在伪码中

void __thiscall sub_4012F0(_DWORD *this)
{
  int v1; // edi
  _BYTE *v2; // esi
  const char *v3; // edx
  _BYTE *v4; // esi
  int v5; // ecx
  int v6; // eax
  int v7; // ecx
  int v8; // edx
  int v9; // edi
  int v10; // esi
  _BYTE *v11; // ecx
  unsigned int len_input; // ecx
  size_t v13; // [esp-8h] [ebp-A8h]
  char v15[4]; // [esp+10h] [ebp-90h] BYREF
  char v16[4]; // [esp+14h] [ebp-8Ch] BYREF
  _BYTE *v17; // [esp+18h] [ebp-88h]
  const char *input; // [esp+1Ch] [ebp-84h]
  int v19; // [esp+20h] [ebp-80h]
  int v20; // [esp+24h] [ebp-7Ch] BYREF
  _BYTE *v21; // [esp+28h] [ebp-78h] BYREF
  char v22[60]; // [esp+2Ch] [ebp-74h] BYREF
  __int128 v23[2]; // [esp+68h] [ebp-38h] BYREF
  __int64 v24; // [esp+88h] [ebp-18h]
  int v25; // [esp+9Ch] [ebp-4h]

  QLineEdit::text(*(_DWORD *)(this[6] + 4), v15);// input
  v25 = 0;
  QString::toLatin1(v15, v16);
  LOBYTE(v25) = 1;
  input = QByteArray::data((QByteArray *)v16);  // input processed
  memset(v23, 0, sizeof(v23));
  v24 = 0i64;
  strcpy(v22, "123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz");// 58 chars guess it as base58
  v20 = 138 * strlen(input) / 0x64;
  v13 = v20 + 1;
  v1 = 0;
  v21 = malloc(v20 + 1);
  v2 = v21;
  memset(v21, 0, v13);
  v3 = input;
  v19 = (int)(input + 1);
  if ( strlen(input) )
  {
    v4 = &v2[v20];
    v17 = v4;
    while ( 1 )
    {
      v19 = ((char)*v4 << 8) + v3[v1];
      v5 = v19 / 58;
      *v4 = v19 % 58;
      if ( v5 )
      {
        do
        {
          v6 = (char)*--v4;
          v7 = (v6 << 8) + v5;
          v19 = v7 / 58;
          *v4 = v7 % 58;                        // / and % 58 
          v5 = v19;
        }
        while ( v19 );
        v4 = v17;
      }
      if ( ++v1 >= strlen(input) )
        break;
      v3 = input;
    }
    v2 = v21;
  }
  v8 = 0;
  if ( !*v2 )
  {
    do
      ++v8;
    while ( !v2[v8] );
  }
  v9 = v20;
  if ( v8 <= v20 )
  {
    v10 = v2 - (_BYTE *)v23;
    do
    {
      v11 = (char *)v23 + v8++;
      *v11 = v22[(char)v11[v10]];
    }
    while ( v8 <= v9 );
  }
  if ( !qstrcmp((const char *)v23, "56fkoP8KhwCf3v7CEz") )// check
  {
    if ( input )
      len_input = strlen(input);
    else
      len_input = -1;
    v21 = (_BYTE *)QString::fromAscii_helper(input, len_input);
    LOBYTE(v25) = 2;
    v20 = QString::fromAscii_helper("flag", 4);
    LOBYTE(v25) = 3;
    QMessageBox::warning(this, &v20, &v21, 1024, 0);// print flag
    QString::~QString((QString *)&v20);
    QString::~QString((QString *)&v21);
  }
  QByteArray::~QByteArray((QByteArray *)v16);
  QString::~QString((QString *)v15);
}

b58解密就是flag

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1053443.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

差分运算放大器的放大倍数的计算及结论

由于虚断&#xff0c;流入V的电流几乎为0&#xff0c;根据分压定理可得&#xff1a; 同理&#xff0c;在V-处有&#xff1a; 由于虚短&#xff0c;可得&#xff1a; 化简可得&#xff1a; 其中&#xff1a; 称为正相放大倍数 称为反相放大倍数

学信息系统项目管理师第4版系列14_沟通管理

1. 与IT项目成功有关的最重要的四个因素 1.1. 主管层的支持 1.2. 用户参与 1.3. 有经验的项目经理 1.4. 清晰的业务目标 1.5. 依赖于项目经理和团队具有良好的沟通能力 2. 沟通的主旨 2.1. 互动双方建立彼此相互了解的关系 2.2. 相互回应 2.3. 期待能经由沟通的行为与…

计算机图像处理-中值滤波

非线性滤波 非线性滤波是利用原始图像跟模版之间的一种逻辑关系得到结果&#xff0c;常用的非线性滤波方法有中值滤波和高斯双边滤波&#xff0c;分别对应cv2.medianBlur(src, ksize)方法和cv2.bilateralFilter(src, d, sigmaColor, sigmaSpace[, dst[, borderType]])方法。 …

【算法分析与设计】贪心算法(上)

目录 一、学习要点二、找硬币问题2.1 概述 三、活动安排问题3.1 策略选择3.2 活动安排问题程序代码3.3 一般使用数学归纳法进行证明3.4 活动选择算法的命题3.4.1 先看k1时是否正确3.4.2 归纳步骤&#xff0c;k->k13.4.3 归纳步骤&#xff08;续&#xff09; 四、贪心算法的基…

28385-2012 印刷机械 锁线机 学习笔记

声明 本文是学习GB-T 28385-2012 印刷机械 锁线机. 而整理的学习笔记,分享出来希望更多人受益,如果存在侵权请及时联系我们 1 范围 本标准规定了锁线机的型式、基本参数、要求、试验方法、检验规则、标志、包装、运输与贮存。 本标准适用于用线将书帖装订成书芯的锁线机。 …

第四十三章 持久对象和SQL - 查看存储的数据

文章目录 第四十三章 持久对象和SQL - 查看存储的数据查看存储的数据SQL 生成代码的存储 第四十三章 持久对象和SQL - 查看存储的数据 查看存储的数据 本节演示对于任何持久对象&#xff0c;相同的值通过对象访问、SQL 访问和直接Global访问都是可见的。 在我们的 IDE 中&am…

信息安全第四周

社会工程学 社会工程学主要研究如何操纵人的心理和情感来获取机密信息或其他目标。它主要不是通过技术手段攻击计算机系统&#xff0c;而是通过心理学和人际交往技巧来欺骗人&#xff0c;使他们泄露密码、安全代码或其他敏感信息。社会工程学主要是一种安全风险&#xff0c;主要…

Ubuntu部署运行ORB-SLAM2

ORB-SLAM2是特征点法的视觉SLAM集大成者&#xff0c;不夸张地说是必学代码。博主已经多次部署运行与ORB-SLAM2相关的代码&#xff0c;所以对环境和依赖很熟悉&#xff0c;对整个系统也是学习了几个月&#xff0c;一行行代码理解。本次在工控机上部署记录下完整的流程。 ORB-SLA…

计算机图像处理-高斯滤波

高斯滤波 高斯滤波是一种线性平滑滤波&#xff0c;适用于消除高斯噪声&#xff0c;广泛应用于图像处理的减噪过程。通俗的讲&#xff0c;高斯滤波就是对整幅图像进行加权平均的过程&#xff0c;每一个像素点的值&#xff0c;都由其本身和邻域内的其他像素值经过加权平均后得到…

gitee 远程仓库操作基础(二)

(1&#xff09;clone远端仓库,本地建立分支推送 (基于远程仓库版本库 本地建立分支开发新功能) git clone gitgitee.com:xxxxx/alsa_test.git git remote add origin gitgitee.com:xxxxx/alsa_test.git进入clone过后路径代码,查看本地分支,发现该项目远程仓库有很多分支 基于…

初级篇—第六章创建和管理表

文章目录 一条数据存储的过程常用的数据类型创建和管理数据库创建数据库使用数据库修改数据库创建表创建方式1例1例2 创建方式2 查看数据表结构修改表追加一个列修改一个列重命名一个列删除一个列修改表名 删除表清空表 MySQL8新特性—DDL的原子化练习 一条数据存储的过程 存储…

Ubuntu系统下使用apt-get安装Mysql8

记录一下在Ubuntu20.04 64位系统下面使用apt-get方式安装mysql8关系型数据库 Centos下使用yum安装Mysql8&#xff08;Mysql5.7&#xff09;以及常见的配置和使用 首先肯定是检查下当前Ubuntu系统是否已经安装过mysql数据库 一般拿到新的云服务器是没有安装的 rootmyw:~# whe…

【STM32 CubeMX】移植u8g2(一次成功)

文章目录 前言一、下载u8g2源文件二、复制和更改文件2.1 复制文件2.2 修改文件u8g2_d_setup文件u8g2_d_memory 三、编写oled.c和oled.h文件3.1 CubeMX配置I2C3.2 编写文件oled.holed.c 四、测试代码main函数测试代码 总结 前言 在本文中&#xff0c;我们将介绍如何在STM32上成…

【IDEA】maven项目添加模块时,webapp没有被标识,无法识别的解决方法

问题 新添加maven项目模块后&#xff0c;webapp目录未被标识&#xff0c;即没有小蓝点的图标显示。如下图 解决方法 点击“File”下的“Project Strucure”&#xff0c;在弹出的框中&#xff0c;选中“Modules”下的项目名称&#xff0c;也就是“demo1”&#xff0c;点击“…

从零手搓一个【消息队列】创建核心类, 数据库设计与实现

文章目录 一、创建核心类1, 交换机2, 交换机类型3, 队列4, 绑定5, 交换机转发 & 绑定规则6, 消息7, 消息属性 二、数据库设计1, 使用 SQLite2, 使用 MyBatis2.1, 创建 Interface2.2, 创建 xml 文件 三、硬盘管理 -- 数据库1, 创建 DataBaseManager 类2, init() 初始化数据库…

2023年中国新能源圆柱电池市场发展前景分析:新能源圆柱行业发展前景乐观向好[图]

新能源圆柱电池是指电芯由正极材料&#xff08;钴酸镍或锰酸锌&#xff09;、隔膜纸及电解液组成&#xff1b;外壳采用铝塑复合管材制成的以钢壳圆柱磷酸铁锂电池为主的新型锂电池。 圆柱电池分类 资料来源&#xff1a;共研产业咨询&#xff08;共研网&#xff09; 新能源圆柱…

2023年8月嵌入式项目开发专题总汇

一、前言 本文介绍基于嵌入式系统和C语言开发的系列项目。这些项目涵盖了多个领域&#xff0c;从自动化控制到游戏开发&#xff0c;从计算机网络到物联网应用。通过这些项目的开发过程&#xff0c;将深入探讨各种技术和解决方案&#xff0c;并分享相关经验和知识。 在本文中&…

如何面对失败

失败是常态&#xff0c;有时候甚至是“败败败败乃兵家常事”。那么如何定义失败&#xff0c;面对失败的恐惧源自哪里&#xff0c;如何克服失败的恐惧、以至于如何克服失败本身&#xff1f; 什么是失败&#xff1f; 《道德经》第二章有云&#xff1a;“有无相生&#xff0c;难易…

std::initializer_list详解

std::initializer_list介绍 initializer_list是C11提供的一种新类型&#xff0c;其定义于头文件<initializer_list>中&#xff0c;此头文件是工具库的一部分&#xff0c; <initializer_list>定义如下&#xff1a; namespace std {template<class E> class…

蓝桥等考Python组别九级007

第一部分&#xff1a;选择题 1、Python L9 &#xff08;15分&#xff09; 运行下面程序&#xff0c;可以输出几行“*”&#xff1f;&#xff08; &#xff09; for i in range(0, 3): for j in range(0, 5): print(*, end ) print() 2345 正确答案&#xff1a;B 2、P…