當前位置:
首頁 > 新聞 > 步步為營:如何通過USB方式攻破Android設備

步步為營:如何通過USB方式攻破Android設備

一、概述

最近,對智能手機的物理攻擊話題引起了一定的關注,其中的一個主要關注點是:攻擊者是否能夠在設備鎖定的狀態下,成功通過USB連接訪問存儲在設備上的數據。本文主要描述了針對Android設備如何成功實現此類攻擊,我們選用了Pixel 2設備進行測試。

在Android手機啟動後,會要求用戶進行一次解鎖(在較新的設備上,會顯示「解鎖所有功能和數據」頁面;在較老的設備上,會顯示「要啟動Android,請輸入密碼」),設備會保存加密密鑰,用於解密內核內存中的文件。即使屏幕在鎖定狀態,加密的文件系統區域或分區仍然可以訪問。因此,如果在鎖定的設備上成功提升許可權,那麼攻擊者不僅可以在設備上執行任意代碼並藉助後門訪問設備,還可以直接訪問用戶的數據。

本文相關的漏洞報告及PoC代碼,詳見以下鏈接:

https://bugs.chromium.org/p/project-zero/issues/detail?id=1583(通過blkid輸出注入USB實現目錄遍歷)

https://bugs.chromium.org/p/project-zero/issues/detail?id=1590(privesc zygote->init;USB攻擊鏈)

