title: 代码审计学习-2
comments: false
date: 2016-09-13 01:47:25
categories: 安全
tags: 代码审计
代码执行&&命令执行
代码执行
代码执行漏洞的危险函数包括:eval(),assert(),preg_replace(),call_user_func()、call_user_func_array()、create_function()等。
eval()
eval函数作用:把字符串作为PHP代码执行
常见PHP 一句话:<?php eval($_POST['c']);?>
assert()
assert函数作用:检查一个断言是否为 FALSE
bool assert ( mixed $assertion [, string $description ] )
如果 assertion 是字符串,它将会被 assert() 当做 PHP 代码来执行。
所以一句话也可以是<?php assert($_POST[c]);?>
preg_replace()
preg_replace函数作用:执行一个正则表达式的搜索和替换
mixed preg_replace ( mixed $pattern , mixed $replacement , mixed $subject [, int $limit = -1 [, int &$count ]] )
搜索subject中匹配pattern的部分, 以replacement进行替换。
当
p
a
t
t
e
r
n
存
在
′
e
′
(
P
R
E
G
R
E
P
L
A
C
E
E
V
A
L
)
修
饰
符
时
,
pattern存在'e'(PREG_REPLACE_EVAL)修饰符时,
pattern存在′e′(PREGREPLACEEVAL)修饰符时,replacement参数被当作 PHP 代码执行。
如<?php echo preg_replace("/test/e",$_GET["c"],"test"); ?>
当提交?h=phpinfo()时,会显示phpinfo信息。
5.5.0 /e 修饰符已经被弃用了。使用 preg_replace_callback() 代替。
call_user_func()
call_user_func函数作用: 把第一个参数作为回调函数调用
mixed call_user_func ( callable $callback [, mixed $parameter [, mixed $... ]] )
第一个参数 callback 是被调用的回调函数,其余参数是回调函数的参数。
测试代码:
<?php
$b="phpinfo()";
call_user_func($_GET['a'],$b);
?>
此时,提交a=assert则执行代码
create_function()
函数create_function主要用来创建匿名函数
string create_function ( string $args , string $code )
测试代码:
<?php
//how to exp this code
$sort_by=$_GET['sort_by'];
$sorter='strnatcasecmp';
$databases=array('test','test');
$sort_function = ‘ return 1 * ‘ . $sorter . ‘($a[“‘ . $sort_by . ‘”], $b[“‘ . $sort_by . ‘”]);';
usort($databases, create_function(‘$a, $b', $sort_function));
?>
当输入?sort_by=”]);}phpinfo();/*
时,会执行phpinfo.
此时语句为return 1 * ‘ . $sorter . ‘($a[“‘ . ”]);}phpinfo();/*. ‘”], $b[“‘ . $sort_by . ‘”]);
命令执行
命令执行漏洞的危险函数包括system(),exec(),shell_exec(),passthru(),pcntl_exec(),popen(),proc_open()以及反引号(`)。
PHP命令执行权限为运行web服务器的用户权限。
system()
system — 执行外部程序,并且显示输出
string system ( string $command [, int &$return_var ] )
执行 command 参数所指定的命令, 并且输出执行结果
exec()
exec — 执行一个外部程序
string exec ( string $command [, array &$output [, int &$return_var ]] )
shell_exec()
shell_exec — 通过 shell 环境执行命令,并且将完整的输出以字符串的方式返回。
string shell_exec ( string $cmd )
passthru()
passthru — 执行外部程序并且显示原始输出
void passthru ( string $command [, int &$return_var ] )
pcntl_exec()
pcntl_exec — 在当前进程空间执行指定程序
void pcntl_exec ( string $path [, array $args [, array $envs ]] )
以给定参数执行程序,其中
path必须时可执行二进制文件路径或一个在文件第一行指定了 一个可执行文件路径标头的脚本(比如文件第一行是#!/usr/local/bin/perl的perl脚本)。
args是一个要传递给程序的参数的字符串数组。
envs是一个要传递给程序作为环境变量的字符串数组。
popen()
popen — 打开进程文件指针
resource popen ( string $command , string $mode )
打开一个指向进程的管道,该进程由派生给定的 command 命令执行而产生。
proc_open()
proc_open — 执行一个命令,并且打开用来输入/输出的文件指针。
resource proc_open ( string $cmd , array $descriptorspec , array &$pipes [, string $cwd [, array $env [, array $other_options ]]] )
popen(),proc_open()函数不会返回执行结果,而是返回文件指针
反引号
反引号执行命令是调用shell_exec()函数。
参考:
http://www.cnseay.com/1901/
《代码审计:企业级web代码安全架构》