ksnctf 27 Lives out
exeファイルをダウンロードして実行するとライフゲームが開始されます。区画を種と見立ててその絶滅や誕生をシミュレーションしてくれるみたいです。
説明文にある「Can you switch all the lights off? 」とはこの赤い場所をすべて消してみろということでしょう。
<Write up>
リバースエンジニアリングの問題だろうと思ってIDAを開きましたが64bitには対応していないらしく怒られてしまいました。
64bitを読み込んでくれるデバッガを急遽ダウンロード。
エントリーポイントからトレースしていくとブロックの描画処理と思われる場所が出てきます。
1つ目のブレークポイントからjl命令(赤矢印のところ)まででブロック1つが描画され、それがループ構造になっています。
見た感じRectangle(3つめのブレークポイント)で位置を決めてシステムコールにより
ブロックを描画しているみたいです。
ならSelectObject(2つめのブレークポイント)でブロックの色を赤(生存)か白(死滅)かに決めていると思ったのですが中を見てもよくわかりませんでした。
そこでブレークポイント1-2の間の処理に注目しました。
cmovne rdx, r14は 「ZF = 0 のときにrdxにr14を転送する」というものです。
cmovneの直後にRIPを置いて検証します。
するとrdxにr14が正常に転送されたときは赤いブロックが、またそうでないとき(こちらの環境ではedx=4E011A09のとき)は白いブロックが描画されることが分かりました。
ここではすべて白いブロックにしたいので
「cmovne rdx,r14」を「mov edx, 4E011A09」に書き換えます。(nopでもうまくいきました)
真っ白になりました。
このままでは描画処理が終わらないので必要に応じてジャンプ命令をnopに変えてループ処理をつぶしていきます。
「TextoutW」まで来ると、左上にflagが出てきます。