DVWA之CSRF漏洞(详细)

CSRF简介

csrf全称为:Cross-site request forgery,是一种常见的web攻击。在场景中,攻击者会伪造一个请求(通常是一个链接),然后欺骗目标用户点击,用户一旦点击,攻击也就完成了。

与xss的区别:csrf是借助用户的权限完成攻击,攻击者并没有拿到权限;而xss是直接盗取用户权限去进行破坏。
更改难度:
DVWA之CSRF漏洞(详细)_第1张图片
点击dvwa security,选择难度,然后点击submit完成更改

LOW难度

DVWA之CSRF漏洞(详细)_第2张图片
首先,我们先看一下网页源代码
DVWA之CSRF漏洞(详细)_第3张图片
我们可以看到low难度的源代码中,并没有隐藏的token,这样我们的难度就小了很多。
然后我猜测这里的密码检测是直接将输入的进行拼接,检验password_new与password_conf是否一致。
于是可以先伪造一个简陋的链接:
http://192.168.1.102/dvwa-master/vulnerabilities/csrf/?password_new=password&password_conf=password&Change=Change#
(注:里面的ip要改成自己的)
一旦用户点击链接,就会出现红字:
DVWA之CSRF漏洞(详细)_第4张图片
这样我们就成功地将密码更改为password了
当然,我们可以将链接修饰一下,毕竟这样一看就能看出来。
比如我们可以在网上找一个短链接生成器
DVWA之CSRF漏洞(详细)_第5张图片
也可以利用html构造一个攻击界面
<·img src=“http://192.168.1.102/dvwa-master/vulnerabilities/csrf/?password_new=password&password_conf=password&Change=Change#” border=“0” style=“display:none;”/>

<·h1>404<·h1>

<·h2>file not found.
(请自行去掉尖括号里面的点)
DVWA之CSRF漏洞(详细)_第6张图片
看似是一个失效的页面,但其实已将改掉了密码。

Medium难度

我们看一下网页代码:
DVWA之CSRF漏洞(详细)_第7张图片
与low难度一样,没有token,这时候,我们可以看一下源代码

