Tổng hợp writeup cuộc thi vòng loại SVATTT 2017

Sugi_b3o

Moderator
Thành viên BQT
30/08/2016
317
446 bài viết
Tổng hợp writeup cuộc thi vòng loại SVATTT 2017
Topic này tổng hợp writeup từ các bạn tham dự, cũng như các bạn yêu an ninh mạng muốn chia sẻ kiến thức, kinh nghiệm từ vòng loại của cuộc thi Sinh Viên với An Toàn Thông Tin 2017 do Vnisa (hiệp hội An Toàn Thông Tin Việt Nam) tổ chức.
04112017vthuy14.jpg

Cuộc thi vòng loại sinh viên với An Toàn Thông Tin 2017. Ảnh qdnd.vn​
 
Chỉnh sửa lần cuối:
Mời các bạn tham gia Group WhiteHat để thảo luận và cập nhật tin tức an ninh mạng hàng ngày.
Lưu ý từ WhiteHat: Kiến thức an ninh mạng để phòng chống, không làm điều xấu. Luật pháp liên quan
  • Thích
Reactions: whf
Đề bài pwn400 năm nay hơi fail, khi mà cách giải của người chơi không được đúng ý tác giả. Còn bài pwn100 khá hay, là lỗi format string hay gặp, tuy nhiên nằm ở snprintf chứ không phải printf. Khá ít đội làm được bài pwn100 do chưa quen với snprintf.

Bài pwn400

Theo ý của tác giả, thì để giải bài này, người chơi cần phải viết được con shellcode chỉ dùng các ký tự printable. Tuy nhiên, cách giải đơn giản chỉ là viết rop, gọi tới hàm get_string với tham số là địa chỉ vùng ghi được, và nhảy luôn tới đó.

upload_2017-11-5_0-52-11-png.2577


Mã khai thác:

upload_2017-11-5_0-59-24-png.2579


Bài pwn100

Lỗi format string cơ bản, với hàm bị lỗi là snprintf. Tác giả chỉ cho xâu format dài 0x7F byte, do đó ta không thể ghi đè dữ liệu thoải mái được. Tuy nhiên, để biến atoi thành system, thì ta chỉ cần ghi đè 4 byte thấp của atoi thành 4 byte thấp của system là được. Và với 0x7F byte thì ta hoàn toàn làm được.

upload_2017-11-5_1-30-31-png.2583

Mã khai thác:

upload_2017-11-5_1-0-37-png.2580


Link tải đề bài và mã khai thác: pwn_vongloai_svatt2017.zip
Trích bài của Mod tmnt53
Pwn400 – nokiacum
Đầu tiên phải nói là, trên đề không cho trực tiếp file binary mà nói rằng mỗi một mã máy có 1 file binary khác nhau, khiến mình khá sợ khi mà mỗi lần request thấy cái mã số nó cứ nhảy 6 chữ số. Nhưng sau khi tải 4 5 file về thông qua netcat thì mình thấy toàn bộ các file đều giống nhau, không chắc có file nào khác không nhưng các file mình tải được là giống nhau hoàn toàn. Nên mình đã đưa ra giả thuyết đơn giản: cái trò nhiều file bin chẳng qua là làm màu :v.

capture1.png


Tiếp tục sang phần chính, mình decompile 1 file mình tải về với IDA thì được đoạn code Login và get_string này.
capture.png

capture2.png

Khi để ý hàm kiểm tra sử dụng strncmp tức là bạn nhập ra sao cũng được, miễn là 6 kí tự đầu tiên trùng với chuỗi “anlpth” và tương tự với đoạn kiểm tra mật khẩu. Cùng với đó là đoạn nhập chuỗi từng kí tự một nhưng không giới hạn và kết thúc khi gặp kí tự NULL hoặc kí tự xuống dòng làm mình nghĩ đến việc buffer overflow. sau đó mình checksec thì thấy:

gdb-peda$ checksec
CANARY : disabled
FORTIFY : disabled
NX : disabled
PIE : disabled
RELRO : disabled​

