よーでんのブログ

One for All,All for わんわんお!

#ISCCTF2020 作問しました(1問だけ)

crackjwt

f:id:y0d3n:20201024222052g:plain
welcome.gif

かわいい(かわいい)

ということで、crackjwtというweb問を作りました。
writeupはこちら

折角なので裏話的な何かをします。

もともと

入門者向けということで、もともとはjwtのalgをnoneにするアレにするつもりでした。

しかしどうしても自然に脆弱性を作りこむことができず、奮闘していた時にnginxのalias traversalを知り、面白そうだったので採用しました。
(少しニッチ過ぎたかもしれません...)

非想定解

問題のレビューで、flag.phpの署名エラー時の処理が修正されました。

if (isset($flg) || hash('sha256', base64_decode($parted[0]) . base64_decode($parted[1]) . $secret) != base64_decode($signature)) {
+            die('<script>alert("Invalid token!!");document.location="/"</script>');
-            echo('<script>alert("Invalid token!!");document.location="/"</script>');
}

これ、echoだと以下に続くphpも実行されてしまいます。

なので署名が間違っていてもisAdminが1になっていたらflagが見えてしまう状態でした。
(burpで画面遷移を止める、jsを無効化する等すると見れる状態だった)

レビューで気付いてくれたので感謝です。

意識したポイント

以下3つ、意識していた点です。

スコープ

自分が入門者向け問題でとても大事な要素だと考えてるのが、スコープの広さです。

「どこを攻撃すればいいのかわからない」
といった理由でチャレンジを諦めてしまうことが無いようにスコープをだいぶ狭くしました。

更に問題名も単純にcrackjwtとし、「やるべきこと」をできるだけ自明にしました。

配布ファイル

ファイルはもともと、シークレットな情報を抜いて全ファイルを圧縮して配布する予定でした。
しかし、スコープの広さと同じ理由でdefault.confの1ファイルのみにしました。

「わざわざこのファイルを配布したってことは・・・」という思考からalias traversalに辿り着いた方もいると思います。(いて欲しい)

そして、「default.confだとnginxの設定ファイルってわからない人いそう」ということでnginx.confという名前で配布しました。
配布したのはnginx.conf、しかしgithubでのファイル名がdefault.confになっているのはこのような理由です。

ひよこ

f:id:y0d3n:20201024222113g:plain
nyoronyoro

flag.phpnyoronyoro.gifはできるだけ煽ってる風なgifを探してきました。
イライラしてくれてたらうれしいです。

ひよこかわいいですよね!!!

最後に

f:id:y0d3n:20201026193323g:plain
congrats

phpもnginxもdockerも「少し触ったことがある」程度でまともに使うのは初めてだったので良い刺激でした。

解いてくれた方、チャレンジしてくれた方、ありがとうございました!