Darkctf部分re题目
1.so_much
ida打开得到从main()函数发现一个get_flag()函数。
get_flag函数:
void __usercall get_flag(__int64 a1@<rcx>, __int64 a2@<rbp>, __int64 *a3@<rdi>, __int64 *a4@<rsi>) { signed int i; // [rsp-5Ch] [rbp-5Ch] __int64 v5; // [rsp-58h] [rbp-58h] __int64 v6; // [rsp-50h] [rbp-50h] __int64 v7; // [rsp-48h] [rbp-48h] int v8; // [rsp-40h] [rbp-40h] __int16 v9; // [rsp-3Ch] [rbp-3Ch] __int64 v10; // [rsp-38h] [rbp-38h] __int64 v11; // [rsp-30h] [rbp-30h] __int64 v12; // [rsp-28h] [rbp-28h] __int64 v13; // [rsp-20h] [rbp-20h] __int64 v14; // [rsp-18h] [rbp-18h] unsigned __int64 v15; // [rsp-10h] [rbp-10h] __int64 v16; // [rsp-8h] [rbp-8h] __asm { endbr64 } v16 = a2; v15 = __readfsqword(0x28u); v5 = 0LL; v6 = 0LL; v7 = 0LL; v8 = 0; v9 = 0; for ( i = 7; i <= 29; ++i ) { v11 = 0LL; v12 = 0LL; v13 = 0LL; v14 = 0LL; v10 = flag_48(&v16, i); sub_10D0(); } *a3 = &v5; if ( __readfsqword(0x28u) != v15 ) sub_10A0(); }
可以看到有一个循环,i从7开始猜测v10每次循环的值为flag的内容。
用gdb调试可以得到flag,而钱7位为darkCTF。最终的flag为:darkCTF{w0w_s0_m4ny_funct10ns}
2.strings
在main()函数有这样的字符串
"Use this as ur input: %s\n", "!8u)05/>!#,.W/%H-G"
按照提示输入相应的字符串。
*dest = 0LL; v7 = 0LL; v8 = 0; v9 = 0; v26 = 0; for ( n = 8; n >= 0; --n ) { strncat(dest, &v12 + v26, 1uLL); strncat(dest, &v10 + n, 1uLL); ++v26; }
其中v12,v10为输入的字符串经过变化后的字符串,所以调试的时候观察*dest的内存就能得到flag:darkCTF{wah_howdu_found_me}。
3.HelloWrold
两种解法,一种是下断点查看比较的字符串是什么,另一种是改代码逻辑。
1.下断点
在0x555555555595,0x555555555607,下断点。这两个位置是调用strcmp()函数,然后在运行到断点的地方查看rdi寄存器地址的内容就得到要比较的字符串"H3ll0","W0rld"。输入即可得到flag。
check函数
__int64 __usercall check@<rax>(__int64 a1@<rbp>, _BYTE *a2@<rdi>, int a3@<esi>) { __int64 result; // rax double v4; // xmm0_8 double v5; // xmm0_8 signed int i; // [rsp-50h] [rbp-50h] signed int j; // [rsp-4Ch] [rbp-4Ch] signed int v8; // [rsp-48h] [rbp-48h] signed int v9; // [rsp-44h] [rbp-44h] signed int v10; // [rsp-40h] [rbp-40h] signed int v11; // [rsp-3Ch] [rbp-3Ch] signed int v12; // [rsp-38h] [rbp-38h] signed int v13; // [rsp-34h] [rbp-34h] signed int v14; // [rsp-30h] [rbp-30h] signed int v15; // [rsp-2Ch] [rbp-2Ch] signed int v16; // [rsp-28h] [rbp-28h] signed int v17; // [rsp-24h] [rbp-24h] unsigned __int64 v18; // [rsp-10h] [rbp-10h] __int64 v19; // [rsp-8h] [rbp-8h] __asm { endbr64 } v19 = a1; v18 = __readfsqword(0x28u); result = 0LL; v8 = 5184; v9 = 2601; v10 = 11664; v11 = 11664; v12 = 2304; v13 = 7569; v14 = 2304; v15 = 12996; v16 = 11664; v17 = 10000; if ( a3 == 1 ) { for ( i = 0; i <= 4; ++i ) { v4 = *(&v19 + i - 16); sub_10D0(); sub_1110(); } result = sub_1100(); } else if ( a3 == 2 ) { for ( j = 0; j <= 4; ++j ) { v5 = *(&v19 + j + 5 - 16); sub_10D0(); sub_1110(); } result = sub_1100(); } if ( __readfsqword(0x28u) != v18 ) result = sub_10E0(); return result; }
其中这里比较坑的地方就是sub_1100()这个函数,在运行的时候这个就是strcmp函数。
2.改代码逻辑
在地址0x55555555524A,0x555555555266的地方是jnz指令,直接改成jz,然后随便输入2个参数运行即可得到flag。

浙公网安备 33010602011771号