diff --git a/notes/pics/xss-stored.png b/notes/pics/xss-stored.png index 41513eb5..fea4fc16 100644 Binary files a/notes/pics/xss-stored.png and b/notes/pics/xss-stored.png differ diff --git a/notes/攻击技术.md b/notes/攻击技术.md index 303ae651..81b240c2 100644 --- a/notes/攻击技术.md +++ b/notes/攻击技术.md @@ -13,7 +13,7 @@ ### 概念 -跨站脚本攻击(Cross-Site Scripting, XSS),可以将代码注入到用户浏览的网页上,这种代码包括 HTML 和 JavaScript。 +跨站脚本攻击(Cross-Site Scripting, XSS)指的是攻击者把 HTML 和 JavaScript 代码注入到其他用户浏览的网页中。这些代码以该网站的身份在用户的浏览器中运行,能读取该网站的 Cookie、以用户的身份发送请求。 主要有三种类型: @@ -35,22 +35,22 @@

``` -另一个用户浏览了含有这个内容的页面将会跳转到 domain.com 并携带了当前作用域的 Cookie。如果这个论坛网站通过 Cookie 管理用户登录状态,那么攻击者就可以通过这个 Cookie 登录被攻击者的账号了。 +另一个用户浏览了含有这个内容的页面将会跳转到 domain.com,并把该论坛的 Cookie 作为参数带过去。如果这个论坛网站通过 Cookie 管理用户登录状态,并且这个 Cookie 没有设置 HttpOnly,那么攻击者就可以通过这个 Cookie 登录被攻击者的账号了。

### 危害 -- 窃取用户的 Cookie -- 伪造虚假的输入表单骗取个人信息 -- 显示伪造的文章或者图片 -- 以用户的身份向网站发起请求 +- 窃取用户的 Cookie; +- 伪造虚假的输入表单骗取个人信息; +- 显示伪造的文章或者图片; +- 以用户的身份向网站发起请求。 ### 防范手段 #### 1. 设置 Cookie 为 HttpOnly -设置了 HttpOnly 的 Cookie 可以防止 JavaScript 脚本调用,就无法通过 document.cookie 获取用户 Cookie 信息。 +设置了 HttpOnly 的 Cookie 可以防止 JavaScript 脚本调用,就无法通过 document.cookie 获取用户 Cookie 信息。需要注意的是,它只能防止 Cookie 被偷走,注入的脚本仍然可以在页面中以用户的身份发送请求,浏览器会照常带上这个 Cookie。 #### 2. 转义特殊字符 @@ -58,9 +58,9 @@ 富文本编辑器允许用户输入 HTML 代码,就不能简单地将 `<` 等字符进行过滤了,极大地提高了 XSS 攻击的可能性。 -富文本编辑器通常采用 XSS filter 来防范 XSS 攻击,通过定义一些标签白名单或者黑名单,从而不允许有攻击性的 HTML 代码的输入。 +富文本编辑器通常用基于白名单的 HTML 清理库来防范 XSS 攻击,例如前端的 DOMPurify、Java 的 OWASP Java HTML Sanitizer,只保留允许的标签和属性。黑名单很难列全危险的标签、属性和编码方式,容易被绕过。 -以下例子中,form 和 script 等标签都被转义,而 h 和 p 等标签将会保留。 +以下例子是 js-xss 按默认白名单处理的结果:form 和 script 等标签被转义成文本,h1 和 p 等标签保留,但不在白名单中的 id 属性被去掉。 ```html

XSS Demo