Chả có cái nào được bật cả :v Ê, thế thì mình up shell thôi :v và thế là mình thực hiện với việc dùng hàm get_string của tác giả để up shell lên BSS chạy. Cơ mà thế thì dễ vãi, 400 điểm mà dễ thế ????? ?????. Đây là code của mình sử dụng cho bài này.
capture3.png
Hướng làm của tác giả
Thật ra thì khi nhìn mặt idol Lê Ân có chút đau đớn với cách làm của mình thì anh cũng đã nêu ý tưởng rằng muốn các bạn upshell nhưng là ASCII shell nằm trên username hoặc password và sau đó trỏ về đó, đó là lý do chính mà tác giả sử dụng địa chỉ của nơi lưu trữ username là cố định và anh sử dụng hàm check_char để kiểm tra đầu vào.

capture4.png
Với hàm này, nhưng gì được nhập vào username và password phải là printable.

Vậy xử lý sao với cái này? Rất may là tôi vừa làm bài Death_note trên pwnable.tw nên nếu thực sự bài có yêu cầu phải làm vậy thì t tin mình vẫn làm được :v “trời phù hộ người tốt” Ơn trời. Các mã lệnh sử dụng được nằm trong bảng printable nằm ở đây.

Trich blog kad96
 
Chỉnh sửa lần cuối:
Mời các bạn tham gia Group WhiteHat để thảo luận và cập nhật tin tức an ninh mạng hàng ngày.
Lưu ý từ WhiteHat: Kiến thức an ninh mạng để phòng chống, không làm điều xấu. Luật pháp liên quan
  • Thích
Reactions: likehack
Comment
Forensics 100
Mặc dù trong team mình hay làm crypto, nhưng gặp một bài forensics, và chỉ có 100 điểm thì dại gì không làm, nhỉ =))

À ờ, đó là trong trường hợp bình thường thôi. Chứ trường hợp cái file pcap đề cho nó đến hai mươi mấy MB thì cũng hơi… ngán đó =))

Load vào wireshark, nói thật là file pcap trừ khi có mấy protocol lạ lạ, còn lại thì cũng có mấy dạng, làm nhiều thì quen tay thôi. File pcap này có khá nhiều http protocol, nên việc đầu tiên mình làm là File / Export Objects / HTTP

screen-shot-2017-11-05-at-3-32-55-pm.png


Forensics, giống như người ta ném bạn vào đống rác, sau đó bảo bạn tìm cho bạn cờ, nằm trong tờ giấy gói bánh mì vậy. Bới tung đống rác lên để tìm:

screen-shot-2017-11-05-at-3-36-06-pm.png

nothing.py à =)) không tin, lừa nhau à =)) Save file lại, mở ra xem thử:

screen-shot-2017-11-05-at-3-39-15-pm.png

Thuật toán chỉ đơn giản là cộng xong xor, vậy giờ làm ngược lại thôi, xor xong trừ thôi. Mình thì lười, nên mình copy hàm cộng, đổi tên biến, sửa dấu cộng thành dấu trừ…

screen-shot-2017-11-05-at-3-44-32-pm.png
Trích Blog Quân Đoàn UIT​
 
Mời các bạn tham gia Group WhiteHat để thảo luận và cập nhật tin tức an ninh mạng hàng ngày.
Lưu ý từ WhiteHat: Kiến thức an ninh mạng để phòng chống, không làm điều xấu. Luật pháp liên quan
  • Thích
Reactions: sunny
Comment
Crypto 100.
Mình khá là bất ngờ khi nhìn vào dashboard, chỉ có một bài forensics và đến ba bài crypto, lại có đến hai bài 100. Hy vọng không quá khó, chứ mang tiếng chơi crypto, làm không được thì cũng… ahihi.

Download file về, giải nén, mở source encrypt.pylên đọc:
Mã:
import gmpy2
from ctf import MESSAGES

N = 1552518092300708935148979488462502555256886017116696611139052038026050952686376886330878408828646477971459063658923221258297866648143023058142446317581796810373905913084934869211153276980011573717416472395713363686571638755823503877
e = 3
BS = 32

to_int = lambda text: int(''.join(x.encode('hex') for x in text), 16)

