「URL 的開頭明明是真網域,點進去卻被轉到完全不同的站點」——這就是開放重新導向。下面講解其原理和可靠的防禦方法(不會寫攻擊步驟)。
為什麼危險
危險的本質在於「對網域的信任被濫用」這一點。
| 被濫用的方式 | 會發生什麼 |
|---|---|
| phishing 的跳板 | 連結開頭是真網域→使用者和過濾器都信任→被誘導到假站點 |
| 認證流程被劫持 | 竄改 OAuth 等的重新導向目標,盯上 token/code 的傳遞 |
| 放大其他漏洞 | 與 SSRF 或 XSS 組合,擴大危害 |
為什麼會成立(原理)
在「登入後回到原來的頁面」之類的功能裡,如果原樣信任並轉發返回位址 URL,就會發生。使用者看到的 URL 的「開頭」是真網域,所以很難一直懷疑到最後,這正是麻煩之處。
防禦:不接收外部 URL
跳轉目標只允許相對路徑(最重要)
返回位址只接受 /dashboard 這樣的相對路徑,拒絕完整 URL(以 http://、// 開頭的)。不給使用者留下任何能指定跳轉目標網域的餘地。
對照允許清單校驗
如果需要動態的跳轉目標,就只對已知跳轉目標的固定集合(對應表)放行。不符合就回到預設頁面。
不要依賴字串判斷
//evil、反斜線、@、多重編碼等繞過手法很多。改變接收方式的設計(相對路徑+允許清單)比一條條往過濾器裡追加規則更可靠。
實在要跳到外部就明確告知
如果跳到外部是規格需要,就插入一個確認頁面,向使用者顯示「即將跳轉到外部站點」。不要悄無聲息地跳走。
本站的視角:單獨看是「低」,但和 phishing 組合就很有殺傷力
開放重新導向單獨看時往往被認為嚴重度低,但因為它會把真網域的信任借出去,所以一旦和 phishing 或認證劫持組合起來,就會一下子變得很有殺傷力。正因如此,用「相對路徑+允許清單」這種設計層面的一招從根上斬斷才高效。它和 SSRF(讓伺服器去存取任意目標)的思路相似,二者共同的防禦原則都是「不讓使用者來決定跳轉目標・連線目標」。
接下來讀
FAQ
Q開放重新導向到底有什麼問題?
因為 URL 的「最前面的網域」是可信的真站點(例如登入頁),所以使用者和郵件過濾器都會放心地點擊。可是網站會把使用者轉發到任意外部站點,於是它會被濫用:把真網域當成「跳板」來做 phishing,或作為認證流程中竊取 token 的起點。
Q最有效的防禦是什麼?
就是「跳轉目標不接收外部 URL」。登入後的返回位址等,不要用完整 URL,只允許相對路徑(如 /dashboard),並對照允許清單(已知跳轉目標的固定集合)進行校驗。如果實在要跳到外部,就插入一個確認頁面明確告知使用者。
Q只檢查是不是 http 就夠了嗎?
不夠。還有許多繞過手法,比如以 // 開頭的省略形式(//evil.example)、反斜線、編碼、用 @ 構造的迷惑性 URL 等。與其判斷字串,不如從設計上根本就不接收外部 URL(相對路徑+允許清單)來得可靠。