世界を動かす技術を、日本語で。

Chromeの隠れたX-Browser-Validationヘッダーのリバースエンジニアリング

概要

Google Chromeが新たに導入した X-Browser-Validationヘッダー の仕組みを解説。 このヘッダーは APIキーとUser-Agent を結合し、SHA-1でハッシュ化後、Base64エンコードして生成。 主な目的は クライアントの整合性検証 やUser-Agentの偽装検出。 Chromeバイナリのリバースエンジニアリングで 実装手順 が明らかに。 プラットフォームごとに 異なるAPIキー が利用されている点も特徴。

Chrome X-Browser-Validationヘッダーのリバースエンジニアリングと生成手順

  • Chromeが追加した 新規ヘッダー:

    • x-browser-channel: ブラウザのリリースチャンネル情報
    • x-browser-copyright: 著作権表示
    • x-browser-validation: ハッシュ値(主題)
    • x-browser-year: 年度情報
  • x-browser-validation の特徴:

    • Base64デコードすると SHA-1ハッシュ のような値
    • 目的は User-Agentとプラットフォームの整合性検証
    • User-Agent偽装の検出や信号として活用
  • 生成手順:

    • APIキー (OSごとに異なる)を取得
    • User-Agent文字列 を用意
    • 2つを 連結 してバッファを作成
    • そのバッファを SHA-1でハッシュ化
    • Base64エンコード してヘッダー値とする
  • プラットフォーム別APIキー:

    • Windows: AIzaSyA2KlwBX3mkFo30om9LUFYQhpqLoa_BNhE
    • Linux: AIzaSyBqJZh-7pA44blAaAkH6490hUFOwX0KCYM
    • macOS: AIzaSyDr2UxVnv_U85AbhhY8XSHSIavUW0DC-sY
  • Pythonによる生成例:

    • header_value = generate_validation_header(ua)
    • 必要に応じてapi_keyを明示指定
  • リバースエンジニアリングによる実装確認:

    • Chromeバイナリ(chrome.dll)をIDAで解析
    • APIキーとUser-Agentを バッファに連結
    • SHA-1ハッシュ関数に渡す(典型的な初期値からSHA-1と判明)
    • 20バイトのダイジェストを Base64エンコード
    • 最終的に X-Browser-Validationヘッダー としてリクエストに追加
  • 動的デバッグでの検証:

    • ハッシュ直前でバッファ内容をダンプ
    • 実際に APIキー+User-Agent のみで構成されていることを確認
  • まとめ:

    • Base64(SHA-1(API_KEY+User-Agent)) がX-Browser-Validationの正体
    • Chrome独自の クライアント検証メカニズム
    • 解析・再現が容易なため、 自作生成器の開発も可能

X-Browser-Validationヘッダーの用途と今後の動向

  • 主な用途:

    • User-Agent偽装や不正クライアントの検出
    • Webサービス側での Chrome正規性判定
    • セキュリティやトラフィック分析での活用
  • 今後の展望:

    • Chrome以外のブラウザでも類似メカニズム導入の可能性
    • サーバー側での 利用拡大 や検証強化
    • APIキーの 定期的な更新 や仕組みの複雑化も予想
  • 注意点:

    • APIキーは Chromeバイナリにハードコード されているため、簡単に抽出可能
    • セキュリティ上の 過信は禁物
    • 仕様変更や追加対策に備えた 継続的なリサーチ が必要

Hackerたちの意見

chrome.dllを掘り下げて、x-browser-validationヘッダーがどう生成されるかを理解したよ。詳しい内容とPoCコードはここにあるよ: https://github.com/dsekz/chrome-x-browser-validation-header なんでChromeがこんな余計なヘッダーを追加してると思う?アンチスプーフィング、ボット検出、整合性のため、それとも他に理由があるのかな?

これらのヘッダーは、google.comへのリクエストにだけ使われてるみたいだね。

「未承認」や「サポートされていない」ブラウザを拒否しやすくして、ユーザーの自由を奪おうとしてるね。他のブラウザが競争するのを難しくしようとしてる。

