一. careful
- 动态调试 设置断点在 ds:gethostbyname 处
- 进入gethostbyname 内部其实存在了内联HOOK hook了这个API函数 修改了传入的参数 然后调用真正的API
- 需要更进一步步入进入该内联函数分析
- 最后看参数即可得到flag
二. babyre
-
首先找到关键字符串
-
交叉引用到7A80处
-
__int64 __fastcall sub_140007A80(int a1, __int64 a2) { char *v2; // rdi __int64 i; // rcx char v5[32]; // [rsp+0h] [rbp-40h] BYREF char v6; // [rsp+40h] [rbp+0h] BYREF DWORD dwProcessId; // [rsp+44h] [rbp+4h] HANDLE v8; // [rsp+68h] [rbp+28h] char Parameter[132]; // [rsp+90h] [rbp+50h] BYREF int j; // [rsp+114h] [rbp+D4h] HRSRC hResInfo; // [rsp+138h] [rbp+F8h] size_t Size; // [rsp+154h] [rbp+114h] HGLOBAL hResData; // [rsp+178h] [rbp+138h] void *Src; // [rsp+198h] [rbp+158h] void *v15; // [rsp+1B8h] [rbp+178h] __int64 v16; // [rsp+1D8h] [rbp+198h] __int64 v17; // [rsp+1F8h] [rbp+1B8h] int k; // [rsp+214h] [rbp+1D4h] __int64 v19; // [rsp+2E8h] [rbp+2A8h] v2 = &v6; for ( i = 130i64; i; --i ) { *(_DWORD *)v2 = -858993460; v2 += 4; } sub_1400012A8(&unk_1400140F4); dwProcessId = GetCurrentProcessId(); v8 = OpenProcess(0x1FFFFFu, 0, dwProcessId); if ( a1 != 2 ) exit(0); for ( j = 0; ; ++j ) { v19 = j; if ( j >= strlen(*(const char **)(a2 + 8)) ) break; Parameter[j] = *(_BYTE *)(*(_QWORD *)(a2 + 8) + j); } hResInfo = FindResourceW(0i64, (LPCWSTR)0x65, L"cod"); LODWORD(Size) = SizeofResource(0i64, hResInfo); hResData = LoadResource(0i64, hResInfo); Src = LockResource(hResData); v15 = malloc((unsigned int)Size); memcpy(v15, Src, (unsigned int)Size); sub_140001087(v15);//decrypt shellcode v16 = qword_14000FC30(v8, 0i64, 874i64, 4096i64, 64);//VirtualAllocEx qword_14000FC28(v8, v16, v15, 874i64, 0i64);//WriteProcessMemory v17 = qword_14000FC18(v8, 0i64, 0i64, v16, Parameter, 0, 0i64);//CreateRemoteThread Sleep(0x1F4u); for ( k = 0; k < 44; ++k ) ; CreateThread(0i64, 0i64, StartAddress, Parameter, 0, 0i64);//子进程:checkflag Sleep(0x190u); sub_140001253(v5, &unk_14000BEE0); return 0i64; }
-
cod二进制资源,在2940中会进行解密
-
关于cod:通过对资源进行解密 并且Write到自身的内存中去 然后通过远程线程执行
-
其中会用到反调试在28F0
-
直接静态即可
-
将cod提取至resource hack
-
生成.bin文件后解密
-
解密脚本如下:
-
arr = [0x18, 0x57, 0x68, 0x64] with open('C:\\Users\\lenovo\\Desktop\\COD101', 'rb') as f: b = f.read() b = bytearray(b) for i in range(len(b)): b[i] = b[i] ^ arr[i % 4] with open('C:\\Users\\lenovo\\Desktop\\COD_de', 'wb') as f: f.write(b)
-
将解密后的bin文件用ida分析
-
按c键将二进制数据转换成汇编代码
-
下面开始去花
-
其中注意loc_1EE,
-
直接nop掉
-
这时就能生成伪代码了
-
__int64 __fastcall sub_0(_BYTE *a1) { void *v1; // rax __int64 result; // rax char v3[292]; // [rsp+40h] [rbp+10h] unsigned int j; // [rsp+164h] [rbp+134h] unsigned int v5; // [rsp+184h] [rbp+154h] unsigned int v6; // [rsp+1A4h] [rbp+174h] int v7; // [rsp+1C4h] [rbp+194h] char v8[44]; // [rsp+1E8h] [rbp+1B8h] BYREF unsigned int v9; // [rsp+214h] [rbp+1E4h] _BYTE *i; // [rsp+238h] [rbp+208h] int v11; // [rsp+254h] [rbp+224h] __int64 v12; // [rsp+3E8h] [rbp+3B8h] memset(v1, 0, 0x101ui64); qmemcpy(v8, "]Bb)", 4); v8[4] = 3; v8[5] = 54; v8[6] = 71; v8[7] = 65; v8[8] = 21; v8[9] = 54; v9 = 0; for ( i = a1; *i; ++i ) ++v9; for ( j = 0; j < 256; ++j ) v3[j] = j; v6 = 0; v5 = 0; for ( j = 0; j < 256; ++j ) { v7 = v3[j]; v5 = (v8[v6] + v7 + 2 * v5) % 0x100; v3[j] = v3[v5]; v3[v5] = v7; if ( ++v6 >= 0xA ) v6 = 0; } v6 = 0; v5 = 0; for ( j = 0; ; ++j ) { result = v9; if ( j >= v9 ) break; v5 = (v6 + v5) % 0x100; v6 = (v3[v5] + v6) % 0x100; v7 = v3[v5]; v3[v5] = v3[v6]; v3[v6] = v7; v11 = v3[(v3[v5] + v6 + v3[v6]) % 0x100]; a1[j] ^= v11; v12 = j; a1[j] += j % 0xD; } return result; }
-
很明显的魔改RC4代码
-
这里我们找到起始key就是v8
-
同时flag的检验在程序的另一个子进程中
-
checkflag伪代码如下:
-
void __fastcall __noreturn StartAddress_0(__int64 a1) { char *v1; // rdi __int64 i; // rcx char v3; // [rsp+20h] [rbp+0h] BYREF char v4[76]; // [rsp+28h] [rbp+8h] int j; // [rsp+74h] [rbp+54h] v1 = &v3; for ( i = 30i64; i; --i ) { *(_DWORD *)v1 = -858993460; v1 += 4; } sub_1400012A8((__int64)&unk_1400140F4); v4[0] = 0xF7; v4[1] = 46; v4[2] = 52; v4[3] = -16; v4[4] = 114; v4[5] = -49; v4[6] = 94; v4[7] = 10; v4[8] = -69; v4[9] = -20; v4[10] = -79; v4[11] = 43; v4[12] = 112; v4[13] = -120; v4[14] = -120; v4[15] = -19; v4[16] = 70; v4[17] = 56; v4[18] = -37; v4[19] = -38; v4[20] = 108; v4[21] = -67; v4[22] = -44; v4[23] = 6; v4[24] = 119; v4[25] = -14; v4[26] = -49; v4[27] = 86; v4[28] = -120; v4[29] = -58; v4[30] = 49; v4[31] = -46; v4[32] = -73; v4[33] = 90; v4[34] = -63; v4[35] = 66; v4[36] = -80; v4[37] = -12; v4[38] = 72; v4[39] = 55; v4[40] = -11; v4[41] = 44; v4[42] = -11; v4[43] = 88; puts(" "); for ( j = 0; j < 44; ++j ) { if ( *(char *)(a1 + j) != v4[j] ) { sub_14000114A("error!\n"); exit(0); } } sub_14000114A("get flag!"); exit(0); }
-
exp如下:
-
class RC4: def __init__(self, key) -> None: self.key = key self.S = 0 self.__rc4_init__() def __rc4_init__(self): S = [i for i in range(256)] j = 0 for i in range(256): j = (2 * j + S[i] + key[i % len(key)]) % 256 S[i], S[j] = S[j], S[i] self.S = S def rc4_encrypt(self, plain) -> list: i = 0 j = 0 cipher = [] cnt = 0 for p in plain: p = (p + 256 - cnt % 0xd) % 256 cnt += 1 i = (i + j) % 256 j = (j + self.S[i]) % 256 self.S[i], self.S[j] = self.S[j], self.S[i] tmp = self.S[(self.S[i] + self.S[j] + j) % 256] k = p ^ tmp cipher.append(k) return cipher key = [0x5D , 0x42 , 0x62 , 0x29 , 0x3, 0x36 , 0x47 , 0x41 , 0x15, 0x36] data = [0xF7, 0x2E, 0x34, 0xF0, 0x72, 0xCF, 0x5E, 0x0A, 0xBB, 0xEC, 0xB1, 0x2B, 0x70, 0x88, 0x88, 0xED, 0x46, 0x38, 0xDB, 0xDA, 0x6C, 0xBD, 0xD4, 0x06, 0x77, 0xF2, 0xCF, 0x56, 0x88, 0xC6, 0x31, 0xD2, 0xB7, 0x5A, 0xC1, 0x42, 0xB0, 0xF4, 0x48, 0x37, 0xF5, 0x2C, 0xF5, 0x58] rc4 = RC4(key) plain = rc4.rc4_encrypt(data) print(''.join(map(chr,plain)))
-
三. ez_exe
-
这里我们查壳发现是pyinstaller打包的exe
-
首先用pyinstxtractor进行解包
-
然后用uncompyle6进行反编译
-
这里有修改magic number的问题没有解决
-
找到:https://github.com/google/pytype/blob/main/pytype/pyc/magic.py(不同版本python对应的magic number
-
以及magic number详解:http://t.csdn.cn/Lxf0T
-
然而解决不了,那么我们不妨用在线反编译网站进行反编译:在线Python pyc文件编译与反编译 (lddgo.net)
-
得到python代码:
# Visit https://www.lddgo.net/string/pyc-compile-decompile for more information # Version : Python 3.11 import ctypes from time import * from ctypes import * from ctypes import wintypes from hashlib import md5 class _STARTUPINFO(Structure): _fields_ = [ ('cb', c_ulong), ('lpReserved', c_char_p), ('lpDesktop', c_char_p), ('lpTitle', c_char_p), ('dwX', c_ulong), ('dwY', c_ulong), ('dwXSize', c_ulong), ('dwYSize', c_ulong), ('dwXCountChars', c_ulong), ('dwYCountChars', c_ulong), ('dwFillAttribute', c_ulong), ('dwFlags', c_ulong), ('wShowWindow', c_ushort), ('cbReserved2', c_ushort), ('lpReserved2', c_char_p), ('hStdInput', c_ulong), ('hStdOutput', c_ulong), ('hStdError', c_ulong)] class _PROCESS_INFORMATION(Structure): _fields_ = [ ('hProcess', c_void_p), ('hThread', c_void_p), ('dwProcessId', c_ulong), ('dwThreadId', c_ulong)] StartupInfo = _STARTUPINFO() ProcessInfo = _PROCESS_INFORMATION() key1 = bytes(md5(b'bin1bin1bin1').hexdigest().encode()) file = open('bin1', 'rb').read() arr = range(len(file))() open('bin1', 'wb').write(bytes(arr)) sleep(0) bet = ctypes.windll.kernel32.CreateProcessA(b'bin1', ctypes.c_int(0), ctypes.c_int(0), ctypes.c_int(0), ctypes.c_int(0), ctypes.c_int(0), ctypes.c_int(0), ctypes.c_int(0), byref(StartupInfo), byref(ProcessInfo)) ctypes.windll.kernel32.WaitForSingleObject(ctypes.c_int(ProcessInfo.hProcess), ctypes.c_int(-1)) open('bin1', 'wb').write(file)
-
运行ez_exe,发现please use zhe execute file decrypt 'bin2' and your will get flag!
-
提示我们用这个去解密bin2
-
我们运行ez_py.pyc,从而解密bin2
-
这里是xxtea算法
-
直接写脚本逆向即可
-
#include <iostream> #include <stdio.h> using namespace std; #include <stdint.h> //delta changed #define DELTA 0x7937B99E #define MX (((z>>5^y<<2) + (y>>3^z<<4)) ^ ((sum^y) + (key[(p&3)^e] ^ z))) void btea(uint32_t* v, int n, uint32_t const key[4]) { uint32_t y, z, sum; unsigned p, rounds, e; if (n > 1) { /* Coding Part */ rounds = 6 + 52 / n; sum = 0; z = v[n - 1]; do { sum += DELTA; e = (sum >> 2) & 3; for (p = 0; p < n - 1; p++) { y = v[p + 1]; z = v[p] += MX; } y = v[0]; z = v[n - 1] += MX; } while (--rounds); } else if (n < -1) { /* Decoding Part */ n = -n; //round changed rounds = 52 / n; sum = rounds * DELTA; y = v[0]; do { e = (sum >> 2) & 3; for (p = n - 1; p > 0; p--) { z = v[p - 1]; y = v[p] -= MX; } z = v[n - 1]; y = v[0] -= MX; } while ((sum -= DELTA) != 0); } } int main() { uint32_t key[4] = { 0 }; key[0] = 0x4B5F; key[1] = 0xDEAD; key[2] = 0x11ED; key[3] = 0xB3CC; uint32_t v5[11] = { 0 }; v5[0] = 0xCC45699D; v5[1] = 0x683D5352; v5[2] = 0xB8BB71A0; v5[3] = 0xD3817AD; v5[4] = 0x7547E79E; v5[5] = 0x4BDD8C7C; v5[6] = 0x95E25A81; v5[7] = 0xC4525103; v5[8] = 0x7049B46F; v5[9] = 0x5417F77C; v5[10] = 0x65567138; btea(v5, -11, key); for (int i = 0; i < 44; i++) { printf("%c",*((char *)v5 +i) & 0xff); } return 0; }
- 注意加密的轮数与delta都改了
- DASCTF{7eb20cb2-deac-11ed-ae42-94085339ce84}
四. cap
-
main函数如下:
-
__int64 __fastcall sub_140001030(HWND hWnd) { HBITMAP v2; // r14 HDC hdcSrc; // r13 HDC DC; // rsi HDC CompatibleDC; // r15 int hSrc; // ebx int wSrc; // eax HBITMAP CompatibleBitmap; // rax signed int v9; // ebx HANDLE FileW; // rax void *v11; // r12 signed int v12; // r10d _BYTE *v13; // r9 int v14; // ecx int v15; // edx void *lpBuffer; // [rsp+60h] [rbp-59h] HGLOBAL hMem; // [rsp+68h] [rbp-51h] struct tagRECT Rect; // [rsp+70h] [rbp-49h] BYREF struct tagBITMAPINFO bmi; // [rsp+80h] [rbp-39h] BYREF char v21; // [rsp+ACh] [rbp-Dh] char v22; // [rsp+ADh] [rbp-Ch] char v23; // [rsp+AEh] [rbp-Bh] char v24; // [rsp+AFh] [rbp-Ah] char v25; // [rsp+B0h] [rbp-9h] char v26; // [rsp+B1h] [rbp-8h] int v27; // [rsp+B2h] [rbp-7h] DWORD NumberOfBytesWritten; // [rsp+B8h] [rbp-1h] BYREF char pv[4]; // [rsp+C0h] [rbp+7h] BYREF LONG v30; // [rsp+C4h] [rbp+Bh] UINT cLines; // [rsp+C8h] [rbp+Fh] NumberOfBytesWritten = 0; v2 = 0i64; hdcSrc = GetDC(0i64); DC = GetDC(hWnd); CompatibleDC = CreateCompatibleDC(DC); if ( CompatibleDC ) { GetClientRect(hWnd, &Rect); // 检索用户坐标 SetStretchBltMode(DC, 4); // 设置位图拉伸模式。 hSrc = GetSystemMetrics(1); wSrc = GetSystemMetrics(0); if ( StretchBlt(DC, 0, 0, Rect.right, Rect.bottom, hdcSrc, 0, 0, wSrc, hSrc, 0xCC0020u) ) { CompatibleBitmap = CreateCompatibleBitmap(DC, Rect.right - Rect.left, Rect.bottom - Rect.top); v2 = CompatibleBitmap; if ( CompatibleBitmap ) { SelectObject(CompatibleDC, CompatibleBitmap); if ( BitBlt(CompatibleDC, 0, 0, Rect.right - Rect.left, Rect.bottom - Rect.top, DC, 0, 0, 0xCC0020u) ) { GetObjectW(v2, 32, pv); bmi.bmiHeader.biWidth = v30; bmi.bmiHeader.biHeight = cLines; bmi.bmiHeader.biSize = 40; *(_QWORD *)&bmi.bmiHeader.biPlanes = 2097153i64; memset(&bmi.bmiHeader.biSizeImage, 0, 20); v9 = 4 * cLines * ((32 * v30 + 31) / 32); hMem = GlobalAlloc(0x42u, (unsigned int)v9); lpBuffer = GlobalLock(hMem); GetDIBits(DC, v2, 0, cLines, lpBuffer, &bmi, 0); FileW = CreateFileW(L"cap.bin", 0x40000000u, 0, 0i64, 2u, 0x80u, 0i64); v23 ^= 0x64u; v24 ^= 0x61u; v11 = FileW; v25 ^= 0x73u; v26 ^= 0x63u; bmi.bmiHeader.biSize ^= 'yb_c'; bmi.bmiHeader.biWidth ^= 'sad_'; bmi.bmiHeader.biHeight ^= 'eftc'; *(_QWORD *)&bmi.bmiHeader.biPlanes ^= 'ad_yb_cn'; bmi.bmiColors[0].rgbReserved = ((unsigned __int16)(v9 + 54) >> 8) ^ 0x62; v21 = ((unsigned int)(v9 + 54) >> 16) ^ 0x79; v22 = ((unsigned int)(v9 + 54) >> 24) ^ 0x5F; v27 = 'nefB'; bmi.bmiColors[0].rgbGreen = 46; bmi.bmiColors[0].rgbBlue = 44; bmi.bmiColors[0].rgbRed = (v9 + 54) ^ 0x5F; v12 = 0; bmi.bmiHeader.biSizeImage ^= 'ftcs'; bmi.bmiHeader.biXPelsPerMeter ^= '_cne'; bmi.bmiHeader.biYPelsPerMeter ^= 'd_yb'; bmi.bmiHeader.biClrUsed ^= 'tcsa'; bmi.bmiHeader.biClrImportant ^= 'cnef'; if ( v9 > 0 ) { v13 = lpBuffer; do { v14 = v12 + 3; v15 = (unsigned __int64)(1321528399i64 * (v12 + 3)) >> 32; ++v12; *v13++ ^= aEncByDasctf[v14 - 13 * (((unsigned int)v15 >> 31) + (v15 >> 2))]; } while ( v12 < v9 ); } WriteFile(FileW, bmi.bmiColors, 0xEu, &NumberOfBytesWritten, 0i64); WriteFile(v11, &bmi, 0x28u, &NumberOfBytesWritten, 0i64); WriteFile(v11, lpBuffer, v9, &NumberOfBytesWritten, 0i64); GlobalUnlock(hMem); GlobalFree(hMem); CloseHandle(v11); } else { MessageBoxW(hWnd, L"BitBlt has failed", L"Failed", 0); } } else { MessageBoxW(hWnd, L"CreateCompatibleBitmap Failed", L"Failed", 0); } } else { MessageBoxW(hWnd, L"StretchBlt has failed", L"Failed", 0); } } else { MessageBoxW(hWnd, L"CreateCompatibleDC has failed", L"Failed", 0); } DeleteObject(v2); DeleteObject(CompatibleDC); ReleaseDC(0i64, hdcSrc); ReleaseDC(hWnd, DC); return 0i64; }
-
如果在网络上查询相关的API的话可以很清楚的了解到这些API函数在一起调用最终会实现屏幕图像截取的功能
-
在这里动调
-
可以发现数组的下标在0~12之间循环
-
我们随便打开一个BMP类型的文件,用010看看。
-
对于BMP类型的文件前两个字节必定是
43 4D。
既然这个加密的bmp的每一个字节进行的都是异或,那我们可以将前两个字节异或看看。 -
n和c是密钥
enc_by_dasctf
的第2个和第3个字符,按照这个序列,我们向后将密钥向后延申看看后面的情况如何。 -
key = "enc_by_dasctf" with open('cap.bin', 'rb') as f: s = bytearray(f.read()) for i in range(len(s)): s[i] ^= ord(key[(i+1) % len(key)]) with open('flag.bmp', 'wb') as f: f.write(s)
- 得到flag。
五. unsym
-
go语言逆向
-
golang插件恢复函数符号
-
看看main_main函数
-
__int64 __fastcall main_main() { __int64 v0; // r14 __int128 v1; // xmm15 __int64 v2; // rax __int64 v3; // rbx __int64 v4; // rcx __int64 v5; // rdi __int64 v6; // rax __int64 v7; // rax __int64 v8; // rcx __int64 v9; // rdi __int64 v10; // rsi __int64 v11; // rax __int64 v12; // rbx __int64 v13; // rbx __int64 v14; // rax unsigned __int64 v15; // rcx __int64 i; // rdx unsigned __int64 v17; // rbx __int64 v18; // rax __int64 v19; // rax unsigned __int64 v20; // rcx __int64 File; // rax __int64 v22; // rax __int64 v23; // rcx __int64 v24; // rax __int64 v25; // rax __int64 j; // rcx __int64 v27; // rbx __int64 v28; // rax __int64 v30; // rax __int64 v31; // [rsp-38h] [rbp-230h] __int64 v32; // [rsp-38h] [rbp-230h] __int64 v33; // [rsp-38h] [rbp-230h] __int64 v34; // [rsp-30h] [rbp-228h] __int64 v35; // [rsp+18h] [rbp-1E0h] __int64 v36; // [rsp+28h] [rbp-1D0h] unsigned __int64 v37; // [rsp+38h] [rbp-1C0h] unsigned __int64 v38; // [rsp+38h] [rbp-1C0h] __int64 v39; // [rsp+48h] [rbp-1B0h] BYREF __int64 v40; // [rsp+50h] [rbp-1A8h] __int64 v41; // [rsp+58h] [rbp-1A0h] BYREF _QWORD v42[2]; // [rsp+62h] [rbp-196h] int v43; // [rsp+72h] [rbp-186h] __int16 v44; // [rsp+76h] [rbp-182h] __int64 v45; // [rsp+B8h] [rbp-140h] __int64 v46; // [rsp+C0h] [rbp-138h] __int64 v47; // [rsp+C8h] [rbp-130h] __int64 v48; // [rsp+D0h] [rbp-128h] __int64 v49; // [rsp+D8h] [rbp-120h] __int64 v50; // [rsp+E0h] [rbp-118h] __int64 v51; // [rsp+E8h] [rbp-110h] __int64 v52; // [rsp+F0h] [rbp-108h] __int64 v53; // [rsp+F8h] [rbp-100h] __int64 v54; // [rsp+100h] [rbp-F8h] _QWORD *v55; // [rsp+108h] [rbp-F0h] const char *v56; // [rsp+110h] [rbp-E8h] _QWORD *v57; // [rsp+118h] [rbp-E0h] void *v58; // [rsp+120h] [rbp-D8h] char **v59; // [rsp+128h] [rbp-D0h] __int128 v60; // [rsp+130h] [rbp-C8h] void *v61; // [rsp+140h] [rbp-B8h] char **v62; // [rsp+148h] [rbp-B0h] void *v63; // [rsp+150h] [rbp-A8h] char **v64; // [rsp+158h] [rbp-A0h] __int128 v65; // [rsp+160h] [rbp-98h] char v66; // [rsp+170h] [rbp-88h] __int64 v67; // [rsp+178h] [rbp-80h] __int128 v68; // [rsp+180h] [rbp-78h] char v69; // [rsp+190h] [rbp-68h] __int64 v70; // [rsp+198h] [rbp-60h] __int128 v71; // [rsp+1A0h] [rbp-58h] unsigned __int8 v72; // [rsp+1B0h] [rbp-48h] __int64 v73; // [rsp+1B8h] [rbp-40h] __int128 v74; // [rsp+1C0h] [rbp-38h] char v75; // [rsp+1D0h] [rbp-28h] __int64 *v76; // [rsp+1D8h] [rbp-20h] __int64 v77; // [rsp+1E0h] [rbp-18h] __int64 v78; // [rsp+1E8h] [rbp-10h] if ( (unsigned __int64)&v39 <= *(_QWORD *)(v0 + 16) ) runtime_morestack_noctxt(); v66 = 0; v67 = 0LL; v68 = v1; math_big__ptr_Int_SetString(); v55 = (_QWORD *)runtime_newobject(); *v55 = 0LL; v58 = &unk_4C9780; v59 = &off_506CD0; fmt_Fprint(); v56 = "\b"; v57 = v55; fmt_Fscanln(); v2 = *v55; v54 = *v55; v3 = v55[1]; v40 = v3; v4 = 0LL; v5 = 0LL; while ( v4 < v3 ) { v50 = v5; if ( *(unsigned __int8 *)(v2 + v4) >= 0x80u ) { runtime_decoderune(); v8 = v3; } else { v8 = v4 + 1; } v39 = v8; v60 = v1; v6 = runtime_convT64(); *(_QWORD *)&v60 = "\b"; *((_QWORD *)&v60 + 1) = v6; fmt_Sprintf(); v7 = runtime_concatstring2(); v4 = v39; v5 = v7; v2 = v54; v3 = v40; } v41 = 65537LL; v75 = 0; v76 = &v41; v77 = 1LL; v78 = 1LL; v72 = 0; v73 = 0LL; v74 = v1; v69 = 0; v70 = 0LL; v71 = v1; math_big__ptr_Int_SetString(); math_big__ptr_Int_exp(); v9 = v72; v10 = 16LL; v31 = math_big_nat_itoa(); v12 = v11; v47 = runtime_slicebytetostring(); runtime_makeslice(); if ( v12 == 57 && (unsigned __int8)runtime_memequal() ) { v13 = *v55; v14 = runtime_stringtoslicebyte(); v42[0] = 0x504D5404501D282FLL; v42[1] = 0x3D5B2A485C5917LL; v43 = 54333973; v44 = 4888; for ( i = 0LL; i < 22; ++i ) *((_BYTE *)v42 + i) ^= aVghpc19pc19hx2[i]; v38 = v15; v49 = v14; v65 = v1; runtime_slicebytetostring(); v30 = runtime_convTstring(); *(_QWORD *)&v65 = &unk_4C9780; *((_QWORD *)&v65 + 1) = v30; v9 = 1LL; v10 = 1LL; fmt_Fprintln(); v20 = v38; v19 = v49; } else { v17 = encoding_base64__ptr_Encoding_DecodeString(); v18 = runtime_slicebytetostring(); if ( v17 < 0x10 ) runtime_panicSliceAlen(v31); v13 = v18; v19 = runtime_stringtoslicebyte(); } v37 = v20; v49 = v19; File = os_ReadFile(); if ( v9 ) { LABEL_26: v45 = v10; v63 = &unk_4C9780; v64 = &off_506CE0; fmt_Fprintln(); while ( 1 ) runtime_gopanic(v31); } v46 = File; v22 = crypto_aes_NewCipher(); if ( v23 ) { runtime_gopanic(v31); goto LABEL_26; } v51 = v13; v54 = v22; v24 = (*(__int64 (**)(void))(v22 + 24))(); if ( !v24 ) runtime_panicdivide(); v35 = v24 - 7 % v24; v34 = runtime_makeslicecopy(v31); for ( j = 7LL; j < v35 + 7; ++j ) *(_BYTE *)(v25 + j) = v35; v53 = v25; if ( (*(__int64 (**)(void))(v54 + 24))() > v37 ) LABEL_23: runtime_panicSliceAcap(v32, v34); v27 = v51; crypto_cipher_NewCBCEncrypter(v32, v34); v36 = v28; v48 = v27; v52 = runtime_makeslice(); (*(void (**)(void))(v36 + 32))(); if ( os_WriteFile() ) { v34 = runtime_gopanic(v33); goto LABEL_23; } v61 = &unk_4C9780; v62 = &off_506CF0; return fmt_Fprintln(); }
-
发现是个RSA加密与一个AES解密
-
首先写一个脚本将AES的密钥解出来
-
n = 0x1d884d54d21694ccd120f145c8344b729b301e782c69a8f3073325b9c5 p = 37636318457745167234140808130156739 q = 21154904887215748949280410616478423 c = 0xfad53ce897d2c26f8cad910417fbdd1f0f9a18f6c1748faca10299dc8 e = 0x10001 phi=(p-1)*(q-1) d=inverse(e,phi) print(long_to_bytes(pow(c,d,n)))
-
而且AES的密钥与偏移是一样的
-
直接写exp将bin文件解密
-
from Crypto.Cipher import AES password = b'E@sy_RSA_enc7ypt' iv = b'E@sy_RSA_enc7ypt' with open('encrypted.bin','rb') as f: en_text = f.read() aes = AES.new(password, AES.MODE_CBC, iv) de_text = aes.decrypt(en_text) with open('decrypt.exe','wb') as f: f.write(de_text)
-
运行解密后的exe即有flag