去年帮一个朋友看他的何测电商站,登录框里输入 ' or 漏洞1=1 --,页面直接跳进了后台。何测他脸都白了。漏洞这不是何测电影桥段,是漏洞每天都在发生的真事。SQL注入没死,何测只是漏洞很多人忘了怎么找它。
先搞清楚你要测什么。何测SQL漏洞的漏洞本质是:用户输入被当成代码执行了。所以测试的何测核心就一件事——想尽办法让数据库把输入当命令跑。手工测试永远比扫漏洞工具靠谱,漏洞工具会漏掉逻辑复杂的何测注入点。
别只盯着登录框。漏洞URL参数、何测Cookie、HTTP头里的X-Forwarded-For、搜索框、排序字段、甚至JSON请求体里的每个值,都是潜在入口。我习惯用Burp Suite把所有请求抓下来,逐个参数加单引号 ',看响应有没有报错或内容变化。
有个细节:数字型参数加 ' 可能没反应,试试 1' 或 1 and 1=1。字符型参数直接上 ' 往往就出SQL语法错误。
报错型最省事。输入 ' 后页面返回 You have an error in your SQL syntax,基本确认。但很多站关了报错显示,那就用布尔盲注。
假设参数是 id=1,试:
id=1 and 1=1 → 页面正常 id=1 and 1=2 → 页面异常或内容不同 如果两者有差异,说明 and 后面的条件被数据库执行了。接着可以猜数据库版本、表名、字段名。时间盲注更隐蔽:id=1; waitfor delay '0:0:5'--(SQL Server)或 id=1 and sleep(5)(MySQL)。页面卡5秒才返回,就是它了。
联合查询是效率最高的。先猜字段数:order by 1--、order by 2--,直到报错,就知道列数了。然后:
union select 1,2,3,table_name from information_schema.tables-- MySQL里 information_schema 是宝库,库名、表名、列名全在里面。SQL Server用 sysobjects 和 syscolumns。Oracle麻烦点,得查 all_tables。
遇到过滤别慌。空格被拦就用 /**/ 代替,select 被拦就 SeLeCt 大小写混写,或者 selselectect 双写。注释符 -- 后面必须跟空格,URL里要编码成 --+ 或 %23(#)。
sqlmap 确实快:sqlmap -u "http://target.com/page?id=1" --dbs。但它流量特征明显,容易触发WAF。我一般先手工确认注入点,再用sqlmap的 --tamper 脚本绕WAF,比如 space2comment.py。记住,工具跑出来的结果要手工验证,误报不少。
有些WAF只查 union select,那试试 union%0aselect(换行)。或者用 /*!50000union*/ /*!50000select*/,MySQL特有注释语法,WAF经常漏掉。参数污染也管用:?id=1&id=2 union select...,看后端取哪个值。
确认漏洞后,最小化验证。读个 @@version 或 current_user 就够了,别拖库。见过有人测试时把生产库拖了,直接进去踩缝纫机。测试授权范围要白纸黑字写清楚。
最后说个观察:现在很多站用ORM框架,注入点少了,但一旦有,往往在拼接SQL的地方——比如动态表名、order by字段、in子句。这些地方预编译处理不了,得手工过滤。测试时多留意这些角落,比扫全站参数更有效率。