几道reverse基础题目wp
很简单,写的c语言脚本
 1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
  
#include  <stdio.h> 
 #include  <string.h> 
 int  main ()  { 
	char  Str1 [ 1000 ]; 
 	strcpy_s ( Str1 ,  sizeof ( Str1 ),  "{34sy_r3v3rs3}" ); 
 	int  i ; 
 	for  ( i  =  0 ;  i  <=  665 ;  ++ i ) 
 	{ 
 		if  ( Str1 [ i ]  ==  '3' ) 
 			Str1 [ i ]  =  'e' ; 
 	} 
 	for  ( i  =  0 ;  i  <=  665 ;  ++ i ) 
 	{ 
 		if  ( Str1 [ i ]  ==  '4' ) 
 			Str1 [ i ]  =  'a' ; 
 	} 
 	printf ( "%s" ,  Str1 ); 
 } 
 
 
Tips: 
	1.使用strcpy函数要添加#include <string.h>函数头
	2.在比较新的编译器里面,会对strcpy的安全问题报错,需对strcpy进行改进:
strcpy_s(str1,中间参数,str2);
中间参数的意义可以理解为:str2预计需要向str1占用多少空间
所以很显然中间参数的值的大小,必须大于等于str2的空间,但是小于等于str1空间(前提:str1>=str2)
通常情况下可以写为:
strcpy_s(str1,sizeof(str2),str2); 
或者strcpy_s(str1,strlen(str2)+1,str2); 
 
         
1
 2
 3
 4
 5
 6
 7
 8
 9
  
#include  <stdio.h> 
 int  main ()  { 
	char  a []  =  "d`vxbQd" ; 
 	for  ( int  i  =  0 ;  i  <  7 ;  i ++ )  { 
 		a [ i ]  =  a [ i ]  ^  2 ; 
 		a [ i ] -- ; 
 	} 
 	printf ( "%s" , a ); 
 } 
 
 
把原本的python的脚本稍作修改,再跑一遍(xor加密)得到flag
 1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
  
import base64,urllib.parse
 key = "HereIsFlagggg"
 flag = "xxxxxxxxxxxxxxxxxxx"
 
 s_box = list(range(256))
 j = 0
 for i in range(256):
     j = (j + s_box[i] + ord(key[i % len(key)])) % 256
     s_box[i], s_box[j] = s_box[j], s_box[i]
 res = []
 i = j = 0
 for s in flag:
     i = (i + 1) % 256
     j = (j + s_box[i]) % 256
     s_box[i], s_box[j] = s_box[j], s_box[i]
     t = (s_box[i] + s_box[j]) % 256
     k = s_box[t]
     res.append(chr(ord(s) ^ k))
 cipher = "".join(res)
 crypt = (str(base64.b64encode(cipher.encode('utf-8')), 'utf-8'))
 enc = str(base64.b64decode(crypt),'utf-8')
 enc = urllib.parse.quote(enc)
 print(enc)
 # enc = %C2%A6n%C2%87Y%1Ag%3F%C2%A01.%C2%9C%C3%B7%C3%8A%02%C3%80%C2%92W%C3%8C%C3%BA
  
 
下面是修改之后的脚本:
 1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
  
import urllib.parse
 key = "HereIsFlagggg"
 flag = "%C2%A6n%C2%87Y%1Ag%3F%C2%A01.%C2%9C%C3%B7%C3%8A%02%C3%80%C2%92W%C3%8C%C3%BA"
 flag =urllib.parse.unquote(flag)
 s_box = list(range(256))
 j = 0
 for i in range(256):
     j = (j + s_box[i] + ord(key[i % len(key)])) % 256
     s_box[i], s_box[j] = s_box[j], s_box[i]
 res = []
 i = j = 0
 for s in flag:
     i = (i + 1) % 256
     j = (j + s_box[i]) % 256
     s_box[i], s_box[j] = s_box[j], s_box[i]
     t = (s_box[i] + s_box[j]) % 256
     k = s_box[t]
     res.append(chr(ord(s) ^ k))
 cipher = "".join(res)
 
 print(cipher)
 //NSSCTF{REAL_EZ_RC4}
  
 
Tips :python脚本中最下边注释掉的enc就是正确的flag之后加密的,千万不要覆盖掉
反编译,很简单的代码审计,复制改程序的代码进行修改,逆向运算进行解密
         
下面是C语言写的脚本
 1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
  
#include  <stdio.h> 
 int  main ()  { 
    char  Str []  =  "ylqq]aycqyp{" ; 
     int  v7  =  strlen ( Str ); 
     for  ( int  i  =  0 ;  i  <  v7 ;  ++ i ) 
     { 
         if  (( Str [ i ]  <=  96  ||  Str [ i ]  >  98 )  &&  ( Str [ i ]  <=  64  ||  Str [ i ]  >  66 )) 
             Str [ i ]  +=  2 ; 
         else 
             Str [ i ]  -=  24 ; 
     } 
     printf ( "%s" ,  Str ); 
 } 
 
 
但输出的flag好像有点问题,确实怪
1
  
//{nss_c{es{r},{用a替换,得到{nss_caesar}为正确答案
  
 
非预期解:在十六进制数据对应的ASCII中发现了flag
         
    [SWPUCTF 2021 新生赛]fakerandom 
         
append()函数  ⽤于在列表末尾添加新的对象
 
random.getrandbits(k)
返回一个不大于K位的Python 整数(十进制),比如k=10,则结果是0~2^10之间的整数。
 
