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

PHPCMS 2008 最新漏洞之通杀注入漏洞

[复制链接]
跳转到指定楼层
楼主
发表于 2013-3-25 20:43:29 | 只看该作者 回帖奖励 |正序浏览 |阅读模式
0×01 前沿
" [' \3 B# K1 k# M. N/ @- w3 w, H7 L  N9 i- Q
      Phpcms2008 是一款基于 PHP+Mysql 架构的网站内容管理系统,也是一个开源的 PHP 开发平台。Phpcms  采用模块化方式开发,功能易用便于扩展,可面向大中型站点提供重量级网站建设解决方案。3年来,凭借 Phpcms  团队长期积累的丰富的Web开发及数据库经验和勇于创新追求完美的设计理念,使得 Phpcms  得到了近10万网站的认可,并且越来越多地被应用到大中型商业网站。
6 N7 u8 V% n/ ]/ @. \
( y0 F- {: Z/ m* ]& Z0×02 写在前面的话
5 I+ ~$ I& K2 c8 |1 v" {) v
: M1 O! Z! p. n8 T! D6 ]    phpcms 2008 这是我看第二次代码了,之前已经发现了一些问题,只是没放出来,这次稍微仔细看了看,又发现了一些问题
  p/ N3 i% {! ]7 X
" d  Q" z; X& k, P3 |" D  E这次就放2个吧,其中啥啥的getshell暂时就不会放了,比起v9来说,2008的安全性能确实差很多,模块化以及代码严谨程度也没有v9强
% F( y2 ~8 S3 H1 J8 K. T. Q3 ~+ l$ E2 Z% @
这次还没把代码看完,只看完几个页面,就先放2个有问题的地方,如果有更好的方式,到时候一起讨论1 q  I% V, S3 b& ^6 `9 d3 q4 H- O

$ U  L, c1 z! T8 C/ A. r0×03 路径? ? ?2 Y. H% k6 a7 p+ K: E

+ B+ x, w/ @1 p    在include/common.inc.php中 ,这是phpcms的全局要加载的配置文件8 R" r3 T/ p, f( G# o
! T' `7 z1 L) R1 B% \. X4 @
$dbclass = 'db_'.DB_DATABASE; require $dbclass.'.class.php'; $db = new $dbclass; $db->connect(DB_HOST, DB_USER, DB_PW, DB_NAME, DB_PCONNECT, DB_CHARSET); require 'session_'.SESSION_STORAGE.'.class.php'; $session = new session(); session_set_cookie_params(0, COOKIE_PATH, COOKIE_DOMAIN); if($_REQUEST) { if(MAGIC_QUOTES_GPC) { $_REQUEST = new_stripslashes($_REQUEST); if($_COOKIE) $_COOKIE = new_stripslashes($_COOKIE); extract($db->escape($_REQUEST), EXTR_SKIP); } else { $_POST = $db->escape($_POST); $_GET = $db->escape($_GET); $_COOKIE = $db->escape($_COOKIE); @extract($_POST,EXTR_SKIP); @extract($_GET,EXTR_SKIP); @extract($_COOKIE,EXTR_SKIP); } if(!defined('IN_ADMIN')) $_REQUEST = filter_xss($_REQUEST, ALLOWED_HTMLTAGS); if($_COOKIE) $db->escape($_COOKIE); } if(QUERY_STRING && strpos(QUERY_STRING, '=') === false && preg_match("/^(.*)\.(htm|html|shtm|shtml)$/", QUERY_STRING, $urlvar)) { parse_str(str_replace(array('/', '-', ' '), array('&', '=', ''), $urlvar[1])); } : r) p1 }) \  N) t5 b9 L4 g, R
6 G3 u1 k; U6 E- t. P: [4 g' _
这里的话首先实例化了这个数据库,产生了一个$db资源句柄,他是用来操作数据库的" `+ W. x7 G( S3 e* T6 F9 O

# X  n1 Y1 `7 N: Q' Z' n; ?然后就是将我们传进来的参数进行变量化0 M2 v3 T# n0 _

" J! {  [! v# r) N* N# j1 H! H这里有一些小过滤,自己可以看,所以这里传进来的参数就作为了变量  {' H. D7 {+ }- l$ k% J% |' s

4 n* R  U1 r( P8 _# M但是接下来这行呢?
7 i( w$ T5 Y5 i  a+ u9 z6 M: d4 X7 e! ]$ K) {, o4 G" Z

5 v* U9 V, m- n; J' c4 K' H# ~
1 X6 ?$ F4 o2 F# d' a( L1 gif(QUERY_STRING && strpos(QUERY_STRING, '=') === false && preg_match("/^(.*)\.(htm|html|shtm|shtml)$/", QUERY_STRING, $urlvar)) { parse_str(str_replace(array('/', '-', ' '), array('&', '=', ''), $urlvar[1])); }
4 _$ ^) i4 ^. A. `% ?6 V; I  H# S6 s. y0 W0 f  y9 C( i: c, W$ X2 C5 I

  X7 r6 Y0 E$ C% X
) e4 }9 A: S+ j$ Y7 C6 @看看这里?2 m' w& z: I" f% H) u$ v& k' }

/ E; b0 a2 T' M1 H- N这里的QUERY_STRING来自前面
4 g+ x! s4 S# y/ k* `# S
2 f0 l4 i' W. j( q% ?3 @1 x
# |. G+ M: B: }4 s& P/ K7 [
" R) {: y0 H( @' S8 }8 ]4 A2 i% rdefine('IP', ip()); define('HTTP_REFERER', isset($_SERVER['HTTP_REFERER']) ? $_SERVER['HTTP_REFERER'] : ''); define('SCRIPT_NAME', isset($_SERVER['SCRIPT_NAME']) ? $_SERVER['SCRIPT_NAME'] : preg_replace("/(.*)\.php(.*)/i", "\\1.php", $_SERVER['PHP_SELF'])); define('QUERY_STRING', safe_replace($_SERVER['QUERY_STRING']));
$ M% N( k3 l8 W这里有个过滤,但是不影响
" o# W5 n& }- T: v6 j. ]9 z8 T; r: ?5 }0 s+ c
如果我们在这里进行覆盖这个db变量呢* z! a+ j7 u: F/ [8 R; f

8 M, \5 s; J9 v7 W' S  h因为这里 parse_str(str_replace(array(‘/’, ’-', ’ ’), array(‘&’, ’=', ”), $urlvar[1]));9 C# N- ?& ]4 X& P* [: \% D
, O; B$ L6 a: u/ Q
可以将我们传进去的/ - 进行替换
5 {! F  @7 I9 |- _6 I% h5 _8 y2 t% ?# s9 A0 m& `
所以我们如果提交如下字符" ?% x, B: F, [9 h- i5 j( |1 M

/ j+ _$ \& H: t0 z1 uhttp://localhost/phpcms/index.php?db-5/gid-xd.html: J% a6 _6 n9 o- r' H' ]

( b7 F9 S! x+ |# q- p他由于这个db被覆盖就会出错,所以物理路径就爆出来了
8 M- H  n( N" F4 M. R. o- C" L- o
! v) x1 D7 O0 J( \6 I0×04  SQL注入!!!
1 }* k. M% ^) a$ g) a4 O+ G
- E8 z+ L7 I. B+ B! H( C  在c.php中$ n9 v4 @  M, P

# @; f8 p: r" ?% q& \ : ~7 j- j5 c5 E

8 B; V  m" y, P' H6 h" n" S<?php require './ads/include/common.inc.php'; $id = intval($id); $ads = $c_ads->get_info($id); if($ads) { $db->query("UPDATE ".DB_PRE."ads SET `clicks`=clicks+1 WHERE adsid=".$ads['adsid']); $info['username'] = $_username; $info['clicktime'] = time(); $info['ip'] = IP; $info['adsid'] = $id; $info['referer'] = HTTP_REFERER; $year = date('ym',TIME); $table = DB_PRE.'ads_'.$year; $table_status = $db->table_status($table); if(!$table_status) { include MOD_ROOT.'include/create.table.php'; } $db->insert($table, $info); $url = strpos($ads['linkurl'], 'http://')===FALSE ? 'http://'.$ads['linkurl'] : $ads['linkurl']; }
: e& `; a5 F+ e. a! t$ i, w/ A* b8 M
6 j3 W2 R# }% ]4 H7 u( x

+ S2 v4 T) w7 e! o* d7 o注意这里的HTTP_REFERER这个常量5 a* O  t. r  @9 R
- h4 ^2 `6 |, x& e9 ~
这里的常量是通过前面的common.inc.php定义好的+ Q* f+ E7 A9 l6 N

1 ?) N/ ?( I; ~; d0 Vdefine(‘HTTP_REFERER’, isset($_SERVER['HTTP_REFERER']) ? $_SERVER['HTTP_REFERER'] : ”);5 x: J% [( s% N" I
- W9 E5 A1 a7 R) _! H  l
没有经过任何过滤操作,所以你懂的,我估计很多同学已经发现了,只是没去公布了,所以俺就替你们xxoo了,哈哈…别骂我
3 s3 K! d: X: _1 \4 f8 z! _% i* S+ P5 _9 |, a( l9 P3 ~$ r
然后
0 e  q- _0 y, p( U/ W, `7 |& M+ x6 [/ g% S: U* S
$db->insert($table, $info);
8 [! W+ \. ^, E6 V# ~我们来看一下它这里的操作4 s, x6 {4 X& l

8 c1 W4 K3 G# ~: ]$ c1 z+ }& @/ l/ ifunction insert($tablename, $array) { $this->check_fields($tablename, $array); return $this->query("INSERT INTO `$tablename`(`".implode('`,`', array_keys($array))."`) VALUES('".implode("','", $array)."')"); } ( b* S! _, M$ Q9 |- E& ^( _" L

7 r# d* B) e, a4 W+ R所以你懂的
% E2 l1 e. D/ x& r# o  y4 M3 W2 m: B% \( q

- j6 z9 o$ v! x& O( l) b+ u. E* t9 P7 n! U. Q' A
附EXP:http://pan.baidu.com/share/link?shareid=468231&uk=4045637737. O0 \4 C, x% K$ G0 Q6 z' }
3 K/ ^) y* B2 ~! T  K, {
7 l5 q0 Z5 A" R1 y8 {% d" O

# t: R6 H: _; y$ u- @. z: d/ A' C
回复

使用道具 举报

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

本版积分规则

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