[Re]南邮ctf平台逆向题
繼續學習,這次嘗試做了一下南郵ctf平臺的逆向題來練習
目錄
第一題 HELLO,RE!
第二題 ReadAsm2
第三題 Py交易
第四題?WxyVM
第五題 maze
第六題?WxyVM 2
?
第一題 HELLO,RE!
打開ida,找到main函數按F5,hexray反編譯
就在眼前?flag{Welcome_To_RE_World!}
第二題 ReadAsm2
來鍛煉匯編的閱讀能力吧
main函數定義了一串字符串,應該就是加密的密文
通過func解密后輸出結果,題目提示調用約定為System V AMD64 ABI
百度調用約定后,分析結果如下
總的來說,意思就是函數對輸入的字符串每一個字符都與其
所在緩沖區的索引做異或運算,最后輸出結果。
用py來寫解密腳本吧
flag = [0x0,0x67,0x6e,0x62,0x63,0x7e,0x74,0x62,0x69,0x6d,0x55, 0x6a, 0x7f, 0x60, 0x51, 0x66,0x63, 0x4e, 0x66, 0x7b,0x71, 0x4a, 0x74, 0x76, 0x6b, 0x70, 0x79, 0x66 , 0x1c]flagstr = []index = 0 for ech in flag:flag[index] = ech^indexflagstr.append(chr(flag[index]))index = index+1print ''.join(flagstr)運行后得到答案?flag{read_asm_is_the_basic}
第三題 Py交易
Pyc文件,直接就是讓我們,來反編譯源文件了
百度就可以找到pyc在線反編譯網站https://tool.lu/pyc/
反編譯結果如下
import base64def encode(message):s = ''for i in message:x = ord(i) ^ 32x = x + 16s += chr(x)return base64.b64encode(s)correct = 'XlNkVmtUI1MgXWBZXCFeKY+AaXNt' flag = '' print 'Input flag:' flag = raw_input() if encode(flag) == correct:print 'correct' else:print 'wrong' import base64def encode(message):s = ''for i in message:x = ord(i) ^ 32x = x + 16s += chr(x)return base64.b64encode(s)correct = 'XlNkVmtUI1MgXWBZXCFeKY+AaXNt' flag = '' print 'Input flag:' flag = raw_input() if encode(flag) == correct:print 'correct' else:print 'wrong'對上述代碼中的encode加密函數作逆就可以得到結果了
py腳本如下
from base64 import *correct = 'XlNkVmtUI1MgXWBZXCFeKY+AaXNt' correct = b64decode(correct) correct = list(correct)flag = [] for ech in correct:x = ord(ech) - 16x = x ^ 32flag.append(chr(x))print ''.join(flag)最終結果為 nctf{d3c0mpil1n9_PyC}
第四題?WxyVM
扔到64位windows Linux子系統下運行,顯示要求我們輸入flag
扔到ida,找到main函數,F5反編譯
主函數沒什么好說的,判斷輸入的字符數,sub_4005b6這個函數對其加密,然后與601060這的數組做比對
現在只要解密601060的數組即可
進入sub_4005b6函數
看來是根據6010c0表的值以及做運算
dump下6010c0處的數組,以及最后用于比較的位于601060處的密文
值得注意的是601060處的數組是一個雙字數組,而我們的輸入時字符單字節數組
所以做比較時,只有雙字的低8位與我們的輸入做比較,其他都是垃圾數據,所以
密文保存的時候只要保存低8位的字節就行了
py腳本如下
biao = open('biao','rb') flag = [0xC4,0x34,0x22,0xB1,0xD3,0x11,0x97,0x7,0xDB,0x37,0xC4,0x6,0x1D,0xFC,0x5B,0xED,0x98,0xDF,0x94,0xD8,0xB3,0x84,0xCC,0x8]biaolist = [] for i in range(0,15000):tmp = biao.readline(1)biaolist.append(ord(tmp))biao.close()for i in range(14997,-1,-3):v0 = biaolist[i]v3 = biaolist[i+2]result = v0if v0 == 1:result = biaolist[i+1]flag[result] -= v3elif v0 == 2:result = biaolist[i+1]flag[result] += v3elif v0 == 3:result = biaolist[i+1]flag[result] ^= v3elif v0 == 4:result = biaolist[i+1]flag[result] = flag[result]/v3elif v0 == 5:result = biaolist[i+1]flag[result] ^= flag[biaolist[i+2]]else:continueflagstr = []for ech in flag:flagstr.append(chr(ech%256))flagstr = ''.join(flagstr) print flagstr?
py的變量沒有溢出之類的概念,所以記得對256取模來保證,字符正常輸出
“biao"是我們dump下來的加密函數用的數組
最終結果如下:nctf{Embr4ce_Vm_j0in_R3}
第五題 maze
前天看到bugku上有一道take the maze,還沒弄懂,還好這個還簡單些
依然是扔到ida里去在main函數中反編譯
很長呢...改了幾個變量名字看著舒服多了
整體看下來就是大概用了一個變量,64位的road(這是我自己重命名的變量)
他的高32位用作列索引,低32位用作行索引(小端序機器),在提供給的maze_list這個二維
數組中前進,如果遇到 # 就算成功,幾個條件判斷語句控制,前進的方向,road保存著當前的位置
結果是'O'向左,'o'向右,'.'向上,'0'向下,去吧maze_list的表給dump下來
一行8個的二維數組,我用py打印出來直觀的看一下
maze = ' ******* * **** * **** * *** *# *** *** *** *********'tu = []tuech = []index = 0 for ech in maze:if index == 7:index = 0tuech.append(ech)tu.append(tuech)tuech = []continuetuech.append(ech)index = index+1for ech in tu:print ''.join(ech)然后自己畫著走就可以看出來了
應該是o0oo00O000oooo..OO
最后結果為 nctf{o0oo00O000oooo..OO}
第六題?WxyVM 2
隔了一天弄好了,解密腳本一開始就寫完了,
結果運算結果匪夷所思,弄了半天才發現,原來py沒有
自增運算符。。。。。
首先是main函數,光反編譯就等了一會兒。。。
總的來說就是有一大串沒有意義的運算,有意義的就只有以字節運算的語句
byte_694100是我們的輸入,最后這個循環就是用來比較的,和前面一道題
差不多,也只要關注第一個字節就行。
把所有的運算語句copy下來選出byte運算的就可以。
我第一次弄完了后,打算迭代直接exec(),
結果由于py沒有自增運算符,輸出成很奇怪的
flag
郁悶了我好久。。。。。
偷個懶干脆直接生成c語言風格的語句,用c計算了。。。
python生成c語言語句
f = open('shanxuan.txt') byte_694100 = 0xC0 byte_694101 = 0x85 byte_694102 = 0xF9 byte_694103 = 0x6C byte_694104 = 0xE2 byte_694105 = 0x14 byte_694106 = 0xBB byte_694107 = 0xe4 byte_694108 = 0xd byte_694109 = 0x59 byte_69410A = 0x1c byte_69410B = 0x23 byte_69410C = 0x88 byte_69410D = 0x6e byte_69410E = 0x9b byte_69410F = 0xca byte_694110 = 0xba byte_694111 = 0x5c byte_694112 = 0x37 byte_694113 = 0xfff byte_694114 = 0x48 byte_694115 = 0xd8 byte_694116 = 0x1f byte_694117 = 0xab byte_694118 = 0xa5 flist = f.readlines()for i in range(len(flist)):flist[i] = flist[i].strip(' \n;u')tmp = [] index1 = 0 index2 = 0 for ech in flist:index2 = 0if ech.find('+') != -1:tmp = list(ech)for c in tmp:if c=='+':tmp[index2] = '-'index2 = index2+1flist[index1] = ''.join(tmp)tmp = []elif ech.find('-') != -1:tmp = list(ech)for c in tmp:if c=='-':tmp[index2] = '+'index2 = index2+1flist[index1] = ''.join(tmp)tmp = []index1 = index1+1tmp = []flist.reverse() i = 0 for ech in flist:if ech.find('byte') != -1: print ech+';'笨笨的腳本,不想管了。。
把變量,和輸出結果copy到vs里再定義一下,編譯出結果
結果?nctf{th3_vM_w1th0ut_dAta}。好累再去刷bugku的題。。。
?
?
?
?
?
?
?
?
總結
以上是生活随笔為你收集整理的[Re]南邮ctf平台逆向题的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Java 中各数字类型(Double,
- 下一篇: 基于Java内存溢出的解决方法详解