<·?php
if( isset( $_GET[ ‘Change’ ] ) ) {
// Checks to see where the request came from
if( eregi( $_SERVER[ ‘SERVER_NAME’ ], $_SERVER[ ‘HTTP_REFERER’ ] ) ) {
// Get input
$pass_new = $_GET[ ‘password_new’ ];
$pass_conf = $_GET[ ‘password_conf’ ];

    // Do the passwords match?
    if( $pass_new == $pass_conf ) { 
        // They do! 
        $pass_new = mysql_real_escape_string( $pass_new );
        $pass_new = md5( $pass_new );

        // Update the database 
        $insert = "UPDATE `users` SET password = '$pass_new' WHERE user = '" . dvwaCurrentUser() . "';"; 

(正常如果我们想要知道有什么漏洞只能靠猜,但是现在我们有本地源代码,可以看一下)
比起low难度,多了一行:
if( eregi( $_SERVER[ ‘SERVER_NAME’ ], $_SERVER[ ‘HTTP_REFERER’ ] ) )
【 注:在php语言中int eregi(string pattern, string string),译为
检查string函数中是否含有pattern,如果有返回True,反之False。】

因此,此句是判断HTTP_REFERER中是否包含SERVER_NAME
HTTP_REFERER是Referer参数值,即来源地址
SERVER_NAME是host参数及主机ip名(我这里是192.168.1.102)
所以,如果我们想要破解它,就要让Referer参数值包含主机名
我们写一个html文件,和low难度的那个文件内容相同:
<·img src=“http://192.168.1.102/dvwa-master/vulnerabilities/csrf/?password_new=password&password_conf=password&Change=Change#” border=“0” style=“display:none;”/>

<·h1>404<·h1>

<·h2>file not found.
写好后将其命名为ip地址.html格式,如:192.168.1.102.html
然后将其放在网页根目录WWW的DVWA文件中
DVWA之CSRF漏洞(详细)_第8张图片
然后我们打开burp suite,对csrf界面抓一次包,发送至repeater,将Referer地址改为http://攻击者服务器地址/dvwa/被攻击ip地址.html格式,如图:
DVWA之CSRF漏洞(详细)_第9张图片
点击go,可以看到
DVWA之CSRF漏洞(详细)_第10张图片
DVWA之CSRF漏洞(详细)_第11张图片
密码成功更改。

High难度

我们看一下网页代码:
DVWA之CSRF漏洞(详细)_第12张图片

这次有了token值,这个值并不是很容易就看到的,我们需要在攻击者服务器上获取被攻击者的token值。
csrf攻击本质是重要操作的所有参数,都可以被攻击者猜测到
因此我们必须要获得token值!
我们要先看一下源代码:
<·?php

if( isset( $_GET[ ‘Change’ ] ) ) {
// Check Anti-CSRF token
checkToken( $_REQUEST[ ‘user_token’ ], $_SESSION[ ‘session_token’ ], ‘index.php’ );

// Get input 
$pass_new  = $_GET[ 'password_new' ]; 
$pass_conf = $_GET[ 'password_conf' ]; 

// Do the passwords match? 
if( $pass_new == $pass_conf ) { 
    // They do! 
    $pass_new = mysql_real_escape_string( $pass_new ); 
    $pass_new = md5( $pass_new ); 

    // Update the database 
    $insert = "UPDATE `users` SET password = '$pass_new' WHERE user = '" . dvwaCurrentUser() . "';"; 
    $result = mysql_query( $insert ) or die( '
' . mysql_error() . '
' ); // Feedback for the user echo "
Password Changed.
"; } else { // Issue with passwords matching echo "
Passwords did not match.
"; } mysql_close();

}

// Generate Anti-CSRF token
generateSessionToken();

?>
好吧,防护措施做的很严密。其实有一种漏洞类型是加token但不加校验。这种漏洞是即使加上了token,服务器也没有进行验证。在这里并不适用,看来我们需要找别的方法。
我们的攻击思路是试着去构造一个攻击页面,将其放置在攻击者的服务器,引诱受害者访问,从而获得token值,并向服务器发送改密请求,完成攻击。
但是,浏览器并不允许跨域请求,因此,我们可以利用xss漏洞
点击XSS(Stored),我们需要构造一条语句来获取token,由于有字符数限制,这里有两种方法,一是利用burp suite进行抓包,然后改参数,运行获取token。二是利用火狐浏览器。两种大体思路一致,这里我具体说一下第二种。
火狐浏览器打开xss(stored)界面,点击浏览器中的设置->web开发者->查看器,找到和name框架有关的代码(ctrl+f,输入txtname)
DVWA之CSRF漏洞(详细)_第13张图片
我们将size和maxlength值改大一点,
在这里插入图片描述
这样,我们就可以在name框中输入构造代码了,代码如下:

<·iframe src="…/csrf"οnlοad=alert(frames[0].document.getElementsByName(‘user_token’)[0].value)>

meesge框随意输入,点击sign guestbook,得到弹窗
DVWA之CSRF漏洞(详细)_第14张图片
此为token,有了这个,我们就可以利用medium中的方法进行攻击。

impossible难度

我们看一下网页代码
DVWA之CSRF漏洞(详细)_第15张图片
不仅有token,还要输入原密码。
再看一下源代码

<·?php

if( isset( $_GET[ ‘Change’ ] ) ) {
// Check Anti-CSRF token
checkToken( $_REQUEST[ ‘user_token’ ], $_SESSION[ ‘session_token’ ], ‘index.php’ );

// Get input 
$pass_curr = $_GET[ 'password_current' ]; 
$pass_new  = $_GET[ 'password_new' ]; 
$pass_conf = $_GET[ 'password_conf' ]; 

// Sanitise current password input 
$pass_curr = stripslashes( $pass_curr ); 
$pass_curr = mysql_real_escape_string( $pass_curr ); 
$pass_curr = md5( $pass_curr ); 

// Check that the current password is correct 
$data = $db->prepare( 'SELECT password FROM users WHERE user = (:user) AND password = (:password) LIMIT 1;' ); 
$data->bindParam( ':user', dvwaCurrentUser(), PDO::PARAM_STR ); 
$data->bindParam( ':password', $pass_curr, PDO::PARAM_STR ); 
$data->execute(); 

// Do both new passwords match and does the current password match the user? 
if( ( $pass_new == $pass_conf ) && ( $data->rowCount() == 1 ) ) { 
    // It does! 
    $pass_new = stripslashes( $pass_new ); 
    $pass_new = mysql_real_escape_string( $pass_new ); 
    $pass_new = md5( $pass_new ); 

    // Update database with new password 
    $data = $db->prepare( 'UPDATE users SET password = (:password) WHERE user = (:user);' ); 
    $data->bindParam( ':password', $pass_new, PDO::PARAM_STR ); 
    $data->bindParam( ':user', dvwaCurrentUser(), PDO::PARAM_STR ); 
    $data->execute(); 

    // Feedback for the user 
    echo "
Password Changed.
"; } else { // Issue with passwords matching echo "
Passwords did not match or current password incorrect.
"; }

}

// Generate Anti-CSRF token
generateSessionToken();

?>
加入了PDO预编译语句防止SQL注入,防止CSRF不仅用了token,还要求用户输入原密码,这样在不知道原密码的情况下就无法构造参数。因此,目前还无法破解。

你可能感兴趣的:(作业)