@@ -94,17 +94,17 @@ alert(/xss/); </script> ``` -> [XSS 过滤在线测试](http://jsxss.com/zh/try.html) +> [XSS 过滤在线测试](https://jsxss.com/zh/try.html) #### 3. 内容安全策略 -通过 Content-Security-Policy 首部告诉浏览器只允许执行来自指定来源的脚本,禁止内联脚本,即使攻击者注入了代码也不会被执行。 +通过 Content-Security-Policy 首部告诉浏览器只允许执行来自指定来源的脚本,禁止内联脚本,这样注入到页面中的脚本不会被执行。效果取决于策略的配置(例如允许了 `'unsafe-inline'` 就挡不住内联脚本),它是补充的防线,不能代替转义。 ## 二、跨站请求伪造 ### 概念 -跨站请求伪造(Cross-site request forgery,CSRF),是攻击者通过一些技术手段欺骗用户的浏览器去访问一个自己曾经认证过的网站并执行一些操作(如发邮件,发消息,甚至财产操作如转账和购买商品)。由于浏览器曾经认证过,所以被访问的网站会认为是真正的用户操作而去执行。 +跨站请求伪造(Cross-Site Request Forgery, CSRF)是攻击者通过一些技术手段欺骗用户的浏览器去访问一个自己曾经认证过的网站并执行一些操作(如发邮件,发消息,甚至财产操作如转账和购买商品)。浏览器向一个网站发请求时会自动带上该网站的 Cookie,从其它网站的页面发起的请求也一样(Cookie 的 SameSite 属性可以限制这一点,见下文),所以被访问的网站会认为是真正的用户操作而去执行。 XSS 利用的是用户对指定网站的信任,CSRF 利用的是网站对用户浏览器的信任。 @@ -134,9 +134,9 @@ http://www.examplebank.com/withdraw?account=AccountName&amount=1000&for=PayeeNam #### 1. 检查 Referer 首部字段 -Referer 首部字段位于 HTTP 报文中,用于标识请求来源的地址。检查这个首部字段并要求请求来源的地址在同一个域名下,可以极大的防止 CSRF 攻击。 +Referer 首部字段位于 HTTP 报文中,用于标识请求来源的地址。检查这个首部字段并要求请求来源的地址在同一个域名下,可以极大地防止 CSRF 攻击。 -这种办法简单易行,工作量低,仅需要在关键访问处增加一步校验。但这种办法也有其局限性,因其完全依赖浏览器发送正确的 Referer 字段。虽然 HTTP 协议对此字段的内容有明确的规定,但并无法保证来访的浏览器的具体实现,亦无法保证浏览器没有安全漏洞影响到此字段。并且也存在攻击者攻击某些浏览器,篡改其 Referer 字段的可能。 +这种办法简单易行,仅需要在关键访问处增加一步校验。局限在于它依赖浏览器发送 Referer:网站可以用 Referrer-Policy 让浏览器不发送或只发送部分地址,部分隐私插件也会去掉它,请求中没有 Referer 时,放行会留下漏洞,拒绝又会误伤正常用户。因此它通常和 Origin 首部的检查一起,作为 Token 之外的补充。 #### 2. 添加校验 Token @@ -144,42 +144,42 @@ Referer 首部字段位于 HTTP 报文中,用于标识请求来源的地址。 #### 3. 设置 Cookie 的 SameSite 属性 -SameSite=Strict 表示跨站请求不携带 Cookie,Lax 则只允许顶级导航的 GET 请求携带。Chrome 等浏览器的默认值已经是 Lax,上面例子中图片发出的请求不会带上 Cookie。 +SameSite=Strict 表示跨站请求不携带 Cookie,Lax 则只允许顶级导航的 GET 请求携带。Chrome、Edge 对没有设置 SameSite 的 Cookie 按 Lax 处理,Firefox、Safari 没有这样做,因此需要显式设置。设置为 Lax 时,上面例子中图片发出的请求不会带上 Cookie,但点击链接这类顶级导航的 GET 请求仍然会带,所以修改数据的接口不能用 GET。 #### 4. 输入验证码 -因为 CSRF 攻击是在用户无意识的情况下发生的,所以要求用户输入验证码可以让用户知道自己正在做的操作。 +因为 CSRF 攻击是在用户无意识的情况下发生的,所以对转账这类敏感操作,可以要求用户重新输入密码或短信验证码,确认的是本次操作,攻击者无法替用户完成。普通的图形验证码只用来区分人和程序,不能用来防范 CSRF。 ## 三、SQL 注入攻击 ### 概念 -服务器上的数据库运行非法的 SQL 语句,主要通过拼接来完成。 +SQL 注入指的是攻击者在输入中混入 SQL 片段,服务器把输入直接拼接到 SQL 语句中,这些片段就被数据库当作语句的一部分执行。 ### 攻击原理 例如一个网站登录验证的 SQL 查询代码为: -```sql +```text strSQL = "SELECT * FROM users WHERE (name = '" + userName + "') and (pw = '"+ passWord +"');" ``` 如果填入以下内容: -```sql +```text userName = "1' OR '1'='1"; passWord = "1' OR '1'='1"; ``` 那么 SQL 查询字符串为: -```sql +```text strSQL = "SELECT * FROM users WHERE (name = '1' OR '1'='1') and (pw = '1' OR '1'='1');" ``` -此时无需验证通过就能执行以下查询: +两个括号中的条件对每一行都成立,不需要知道密码,查询就等价于: -```sql +```text strSQL = "SELECT * FROM users;" ``` @@ -214,9 +214,9 @@ Query SELECT * FROM users WHERE name = '1'' OR ''1''=''1' AND pw = '1'' OR '' ## 四、拒绝服务攻击 -拒绝服务攻击(denial-of-service attack,DoS),亦称洪水攻击,其目的在于使目标电脑的网络或系统资源耗尽,使服务暂时中断或停止,导致其正常用户无法访问。 +拒绝服务攻击(Denial-of-Service Attack, DoS)的目的在于使目标电脑的网络或系统资源耗尽,使服务暂时中断或停止,导致其正常用户无法访问。 -分布式拒绝服务攻击(distributed denial-of-service attack,DDoS),指攻击者使用两个或以上被攻陷的电脑作为“僵尸”向特定的目标发动“拒绝服务”式攻击。 +分布式拒绝服务攻击(Distributed Denial-of-Service Attack, DDoS),指攻击者使用两个或以上被攻陷的电脑作为“僵尸”向特定的目标发动“拒绝服务”式攻击。 常见类型: @@ -238,3 +238,5 @@ Query SELECT * FROM users WHERE name = '1'' OR ''1''=''1' AND pw = '1'' OR '' - [维基百科:拒绝服务攻击](https://zh.wikipedia.org/wiki/%E9%98%BB%E6%96%B7%E6%9C%8D%E5%8B%99%E6%94%BB%E6%93%8A) - [OWASP Cross Site Scripting Prevention Cheat Sheet](https://cheatsheetseries.owasp.org/cheatsheets/Cross_Site_Scripting_Prevention_Cheat_Sheet.html) - [OWASP Cross-Site Request Forgery Prevention Cheat Sheet](https://cheatsheetseries.owasp.org/cheatsheets/Cross-Site_Request_Forgery_Prevention_Cheat_Sheet.html) +- [MDN: Set-Cookie](https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers/Set-Cookie) +- [OWASP Input Validation Cheat Sheet](https://cheatsheetseries.owasp.org/cheatsheets/Input_Validation_Cheat_Sheet.html)