HOTP カウンタ検証ツール|RFC 4226 の窓ずれ ±N をブラウザで検証
Base32 共有秘密とカウンタ値から HMAC-SHA-1 ベースの HOTP コードを算出し、受け取ったコードがカウンタ ±N の窓内で一致するかを表で確認できるカウンタ型 OTP 検証ツール。サーバを立てずに、手元の入力だけで RFC 4226 の挙動を再現する。
💡 このツールについて
HOTP (RFC 4226) は、時刻ではなく「カウンタ」を動かす要素にした使い捨てパスワードの方式。Yubico の OATH-HOTP スロットのようなハードウェアトークンや、SMS を補う認証コードで使われる。時計合わせが要らないため、時刻同期が不安定な環境やオフライン端末に向く。
カウンタ型 OTP で必ず付きまとうのが「同期ずれ」の問題。トークン側のカウンタはボタンを押すたびに進むが、サーバ側のカウンタは認証が成功したときだけ進む。ユーザがトークンを空打ちすると両者がずれ、コードが通らなくなる。RFC 4226 はこれを「先読み窓 (look-ahead window)」で吸収する。サーバが現在のカウンタから先の値まで計算して照合し、一致した値+1 まで自分のカウンタを進める運用だ。
このツールは、その窓内の全コードを一覧表で同時に開示する。現在カウンタの行を強調し、受け取ったコードと一致した行を別色で示すので、「どの offset まで許容すべきか」というサーバ側のポリシー検討や、トークンのデバッグを、サーバを起動せずに手元で試せる。時刻ベースの TOTP とは別物なので、TOTP 用ツールとは使い分ける。
🧐 よくある質問
HOTP と TOTP の違いは? 動かす要素が違う。HOTP はカウンタ (イベント)、TOTP は時刻。HOTP のコードは使うまで有効なまま残り、TOTP は 30〜60 秒で自動失効する。本ツールは HOTP 専用。
共有秘密はどの形式で入れる?
RFC 4648 の Base32 (A-Z と 2-7)。空白とハイフンは無視され、末尾の = パディングは任意。Base32 として不正な文字が混ざるとエラー表示になる。
検証窓 ±N は何を表す? 現在カウンタから前後 N 個ぶんのコードを照合する範囲。N を大きくすると同期ずれに強くなる反面、総当たり耐性は下がる。RFC §7.4 は既に通ったカウンタ以下を受理しないことを推奨している。
桁数は何を選べばいい? 出力 OTP の長さ。Google Authenticator は 6 桁、Yubico のトークンは 8 桁が多い。トークンの仕様に合わせる。
計算はどこで行われる? すべてブラウザ内の Web Crypto API で完結し、入力した共有秘密はサーバに送信されない。
📚 HOTP のトランケーションの豆知識
HOTP の核心は「動的トランケーション」にある。HMAC-SHA-1 の 20 バイト出力の最後の 4 ビットを offset として読み、そこから 4 バイトを切り出し、最上位ビットを 0 にマスクして 31 ビットの整数を作る。最上位ビットを落とすのは、符号付き整数として解釈される実装差を避けるためだ。最後にその整数を 10 の桁数乗で割った余りを取る。RFC 4226 付録 D には秘密 12345678901234567890 でカウンタ 0 のとき 755224、カウンタ 1 のとき 287082 というテストベクタが載っており、実装の正しさを 1 件ずつ照合できる。HOTP がこの固定手順で定義されているからこそ、トークンとサーバが別ベンダでも同じコードを再現でき、後発の TOTP も同じトランケーションを土台にしている。