[ 筆記 ] 資訊安全 - CSRF


Posted by krebikshaw on 2020-08-13

CSRF 原理 ( Cross Site Request Forgery )

其實跟 XSS 有點像,CSRF 的原理是,駭客在其他網頁塞入一個「 目標 domain 」 的連結,偷偷發 request( 利用隱藏圖片或隱藏表單 )。

所以假設你點入駭客提供的 A 網站,其實背後已經發了個 B 網站的 request 而渾然不知。

而這漏洞最可怕的是,如果你曾造訪過 B 網站,且 B 網站的 session 週期還沒過期(換言之,還在登入狀態),同時 B 網站的 Server 驗證機制不夠全面,B 網站很可能就會認為此 request 是來自本人造訪 B網站 。

結論:如果你在某網站是保持登入狀態,就存在 CSRF 的風險,其手法是欺騙瀏覽器、讓網站以為是使用者本人的操作。

聽起來還是不知道可怕在哪,只要試想把 B 網站換成「 我們常用的網路銀行 」,有可能你默默就把錢轉出去也沒發現,就知道 CSRF 是很危險的。

防範方法

參考:讓我們來談談 CSRF

不推薦做法

☞ 比對 request 參數 & session_id (不安全)

  • 漏洞:典型的 CSRF 漏洞,有可能從別的 domain 發出惡意 request,如果我是登入狀態,一樣會被攻擊

☞ 傳送方式從 GET 改為 POST(不安全)

  • 漏洞: 開一個隱藏 iframe,把 form 藏在裡面,一載入自動 submit

☞ 把 API 改成只接收 JSON(不安全)

  • 漏洞: 把 content type 改成 text/plain,一樣可以用 form 傳送 JSON
    雖然 Server 可以擋 text/plain,但如果 Server 的 Access-Control-Allow-Origin: *,代表別的 domain 的 request 都可以發過來

☞ 檢查 request 的 header Referer,擋掉不合法 domain(不安全)

  • 漏洞:url 變形方法很多,且 user 有可能不會帶上 Referer,不是很保險

推薦做法

☞ 加上圖形驗證碼、簡訊驗證碼

  • 安全但麻煩,通常有金流操作的網站才會用

☞ 加上 CSRF token

  • 產生: Server
  • 儲存: Server
  • 在 form 裡新增一個 name='csrftoken' value='<亂碼>',比對 Server 端的 session
  • 漏洞:攻擊者可以先發一個 request 取得 csrftoken

☞ Double Submit Cookie

  • 產生: Server
  • 儲存: Client
  • 一樣在表單放 CSRF token,但這次參照值不是存在 Server 裡,而是存在 cookie 裡這方法利用的是 cookie 只會從相同 domain 帶上來,攻擊者無法從不同 domain 帶上此 cookie
  • 漏洞: 攻擊者如果掌握了你底下任何一個 subdomain,就可以幫你來寫 cookie

☞ Client 端生成的 Double Submit Cookie

  • 產生: Client
  • 儲存: Client
  • 之前提的 Double Submit Cookie,是由 Server 產生、存在 Client 的 Cookie但由於 SPA 在拿取 CSRF token 會有困難,所以可以改成 Client 端生成,此 cookie 只是要確保攻擊者無法取得、沒有包含任何敏感資訊,所以不避擔心安全性考量
  • 某些 library(如:axios),只要設定好 cookie 的值,會幫你自動在 request 的 header 填上 cookie 值,就不用每個表單都要手動加。

最佳作法

☞ 瀏覽器端的防禦:SameSite cookie ( 最推薦 )
其原理就是幫 Cookie 再加上一層驗證,不允許跨站請求。

意思是除了在 B 網站這個 domain 發出的請求,其他 domain(如 A 網站)的發出的 request 都不會帶上此 Cookie,等於是張更安全的通行證。

只要在設置 Cookie 加上:

Set-Cookie: key=value; path=/; domain=example.org; HttpOnly; SameSite=Lax

SameSite 有兩種模式:Strict 、Lax

  • strict 嚴格
    • <a href="">, <form>, new XMLHttpRequest… 等標籤,只要不同 domain 都不會帶上此 Cookie
  • Lax 寬鬆
    • 上述標籤可以帶上 cookie 除了 Get 方法,其他的 POST、DELETE、PUT… 都不會帶上 Cookie,意思是 Lax 模式之下就沒辦法擋掉 GET 形式的 CSRF

所以某些網站會準備兩種 cookie,一般瀏覽網頁時、帶上沒有 samesite 的 Cookie。

當使用者有敏感操作(如:購買、帳戶…等),會帶上 SameSite=strict 的 Cookie,所以如果從外部網站發 B 網站的 request 就會要求重新登入,讓攻擊者無法 CSRF










Related Posts

【隨堂筆記】基礎演算法概論

【隨堂筆記】基礎演算法概論

[Html] 網站method的http都變成https!?

[Html] 網站method的http都變成https!?

使用 Golang 打造 Discord 機器人 (一)

使用 Golang 打造 Discord 機器人 (一)


Comments