實施 SELinux

SELinux 設置為默認拒絕,這意味著它在內核中具有掛鉤的每個訪問都必須被策略明確允許。這意味著策略文件包含大量有關規則、類型、類、權限等的信息。全面考慮 SELinux 超出了本文檔的範圍,但現在在推出新的 Android 設備時,了解如何編寫策略規則至關重要。已經有大量關於 SELinux 的可用信息。有關建議的資源,請參閱支持文檔

關鍵文件

要啟用 SELinux,請集成最新的 Android 內核,然後合併在system/sepolicy目錄中找到的文件。編譯後,這些文件包含 SELinux 內核安全策略並涵蓋上游 Android 操作系統。

通常,您不應直接修改system/sepolicy文件。相反,在/device/ manufacturer / device-name /sepolicy目錄中添加或編輯您自己的特定於設備的策略文件。在 Android 8.0 及更高版本中,您對這些文件所做的更改只會影響您的供應商目錄中的策略。有關在 Android 8.0 及更高版本中分離公共 sepolicy 的更多詳細信息,請參閱在 Android 8.0+ 中自定義 SEPolicy 。無論 Android 版本如何,您仍在修改這些文件:

政策文件

*.te結尾的文件是 SELinux 策略源文件,用於定義域及其標籤。您可能需要在/device/ manufacturer / device-name /sepolicy中創建新的策略文件,但您應該盡可能嘗試更新現有文件。

上下文文件

上下文文件是您為對象指定標籤的地方。

  • file_contexts為文件分配標籤並被各種用戶空間組件使用。在創建新策略時,創建或更新此文件以將新標籤分配給文件。要應用新的file_contexts ,請重建文件系統映像或在要重新標記的文件上運行restorecon 。升級時, file_contexts的更改會自動應用於系統和用戶數據分區,作為升級的一部分。通過向您的 init 添加restorecon_recursive調用,也可以在升級到其他分區時自動應用更改。分區以讀寫方式掛載後的board .rc 文件。
  • genfs_contexts將標籤分配給不支持擴展屬性的文件系統,例如procvfat 。此配置作為內核策略的一部分加載,但更改可能不會對核心 inode 生效,需要重新啟動或卸載並重新安裝文件系統才能完全應用更改。特定的標籤也可以分配給特定的掛載,例如使用context=mount選項的vfat
  • property_contexts將標籤分配給 Android 系統屬性以控制哪些進程可以設置它們。此配置在啟動期間由init進程讀取。
  • service_contexts將標籤分配給 Android binder 服務,以控制哪些進程可以添加(註冊)和查找(查找)服務的 binder 引用。此配置在啟動期間由servicemanager進程讀取。
  • seapp_contexts將標籤分配給應用程序進程和/data/data目錄。 zygote進程在每次應用啟動時讀取此配置,並在installd期間安裝。
  • mac_permissions.xml根據應用程序的簽名和可選的包名稱為應用程序分配一個seinfo標記。然後可以將seinfo標記用作seapp_contexts文件中的鍵,以將特定標籤分配給具有該seinfo標記的所有應用程序。此配置在啟動期間由system_server讀取。
  • keystore2_key_contexts將標籤分配給 Keystore 2.0 命名空間。這些命名空間由 keystore2 守護程序強制執行。 Keystore 一直提供基於 UID/AID 的命名空間。 Keystore 2.0 還強制執行 sepolicy 定義的命名空間。可以在此處找到有關此文件格式和約定的詳細說明。

BoardConfig.mk 生成文件

編輯或添加策略和上下文文件後,更新您的/device/ manufacturer / device-name /BoardConfig.mk生成文件以引用sepolicy子目錄和每個新策略文件。有關BOARD_SEPOLICY變量的更多信息,請參閱system/sepolicy/README文件

BOARD_SEPOLICY_DIRS += \
        <root>/device/manufacturer/device-name/sepolicy

BOARD_SEPOLICY_UNION += \
        genfs_contexts \
        file_contexts \
        sepolicy.te

重建後,您的設備將啟用 SELinux。您現在可以自定義您的 SELinux 策略以適應您自己對 Android 操作系統的添加,如自定義中所述,或者驗證您現有的設置,如驗證中所述。

當新的策略文件和 BoardConfig.mk 更新到位時,新的策略設置會自動構建到最終的內核策略文件中。有關如何在設備上構建 sepolicy 的更多信息,請參閱構建 sepolicy