c = 0L
cipher = []
for chunk in [MESSAGES[i:i + BS] for i in range(0, len(MESSAGES), BS)]:
    c1 = int(hex(c)[2:-1][:BS*2+1], 16)
    c = gmpy2.powmod(c1 + to_int(chunk), e, N)
    cipher.append(hex(c)[2:])

with open('cipher.txt', 'w') as f:
    f.write(' '.join(cipher))
Có e, có N, chắc là RSA. Quăng vào factordb.com, tạch =))

Xem kỹ hơn, ta thấy e quá nhỏ và N không quá lớn, đây là nguồn gốc của đủ thể loại tấn công RSA trên đời. c ban đầu bằng 0, vậy block đầu tiên của message sẽ là căn bậc ba của block ciphertext đầu tiên.

screen-shot-2017-11-05-at-4-00-05-pm.png


Ơ nhưng mà tới đây rồi sao nữa =)) thấy hơi ngáo ngáo rồi =)) mình stuck ở đây luôn =))

Và rồi một tiếng sau đó, mình nhận ra rằng, cuộc sống này thật đáng buồn. Đã code sẵn cái lib chuyên trị RSA, tự nhiên tới lúc cần thì không lấy ra xài =))

screen-shot-2017-11-05-at-4-05-02-pm.png


Mọi chuyện đã quá dễ dàng khi ta có p và q…
Mã:
from qd import *
n = 1552518092300708935148979488462502555256886017116696611139052038026050952686376886330878408828646477971459063658923221258297866648143023058142446317581796810373905913084934869211153276980011573717416472395713363686571638755823503877
p, q = fermatfactor(n)
#p = 39402006196394479212279040100143613805079739270465446667948293404245721771497210611414266254884915640806628012398823
#q = 39402006196394479212279040100143613805079739270465446667948293404245721771497210611414266254884915641338868201294899

f = open("cipher.txt").read()
f = f.split(" ")

print f
a = []
c = [0]

for cipher in f:
    a.append(solvepq(int(cipher, 16), p, q, e=3)[0])

for i in range(1, len(f)+1):
    c1 = int(hex(int(f[i-1], 16))[2:-1][:32    *2+1], 16)
    c.append(c1)

print c
flag = ""
for i in range(len(a)):
    flag+= long_to_bytes(a[i] - c[i])
print flag
#What I'm trying to say here is... sometimes that *thing* you're searching for your whole life... is right there by your side all along. The flag is {Old_RSA_close_factor_problem}. And you don't even know it.
Trích Blog Quân Đoàn UIT​
 
Mời các bạn tham gia Group WhiteHat để thảo luận và cập nhật tin tức an ninh mạng hàng ngày.
Lưu ý từ WhiteHat: Kiến thức an ninh mạng để phòng chống, không làm điều xấu. Luật pháp liên quan
  • Thích
Reactions: likehack
Comment
Web 100.
Bài này, là cái bài mình thấy khó hiểu nhất. Lần đầu tiên, mình thấy tất cả đề cho đều là thật, trừ cái flag troll.

Tóm tắt ngắn gọn: check robots.txt, thấy /.git/, dùng gitdumper lôi source về, vào trang admin.php, có flag.

screen-shot-2017-11-05-at-4-13-06-pm.png

Submit, fail -_- bị lừa.

Qua trang index.php:

screen-shot-2017-11-05-at-4-14-17-pm.png

Mình chỉ muốn nói, đôi khi chúng ta không tin vào những thứ mắt mình đang thấy, nhưng nó lại là sự thật.

Server tắt mất rồi, nên xem tạm log qua Burp nhé các bạn =))

screen-shot-2017-11-05-at-4-17-04-pm.png

screen-shot-2017-11-05-at-4-17-52-pm.png

Trích Blog Quân Đoàn UIT​
WEB 100 - MrĐoàn UIT-NoPwn
Thiết nghĩ người ra đề đầu tư khá kỹ về nội dung và mê kiếm hiệp cực kỳ :v. Cơ mà lại để misconfigured làm bài mất vui :3.

