sql注入:SQL注入终级测试来源: 发布时间:星期四, 2009年2月12日 浏览:145次 评论:0
很多web开发者没有注意到SQL查询是可以被篡改因而把SQL查询当作可信任命令殊不知道SQL查询可以绕开访问控制从而绕过身份验证和权限检查更有甚者有可能通过SQL查询去运行主机操作系统级命令 直接SQL命令注入就是攻击者常用种创建或修改已有SQL语句技术从而达到取得隐藏数据或覆盖关键值甚至执行数据库主机操作系统命令目这是通过应用取得用户输入并和静态参合成SQL查询来实现下面将会给出些真实例子 由于在缺乏对输入数据进行验证并且使用了超级用户或其它有权创建新用户数据库帐号来连接攻击者可以在数据库中新建个超级用户 Example#1段实现数据分页显示代码……也可以被用作创建个超级用户(PostgreSQL系统) 复制PHP内容到剪贴板 PHP代码: $off=$argv[0];//注意没有输入验证! $query=\"SELECTid,nameFROMproductsORDERBYnameLIMIT20OFFSET$off;\"; $result=pg_query($conn,$query); 般用户会点击$off已被斌值“上页”、“下页”链接原本代码只会认为$off是个数值然而如果有人尝试把以下语句先经过urlencode处理然后加入URL中话: 0; insertopg_shadow(usename,usesysid,usesuper,usecatupd,passwd) select’crack’,usesysid,’t’,’t’,’crack’ frompg_shadowwhereusename=’postgres’; -- 那么他就可以创建个超级用户了注意那个0;只不过是为了提供个正确偏移量以便补充完整原来查询使它不要出错而已 Note:--是SQL注释标记般可以使用来它告诉SQL解释器忽略后面语句 对显示搜索结果页面下手是个能得到密码可行办法攻击者所要做只不过是找出哪些提交上去变量是用于SQL语句并且处理不当而这类变量通常都被用于SELECT查询中条件语句如WHERE,ORDERBY,LIMIT和OFFSET如果数据库支持UNION构造话攻击者还可能会把个完整SQL查询附加到原来语句上以便从任意数据表中得到密码因此对密码字段加密是很重要 Example#2显示文章……以及些密码(任何数据库系统) 复制PHP内容到剪贴板 PHP代码: $query=\"SELECTid,name,inserted,sizeFROMproducts WHEREsize=’$size’ ORDERBY$orderLIMIT$limit,$off;\"; $result=odbc_exec($conn,$query); 可以在原来查询基础上添加另个SELECT查询来获得密码: ’ unionselect’1’,concat(uname||’-’||passwd)asname,’1971-01-01’,’0’fromusertable; -- 假如上述语句(使用’和--)被加入到$query中任意个变量话那么就麻烦了 SQL中UPDATE也会受到攻击这种查询也可能像上面例子那样被插入或附加上另个完整请求但是攻击者更愿意对SET子句下手这样他们就可以更改数据表中些数据这种情况下必须要知道数据库结构才能修改查询成功进行可以通过表单上变量名对字段进行猜测或者进行暴力破解对于存放用户名和密码字段命名思路方法并不多 Example#3从重设密码……到获得更多权限(任何数据库系统) 复制PHP内容到剪贴板 PHP代码: $query=\"UPDATEusertableSETpwd=’$pwd’WHEREuid=’$uid’;\"; 但是恶意用户会把’oruidlike’%admin%’;--作为变量值提交给$uid来改变admin密码或者把$pwd值提交为\"hehehe’,admin=’yes’,trusted=100\"(后面有个空格)去获得更多权限这样做话查询语句实际上就变成了: [Page] 复制PHP内容到剪贴板 PHP代码: //$uid’oruidlike’%admin%’;-- $query=\"UPDATEusertableSETpwd=’...’WHEREuid=’’oruidlike’%admin%’;--\"; //$pwd\"hehehe’,admin=’yes’,trusted=100\" $query=\"UPDATEusertableSETpwd=’hehehe’,admin=’yes’,trusted=100WHERE ...;\"; 下面这个可怕例子将会演示如何在某些数据库上执行系统命令 Example#4攻击数据库所在主机操作系统(MSSQLServer) 复制PHP内容到剪贴板 PHP代码: $query=\"SELECT*FROMproductsWHEREidLIKE’%$prod%’\"; $result=mssql_query($query); 如果攻击提交a%’execmaster..xp_cmdshell’netusertesttestpass/ADD’--作为变量$prod值那么$query将会变成 复制PHP内容到剪贴板 PHP代码: $query=\"SELECT*FROMproducts WHEREidLIKE’%a%’ execmaster..xp_cmdshell’netusertesttestpass/ADD’--\"; $result=mssql_query($query); MSSQL服务器会执行这条SQL语句包括它后面那个用于向系统添加用户命令如果这个是以sa运行而MSSQLSERVER服务又有足够权限话攻击者就可以获得个系统帐号来访问主机了 Note:虽然以上例子是针对某特定数据库系统但是这并不代表不能对其它数据库系统实施类似攻击使用区别思路方法各种数据库都有可能遭殃 预防措施 也许有人会自我安慰说攻击者要知道数据库结构信息才能实施上面攻击没错确实如此但没人能保证攻击者定得不到这些信息但他们得到了数据库有泄露危险如果你在用开放源代码软件Software包来访问数据库比如论坛攻击者就很容得到到相关代码如果这些代码设计不良话风险就更大了 这些攻击总是建立在发掘安全意识不强代码上所以永远不要信任外界输入数据特别是来自于客户端包括选择框、表单隐藏域和cookie就如上面第个例子那样就算是正常查询也有可能造成灾难 永远不要使用超级用户或所有者帐号去连接数据库要用权限被严格限制帐号 检查输入数据是否具有所期望数据格式PHP有很多可以用于检查输入从简单变量和类型(比如is_numericctype_digit)到复杂Perl兼容正则表达式都可以完成这个工作 如果等待输入个数字可以考虑使用is_numeric来检查或者直接使用type来转换它类型也可以用sprf把它格式化为数字 Example#5个实现分页更安全思路方法 复制PHP内容到剪贴板 PHP代码: type($off,’eger’); $query=\"SELECTid,nameFROMproductsORDERBYnameLIMIT20OFFSET$off;\"; //请注意格式串中%d如果用%s就毫无意义了 $query=sprf(\"SELECTid,nameFROMproductsORDERBYnameLIMIT20OFFSET%d;\", $off); 使用数据库特定敏感转义(比如mysql_escape_和sql_escape_)把用户提交上来非数字数据进行转义如果数据库没有专门敏感转义功能话addslashes和str_replace可以代替完成这个工作看看第个例子此例显示仅在查询静态部分加上引号是不够查询很容易被攻破 [Page] 要不择手段避免显示出任何有关数据库信心尤其是数据库结构参见报告和处理 也可以选择使用数据库存储过程和预定义指针等特性来抽象数库访问使用户不能直接访问数据表和视图但这个办法又有别影响 除此的外在允许情况下使用代码或数据库系统保存查询日志也是个好办法显然日志并不能防止任何攻击但利用它可以跟踪到哪个曾经被尝试攻击过日志本身没用要查阅其中包含信息才行毕竟更多信息总比没有要好 0
相关文章读者评论发表评论 |