以下是算法逆向脚本:
 1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
  
import random
 result = [201, 8, 198, 68, 131, 152, 186, 136, 13, 130, 190, 112, 251, 93, 212, 1, 31, 214, 116, 244]
 random.seed(1)
 l = []
 for i in range(4):
     l.append(random.getrandbits(8))
 flag=[]
 for i in range(len(l)):
     random.seed(l[i])
     for n in range(5):
         flag.append(chr(result[i*5+n]^random.getrandbits(8)))
 print(''.join(flag))
  
 
 1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
  
#include  <stdio.h> 
 int  main () 
{ 
    srand ( 0x2766 ); 
     printf ( "NSSCTF{" ); 
     for  ( int  m  =  0 ;  m  <  13 ;  ++ m  ) 
     { 
         printf ( "%d" ,  rand ()  %  8  +  1 ); 
     } 
     putchar ( '}' ); 
 } 
 
 
Tips :必须在Linux下运行才正确
非预期解:
         
预期解:
IDA32位,定位到main函数,发现花指令
         
快捷键D转换成数据
         
然后nop(90)
         
随后一路快捷键C将黄色代码转换成数据
         
整理完成之后,创建函数,之后就可以进行F5反编译,得到flag
         
根据题目标签可知,UPX脱壳,可以用upx直接进行脱壳
https://github.com/upx/upx/releases 
         
题目代码
 1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
  
flag = 'xxxxxxxxxxxxxxxxxxx'
 
 s_box = 'qwertyuiopasdfghjkzxcvb123456#$'
 tmp = ''
 for i in flag:
     tmp += str(bin(ord(i)))[2:].zfill(8)
 b1 = int(tmp,2)
 s = ''
 while b1//31 != 0:
     s += s_box[b1%31]
     b1 = b1//31
 
 print(s)
 
 # s = u#k4ggia61egegzjuqz12jhfspfkay
  
 
审计注释:
1
 2
 3
 4
 5
 6
 7
  
ord ( i ): 返回字符   ` i `   的   ASCII   码值。 
 bin ( ord ( i ))   将   ASCII   码值转换为二进制数。 
 str ( bin ( ord ( i )))   将二进制数转换为字符串。 
 [ 2 :]   从第二个字符开始取,去除字符串开头的   '0b' 。 
   用   0   补齐字符串的左侧,使其总长度为   8 。 
   tmp   +=   str ( bin ( ord ( i )))[ 2 :]. zfill ( 8 )   将处理结果拼接到   tmp   中。 
   int ( tmp , 2 )   将   tmp   解释为二进制数,并转换为整数类型。 
  
 
本题考察取模逆运算
         
memcmp函数的原型为 int memcmp(const void *str1, const void *str2, size_t n);其功能是把存储区 str1 和存储区 str2 的前 n 个字节进行比较。该函数是按字节比较的,位于string.h。
如果返回值 < 0,则表示 str1 小于 str2。 
如果返回值 > 0,则表示 str1 大于 str2。 
如果返回值 = 0,则表示 str1 等于 str2。 
 
 
通过Shift+F12查看字符串,发现两段类似base64编码的字符串,猜测base64换表,脚本如下:
1
 2
 3
 4
 5
  
import base64
 str1 = "5Mc58bPHLiAx7J8ocJIlaVUxaJvMcoYMaoPMaOfg15c475tscHfM/8=="                        #str1是要解密的代码
 string1 = "qvEJAfHmUYjBac+u8Ph5n9Od17FrICL/X0gVtM4Qk6T2z3wNSsyoebilxWKGZpRD"             #string1是改过之后的base64表
 string2 = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"
 print (base64.b64decode(str1.translate(str.maketrans(string1,string2))))
  
 
         
         
         
python脚本:
1
 2
 3
 4
 5
 6
  
from base64 import *
 enc = "TlJRQFBBdTs4alsrKFI6MjgwNi5p"
 str = b64decode(enc).decode()
 for i in range(len(str)):
     print(chr(i + ord(str[i])),end='')
 NSSCTF{B@se64_HAHAHA}
  
 
一个xor加密
使用 npm 包 escodegen 解密
安装 escodegen 
 
	2.将json 文件转换成 js语句
 1
  2
  3
  4
  5
  6
  7
  8
  9
 10
  
$  esgenerate  附件 . json 
( function  ()  { 
    function  bE ( str ,  key )  { 
         var  arr  =  str . split ( '' ); 
         return  arr . map ( i  =>  { 
             return  String . fromCharCode ( i . charCodeAt ()  ^  key ); 
         }) . join ( '' ); 
     } 
     console . log ( bE ( 'EXXH_Mpjx \x7F BxYnjggrM~eerv' ,  11 )); 
 }()); 
 
 
	3.执行语句即可获得 flag
 1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
  
$  node 
Welcome  to  Node . js  v14 . 13.1 . 
Type  ".help"  for  more  information . 
>  ( function  ()  { 
...      function  bE ( str ,  key )  { 
.....          var  arr  =  str . split ( '' ); 
.....          return  arr . map ( i  =>  { 
.......              return  String . fromCharCode ( i . charCodeAt ()  ^  key ); 
.......          }) . join ( '' ); 
.....      } 
...      console . log ( bE ( 'EXXH_Mpjx \x7F BxYnjggrM~eerv' ,  11 )); 
...  }()); 
 
 
NSSCTF{astIsReallyFunny}