Nhìn vào một bài web thì việc đầu tiên là coi robots.txt :v

Mình thấy có một đường dẫn tới /.git/

Theo thói quen thì google tìm tool mà lấy hết source từ git về thôi.

https://github.com/kost/dvcs-ripper/blob/master/rip-git.pl

Sau khi lấy hết source, nhìn vào trang index.php:

web100-1.png

Chắc người ra đề sensor cái password lại rồi, hardly bruteforce thì ai dám dụng vào, nhìn ngay cái dưới thì phát hiện thêm một cách login là dùng cookie “auth” có dạng là một đoạn được mã hoá sao cho sau khi qua hàm fnDecrypt($auth, $SECRET_ENCRYPT); thì phải có dạng là: TieuPhong:blabla

Okay xem hàm fnDecrypt() trong secret.php

web100-2.png

Vậy là đoạn TieuPhong:blabla sẽ phải được mã hoá dạng

mcrypt_encrypt(MCrYpt_RIJNDAEL_256,$sSecretKey,”TieuPhong:blabla”,MCRYPT_MODE_ECB,iv)

Để ý kỹ thì iv được kèm vào đầu cái cookie “auth” của mình có độ dài 32bit.

Như vậy, iv do mình kiểm soát luôn, tuỳ ý chỉnh sửa mà server dựa đó mà decrypt.

Vậy mình viết hàm encrypt xong kèm iv tự mình chọn vào đầu cipher text rồi base64 lại là xong.

POC:
web100-3.png

Như mình đã nói đầu bài, do misconfigured nên có cách giải “bựa” hơn. Password để vào admin chính là nùi dấu *************** kia. Đâu phải hardly bruteforce đâu!
WEB 300 – SECOND ORDER SQLI - UIT.NoPwn
Thiệt ra muốn xiaolin xíu về bài này mà thôi sợ bị bóc phốt nên nói thẳng ra đây là một bài Recon chứ không hẳn là web :v. Tuy nhiên qua bài này mình học được một kỹ thuật rất hay và đòi hỏi sự nhạy bén cao (mình chưa đủ trình).

Nhìn thấy đường dẫn dạng:

Weburl/index.php?page=login mình nghĩ ngay đến LFI. Thử lấy source bằng php://filter thì có tất cả những gì mình muốn :v.

web4-1.png

Để ý thấy tất cả các param mà mình có thể input đều bị: mysqli_real_escape_string() khiến cho nó không thể SQLi trực tiếp được. Ban đầu mình nhìn thấy biến $details có vẻ không gì cản phá mình control và chèn câu query vào. Lập tức google cách control cái $_SERVER[‘REMOTE_ADDR’].

Điều bất ập đến cuộc đời khi mình tìm ra được challenge gốc của bài web 300 này.

Plaidctf quals 2014 web-300: Whatscat

Mừng quá :v cứ theo write up mà làm. Người ta chỉ tận tình cách set up PTR record và DNS reverse cho VPS. Từ đó control được đoạn dns_get_record(gethostbyaddr($_SERVER[‘REMOTE_ADDR’]) Rồi SQLi mà lấy dữ liệu ra thôi. Chi tiết cách làm.
Trích blog mrdoan1996​
 
Chỉnh sửa lần cuối:
Comment
Bài for100 năm nay ra đề chán,vứt cho một mớ hổ lốn xong cái file python thì lại quá ez =]]
Nói chung năm đầu tiên ra đề về for ko hay,mong các năm sau có thêm stegano,etc...
 
Mời các bạn tham gia Group WhiteHat để thảo luận và cập nhật tin tức an ninh mạng hàng ngày.
Lưu ý từ WhiteHat: Kiến thức an ninh mạng để phòng chống, không làm điều xấu. Luật pháp liên quan
  • Thích
Reactions: Sugi_b3o
Comment
Bài for100 năm nay ra đề chán,vứt cho một mớ hổ lốn xong cái file python thì lại quá ez =]]
Nói chung năm đầu tiên ra đề về for ko hay,mong các năm sau có thêm stegano,etc...
Theo mình thấy thì 3 năm trở lại đây thì 3 năm đều chỉ có 1 bài for :D
 