2つ質問があるんだけど、1つ目は、これを正しく理解してるかで、検証ヘッダーは各インストールごとに個別なの?2つ目は、このヘッダーはGoogle Chromeだけにあるの?それともChromiumにもあるの?

AIボットのLlamaに対して守ってくれる可能性は低いのかな?

Googleは、エージェントリクエストと人間のリクエストを識別しやすくするために、これらのヘッダーを追加したんじゃないかな。腹立つのは、これがユーザーをユニークにフィンガープリンティングするためのまた別の信号になるってことだよ。

実際にはフィンガープリンティングの面積を意味のある形で増やしてるわけじゃないよ。OPが言ったように、ハッシュはすべてのChromeビルドで同じ定数から生成されるからね。実際にやってるのは、Chromeを他のChromiumフォーク(例えばEdgeやBrave)と区別するのを助けることだけだけど、Chromeの中にはすでに十分なプロプライエタリな部分があって、簡単に見分けられるよ。

意図的かどうかは別として、これが非Chromeブラウザを使ってるユーザーに問題を引き起こす可能性があるのが心配だね。例えば、このヘッダーがないリクエストを遅くしたり、異なるコンテンツで応答したりするかもしれないし。

WEIについて知っている人には、これはちょっと警戒すべきことだと思う。「x-browser-copyright」は、競争を抑え込んで独占を進めるために法制度を利用しようとしてるのかな?もしそうなら、セガ対アコレードのことを知らないのかな?SHA-1を使ってるのがちょっと面白いね。MD5やCRC32、あるいは(バカなセキュリティスキャナーが勧めるように)SHA256にすればいいのに。

SHA-1は確かに謎だね。「合理的に安全だけど、SHA-256より短い」っていう論理が欠陥だと思う。SHA-1は壊れてるし、SHA-256はほとんどのハードウェアで速いから、短くしたいならSHA-256の出力を切り詰めればいいだけなのに。

私も心配してる。グーグルは今、クロームとアンドロイドの開発を分けるべきだよ。このクレイジーな垂直統合は、民間企業が道路と車の両方を作って所有するようなもの。もちろん、他の車を作ることはできるけど、私たちの道路を走る前にタイヤが安全かどうかを確認しなきゃいけない。私たちのフレームの上で車を作る限り、好きな色を選んでも大丈夫!でも、その車には広告がついてるよ。

セガ対アッコレードのことを聞いたことがないの?私もすぐにここに思い至ったけど、いくつかの詳細が微妙に違うんだよね。例えば、ローカルで実行されるソフトウェアのコピーではなくリモートサービスであることから、グーグルはその表現に依存してサービスを提供していると主張できるかもしれない。サービスのコードにアクセスできないと、この文字列が相互運用に必要だと証明できないとも言えるし。今の最高裁が微妙に異なる詳細を利用して、長年の前例を無視してファシズムを支持するのは初めてじゃないだろう。

WEI?Windowsエクスペリエンスインデックスのこと?もうちょっと詳しく教えて!

正気の人なら(グーグラー以外)、こんなバリデーションのクソみたいなものが存在するのを許す理由があるの?

クロームの独占禁止訴訟で負けた後に、どうしてこれが良いアイデアだと思ったんだろう?目的はよくわからないけど、競争を妨げる方法がいくつか見える。今はリバースエンジニアリングされてるから、拡張機能で偽装できるかもしれない。でも、ヘッダーがDRMの一種だと主張するつもりなのかな?そうなると、偽装はDMCA違反になるかも…。

拡張機能で偽装できるかもしれないけど、もし動的にする仕組みを作ったら無理だよね(例えば、ハッシュに現在の日付を含めるとか)。MV3の変更で動的なヘッダー操作ができなくなるから、拡張機能で偽装する方法はなくなる。

x-browser-copyrightは、ゲームボーイの任天堂ロゴDRMに似た試みのように見えるね(カートリッジが起動する前に任天堂のロゴビットマップを持っている必要があるから、無許可のカートリッジは商標侵害になる)。

ユーザーエージェントを偽装する拡張機能を使ってたら、これを使って「本当の」UAを推測されちゃうんじゃない?

つまり、これは隠れたクライアントの証明ってこと?