ureshino blog

セキュリティ初心者です。 TwitterID: @enzerus

seccon 2015 online writeup 2問 (´・ω・`

一応解いた問題について。


Connect the server

問題:
login.pwn.seccon.jp:10000

↑のアドレスにブラウザでアクセスすると普通にflagを含む情報がダウンロードできます。

↓がその情報


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 } 
login: 

Login timer timed out.
Thank you for your cooperation.

HINT: It is already in your hands.

Good bye.
flag: SECCON{Sometimes_what_you_see_is_NOT_what_you_get}

もうひとつあまりに重かった時にflag取っておいて完全に送るのを忘れていたやつがあったのでそいつも入れておきます。



問題: じゃんけんに1000回連続で勝ち続けよ

apkファイルが渡される。

まずapkはzipなので、適当に書庫で開いて、

中からclasses.dexを取り出し、それを dex2jar-2.0でjarに変換させる

変換が終わったらjd-guiとかに投げて中身を見る

難読化されていないのですっきりと見ることができる

↓にその時のコードの主要部分を抜粋


        if (1000 == MainActivity.this.cnt) {
          localTextView.setText("SECCON{" + String.valueOf((MainActivity.this.cnt + MainActivity.this.calc()) * 107) + "}");
        }
  static
  {
    System.loadLibrary("calc");
  }
  
  public native int calc();

コード見る限り、

cntが1000回になったら、flagを出すようになっている。

今回少し厄介なのが、その (cnt+calc())ををしているので、

System.loadLibrary('calc')の部分を少し見ないとわからない。

そのため、apk(zip)の中に libフォルダがあると思うのでこの中にcpu?ごとに読みだすsoが入っているのでその中身を確認する。

中身の確認方法は、自分の場合

$objdump -d libcalc.so

実行すると、色々省略して↓のような処理が書かれている。

f:id:enzerus:20151206182320j:plain

eaxに 0x7を代入しているので、単純に 7 を返しているだけだと思った

なので、(1000+7)* 107 = 107749

flag: SECCON{107749}

今回はスケジュールミスってほとんど参加できなかったので、

また次頑張りたいと思う。

来年そんな暇があるかわかりませんが・・・(社畜真っ最中だと思う)

お疲れ様でした。

seccon CTF 2015 九州大会 A&Dに参加してきました。writeup

チーム名:Atelier というチームで行きました。

今回のチームはメンバーをまるごと入れ替えて新チームで、

CTFはほぼ未経験のチームだったので、雰囲気だけでも今後のために味わってもらいたいと思い参加しました。

そんなこんなで、結果は5位でした。

Defense Scoreではなんとか一位でした。(サービスを起動させて立ててだけ)

やばいと思ってもサービスだけは立て続けておきました(笑)

f:id:enzerus:20151129021619j:plain

 

運営からは攻撃もして、防御して、攻撃されてのバランスがいいチームだと評価頂きました(笑)

今回私が見つけた脆弱性は2箇所でそれでなんとかポイントを1万点分ぐらい取りました。

 

見つけた脆弱性の詳細は、

とあるwebシステムで、ログインすると↓のようなアクセスのログがテーブルにinsertされるようになっていて

それを個人でログインしたページから見ることできるような仕組みになっていました。

gist09b080461276086e866d

 User情報が格納されているテーブル一定時間ごと?に運営側からフラグとなる個人情報がinsertされてくるっぽい

gistd05fd4bdfd865989ae11

そこでChromeのUserAgentを書き換えるプラグインを入れていつも使用していたので、

それで変えてログインしてみたところ

自分が任意に入力したUserAgentがそのまま使われているということがわかったので

じゃあUserAgentにシングルクォート入れてみようと思って 「 ’」を素直に入れたら

sqlのエラー文が出てきました。ちなみに今回は、LaravelというPHPフレームワークで作成されており、

そのdebugモード?によりエラーがほとんど表示されてくれるありがたい仕様でした。

そのエラーの時に出てきたSQLが本来は↓のように書かれているようでした。

gista0d8a4000c4b2bc3a0fe

ここに ua のカラムの部分に無駄なシングルクォートが入ってくるのでそこでエラーを吐いている状態でした。

ここでどうしようか迷った結果

二行同時にinsertしてやろうということでした。

一行目は任意に指定したinsert
二行目はそのまま

そしてその一行目にadminの情報をテーブルから指定してやり、自分のユーザーのログイン履歴に持ってくるようにしようと考えました。

そこでまず自分のuseridを特定するため新しくアカウントをターゲットのwebシステム上で作成し、UserAgentに細工をして

自分のUserIDをテーブルで一番最後に入ったIDを取ってくるようにSQLを書きました。

そしてUserAgentの部分に(ブラウザなどのクライアント側)

gist83f36530a34b048d389d

これで最後に登録したユーザーIDのログイン履歴のIPに'10.0.0.ユーザーID'が入ってきます。

なぜconcatしてるのかというとなんとかバレないようにするためにこうしました。バレて一瞬で修正された泣けますし・・

これで自分のユーザーIDが判明したので、あとはこのSQLを変えていくだけです。

まず実行したのは、

gist2f87ef8b4a63ec5b6889

これで私が作成したログイン履歴のIPアドレスのところに、adminのメールアドレスとログインパスワードが入ってきます。

そしてあとは http://10.0.x.1/admin/ というところに管理者用のログイン画面があったので、

特定したメールアドレスとログインパスワードを入れて

ユーザー情報が取得できるので、このIDとパスをチームメンバーに渡してフラグ形式に戻してもらって手作業で得点を手に入れてもらう作業をしてもらいました。

しかしadminのページがやばいとわかって段々対策してきたチームが増えたため、

この作業ができなくなりました。

ですので、

もう時間も少なかったので直にぶっ込むことにしました。

同様の手口でusersの行数も割り出せるので、その分を↓のSQL文を1からその数まで作って

UserAgentに入れてログインして履歴からフラグ形式でゲットしてコピペするという形にしました。

(すげえ地味な作業でした。)

ほんとconcat最高です。

gistfdec81cfd6b055252358

 中野 怜奈,なかの れいな,nakano_reina@example.com,146-3457-9327,098-2546,東京都国分寺市日吉町2-5-3,2548 

↑みたいなものがログイン履歴に出ます

これでadminページがなくてもログイン履歴さえあれば、できたのでadminページだけ消して、

ログイン履歴に対策を取っていないのそのままのチームの場合は

これでポイントが取れました。

中には、お客様(運営)の大事なユーザー情報を抹消させていたり、

パスワードが全て同じなっているデータがありそこがflagが取れなかったので

ポイントが残念ながら伸びませんでした・・・。

そして競技終了後に気づいたのが、

Insertする行数を増やせばログイン一回で終わっていたということに・・(完全に冷静じゃなかったです・・)

とりあえず今回は攻撃も成功することができて、楽しめました。

上位3位の壁は厚かった