上述兩個漏洞編號為CVE-2018-9445( https://source.android.com/security/bulletin/2018-08-01 )和CVE-2018-9488( https://source.android.com/security/bulletin/2018-09-01#system ),分別在2018年8月補丁和9月補丁中實現修復。

二、攻擊面

許多Android手機都支持USB主機模式(通常需要使用OTG適配器),該模式允許手機連接到多種類型的USB設備(這個列表不一定完整):

1、USB存儲卡:當USB記憶棒插入Android手機時,用戶可以在手機和USB存儲卡之間複製文件。即使設備被鎖定,P版本之前的Android系統仍然會嘗試安裝USB存儲卡。(在報告漏洞後,新發布的Android 9中,設備在鎖定狀態不會安裝USB存儲卡。)

2、USB鍵盤和滑鼠:Android支持使用外部輸入設備,來替代原有的觸摸屏。此類設備也會在鎖屏狀態下啟用,比如需要用這些設備來輸入PIN碼。

3、USB乙太網適配器:當USB乙太網適配器連接到Android手機後,手機將會嘗試連接到有線網路,並使用DHCP獲取IP地址。此類設備在手機鎖定狀態下同樣有效。

本文我們將關注的重點放在USB存儲卡上。如果在具有高許可權的系統組件中安裝不受信任的USB存儲卡,將會為攻擊者創造重要的攻擊面。內核必須使用包含SCSI子集的協議與USB大容量存儲設備進行通信,對其分區表進行解析,並使用內核的文件系統實現來解釋其分區內容。用戶空間代碼必須標識文件系統類型,並指示內核將設備安裝到某個位置。在Android上,用戶空間實現主要是在vold中(其中的一個進程與內核具有相同的許可權),它會在SELinux中使用單獨的進程,例如:確定USB存儲卡上分區的文件系統類型。

三、漏洞分析:確定分區屬性

在插入USB存儲卡,且vold確定了設備上的分區列表時,它會嘗試識別每個分區的三個屬性:標籤(描述分區的用戶可讀字元串)、UUID(唯一標識符,可用於確認USB存儲卡是否在此前已經連接過該設備)和文件系統類型。在最新的GPT分區方案中,這些屬性大多可以存儲在分區表之中,然而USB存儲卡傾向於使用MBR分區方案,該方案中不能存儲UUID和標籤。對於普通USB存儲卡,Android同時支持MBR分區方案和GPT分區方案。

為了提供標記分區並為其分配UUID的能力,一旦使用的是MBR分區方案,就會在文件系統的頭部保存一個包含這些屬性的欄位,允許在已經確定文件系統、清除特定文件系統的頭部結構的情況下,以特定的方式提取這一信息。如果vold想要確定Label、UUID和文件系統類型時,它會調用blkid_untrusted SELinux域中的/system/bin/blkid。首先,會嘗試使用Magic Number和一些啟發式識別文件系統類型,隨後提取Label和UUID。

它會將結果以下列格式列印到stdout:

/dev/block/sda1: LABEL="" UUID="" TYPE=""

然而,Android使用的blkid版本沒有對Label字元串進行轉義,而負責解析blkid輸出的代碼部分只會尋找第一次出現的UUID=」和TYPE=」。因此,如果創建一個具有特定Label的分區,就可以實現對UUID的控制,並得到返回到vold的字元串。否則在正常情況下,它將始終是有效的UUID字元串以及一組固定類型字元串中的一個。

四、漏洞分析:掛載文件系統

在使用MBR分區表的新USB存儲卡中,當vold確認包含內核的vfat文件系統實現能夠掛載的vfat類型分區時,PublicVolume::doMount()會根據文件系統UUID構造一個掛載路徑,然後通過嘗試確保mountpoint目錄存在並具有正確的許可權和模式,隨後嘗試掛載該目錄:

if (mFsType != "vfat") {

LOG(ERROR)

return -EIO;

}

if (vfat::Check(mDevPath)) {

LOG(ERROR)

return -EIO;

}

// Use UUID as stable name, if available

std::string stableName = getId();

if (!mFsUuid.empty()) {

stableName = mFsUuid;

}

mRawPath = StringPrintf("/mnt/media_rw/%s", stableName.c_str());

[...]

if (fs_prepare_dir(mRawPath.c_str(), 0700, AID_ROOT, AID_ROOT)) {

PLOG(ERROR)

return -errno;

}

if (vfat::Mount(mDevPath, mRawPath, false, false, false,

AID_MEDIA_RW, AID_MEDIA_RW, 0007, true)) {

PLOG(ERROR)

return -EIO;

}

在此過程中,僅僅使用格式字元串來確定裝載路徑,並不會對blkid提供的UUID字元串進行任何檢查。因此,控制UUID字元串的攻擊者可疑實現目錄遍歷攻擊,並使得FAT文件系統安裝在/mnt/media_rw之外。

這意味著如果攻擊者將帶有標籤字元串為UUID="../##的FAT文件系統的USB存儲卡插入鎖定的手機中,手機會將該USB存儲卡掛載到/mnt/##。

然而,這種直接的攻擊方式有幾個嚴重的局限性,其中的一些能夠解決,另一些則無法避免:

1、標籤字元串長度問題:FAT文件系統的標籤限制為11位元組,而攻擊者要實現注入,UUID =「字元就要佔用6個位元組,這樣一來,目錄遍歷就只剩下了5個字元,不足以到達掛載結構中的任何關鍵位置。我們將在下一節介紹如何避免這一問題。

2、SELinux對掛載點的限制:即使vold被認為是與內核具有同等許可權,但SELinux策略實際上也會對vold進行一些限制。具體而言,mounton許可權僅限於在一組經允許的標籤上使用。

3、可寫性要求:如果目標目錄不是0700許可權,並且chmod()失敗,那麼fs_prepare_dir()也將會失敗。

4、訪問vfat文件系統的限制:安裝vfat文件系統時,其所有文件都被標記為u:object_r:vfat:s0。即使文件系統安裝在載入重要代碼或重要數據的位置,也不允許太多SELinux上下文與文件系統進行實際的交互。例如,該限制不允許zygote和system_server進行此類操作。最重要的是,沒有足夠許可權繞過DAC檢查的進程也需要在media_rw組中。下文中的「處理SELinux:觸發兩次漏洞」一章將會詳細說明如何避免這些限制。

五、漏洞利用:USB大容量存儲

正如上一節中所說,FAT文件系統的標籤限制為11個位元組。然而,blkid支持一系列具有更長標籤長度的其他文件系統類型。如果使用了這些文件系統類型,前提是必須要通過fsck對vfat文件系統的檢查,並且還需要通過在vfat文件系統裝載時由內核執行的文件系統頭部檢查。Vfat內核文件系統在分區開始時並不需要一個固定的Magic Value,所以理論上這種方式是可以實現的。但是,由於FAT文件系統頭部中的幾個值對內核而言十分重要,同事blkid也會對一些超級塊(Superblocks)進行健全性檢查,因此PoC採用的是一種不同的方式。

在blkid讀取了部分文件系統並確定文件系統的類型、標籤和UUID之後,fsck_msdos和內核文件系統實現將會重新讀取相同的數據,並且這些重複讀取的內容將會傳遞到存儲設備上。當用戶控制項直接與塊設備進行交互時,Linux內核會緩存塊設備的頁,但__blkdev_put()會在引用自設備的最後一個已打開文件關閉時,刪除與塊設備關聯的所有緩存數據。

由此,物理攻擊者可以通過附加假的存儲設備來實現這一功能的濫用,該存儲設備返回多次從同一位置讀取的不同數據。這樣一來,就允許我們將帶有長標籤字元串的romfs頭部返回給blkid,同時向fsck_msdos和內核文件系統實現呈現出完全正常的vfat文件系統。

由於Linux內置支持設備端USB,因此這一點實現起來相對簡單。Andrzej Pietrasiewicz曾發表過演講「製作你自己的USB實用工具」( https://events.static.linuxfound.org/sites/events/files/slides/LinuxConNA-Make-your-own-USB-gadget-Andrzej.Pietrasiewicz.pdf ),其演講內容可以作為我們的參考。基本上,內核都會附帶設備端USB大容量存儲、HID設備、乙太網適配器等實現。我們利用相對簡單的基於偽文件系統的配置界面,就可以定製出一個小工具,從而為連接的設備提供一個或多個上述功能(可能會有多個實例)。我們需要一個運行Linux並支持設備端USB的系統,在實際測試中,我們選用了Raspberry Pi Zero W。

f_mass_storage實用工具的作用在於,使用普通文件作為後備存儲(Backing Storage)。為了能夠以交互方式響應來自Android手機的請求,我們使用FUSE文件系統作為後備存儲,並使用direct_io選項 / FOPEN_DIRECT_IO標誌來確保內核中不會增加不需要的緩存。

至此,我們已經可以實施文件竊取攻擊,例如我們可以竊取存儲在外部存儲上的照片。針對攻擊者,在安裝USB存儲卡後,可以立即啟動com.android.externalstorage/.MountReceiver,這是SELinux域中一個允許訪問USB設備的進程。因此,在惡意FAT分區通過標籤字元串UUID="../../data成功在/data掛載之後,zygote進程會fork出一個具有適當SELinux上下文和組成員許可權的子進程,以允許訪問USB設備。隨後,這個子進程從/data/dalvik-cache/載入位元組碼,最終允許我們控制具有泄露外部存儲內容的必要許可權的com.android.externalstorage。

但是,如果攻擊者不只是想要訪問照片那麼簡單,還想要訪問存儲在設備上的聊天日誌或身份驗證憑據等內容,那這種訪問級別通常是不夠的。

六、處理SELinux:觸發兩次漏洞

在這裡,存在一個主要的限制因素。即使是可以掛載到/data下,但運行在設備上的許多高許可權代碼也不允許訪問已經掛載的文件系統。然而,有一個高許可權的服務確實可以,那就是vold。

Vold實際上支持兩種類型的USB存儲卡,分別是PublicVolume和Private Volume。在這裡,我們主要關注PublicVolume。從這裡,PrivateVolume也開始變得重要。

PrivateVolume是必須使用GUID分區表格式化的USB存儲卡,其中必須包含類型為UUID kGptAndroidExpand(193D1EA4-B3CA-11E4-B075-10604B889DCF)的分區,其中包含著dm-crypt加密的ext4(或f2fs)文件系統。相應的密鑰存儲在/data/misc/vold/expand_.key中,其中是GPT表中的分區GUID,作為規範化的小寫十六進位字元串。

作為攻擊者,一般是不應該以這種方式安裝ext4文件系統的,因為手機通常不會設置這類的密鑰。即使設置了這類密鑰,你仍然需要知道正確的分區GUID以及正確的密鑰。然而,在這裡我們可以在/data/misc上安裝一個vfat文件系統,並將我們自己的密鑰放在那裡,用於我們的GUID。然後,當第一個惡意USB大容量存儲設備仍保持連接時,我們可以使用vold從第一個USB大容量存儲設備中讀取的密鑰,連接第二個以PrivateVolume類型載入的存儲卡。

由於PrivateVolume實例使用的是ex4,所以我們可以控制文件系統上DAC的所有權和許可權。又因為PrivateVolume是集成到系統中的,所以我們甚至可以控制該文件系統上的SELinux標籤。

總而言之,至此為止我們可以在/data上裝載可以控制的文件系統,並具有任意文件許可權和任意SELinux上下文。由於此時已經能控制文件許可權和SELinux上下文,所以就可以允許任何進程訪問文件系統上的文件,包括使用PROT_EXEC對它們進行映射。

七、注入Zygote

儘管沒有被列為TCB的一部分,但Zygote進程也確實足夠強大。根據設計,該進程以UID 0運行,可以任意改變其UID,並能夠執行動態SELinux轉換,轉換到system_server或是普通應用程序的SELinux上下文。

當64位zygote在系統啟動時運行時,它會從/data/dalvik-cache/arm64/system@framework@boot*. 載入代碼。通常,oat文件(包含將使用dlopen()載入的ELF庫)和vdex文件是指向/system分區上文件的符號鏈接,只有art文件實際存儲在/data上。但是,我們可以將system@framework@boot.art和system@framework@boot.vdex符號鏈接指向/system(以便在不知道設備Android版本的情況下進行一致性檢查),同時將我們的惡意ELF庫放在system@framework@boot.oat(使用合法oat文件所具有的SELinux上下文)。

然後,在ELF庫中放置一個帶有__attribute__((constructor))的構造函數,我們可以在啟動時調用dlopen(),之後立即在zygote中執行代碼。

在這裡,仍然存在一個問題。當執行攻擊時,zygote已經在運行,而這種攻擊只有在zygote啟動時才能有效。

八、產生系統崩潰

這一部分,比較令人頭疼。

當關鍵系統組件(特別是zygote或system_server)崩潰時,Android會嘗試通過重新啟動大多數用戶空間進程(包括zygote)的方式,嘗試自動恢復。在發生這種情況時,屏幕首先顯示啟動動畫,然後跳轉到鎖定屏幕。在這時,該屏幕上還會顯示「解鎖所有功能和數據」的提示,而這一提示通常僅在系統剛剛啟動後顯示。然而,此時仍然存在可用於訪問用戶數據的密鑰,我們可以通過在設備上運行「ls /sdcard」來驗證ADB是否已打開。

這意味著,如果我們可以以某種方式使system_server崩潰,就可以在用戶空間重啟期間,將代碼注入到zygote中,並且能夠訪問設備上的用戶數據。

當然,在/data上裝載我們自己的文件系統是非常粗糙的方式,並且會產生各種各樣的問題。但令人驚訝的是,系統不會立即崩潰。儘管部分用戶界面無法使用,但大多數地方都有一些容錯機制,能保證在這種情況下不會產生太過嚴重的問題,以至於造成重啟。

經過一些嘗試,我們發現Android的網路帶寬用量跟蹤代碼具有一個安全檢查機制:如果帶寬用量跟蹤代碼無法寫入磁碟,並且自上次成功寫入以來已累計監測到>= 2MiB(mPersistThresholdBytes)的網路流量,就會拋出一個致命的異常(Fatal Exception)。這意味著,如果我們可以創建某種類型的網路連接到設備,然後發送>= 2MiB的Ping泛洪,隨後通過等待定期回寫或更改網路介面的狀態觸發stats回寫,就可以造成設備的重啟。

至於創建網路連接,我們有兩種方法:

1、連接到Wi-Fi網路。在Android 9之前,就算設備被鎖定,通常也可以通過從屏幕頂部向下拖動來連接到新的Wi-Fi網路,點擊Wi-Fi符號下方的下拉菜單,然後選擇Wi-Fi網路的名稱。(這種方式對於受WPA保護的網路不起作用,但攻擊者其實可以將自己的Wi-Fi網路打開。)許多設備也只能自動連接到具有特定名稱的網路。

2、連接到乙太網網路。Android支持USB乙太網適配器,並將自動連接到乙太網網路。

為了測試漏洞,我們手動創建了一個Wi-Fi,並用Android設備與之連接。考慮到更加可靠的網路連接和更加輕鬆的漏洞利用,可能會有讀者更傾向於乙太網連接。

此時,我們可以在zygote上下文中運行任意本地代碼,並訪問用戶數據。但是,目前還不能讀取原始磁碟加密密鑰,直接訪問底層塊設備或者進行RAM轉儲(由於剛剛的系統崩潰,可能有一半的轉儲內容已經丟失)。但在這裡,如果我們希望實現上述內容,就必須要升級我們的特權。

九、從Zygote到vold

即使zygote不是TCB的一部分,但它也可以訪問初始用戶命名空間中的CAP_SYS_ADMIN功能,並且SELinux策略也允許使用此功能。Zygote將此功能用於mount()系統調用,並用於在不設置NO_NEW_PRIVS標誌的前提下安裝seccomp過濾器。實際上,有多種方法可以濫用CAP_SYS_ADMIN。特別是在Pixel 2上,以下幾種方法似乎是可行的:

方法1

我們可以在沒有NO_NEW_PRIVS標誌的情況下安裝seccomp過濾器,然後執行具有許可權轉換的execve()函數(SELinux exec轉換,setuid/setgid執行,或使用允許的文件功能集執行)。Seccomp過濾器可以強制使特定的系統調用失敗,並返回錯誤值0。舉例來說,open()函數中的錯誤值0表明系統調用成功並分配了文件描述符0。這種攻擊方式在這裡能夠成功實現,但顯得有點亂。

方法2

可以指示內核使用我們控制的文件作為高優先順序交換設備,然後產生存儲壓力(Memory Pressure)。一旦內核將棧或者堆頁從一個特權進程寫入交換文件,我們就可以對換出的內存進行編輯,然後讓進程載入這部分內存。這種技術的缺點是非常難以預測,由於涉及到存儲壓力,所以可能會導致系統Kill掉我們想要保留的進程,並且有可能會破壞掉RAM中許多有用內容。同時,需要使用某種方法,來確定換出的頁是屬於哪個進程、是什麼作用。最後,此種方法需要內核支持交換(Swap)。

方法3

我們可以使用pivot_root()替換當前裝載的命名空間或新創建的裝載命名空間的根目錄,從而繞過本應該為mount()執行的SELinux檢查。如果我們希望影響之後提升許可權的子進程,那麼針對新的裝載命名空間執行此操作會非常有效。如果跟文件系統是rootfs文件系統,則該方法不起作用。在我們的嘗試過程中,使用的是這一種方法。

在最近發布的新版本Android中,用於創建崩潰進程轉儲的機制已經發生改變:以前是需要一個特權守護進程創建轉儲,而現在則是進程執行/system/bin/crash_dump64或/system/bin/crash_dump32中的一個助手,其中包含SELinux標籤u:object_r:crash_dump_exec:s0。目前,當任何SELinux域執行具有此類標籤的文件時,都會觸發到crash_dump域的自動域轉換。這也意味著在輔助向量(Auxiliary Vector)中設置了AT_SECURE標誌,從而指示新進程的載入/鏈接器需要留意例如LD_PRELOAD這樣的環境變數。

https://android.googlesource.com/platform/system/sepolicy/+/master/private/domain.te#1

domain_auto_trans(domain, crash_dump_exec, crash_dump);

在報告此錯誤時,crash_dump域具有以下SELinux策略:

https://android.googlesource.com/platform/system/sepolicy/+/a3b3bdbb2fdbb4c540ef4e6c3ba77f5723ccf46d/public

/crash_dump.te:

[...]

allow crash_dump {

domain

-init

-crash_dump

-keystore

-logd

}:process { ptrace signal sigchld sigstop sigkill };

[...]

r_dir_file(crash_dump, domain)

[...]

該策略允許crash_dump通過ptrace()連接到幾乎任何域中的進程(如果DAC控制項允許,則提供接管進程的能力),並允許它讀取procfs中任何進程的屬性。ptrace訪問的排除列表列出了一些TCB進程。但值得注意的是,vold不在名單上。因此,如果我們可以執行crash_dump64,並以某種方式將代碼注入其中,那麼我們就可以接管vold。

請注意,實際ptrace()進程的能力仍由正常的Linux DAC檢查控制,而crash_dump不能使用CAP_SYS_PTRACE或CAP_SETUID。即使一個普通的應用程序成功將代碼注入crash_dump64,但由於UID不匹配,它仍然無法利用它來攻擊系統組件。

如果你一直在仔細閱讀,你現在可能想知道我們是否可以在我們的假/data文件系統上放置自己的二進位文件u:object_r:crash_dump_exec:s0並執行,從而在crash_dump域中獲得代碼執行。實際上,並不起作用。因為在裝載USB存儲設備時,vold會硬編碼MS_NOSUID標誌,這不僅會使得經典的setuid/setgid二進位文件執行被降級,還會使具有文件功能的文件執行被降級,而後者通常涉及自動SELinux域轉換(除非SELinux策略通過授予PROCESS2__NOSUID_TRANSITION明確地選擇退出此行為)。

要將代碼注入crash_dump64,我們可以使用unshare()創建一個新的mount命名空間(使用CAP_SYS_ADMIN功能),然後調用pivot_root()將進程的根目錄指向我們完全控制的目錄,然後執行crash_dump64。然後內核解析crash_dump64的ELF頭,讀取鏈接器的路徑(/system/bin/linker64),從該路徑將鏈接器載入到內存中(所以我們可以在這裡提供我們自己的鏈接器),並執行。

此時,就可以在crash_dump上下文中執行任意代碼,並從那裡提升到vold。在這時,Android的安全策略會認為我們具有與內核同等的許可權。然而,如何又能獲得內核中的代碼執行呢?我們來繼續分析。

十、從vold到init上下文

看起來,似乎沒有一種簡單的方法可以從vold進入到真正的init進程。但是,有一種進入init SELinux上下文的方法。我們查看SELinux策略,試圖尋找一種允許轉換到init上下文的策略,最終找到了以下策略:

https://android.googlesource.com/platform/system/sepolicy/+/master/private/kernel.te:

domain_auto_trans(kernel, init_exec, init)

這意味著,如果我們能夠獲得內核環境的代碼執行,執行一個文件,控制該文件的標籤為init_exec,並且在未使用MS_NOSUID裝載的文件系統上執行,那麼該文件就可以在init的上下文中執行。

在內核上下文中運行的唯一代碼就是內核,因此,我們必須讓內核為我們執行文件。在Linux中,有一種稱為「Usermode Helpers」的機制可以做到這一點:在某些情況下,內核會將操作(例如:創建coredump、將密鑰載入到內核、執行DNS查找等)委託給用戶空間代碼。特別是,當查找不存在的密鑰時(例如通過request_key()函數),將會調用/sbin/request-key(硬編碼,只能在內核創建時使用CONFIG_STATIC_USERMODEHELPER_PATH將其更改為不同的靜態路徑)。

在vold中,我們可以在沒有MS_NOSUID的/sbin上安裝自己的ext4文件系統,然後調用request_key(),內核將在init上下文中調用我們的請求密鑰。

漏洞利用到此就結束了。下面的章節中描述了如何構建以獲得內核中的代碼執行。

十一、從init上下文到內核

從init上下文中,可以通過在顯式請求域轉換後執行適當標記的文件來轉換到modprobe或vendor_modprobe上下文(需要注意的是,這裡是domain_trans(),而不是domain_auto_trans(),這裡是允許在exec上進行轉換的):

domain_trans(init, { rootfs toolbox_exec }, modprobe)

domain_trans(init, vendor_toolbox_exec, vendor_modprobe)

modprobe和vendor_modprobe能夠從適當標記的文件載入內核模塊:

allow modprobe self:capability sys_module;

allow modprobe { system_file }:system module_load;

allow vendor_modprobe self:capability sys_module;

allow vendor_modprobe { vendor_file }:system module_load;

Android現在就不需要內核模塊的簽名了:

walleye:/ # zcat /proc/config.gz | grep MODULE

CONFIG_MODULES_USE_ELF_RELA=y

CONFIG_MODULES=y

# CONFIG_MODULE_FORCE_LOAD is not set

CONFIG_MODULE_UNLOAD=y

CONFIG_MODULE_FORCE_UNLOAD=y

CONFIG_MODULE_SRCVERSION_ALL=y

# CONFIG_MODULE_SIG is not set

# CONFIG_MODULE_COMPRESS is not set

CONFIG_MODULES_TREE_LOOKUP=y

CONFIG_ARM64_MODULE_CMODEL_LARGE=y

CONFIG_ARM64_MODULE_PLTS=y

CONFIG_RANDOMIZE_MODULE_REGION_FULL=y

CONFIG_DEBUG_SET_MODULE_RONX=y

因此,我們可以執行帶有特定標籤的文件,從而在modprobe上下文中執行代碼,然後從那裡載入帶有特定標籤的惡意內核模塊。

十二、總結

值得注意的是,這次漏洞利用跨越了兩個安全邊界:從blkid_untrusted到vold的邊界(由於vold使用blkid_untrusted提供的UUID而未檢查其是否合法),以及從zygote到TCB的邊界(通過濫用zygote的CAP_SYS_ADMIN功能)。作為開發者,必須意識到哪些位置是安全邊界,哪些位置不是。並且,在標出安全邊界後,必須要嚴格加強這些安全邊界。

最後,分析整個漏洞利用的過程,其實是vold和blkid_untrusted之間的安全邊界處產生了漏洞,並沒有起到任何緩解攻擊的作用。如果blkid代碼在vold進程中運行,其實沒有必要序列化其輸出,這樣一來,注入假的UUID就不會再起作用。


喜歡這篇文章嗎?立刻分享出去讓更多人知道吧!

本站內容充實豐富,博大精深,小編精選每日熱門資訊,隨時更新,點擊「搶先收到最新資訊」瀏覽吧!


請您繼續閱讀更多來自 嘶吼RoarTalk 的精彩文章:

高級USB key釣魚攻擊的三種攻擊場景(一)
針對沙特人權活動家和研究人員的NSO間諜軟體

TAG:嘶吼RoarTalk |