sql注入原理:SQL注入原理深度解析

来源:安全中国

对于Web应用来说注射式攻击由来已久攻击方式也 5花 8门常见攻击方式有SQL注射、命令注射以及新近才出现XPath注射等等本文将以SQL注射为例在源码级对其攻击原理进行深入讲解

、注射式攻击原理

注射式攻击根源在于命令和用户数据(即用户输入)的间没有做到泾渭分明这使得攻击者有机会将命令当作用户输入数据提交给We以发号施令为所欲为

为了发动注射攻击攻击者需要在常规输入中混入将被解释为命令“数据”要想成功必须要做 3件事情:

1.确定Web应用所使用技术

注射式攻击对设计语言或者硬件关系密切但是这些可以通过适当踩点或者索性将所有常见注射式攻击都搬出来逐个试下就知道了为了确定所采用技术攻击者可以考察Web页面页脚查看页面检查页面源代码或者使用诸如Nessus等工具来进行刺探

2.确定所有可能输入方式

Web应用用户输入方式比较多其中些用户输入方式是很明显如HTML表单;另外攻击者可以通过隐藏HTML表单输入、HTTP头部、cookies、甚至对用户不可见后端AJAX请求来跟Web应用进行交互般来说所有HTTPGET和POST都应当作用户输入为了找出个Web应用所有可能用户输入我们可以求助于Web代理如Burp等

3.查找可以用于注射用户输入

在找出所有用户输入方式后就要对这些输入方式进行筛选找出其中可以注入命令那些输入方式这个任务好像有点难但是这里有个小窍门那就是多多留意Web应用页面很多时候您能从这里得到意想不到收获

2、SQL注射原理

上面对注射攻击做了般性解释下面我们以SQL注射为例进行讲解以使读者对注射攻击有个感性认识至于其他攻击原理是

SQL注射能使攻击者绕过认证机制完全控制远程服务器上数据库SQL是结构化查询语言简称它是访问数据库事实标准目前大多数Web应用都使用SQL数据库来存放应用数据几乎所有Web应用在后台都使用某种SQL数据库跟大多数语言SQL语法允许数据库命令和用户数据混杂在如果开发人员不细心用户数据就有可能被解释成命令这样远程用户就不仅能向Web应用输入数据而且还可以在数据库上执行任意命令了

3、绕过用户认证

我们这里以个需要用户身份认证简单Web应用为例进行讲解假定这个应用提供个登录页面要求用户输入用户名和口令用户通过HTTP请求发送他们用户名和口令的后Web应用检查用户传递来用户名和口令跟数据库中用户名和口令是否匹配这种情况下会要求在SQL数据库中使用个数据库表开发人员可以通过以下SQL语句来创建表:

CREATETABLEuser_table(

idINTEGERPRIMARYKEY,

usernameVARCHAR(32),

passwordVARCHAR(41)

);

 

上面SQL代码将建立个表该表由 3栏组成栏存放是用户ID如果某人经过认证则用此标识该用户第 2栏存放是用户名该用户名最多由32组成第 3栏存放是口令它由用户口令hash值组成以明文形式来存放用户口令实在太危险所以通常取口令散列值进行存放我们将使用SQLPASSWORD()来获得口令hash值在MySQL中PASSWORD()输出由41组成

个用户进行认证实际上就是将用户输入即用户名和口令跟表中各行进行比较如果跟某行中用户名和口令跟用户输入完全匹配那么该用户就会通过认证并得到该行中ID假如用户提供用户名和口令分别为lonelynerd15和mypassword那么检查用户ID过程如下所示:

SELECTidFROMuser_tableWHEREusername=’lonelynerd15’ANDpassword=PASSWORD(’mypassword’)

 

如果该用户位于数据库表中这个SQL命令将返回该用户相应ID这就意味着该用户通过了认证;否则这个SQL命令返回为空这意味着该用户没有通过认证

下面是用来实现自动登录Java代码它从用户那里接收用户名和口令然后通过个SQL查询对用户进行认证:

Stringusername=req.getParameter("username");

Stringpassword=req.getParameter("password");

Stringquery="SELECTidFROMuser_tableWHERE"+

"username=’"+username+"’AND"+

"password=PASSWORD(’"+password+"’)";

ResultSetrs=stmt.executeQuery(query);

id=-1;//-1impliesthattheuserisunauthenticated.

while(rs.next){

id=rs.getInt("id");

}

 

开头两行代码从HTTP请求中取得用户输入然后在下行开始构造个SQL查询执行查询然后在while()循环中得到结果如果个用户名和口令对匹配就会返回正确ID否则id值仍然为-1这意味着用户没有通过认证表面上看如果用户名和口令对匹配那么该用户通过认证;否则该用户不会通过认证——但是事实果真如此吗?非也!读者也许已经注意到了这里并没有对SQL命令进行设防所以攻击者完全能够在用户名或者口令字段中注入SQL语句从而改变SQL查询为此我们仔细研究下上面SQL查询串:

Stringquery="SELECTidFROMuser_tableWHERE"+

"username=’"+username+"’AND"+

"password=PASSWORD(’"+password+"’)";

 

上述代码认为串username和password都是数据不过攻击者却可以随心所欲地输入任何如果位攻击者输入用户名为

’OR1=1—

而口令为

x

那么查询串将变成下面样子:

SELECTidFROMuser_tableWHEREusername=’’OR1=1--’ANDpassword

=PASSWORD(’x’)

该双划符号--告诉SQL解析器右边东西全部是注释所以不必理会这样查询串相当于:

SELECTidFROMuser_tableWHEREusername=’’OR1=1

 

如今SELECT语句跟以前已经大相径庭了现在只要用户名为长度为零串’’或1=1这两个条件中个为真就返回用户标识符ID——我们知道1=1是恒为真所以这个语句将返回user_table中所有ID在此种情况下攻击者在username字段放入是SQL指令’OR1=1--而非数据





  • 篇文章: 利用WMI打造完美“ 3无”后门-Downloader and Uploader

  • 篇文章: 没有了
  • Tags:  sql注入 php注入原理 注入原理 sql注入原理

    延伸阅读

    最新评论

    发表评论