執行

開始使用 SELinux:

  1. 在內核中啟用 SELinux: CONFIG_SECURITY_SELINUX=y
  2. 更改 kernel_cmdline 或 bootconfig 參數,以便:
    BOARD_KERNEL_CMDLINE := androidboot.selinux=permissive
    BOARD_BOOTCONFIG := androidboot.selinux=permissive
    這僅用於設備策略的初始開發。在您擁有初始引導策略後,請刪除此參數,以便您的設備正在執行,否則它將導致 CTS 失敗。
  3. 以允許的方式啟動系統並查看啟動時遇到的拒絕情況:
    在 Ubuntu 14.04 或更高版本上:
    adb shell su -c dmesg | grep denied | audit2allow -p out/target/product/BOARD/root/sepolicy
    
    在 Ubuntu 12.04 上:
    adb pull /sys/fs/selinux/policy
    adb logcat -b all | audit2allow -p policy
    
  4. 評估類似於init: Warning! Service name needs a SELinux domain defined; please fix!有關說明和工具,請參閱驗證
  5. 識別需要標記的設備和其他新文件。
  6. 為您的對象使用現有的或新的標籤。查看*_contexts文件以了解以前如何標記事物,並使用對標籤含義的了解來分配新的。理想情況下,這將是一個適合策略的現有標籤,但有時需要一個新標籤,並且需要訪問該標籤的規則。將您的標籤添加到適當的上下文文件中。
  7. 識別應該有自己的安全域的域/進程。您可能需要為每個人編寫一個全新的策略。例如,從init產生的所有服務都應該有自己的。以下命令有助於顯示那些仍在運行的命令(但所有服務都需要這樣的處理):
    adb shell su -c ps -Z | grep init
    
    adb shell su -c dmesg | grep 'avc: '
    
  8. 查看init. device .rc來識別沒有域類型的任何域。在開發過程的早期給他們一個域,以避免向init添加規則或以其他方式將init訪問與他們自己的策略中的訪問混淆。
  9. 設置BOARD_CONFIG.mk以使用BOARD_SEPOLICY_*變量。有關設置的詳細信息,請參閱system/sepolicy中的自述文件。
  10. 檢查初始化。 device .rc 和 fstab。 device文件,並確保每次使用mount對應於正確標記的文件系統或指定了context= mount選項。
  11. 仔細檢查每個拒絕並創建 SELinux 策略以正確處理每個拒絕。請參閱自定義中的示例。

您應該從 AOSP 中的策略開始,然後在它們的基礎上進行您自己的自定義。有關策略策略的更多信息以及其中一些步驟的詳細信息,請參閱編寫 SELinux 策略

用例

以下是在製作您自己的軟件和相關 SELinux 策略時要考慮的漏洞利用的具體示例:

符號鏈接——因為符號鏈接以文件的形式出現,所以它們經常被當作文件讀取,這可能導致漏洞利用。例如,某些特權組件,例如init ,會更改某些文件的權限,有時會過度打開。

然後,攻擊者可能會將這些文件替換為他們控制的代碼的符號鏈接,從而允許攻擊者覆蓋任意文件。但是如果您知道您的應用程序永遠不會遍歷符號鏈接,您可以使用 SELinux 禁止它這樣做。

系統文件- 考慮只能由系統服務器修改的系統文件類。儘管如此,由於netdinitvold以 root 身份運行,它們可以訪問這些系統文件。因此,如果netd受到威脅,它可能會危及這些文件,並可能危及系統服務器本身。

使用 SELinux,您可以將這些文件識別為系統服務器數據文件。因此,對它們具有讀/寫訪問權限的唯一域是系統服務器。即使netd受到威脅,它也無法將域切換到系統服務器域並訪問那些系統文件,儘管它以 root 身份運行。

應用程序數據- 另一個示例是必須以 root 身份運行但不應訪問應用程序數據的函數類。這非常有用,因為可以做出廣泛的斷言,例如某些與應用程序數據無關的域被禁止訪問互聯網。

setattr - 對於chmodchown等命令,您可以識別相關域可以執行setattr的文件集。除此之外的任何內容都可能被禁止進行這些更改,即使是 root 也是如此。因此,應用程序可能會針對那些標記為app_data_files而不是shell_data_filessystem_data_files運行chmodchown