元旦篇——浅谈Web安全中的代码安全——HTML、PHP等 Part1:SQL注入 – 作者:无笙security

本文章转自本人——无笙的CSDN博客并经过修改。CSDN名称:Mittsommer(现名:南城无笙)。

未经作者本人允许,不得转载!

图片[1]-元旦篇——浅谈Web安全中的代码安全——HTML、PHP等 Part1:SQL注入 – 作者:无笙security-安全小百科

作者QQ:2569207390

本文章所涉及的知识点作者均受益于道哥的书——《白帽子讲Web安全》,对安全感兴趣的推荐一读。

下面进入正文

OWASP TOP10 A1:SQL Injection.

世界性安全组织OWASP对于危害Web安全的十大漏洞进行了排位、列举构成了如今很多地方都在参考的OWASP TOP 10.

在每一次编排的OWASP TOP10中,SQL注入无疑都是A1(最高)级别

如图是OWASP TOP10 RC2内部发行版本的SQLi排行,在每次的评级中,无一例外,SQLi都是A1级别。:

图片[2]-元旦篇——浅谈Web安全中的代码安全——HTML、PHP等 Part1:SQL注入 – 作者:无笙security-安全小百科

(如果对OWASP的项目感兴趣的可以看看OWASP China的网站:OWASP 中国

一名名为RFP的黑客发布的一篇文章(NT Web Technology Vulnerabilities)中,介绍这种漏洞,及其攻击技巧。下面是一个典型的例子:

var Name;
Name = Request.form ("ExampleTest");
var sql = "select * from TestTable where Name='"+Name+"'"
=====>Example Code<=====

如果用户正常提交了数据,例如提交Amy,那么SQL语句是这样的:

SELECT * FROM TestTable where Name = "Amy"--

上述要达到的功能就是程序编写者想要达到的效果,也就是正常的生产环境中正常运行时的状况。

那么如果用户插入一段SQL语句呢?

如果用户输入如下的数据:

Amy'; drop table TestTable--

那么查询语句可想而知就会变成这个样子:

SELECT * FROM TestTable Where Name="Amy";drop TestTable--'

,那么我们其实不难看出,这里不仅执行了一个对于Name为Amy的查询还执行了drop TestTable(清空TestTable),这显然是开发者所不想看到的情况。

这里其实就构成了注入漏洞。

SQL注入也包含很多类型,例如最简单的Union联合查询注入、Error 注入、Timing Injection等,同时,很多injection漏洞也可以导致命令执行(导出webshell或利用自定义函数执行命令,有些时候构造sqlmap语句,可以直接getshell,例如,使用sqlmap获取一个有SQL注入漏洞的网站的shell:sudo sqlmap -u “http://targetDomain/……” –os-shell

这条命令执行后,如果目标网站存在SQL注入漏洞就可以getshell。

那么,下面来介绍下SQL注入的代码防御:
对于SQL注入,只进行简单的过滤是不安全的,例如:

$sql = "SELECT id,name FROM register WHERE id=".mesql_real_escape_string($_GET['id'])""

对于如上的代码,其实只对SQL注入有一个很小很小程度的防护,如果构造如下的Payload:

www.example.com/index.php?id=12,AND,1=0,union,select,1,concat(user,0x3a,password),3,4,5,6,7,from,sql.user,where,user=substring_index(current_user(),char(64),1)

那么还是可以成功利用SQL注入漏洞。

那么防御SQL注入的最好方法是什么呢?

一般情况下,使用预编译语句是个很好的方法。

例如下面这段Java代码(选自上文提到的书《白帽子讲Web安全》)

$query = "INSECT INTO MyCity (Nmap,CountryCode,District) VALUES (?,?,?)";
$stmt = $mysqli->prepare($query);
$stmt->bind_param("sss",$val1,$val2,$val3);
$val1 = "Stuttgart";
$val2 = "DEU"
$val3 = "Baden-Wuerttemberg";
/* Execute the Statement */
$stmt->execute();

上述是预编译语句的例子

下面再来介绍一种,检查输入数据的例子。

<?php

settype($offset,'integer');
$query = "SELECT id FROM Test ORDER BY id LIMIT 20 OFFSET $offset;";
$query = sprintf("SELECT id FROM Test ORDER BY id LIMIT 20 OFFSET %d;,$offset");

?>

当然,使用安全的函数也可以避免这个问题。

本文章到这里就结束了,对于其他漏洞, 后续文章会有讲述。

来源:freebuf.com 2021-01-01 09:56:38 by: 无笙security

© 版权声明
THE END
喜欢就支持一下吧
点赞0
分享
评论 抢沙发

请登录后发表评论