微博上传图片时只在前端进行验证, 服务器端没有进行安全过滤。
! M# m, e- w. E" p
# l* `9 I# Z' U, K
" G; Z& N* z( }0 ?6 Y# L\api\StatusesApi.class.php
, y* Y# F2 {7 A) k0 S 4 p+ B9 A- I& b7 m- l6 ~( m
function uploadpic(){- R1 M: s- [7 _, O1 q
if( $_FILES['pic'] ){) }" G! e4 Z% `& `
//执行上传操作 s H7 g3 }8 ]. q$ @
$savePath = $this->_getSaveTempPath(); h5 W9 G( ]. B* b$ y
$filename = md5( time().'teste' ).'.'.substr($_FILES['pic']['name'],strpos($_FILES['pic']['name'],'.')+1);
! w' `, Y) u! b5 o* Z0 D if(@copy($_FILES['pic']['tmp_name'], $savePath.'/'.$filename) || @move_uploaded_file($_FILES['pic']['tmp_name'], $savePath.'/'.$filename))
2 H: R5 z; m* A! h# Y B6 p; Q6 p$ W {) ~& n# m k/ M8 J8 ^' H1 M6 K
$result['boolen'] = 1;
7 e( _, P2 [1 J; c $result['type_data'] = 'temp/'.$filename; L e% B5 U$ u% a- f
$result['picurl'] = SITE_PATH.'/uploads/temp/'.$filename;
* {0 w: y4 i( s, \- I! [- y9 C } else {
# s0 `! v) C" R+ _) A9 g; n6 f; x $result['boolen'] = 0;5 [/ I4 t1 e7 `
$result['message'] = '上传失败';
/ a( y' T& v: ]6 o }0 u1 z/ P" `+ O6 o* ~7 r2 I0 o
}else{5 C" A! M! q9 ?9 i
$result['boolen'] = 0;: N% A: l0 j' \8 `
$result['message'] = '上传失败';4 {( o( `1 B2 E2 V1 V4 ]# q# g
}8 l5 ]( [+ Q \& j: n J
return $result;
2 D5 l! F" T1 L! E' R8 U) z }
) e) B- b9 B" a3 x3 ^unloadpic()方法没有对文件类型进行验证4 C6 P. J |6 N1 y2 e& n: K
+ h5 B& X$ A2 a+ D, J+ t
可以构建表单, 选择任意文件, 提交到2 h9 p4 l. M$ G, u+ Z5 [2 ~
/index.php?app=w3g&mod=Index&act=doPost
: s* Y) ]! A% ^8 r0 C . z' N% d) T2 R% y7 K( D( ^
在新提交的微博上可以找到上传的文件地址(去掉small_、middle_ 前缀)
' A$ Z9 O6 G% r# D! e) x# S& M3 K
6 P+ A, @) \/ ]0 o' t
2 c2 m; b# v( K在登录thinksns官方微博后,
# i+ t! l2 o$ s% H8 T1 D0 ]构建以下表单:; S' E/ X; a0 C: g1 {1 n
+ m% } J; I1 X( E" c2 i$ q" W# a<form action="http://t.thinksns.com/index.php?app=w3g&mod=Index&act=doPost" method="post" enctype="multipart/form-data" />% C6 s& }; S! q
<textarea name="content">test</textarea>
0 L* g8 V7 a$ ^7 [8 ffile: <input id="file" type="file" name="pic" />, ]' `/ J1 c5 c, @2 v# [
<input type="submit" value="Post" />+ f4 A ~6 Z3 J; D7 w
</form>
7 [# A) R# q; C- q+ N去掉缩略图的前缀(small_ )$ l! d4 b# J2 l$ C" L
修复方案:0 x, a- k2 Q: I5 c" W6 }" b* C0 V
8 n8 L/ l$ V/ G
8 h) k% P# t; ^2 D I
\api\StatusesApi.class.php
6 f) F* Z! g$ G6 X ; f( ~0 d' T$ J
function uploadpic(){- q( c" a6 l! P8 m+ {
/**5 h% F( n& \0 d1 H
* 20121018 @yelo5 Y/ p/ u, | l3 R; Z8 V7 l
* 增加上传类型验证
( C g" a5 o1 g/ q) B9 R8 R */
( k# E# q1 }% C$ M$ E $pathinfo = pathinfo($_FILES['pic']['name']);- Z8 r8 Z( ?: d6 l2 K* k
$ext = $pathinfo['extension'];2 {2 h8 L8 g4 S. E) c
$allowExts = array('jpg', 'png', 'gif', 'jpeg');
! A5 y$ ?2 ~ O H& N% C0 T; b: T; `
" l) E: A1 M5 v* v4 g6 F4 A1 ] $uploadCondition = $_FILES['pic'] && in_array(strtolower($ext),$allowExts,true);
- P) y. T* F3 Q8 T# ~
1 ?* h% _; H% ?: K1 L if( $uploadCondition ){; b& U. `" u' ~$ P! R3 ]9 }
//执行上传操作
- F7 C& I: }# ~- T2 q: h $savePath = $this->_getSaveTempPath();% L+ c# V! B$ G! \7 s: K) v
$filename = md5( time().'teste' ).'.'.substr($_FILES['pic']['name'],strpos($_FILES['pic']['name'],'.')+1);
: A. T0 M$ I( r) Z7 z. P& k9 J if(@copy($_FILES['pic']['tmp_name'], $savePath.'/'.$filename) || @move_uploaded_file($_FILES['pic']['tmp_name'], $savePath.'/'.$filename)). G& O O# ^' R2 i4 @: M
{
6 t" x& k5 M+ d7 Z $result['boolen'] = 1;
, o3 C3 E6 X% S/ U& l6 z $result['type_data'] = 'temp/'.$filename;
( Y) |5 F1 y: i1 ?% |& c $result['picurl'] = SITE_PATH.'/uploads/temp/'.$filename;( r- M: ?! w9 I7 R# M
} else {- H0 J! C7 ^3 O# b9 t
$result['boolen'] = 0;" k: g8 }9 d) ]2 H+ C2 _5 D
$result['message'] = '上传失败';
3 E7 _0 K. ~- t, m9 J2 i5 ?( D( G6 | }4 t2 q" W. l& F, ` Z& o, ~6 r9 [
}else{4 h2 f# Q' w6 C$ R5 t% V! H! L
$result['boolen'] = 0;
- l( S# g( y) A3 r: V $result['message'] = '上传失败';
8 W; D7 Y. `: l8 k h7 B }2 a0 o/ P/ S1 x/ h( E! G
return $result;
: p) m; t& k1 E* S }, G- Z( a: @- Q5 y% E( Q
& @, g: ~ Z; V; c
! C4 s2 M* A% b7 g% r |