[GXYCTF2019]luck_guy
链接:https://pan.baidu.com/s/1hoU9 uQsSeGr-6p7RBSm56w 提取码:ed2z
0x01 查看有无加壳

没有加壳,64位文件
0x02 打开IDA64,查看main函数,F5反编译

0x03 进入patch_me函数,接着进入get_flag函数界面


0x04 进行代码分析 😞
1 __int64 get_flag() 2 { 3 unsigned int v0; // eax@1 4 signed int i; // [sp+4h] [bp-3Ch]@1 5 signed int j; // [sp+8h] [bp-38h]@7 6 __int64 s; // [sp+10h] [bp-30h]@3 7 char v5; // [sp+18h] [bp-28h]@6 8 __int64 v6; // [sp+38h] [bp-8h]@1 9 10 v6 = *MK_FP(__FS__, 40LL); 11 v0 = time(0LL); //得到时间 12 srand(v0); //使用时间作为种子生成随机数字 13 for ( i = 0; i <= 4; ++i ) 14 { 15 switch ( rand() % 200 ) // 产生1-199之间的随机数 16 { 17 case 1: 18 puts("OK, it's flag:"); 19 memset(&s, 0, 0x28uLL); 20 strcat((char *)&s, f1); // f1='GXY{do_not_' 21 strcat((char *)&s, &f2); //f2初始为空 22 printf("%s", &s); 23 break; 24 case 2: 25 printf("Solar not like you"); 26 break; 27 case 3: 28 printf("Solar want a girlfriend"); 29 break; 30 case 4: 31 v5 = 0; 32 s = 9180147350284624745LL; //在IDA里面选中9180147350284624745LL按H键转换16进制为0x69,0x63,0x75,0x67,0x60,0x6f,0x66,0x7f 33 strcat(&f2, (const char *)&s); //f2和s拼接 34 break; 35 case 5: 36 for ( j = 0; j <= 7; ++j ) 37 { 38 if ( ((((unsigned int)((unsigned __int64)j >> 32) >> 31) + (_BYTE)j) & 1) 39 - ((unsigned int)((unsigned __int64)j >> 32) >> 31) == 1 ) 40 *(&f2 + j) -= 2; 41 else 42 --*(&f2 + j); 43 } 44 break; 45 default: 46 puts("emmm,you can't find flag 23333"); 47 break; 48 } 49 } 50 return *MK_FP(__FS__, 40LL) ^ v6; 51 }

flag就是由f1和f2组成,f1已经告诉,现在只需要求f2就行。
-
case4给f2赋值
-
case5,对f2进行处理
所以顺序是: case5>case4>case1
0x05 脚本构建 🍔
由于IDA是反编译C语言,s=0x69,0x63,0x75,0x67,0x60,0x6f,0x66,0x7f应该逆序成s = 0x7F666F6067756369LL作为小端储存,关于大小端推荐师傅的**文章**
flag = 'GXY{do_not_' f2 = [0x7F, 0x66, 0x6F, 0x60, 0x67, 0x75, 0x63, 0x69][::-1] s = '' for i in range(8): if i % 2 == 1: s = chr(int(f2[i]) - 2) else: s = chr(int(f2[i]) - 1) flag += s print(flag)

GXY{do_not_hate_me}
未亡人

浙公网安备 33010602011771号