本文最后更新于:2025年11月3日 下午
                  
                
              
            
            
              
                
                初识程序 拿到程序后,先放入PEID进行检测
程序无壳,是32位的,可以直接放入IDA32进行反编译
开始整活 进入后找到main函数入口,解析为C语言
有两个函数,一个是_main()函数,一个是func()函数,进入__main发现只有一个if判定没有
没有什么实质性的东西,然后转只能回头找func,进入后确认是主要判定的函数
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 int  func ()  {   int  result;    int  v1;    int  v2;    int  v3;    int  v4;    unsigned  __int8 v5;    unsigned  __int8 v6;    unsigned  __int8 v7;    unsigned  __int8 v8;    unsigned  __int8 v9;    int  v10;    int  v11;    int  v12;    int  v13;    unsigned  __int8 v14;    char  v15;    char  v16;    char  v17;    char  v18;    char  v19;    char  v20;    char  v21;    char  v22;    char  v23;    char  v24;    char  v25;    char  v26;    char  v27;    char  v28;    char  v29;    char  v30;    char  v31;    int  i;    v15 = 'Q' ;   v16 = 's' ;   v17 = 'w' ;   v18 = '3' ;   v19 = 's' ;   v20 = 'j' ;   v21 = '_' ;   v22 = 'l' ;   v23 = 'z' ;   v24 = '4' ;   v25 = '_' ;   v26 = 'U' ;   v27 = 'j' ;   v28 = 'w' ;   v29 = '@' ;   v30 = 'l' ;   v31 = '\0' ;   printf ("Please input:" );   scanf ("%s" , &v5);   result = v5;   if  ( v5 == 'A'  )   {     result = v6;     if  ( v6 == 'C'  )     {       result = v7;       if  ( v7 == 'T'  )       {         result = v8;         if  ( v8 == 'F'  )         {           result = v9;           if  ( v9 == '{'  )           {             result = v14;             if  ( v14 == '}'  )             {               v1 = v10;               v2 = v11;               v3 = v12;               v4 = v13;               for  ( i = 0 ; i <= 15 ; ++i )               {                 if  ( *((_BYTE *)&v1 + i) > 64  && *((_BYTE *)&v1 + i) <= 90  )                   *((_BYTE *)&v1 + i) = (*((char  *)&v1 + i) - 51 ) % 26  + 65 ;                 if  ( *((_BYTE *)&v1 + i) > 96  && *((_BYTE *)&v1 + i) <= 122  )                   *((_BYTE *)&v1 + i) = (*((char  *)&v1 + i) - 79 ) % 26  + 97 ;               }               for  ( i = 0 ; i <= 15 ; ++i )               {                 result = (unsigned  __int8)*(&v15 + i);                 if  ( *((_BYTE *)&v1 + i) != (_BYTE)result )                   return  result;               }               result = printf ("You are correct!" );             }           }         }       }     }   }   return  result; }
 
对有关的字符进行转换后发现逻辑比较简单,就是对字符串进行一个分支结构的判断,根据前面嵌套的if语句判断开头是ACTF{,结尾有一个}(废话),处理以后再和前面的一个字符串连接起来,即可得到解
加大力度 分析到这里问题就很简单了,直接开始脚本
1 2 3 4 5 6 7 8 9 10 11 12 13 14 a="ACTF{"  v15="Qsw3sj_lz4_Ujw@l"  s="" for  k in  range (len (v15)):     for  s in  range (128 ):         i=s         if  i>64  and  i <=90 :             i=(i-51 )%26 +65          if  i>96  and  i<=122 :             i=(i-79 )%26 +97          if  i==ord (v15[k]):             a=a+chr (s)print (a+"}" )
 
最后找到了flagACTF{Cae3ar_th4_Gre@t}