Mời các bạn tham gia Group WhiteHat để thảo luận và cập nhật tin tức an ninh mạng hàng ngày.
Lưu ý từ WhiteHat: Kiến thức an ninh mạng để phòng chống, không làm điều xấu. Luật pháp liên quan
Comment
server có mở lại để mình làm k ta !!! :p:p:p
 
Mời các bạn tham gia Group WhiteHat để thảo luận và cập nhật tin tức an ninh mạng hàng ngày.
Lưu ý từ WhiteHat: Kiến thức an ninh mạng để phòng chống, không làm điều xấu. Luật pháp liên quan
Comment
Bài for100 năm nay ra đề chán,vứt cho một mớ hổ lốn xong cái file python thì lại quá ez =]]
Nói chung năm đầu tiên ra đề về for ko hay,mong các năm sau có thêm stegano,etc...
Thành phần ra đề năm nay có thay đổi so với năm ngoái.
 
Mời các bạn tham gia Group WhiteHat để thảo luận và cập nhật tin tức an ninh mạng hàng ngày.
Lưu ý từ WhiteHat: Kiến thức an ninh mạng để phòng chống, không làm điều xấu. Luật pháp liên quan
Comment
Web 100.
Bài này, là cái bài mình thấy khó hiểu nhất. Lần đầu tiên, mình thấy tất cả đề cho đều là thật, trừ cái flag troll.

Tóm tắt ngắn gọn: check robots.txt, thấy /.git/, dùng gitdumper lôi source về, vào trang admin.php, có flag.

screen-shot-2017-11-05-at-4-13-06-pm.png

Submit, fail -_- bị lừa.

Qua trang index.php:

screen-shot-2017-11-05-at-4-14-17-pm.png

Mình chỉ muốn nói, đôi khi chúng ta không tin vào những thứ mắt mình đang thấy, nhưng nó lại là sự thật.

Server tắt mất rồi, nên xem tạm log qua Burp nhé các bạn =))

screen-shot-2017-11-05-at-4-17-04-pm.png

screen-shot-2017-11-05-at-4-17-52-pm.png

Trích Blog Quân Đoàn UIT​
WEB 100 - MrĐoàn UIT-NoPwn
Thiết nghĩ người ra đề đầu tư khá kỹ về nội dung và mê kiếm hiệp cực kỳ :v. Cơ mà lại để misconfigured làm bài mất vui :3.

Nhìn vào một bài web thì việc đầu tiên là coi robots.txt :v

Mình thấy có một đường dẫn tới /.git/

Theo thói quen thì google tìm tool mà lấy hết source từ git về thôi.

https://github.com/kost/dvcs-ripper/blob/master/rip-git.pl

Sau khi lấy hết source, nhìn vào trang index.php:

web100-1.png

Chắc người ra đề sensor cái password lại rồi, hardly bruteforce thì ai dám dụng vào, nhìn ngay cái dưới thì phát hiện thêm một cách login là dùng cookie “auth” có dạng là một đoạn được mã hoá sao cho sau khi qua hàm fnDecrypt($auth, $SECRET_ENCRYPT); thì phải có dạng là: TieuPhong:blabla

Okay xem hàm fnDecrypt() trong secret.php

web100-2.png

Vậy là đoạn TieuPhong:blabla sẽ phải được mã hoá dạng

mcrypt_encrypt(MCrYpt_RIJNDAEL_256,$sSecretKey,”TieuPhong:blabla”,MCRYPT_MODE_ECB,iv)

Để ý kỹ thì iv được kèm vào đầu cái cookie “auth” của mình có độ dài 32bit.

Như vậy, iv do mình kiểm soát luôn, tuỳ ý chỉnh sửa mà server dựa đó mà decrypt.

Vậy mình viết hàm encrypt xong kèm iv tự mình chọn vào đầu cipher text rồi base64 lại là xong.

POC:
web100-3.png

