Upgrade to PRO for Only $50/Year—Limited-Time Offer! 🔥

Japan VCC 2025 問題解説

Avatar for smz smz
October 24, 2025
150

Japan VCC 2025 問題解説

Avatar for smz

smz

October 24, 2025
Tweet

Transcript

  1. パスワード検証のロジック 16 • ⽂字数をカウントし、11⽂字か検証 • ⼀⽂字ずつforループで検証 ◦ 検証する⽂字位置(pos)を配列から取得 • 戻り値ok_flagは11回(⽂字)のループ全てで

    条件式を満たすと1になる ◦ ok_flag = ok_flag & 条件式 • 条件式 ◦ (複雑な演算) == entered_password[pos] ◦ (複雑な演算)結果が正しいパスワードのpos ⽂字⽬
  2. 固定整数除算の最適化 17 • (複雑な演算)=((PTR_DAT_08001b20[idx + (uint)((ulonglong)0x4EC4EC4F * (ulonglong)idx >>0x22) *

    -0xd] ^ PTR_DAT_08001b24[pos]) - (pos * pos + 3 & 7)) ◦ 配列のインデックスをマジックナンバー0x4EC4EC4Fを使って計算している ◦ これは idx mod 13 = idx + idx / 0xd * -0xdをコンパイラが最適化したもの • ⼀般に除算命令は遅いため、32bit整数の除算 x / dは x * magic >> ( 32 + post_shift )のように乗算と右シフトで最適化される ◦ magicとpost_shiftはすべてのxで誤差が⽣じないように計算される ◦ gccでの実装はgcc/expmed.cのchoose_multiplier() ◦ 理論的基盤はGranlund-Montgomery, Division by Invariant Integers using Multiplication(1994)による
  3. Solverを書いて解く 18 def solve_password(): password = ['?'] * 11 #

    11文字のパスワード for i in range(11): pos = PTR_DAT_08001b18[i] # この反復でチェックする位置 # インデックス計算 idx = pos * 7 + 3 # 期待される文字を計算。idx % 13は固定整数除算最適化の結果に対応 expected = (PTR_DAT_08001b20[idx % 13] ^ PTR_DAT_08001b24[pos]) - ((pos * pos + 3) & 7) password[pos] = chr(expected) return ''.join(password) # ”ELITEHAXXOR”が返る >flag ELITEHAXXOR flag{medi3val_scr3w}