用户
搜索
  • TA的每日心情
    郁闷
    2017-4-25 14:21
  • 签到天数: 1 天

    连续签到: 1 天

    [LV.1]初来乍到

    i春秋作家

    Rank: 7Rank: 7Rank: 7

    11

    主题

    101

    帖子

    165

    魔法币
    收听
    0
    粉丝
    8
    注册时间
    2017-4-25

    i春秋签约作者

    发表于 2017-4-25 19:22:21 2533327
    本文原创作者:黑客小平哥,本文属i春秋原创奖励计划,未经许可禁止转载!


    前言
    近日闲来无事,快两年都没怎么写代码了,打算写几行代码,做代码审计一年了,每天看代码都好几万行,突然发现自己都不会写代码了,真是很DT。想当初入门代码审计的时候真是非常难,网上几乎找不到什么java审计的资料,摸索了很长时间,搜到的也仅仅讲了点原理,为了给想学java代码审计的朋友门一点入门资料,就开始写《java代码审计连载》系列文章,本文章适合初学者,大牛留下脚印后请绕过,若代码有什么其他问题请忽略,因为那不是重点,此片只讲述SQL注入。本次写了两个简单的页面,一个登陆页面,一个查询id界面,如下:
    图片1.png
    图片2.png
    废话不多说,开始!

    SQL注入原理
    先看下百度百科对SQL注入的介绍:
    所谓SQL注入,就是通过把SQL命令插入到Web表单提交或输入域名或页面请求的查询字符串,最终达到欺骗服务器执行恶意的SQL命令。具体来说,它是利用现有应用程序,将(恶意的)SQL命令注入到后台数据库引擎执行的能力,它可以通过在Web表单中输入(恶意)SQL语句得到一个存在安全漏洞的网站上的数据库,而不是按照设计者意图去执行SQL语句。比如先前的很多影视网站泄露VIP会员密码大多就是通过WEB表单递交查询字符暴出的,这类表单特别容易受到SQL注入式攻击

    SQL注入的表现形式
    原理说的很正式,但是对初学者来说很笼统,对代码审计的来说也是不怎么明白。你那么总结起来,SQL注入在代码中体现的有以下3点:
    1、传递的参数为用户可控;
    什么叫参数为用户可控?其实前端传入的一切参数均为用户可控,包括:
    图片3.png
    这里的一切数据,参数传入后台后,接收的形式是什么样的呢?代码如下
    图片4.png
    request.getParameter("searchWord")是从前端获取参数的一种方式(当然还有其他方式,此处不赘述),而从前端获取的参数名为“searchWord”,也就是此处jsp页面中input标签中的id“searchWord”的值,如下:
    图片5.png
    因此“searchWord”就是前端我们输入的id”值。

    2.系统未对传入后台的参数做任何特殊字符过滤,或者字符过滤不全。
    什么是特殊字符,对SQL注入而言,特殊字符包括(注意大小写):
    --,#,//(注释符)
    and
    or
    select
    update
    delete
    drop
    declare
    insert
    xp_shell
    (,)括号
    ||,+, (空格) 连接符
    ' 单引号
    |(竖线符号)
    & & 符号)
    ;(分号)
    $(美元符号)
    %(百分比符号)
    @at 符号)
    '(单引号)
    "(引号)
    \'(反斜杠转义单引号)
    \"(反斜杠转义引号)
    <>(尖括号)
    CR(回车符,ASCII 0x0d
    LF(换行,ASCII 0x0a
    ,(逗号)
    \(反斜杠)


    3SQL语句是以拼接的形式执行,代码如下所示:
    图片6.png
    SQL语句一旦以拼接的方式执行,就表示拼接的参数“word”是表示一个SQL语句,而不仅仅是作为一个参数执行,什么意思呢?详细如下:
    如果word的值为1,那么SQL语句变成:
    Select * from test where id = 1
    如果word的值为1’ and ‘a’=’a,那么SQL语句变成:
    Select * from test where id = 1’ and ‘a’=’a
    最后在数据库中执行的时候就是
    图片7.png
    想必大牛们都明白这一点,就不赘述了。
    以上3点就是造成SQL注入产生的根本原因。
    SQL页面展示
    下面贴上SQL注入漏洞页面:
    搜索框输入:1
    图片8.png
    查看执行结果:
    图片9.png
    搜索框输入:1’
    查看执行结果:
    图片10.png
    搜索框输入:1’ and ‘a’=’a
    查看执行结果:
    图片11.png

    尝试爆出数据库长度(过程忽略):
    图片12.png
    图片13.png
    表示数据库长度为:8
    顺便贴上SqlMap截图:
    图片14.png
    图片15.png
    剩下的不深入,你们比我懂。

    SQL注入的修复
    SQL注入在java代码中的修复其实也是非常简单,主要有两个方式:
    1、添加全局过滤器,过滤特殊字符;方式如下:
    Web.xml:
    图片16.png
    SQLFilter.java中:
    图片17.png

    2.SQL语句使用参数化查询方式,代码如下:
    图片18.png
    使用参数化查询才是SQL注入最根本的修复方式。
    修复后SqlMap截图:
    图片19.png

    结论:
    本篇文章没有多少技术含量,希望对安全开发人员和学习代码审计人员有一点可取之处。本《java代码审计连载篇》会继续编写,希望大家多多支持,若有错误和不足之处,请指出来,谢谢!

    本帖被以下淘专辑推荐:

    坏蛋 管理员 欢迎大家来春秋群找我玩 秦 楚 燕 魏 齐 赵 春秋文阁
    来自 2#
    发表于 2017-5-8 16:58:42
    文章奖励介绍及评分标准:http://bbs.ichunqiu.com/thread-7869-1-1.html,如有疑问请加QQ:286894635!
    奖金
    点评
    100
    sql注入落实到java的这个实际场景这个想法不错,继续加油。

    欢迎加入i春秋QQ群大家庭,每人只能任选加入一个群哦!投稿请加我QQ:286894635。
    i春秋—楚:533191896
    i春秋—韩:556040588
    i春秋CTF交流学习群:234714762
    使用道具 举报 回复
    骑着乌龟抓兔子 发表于 2017-4-26 14:28
    希望楼主清晰的解释一下,java执行sql时使用预编译的时候JDBC.jar做的是什么操作,能做到防SQL注入!这一块 ...

    其实使用预编译的时候,参数就是相当于一个参数执行,而无法当一个语句执行,比如传入一个id,如果id是“1”,传入的值就是1,数据库找的时候就找id的值为“1”的数据,如果id是“1 and 1=1”,数据库就根本找不到id的值为“1 and 1=1”的数据,而不会拼接成sql语句去找id=1的,不知道这么说你可明白,貌似有点绕。
    使用道具 举报 回复
    黑客小平哥 发表于 2017-4-26 15:08
    其实使用预编译的时候,参数就是相当于一个参数执行,而无法当一个语句执行,比如传入一个id,如果id是“ ...

    明白明白,不知道楼主看过拼接sql这部分的代码实现么?按照楼主的解释确实是能解释的通,不过我还是想看代码更清晰一点,
    使用道具 举报 回复
    wang5566 发表于 2017-4-27 11:15
    我想问下对于现在流行的ORM框架sql注入是否就不存在了?

    都是存在的,像Hibernate和上面文章的差不多形式,iBATIS,mybatis什么的拼接的方式是用"$"获取参数,应该用"#"获取
    使用道具 举报 回复
    创想科技时代 版主 爱春秋的天下,我要九十九 i春秋认证 春秋文阁
    推荐
    发表于 2017-5-12 18:24:26
    wang5566 发表于 2017-4-27 11:15
    我想问下对于现在流行的ORM框架sql注入是否就不存在了?

    在Hibernate框架和MyBatis都是可以过滤掉的。Structs2的Filter可以过滤掉这些关键字吧
    觉得自己计算机功底不行?
    有想法又不会编程?
    想要继续深入学习?
    想学习又找不到资料?
    没人带自学很痛苦?群号: 434199192
    使用道具 举报 回复
    骑着乌龟抓兔子 发表于 2017-4-26 15:23
    明白明白,不知道楼主看过拼接sql这部分的代码实现么?按照楼主的解释确实是能解释的通,不过我还是想看 ...

    你是说jdbc的jar包源码么
    使用道具 举报 回复
    黑客小平哥 发表于 2017-4-27 14:10
    都是存在的,像Hibernate和上面文章的差不多形式,iBATIS,mybatis什么的拼接的方式是用"$"获取参数,应 ...

    学习了,非常感谢
    使用道具 举报 回复
    希望楼主清晰的解释一下,java执行sql时使用预编译的时候JDBC.jar做的是什么操作,能做到防SQL注入!这一块一直没弄明白。JDBC底层是怎么做的?
    使用道具 举报 回复
    发表于 2017-4-26 14:24:37
    前排围观
    使用道具 举报 回复
    发表于 2017-4-26 17:49:11
    参数化查询方式,我能问问这个是什么吗
    使用道具 举报 回复
    发表于 2017-4-26 20:10:53
    厉害呀,别的资料都是粗粗的说 审计数据来源。审计容易形成问题的语句等等,这里讲的很细。!加油!
    使用道具 举报 回复
    发表于 2017-4-27 11:15:38
    我想问下对于现在流行的ORM框架sql注入是否就不存在了?
    使用道具 举报 回复
    发表于 2017-4-27 14:08:44
    Ycrazy 发表于 2017-4-26 17:49
    参数化查询方式,我能问问这个是什么吗

    额,请看文章,就是select * from user where id = ? 这种
    使用道具 举报 回复
    发表于 2017-4-28 17:20:49
    很好的文章,学习了。
    使用道具 举报 回复
    发表于 2017-4-28 18:26:11
    使用道具 举报 回复
    发表于 2017-4-28 18:35:23
    平哥,你能想起我不
    使用道具 举报 回复
    12下一页
    发新帖
    您需要登录后才可以回帖 登录 | 立即注册