Như mình đã nói đầu bài, do misconfigured nên có cách giải “bựa” hơn. Password để vào admin chính là nùi dấu *************** kia. Đâu phải hardly bruteforce đâu!
WEB 300 – SECOND ORDER SQLI - UIT.NoPwn
Thiệt ra muốn xiaolin xíu về bài này mà thôi sợ bị bóc phốt nên nói thẳng ra đây là một bài Recon chứ không hẳn là web :v. Tuy nhiên qua bài này mình học được một kỹ thuật rất hay và đòi hỏi sự nhạy bén cao (mình chưa đủ trình).

Nhìn thấy đường dẫn dạng:

Weburl/index.php?page=login mình nghĩ ngay đến LFI. Thử lấy source bằng php://filter thì có tất cả những gì mình muốn :v.

web4-1.png

Để ý thấy tất cả các param mà mình có thể input đều bị: mysqli_real_escape_string() khiến cho nó không thể SQLi trực tiếp được. Ban đầu mình nhìn thấy biến $details có vẻ không gì cản phá mình control và chèn câu query vào. Lập tức google cách control cái $_SERVER[‘REMOTE_ADDR’].

Điều bất ập đến cuộc đời khi mình tìm ra được challenge gốc của bài web 300 này.

Plaidctf quals 2014 web-300: Whatscat

