女子小学生バイナリアンのCTFにっき。

CTF diaries by an elementary schoolgirl who is addicted to binary analysis.

SECCON 2014 CTF オンライン予選 write-up

SECCON 2014 CTFのオンライン予選にとあるチームのバイナリ担当として参加してきました!

とりあえず、解いた問題のwrite-upを書こうかと思いますー。



・バイナリ100 x86アセンブラを読もう

タイトル通りで読むだけの問題でした。ざっと読んだら、適当にPythonのコードにして実行して、

はい、おしまい♪

#!/usr/bin/env python

#-*- coding:utf-8 -*-

def test01361000(arg1):
    ebp4 = 0 
    ebp8 = 1 

    while ebp8 <= arg1:
        ebp4 += ebp8
        ebp8 += 1

    return ebp4 - 2 

def main():
    arg1 = 255 
    ret = test01361000(arg1)
    print "FLAG{%d}" % ret 

main()
FLAG{32638}



・プログラミング100 重ねてみよう

gifファイルだったので、とりあえず画像に分解しようと思ってプレビュー.appで開いていたら、

チームの人が

http://gif-explode.com/

を使って分解してアップロードしてくれてました!

あとは重ねるスクリプトを書くだけ。

白黒画像なのでなにも考えずに既存のコマンドを使えて、簡単でした。

以下、適当スクリプトです。

#!/bin/sh

convert -average 1.png 2.png result.png
for i in `seq 3 49`
do
    convert -average $i.png result.png result.png
    convert result.png -threshold 10000 result.png
done

できた画像

f:id:harukakka_r9:20140722140934p:plain

QRコードリーダーで読み取って、終わりっ

ちょっと欠けてて読めない場合もあるって話を聞いたけど、どうなんだろ?

FLAG{Many dot makes a QR code}



・バイナリ300 ダンプを追え!

dump.binはdata、encrypt.nmはどうやらnmコマンドの実行結果を記録したものみたい。

dump.binをバイナリエディタで読んでみると、V850の文字列が。

検索すると、NECマイコンのようです。

とりあえずIDA Proでは開けなそうだった(←実はいけたらしいです...泣)ので、

binutilsNEC V850向けにコンパイル

# v850-nec-elf-objdump -D -b binary -mv850 dump.bin

とかやって、encrypt.nmを見ながら逆アセしたものを読んでいく。

命令セットリファレンスはこれ。 → http://www17.tok2.com/home/taro/U10243JJ7V0UM00.pdf

00001546 T _proc → FLAGをごにょごにょ
000015a0 T _main → メモリダンプをとってる

00001546 T _procのなかみを少し真面目に読んでいくと、

5692番地(dump上では0x23c)からの16バイトがFLAGをprocessしたものらしい。

XORなので、アルゴリズムを読んでPythonに直して実行すればOK。

以下、適当スクリプトです。

# r12レジスタの中身は追うのが面倒だったのでブルートフォースしました。

import sys

# key = '63 17 86 d8 34 f9 06 8c 9b 80 9d 96 d7 da df 92'.split()
key = '99 23 134 216 52 249 6 140 155 128 157 150 215 218 223 146'.split()

r14 = 16
for r12 in range(255):
    print str(r12) + ':'
    r13 = 0
    while r13 < r14:
        try:
            ret = int(key[r13]) ^ r12
        except:
            continue
        r13 += 1
        r12 += r12
        r12 += 17
        sys.stdout.write(chr(ret))
        r12 &= 255
    print ''
FLAG{Victory850}
(r12=37のとき表示)

#でコメントアウトした部分が競技中のミス。

16進数値をそのまま10進数値みたいに書いちゃった...。

スクリプトを書き上げた時点で終了10分前。

時間ギリギリだったのでミスに気付けずに、FLAGは取れず。

終わってすぐ気付いたときの悔しさといったら...!

ブルートフォースのためにひどい例外処理をしたのも一因なので、

やっぱりめんどうくさがらずにちゃんと読めばよかったですねー。

あんまりにもあんまりなミスなので、次は絶対に繰り返しません!

* *


全体を通して、とても楽しめたと思います。

個人的には、前半バイナリ問題がない時間が長かったので、

バイナリ問題がもうちょっと早い段階から出ていて、もう一問くらいあると嬉しかったですねー。


チームの順位は惜しくも全国出場を逃した感じだったので、

英語のオンライン予選と地方大会で楽しもうと思います!



それでは、また〜。