[网络安全]DVWA之XSS(Reflected)攻击姿势及解题详析合集


XSS(Reflected)-low level

源代码

<?php

header ("X-XSS-Protection: 0");

// Is there any input?
if( array_key_exists( "name", $_GET ) && $_GET[ 'name' ] != NULL ) {
    // Feedback for end user
    echo '<pre>Hello ' . $_GET[ 'name' ] . '</pre>';
}

?> 

无任何过滤 可实施XSS注入

姿势

先提交name1
浏览顶部URL栏发现为GET请求

在这里插入图片描述

Payload:GET<script>alert("qiu")</script>

在这里插入图片描述


XSS(Reflected)-medium level

源代码

<?php

header ("X-XSS-Protection: 0");

// Is there any input?
if( array_key_exists( "name", $_GET ) && $_GET[ 'name' ] != NULL ) {
    // Get input
    $name = str_replace( '<script>', '', $_GET[ 'name' ] );

    // Feedback for end user
    echo "<pre>Hello {$name}</pre>";
}
?> 
使用 str_replace() 函数将 <script> 标签替换为空

姿势

1.双写绕过

Payload:<scri<script>pt>alert("qiu")</script>
由于str_replace() 函数将<script>标签替换为空,且str_replace函数仅执行一次
Payload将变为<script>alert("qiu")</script>,从而实现了正常XSS语句的注入

在这里插入图片描述

2.大小写绕过

在 PHP 中,变量名、函数名、常量名等标识符都是区分大小写的。
例如,$Qiu$qiu 是两个不同的变量
因此我们可构造Payload如下来绕过限制:
Payload:<Script>alert("qiu")</script>

在这里插入图片描述<sCript>alert("qiu")</script><ScRIpt>alert("qiu")</script>均可


XSS(Reflected)-high level

源代码

<?php

header ("X-XSS-Protection: 0");

// Is there any input?
if( array_key_exists( "name", $_GET ) && $_GET[ 'name' ] != NULL ) {
    // Get input
    $name = preg_replace( '/<(.*)s(.*)c(.*)r(.*)i(.*)p(.*)t/i', '', $_GET[ 'name' ] );

    // Feedback for end user
    echo "<pre>Hello {$name}</pre>";
}

?> 
str_replace函数

preg_replace 是 PHP 内置的一个函数,用于使用正则表达式对字符串进行搜索和替换。其语法如下:

preg_replace($pattern, $replacement, $subject);

其中:

  • $pattern:表示正则表达式模式,用于指定需要搜索的规则;
  • $replacement:表示替换后的字符串,可以是字符串、数组或回调函数等;
  • $subject:表示输入的字符串,需要进行搜索和替换的目标字符串。

preg_replace 函数会在 $subject 中搜索符合 $pattern 的子串,并将其用 $replacement 进行替换。如果 $pattern 中包含捕获分组,可以在 $replacement 中使用 $n ($n 表示第 n 个捕获分组)的形式来引用捕获的内容。


.* 是正则表达式中的一个元字符组合,表示匹配任意数量的任意类型字符。其中.表示匹配任意一个字符,* 表示匹配该字符的数量是 0 到无限个。

例如,a.*b 表示匹配以字母 a 开始,以字母 b 结尾的字符串,并且两端之间包含了任意数量的字符。如 acbcaba-&^%$#@!b 等等都是符合这个正则表达式的字符串。


正则表达式 /<(.*)s(.*)c(.*)r(.*)i(.*)p(.*)t/i 中的 /i 表示忽略大小写。
例如,如果输入的字符串中存在如下标签:

<Script></Script>

那么在未加 /i 修饰符时,由于标签名中大小写混合,<Script>无法被/<(.*)s(.*)c(.*)r(.*)i(.*)p(.*)t/i完全匹配,因此不会被过滤掉。而当我们加上 /i 修饰符后,就可以忽略大小写,将其正确地匹配并过滤掉。


正则表达式/<(.*)s(.*)c(.*)r(.*)i(.*)p(.*)t/i表示匹配包含任意字符的 <script 标签。使用 preg_replace() 函数时,将会过滤所有以<开头、以t结尾的字符串
例如,以下的字符串均可被上述正则表达式匹配到:

<script></script>
<Scri<script>pt></scriUIXpt>
<SCCRIRIPPTTTTTt></scriIIOpt>

如果正则表达式为/<(.*)s(.*)c(.*)r(.*)i(.*)p(.*)t(.*)>/i,则会过滤所有以<开头,以>结尾的字符串


姿势

切换XSS语句的标签即可绕过限制
Payload:<img src=1 onerror=alert("qiu")>,注入成功:

在这里插入图片描述


XSS(Reflected)-Impossible level

源代码

<?php

// Is there any input?
if( array_key_exists( "name", $_GET ) && $_GET[ 'name' ] != NULL ) {
    // Check Anti-CSRF token
    checkToken( $_REQUEST[ 'user_token' ], $_SESSION[ 'session_token' ], 'index.php' );

    // Get input
    $name = htmlspecialchars( $_GET[ 'name' ] );

    // Feedback for end user
    echo "<pre>Hello {$name}</pre>";
}

// Generate Anti-CSRF token
generateSessionToken();

?> 

代码审计

1.检查是否存在名为 name 的 GET 参数,并且该参数不为空;
2.使用 checkToken() 函数对用户提交的 Anti-CSRF token 进行验证,通过比对 $_REQUEST['user_token']$_SESSION['session_token']的值,防止跨站请求伪造攻击(CSRF);
3.使用 htmlspecialchars() 函数对用户输入的 name 参数进行 HTML 实体编码,以避免客户端 JavaScript 的执行和 XSS 攻击;
4.输出经过处理的 name 参数,同时包裹在<pre></pre>标签中,使其能够以预格式化的方式显示,提升了输出信息的可读性。

另外,在该代码中也出现了一些与 CSRF 防御相关的函数调用:
1、 generateSessionToken() 函数用于产生随机的 Session Token,用于 CSRF 防御中防止攻击者利用各种手段获取到合法的 token 值;
2、checkToken() 函数用于验证用户提交的 Anti-CSRF token 是否合法。在其中,会比对用户提交的 token 值和服务器端存储的 token 值是否一致,如果不一致,则将会触发防御机制。

  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

秋说

感谢打赏,祝你平安喜乐。

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值