Mừng quá :v cứ theo write up mà làm. Người ta chỉ tận tình cách set up PTR record và DNS reverse cho VPS. Từ đó control được đoạn dns_get_record(gethostbyaddr($_SERVER[‘REMOTE_ADDR’]) Rồi SQLi mà lấy dữ liệu ra thôi. Chi tiết cách làm.
Trích blog mrdoan1996​
Bài web100 mình không ngờ tới cách đó luôn :'(
 
Mời các bạn tham gia Group WhiteHat để thảo luận và cập nhật tin tức an ninh mạng hàng ngày.
Lưu ý từ WhiteHat: Kiến thức an ninh mạng để phòng chống, không làm điều xấu. Luật pháp liên quan
  • Thích
Reactions: likehack
Comment
Sad Book - WEB - Blog l4w.io
Hôm nay dạo qua facebook thì thấy một challenge từ vòng loại SVATTT được đăng tải từ chính tác giả: yeuchimse

Tranh thủ thời gian rảnh rỗi lúc còn ở VN, thấy bài này cũng hay hay nên cũng muốn writeup một tí.

Khác với tất cả 5 năm trước đây, 3 năm là thí sinh, 2 năm là BTC… Năm nay tâm thế là một bên không liên quan bất kì hoạt động gì về SVATTT, cũng là một dịp được quan sát và refresh cuộc chơi.



Edit: Sau khi trao đổi với người ra đề thì có một cách dễ hơn để leak code là dùng bug Open-redirect, như thế ta sẽ không cần phải sử dụng RPO.

http://sadbook.ctf.yeuchimse.com/login.php?utm_client=zzz&return=/report.phpaaaa

Introduction
Cơ bản bài này có hai đường dẫn liên quan.

http://sadbook.ctf.yeuchimse.com/
Trang chính, show những câu nhật ký “tự kỷ” từ các user khác. Trang đăng nhập và một trang report lỗi. Với cách “bày trận” một thử thách như vậy thì người chơi có thể đoán ngay bài này thuộc thể loại Client-side attack, thường những bài như vậy, một là bạn truy xuất ra được document.cookie hoặc nội dung page nào đấy (trong đó có flag), 2 là chiếm được session của admin luôn. Lưu ý là bạn điền bất kì URL nào vào trang report, con bot của tác giả (bot ở đây giữ vai trò như một admin thật sự sẽ xem xét, và click vào đường link report của bạn) sẽ đi đến đấy, và bạn có thể thấy nó trên log server của mình. Vì vậy, nếu giả sử ta có thể đưa một link “nào đó” vào trang report, con bot chứa flag sẽ đi tới đó, và bằng cách nào đó, bạn phải lấy flag từ nó.

Screen-Shot-2017-11-16-at-02.25.47-1024x654.png

http://sadpen.ctf.yeuchimse.com/
Trang này cho phép bạn đăng ký tài khoản, ghi lại những câu nhật ký tình yêu … đồng thời thay đổi những thông tin cá nhân (về sau bạn sẽ hiểu tại sao tác giả cho thay đổi những thông tin này).
Sau khi bạn đăng ký và đăng nhập tài khoản của mình, kể từ lúc này bên trang sadbook , bạn có thể sử dụng chức năng “Đăng nhập qua Sad Pen“. Mà nó sử dụng OAuth . Hm… nôm na là sadpen sẽ trả về một authorization code, và gọi callback.php từ sadbook, nếu code là hợp lệ, bạn sẽ được xác định bởi danh tính đấy. Vậy rất có thể admin (người mà bạn đang muốn lấy flag) đã có tài khoản trên sadpen, và có thể cũng đang login rồi. Thế câu truyện ở đây nhiều khả năng sẽ là làm thế nào cướp được đoạn code chứng thực đó. Hình dưới là những thứ xảy ra khi bạn click vào “Đăng nhập qua Sad Pen“.





Bước 1:
Trình duyệt truy cập trang:

http://sadpen.ctf.yeuchimse.com/oauth.php?client_id=42&type=code&redirect_uri=http%3A%2F%2Fsadbook.ctf.yeuchimse.com%2Foauth%2Fcallback.php



– Nếu bạn đã đọc sơ qua OAuth, sẽ biết khi gọi Authorization Server, chúng ta phải định danh “redirect_uri“, để đảm bảo an toàn, redirect_uri phải hợp lệ và pass được whitelist check với origin đã được đăng ký, ở đây là http://sadbook.ctf.yeuchimse.com/oauth/callback.php . Vì vậy mọi URL bạn đưa vào đây đều được phải bắt đầu bởi chuỗi đấy.

Bước 2:
Về phía Authorization Server, nếu đã xác thực rằng tài khoản bên sadpen có thể dùng để auth với sadbook, sẽ gửi trả lại một Authorization Code là một chuỗi gì đấy, kèm với URL bạn chúng ta cung cấp từ trước, cho nên nó sẽ Location sang

http://sadbook.ctf.yeuchimse.com/oauth/callback.php?code={Authorization Code}

Code sẽ được check, nếu hợp lệ bạn sẽ được đăng nhập với danh tính tương ứng như bên sadpen.

Tips
Từ hai đường dẫn riêng biệt, sự xuất hiện của những thứ … không bình thường, kèm những chức năng cũng tương đối đặc biệt như vậy, trong một cuộc thi CTF thì chắc chắn lỗi và cách khai thác nằm trong sự liên kết của hai thứ này.

Thiệt ra cũng không hẵn là chỉ trong CTF, mà trong trường hợp thực tế, nếu những ứng dụng có những “tính năng” phức tạp, đi trái với thông thường, hoặc những trường hợp họ rất ít có cơ hội code tới thì khả năng có lỗi sẽ tăng lên cao rất nhiều đối với những tính năng thông thường. Giống như bạn chơi giỏi LOL, dù rằng hai game cách chơi tương đối giống nhau nhưng không có điều gì đảm bảo rằng tại lần đầu tiên bạn sẽ chơi giỏi DotA, và ngược lại.



The Vulnerabilities
1f41e.svg

Bug thứ nhất nằm ở phần đường dẫn “redirect_uri” trong khi đăng nhập bằng OAuth. Ta không thể sửa phần đầu vì đã được check rằng phải bắt đầu bởi http://sadbook.ctf.yeuchimse.com/oauth/callback.php, nhưng ta có thể tùy ý với phần đuôi của nó.

Vậy chuyện gì sẽ xảy ra nếu ta đăng nhập bằng URL

http://sadpen.ctf.yeuchimse.com/oau.../sadbook.ctf.yeuchimse.com/oauth/callback.php/../../../index.php

Hợp lệ và ta bị dẫn sang

http://sadbook.ctf.yeuchimse.com/in...0.ezrv2uDurqJJDpJtqlz3Yx73vz_pGyBLVC9Z1apy1XA

Với “../../../” ta có thể quay ngược lại thư mục đường dẫn trước và kết thúc tại index.php, vì vậy mà code đang được truyền vào params của file “index.php” .

Hm để đó… chúng ta vẫn còn thiếu một mắt xích, một mảnh ghép nào đó để hoàn thành.

Tiếp tục tìm kiếm, mình phát hiện thêm một lỗi, đó là RPO (Relative Path Overwrite), bạn có thể đọc chi tiết về phương thức tấn công này tại http://www.thespanner.co.uk/2014/03/21/rpo/

Ngoài ra vào cuộc thi SVATTT 2015, mình cũng đã một lần ra một đề bài liên quan trực tiếp đến phương thức này, bạn có thể đọc writeup của nó tại đây: https://tsublogs.wordpress.com/2015/11/08/svattt-2015-csecretboxes/

Mình nghĩ hai bài trên đã nói quá rõ ràng RPO là gì, mình sẽ không giải thích lại.





Với đường dẫn là http://sadbook.ctf.yeuchimse.com/index.php/ . Ta có thể thấy các file css đã bị relative path làm nó trỏ lại về file index.php… mà trong đấy chứa những câu nhật ký ướt át do chính những user post lên.

Vậy sẽ ra sao nếu nhờ RPO ta có thể leak, và “chôm” được đoạn code chứng thực của admin ?! Thông qua http referer, tới đây làm mình nhớ tới một bài blog nói về một chain, gồm những bug cực kì đơn giản và low risk, để có thể cướp hoàn toàn một session của user. Bạn có thể đọc tại đây: http://homakov.blogspot.com/2014/02/how-i-hacked-github-again.html (Đọc và hiểu cũng giúp ích cho đoạn bên dưới).

Tưởng tượng bạn truy cập vào “https://l4w.io/” , và trong website ấy có một link ảnh đi tới server của bạn, thì có phải mỗi lần có người truy cập vào blog mình, bạn sẽ cũng nhận một http request bên phía server bạn, và referer của nó là “https://l4w.io/” đúng không ?

The Chain
Ngẫm nghĩ về các bước, và mình đã hoàn thành một chain với các bước sau:

Tạo một user, cố gắng spam những câu nhật ký nhiều nhất, để tỉ lệ %, admin có thể “thấy” câu nhật ký của mình là cao nhất.

Sau đó sửa thông tin cá nhân lại thành payload RPO của mình, ở đây mình sử dụng câu như dưới. Vì nếu ta sử dụng

{}*{background: url(…)} thì Referer của nó sẽ là những file css chứ không phải URL “index.php/?code=…” như chúng ta muốn, vì vậy chúng ta phải sử dụng “import…”



Tiếp theo liên tục report trên trang sadbook bằng đường link

http://sadpen.ctf.yeuchimse.com/oau.../sadbook.ctf.yeuchimse.com/oauth/callback.php/../../index.php/

Nếu con bot thấy được nội dung của mình post lên, kèm theo RPO payload là địa chỉ URL homepage mà nó sẽ xuất hiện trên trang chủ index.php, con bot sẽ tiếp tục truy cập các file css, nhưng đã bị ta đè relative path => con bot load file index.php như là một file css => chạy câu “import …” đến URL là server của chúng ta, và HTTP Referer sẽ là “index.php/?code=….” kèm đoạn code chứng thực. Cùng với đoạn code này, ta có thể truy cập

http://sadbook.ctf.yeuchimse.com/oauth/callback.php?code={Authorization Code}

để đăng nhập vào session của admin. Sau khi có flag, bạn có thể ngay lập tức sửa lại URL homepage của mình (nơi chứa payload RPO) để xóa bỏ dấu vết, tránh làm cho các đội khác nhìn thấy,

Bingo!





Ướt át quá đọc mà mình nổi cả da gà.
 
Mời các bạn tham gia Group WhiteHat để thảo luận và cập nhật tin tức an ninh mạng hàng ngày.
Lưu ý từ WhiteHat: Kiến thức an ninh mạng để phòng chống, không làm điều xấu. Luật pháp liên quan
Comment
Thẻ
2017 sinh viên an toàn thông tin svattt svattt2017 vnisa
Bên trên