Questa pagina spiega come viene creata la policy SELinux. La policy SELinux viene creata dalla combinazione della policy AOSP principale (piattaforma) e della policy specifica del dispositivo (fornitore). Il flusso di creazione della policy SELinux per Android 4.4-7.0 univa tutti i frammenti di sepolicy e poi generava file monolitici nella directory principale. Ciò significava che i fornitori di SoC e i produttori ODM modificavano boot.img (per i dispositivi non A/B) o system.img (per i dispositivi A/B) ogni volta che veniva modificata la policy.
In Android 8.0 e versioni successive, la policy della piattaforma e del fornitore viene creata separatamente.
I SoC e gli OEM possono aggiornare le proprie parti della policy, creare le proprie immagini (ad esempio vendor.img e boot.img) e poi aggiornarle indipendentemente dagli aggiornamenti della piattaforma.
Tuttavia, poiché i file della policy SELinux modularizzati sono archiviati nelle partizioni /vendor, il processo init deve montare prima le partizioni system e del fornitore in modo da poter leggere i file SELinux da queste partizioni e unirli ai file SELinux principali nella directory system (prima di caricarli nel kernel).
File di origine
La logica per la creazione di SELinux si trova in questi file:
-
external/selinux: progetto SELinux esterno, utilizzato per creare le utilità della riga di comando dell'host per compilare la policy e le etichette SELinux.-
external/selinux/libselinux: Android utilizza solo un sottoinsieme del progettolibselinuxesterno insieme ad alcune personalizzazioni specifiche di Android. Per maggiori dettagli, vediexternal/selinux/README.android. -
external/selinux/libsepol: -
external/selinux/checkpolicy: compilatore della policy SELinux (eseguibili host:checkpolicy,checkmodule, edispol). Dipende dalibsepol.
-
-
system/sepolicy: configurazioni della policy SELinux di Android principali, inclusi contesti e file di policy. Anche la logica di creazione di sepolicy principale si trova qui (system/sepolicy/Android.mk).
Per maggiori dettagli sui file in system/sepolicy, vedi
File chiave.
Android 7.x e versioni precedenti
Questa sezione spiega come viene creata la policy SELinux in Android 7.x e versioni precedenti.
Processo di compilazione per Android 7.x e versioni precedenti
La policy SELinux viene creata combinando la policy AOSP principale con le personalizzazioni specifiche del dispositivo. La policy combinata viene quindi passata al compilatore della policy e a vari checker. La personalizzazione specifica del dispositivo viene eseguita tramite la variabile BOARD_SEPOLICY_DIRS definita nel file Boardconfig.mk specifico del dispositivo. Questa variabile di creazione globale contiene un elenco di directory che specificano l'ordine in cui cercare file di policy aggiuntivi.
Ad esempio, un fornitore di SoC e un ODM potrebbero aggiungere una directory ciascuno, una per le impostazioni specifiche del SoC e un'altra per le impostazioni specifiche del dispositivo, per generare le configurazioni SELinux finali per un determinato dispositivo:
BOARD_SEPOLICY_DIRS += device/SoC/common/sepolicyBOARD_SEPOLICY_DIRS += device/SoC/DEVICE/sepolicy
I contenuti dei file file_contexts in system/sepolicy e BOARD_SEPOLICY_DIRS vengono concatenati per generare file_contexts.bin sul dispositivo:

Figura 1. Logica di creazione di SELinux.
Il file sepolicy è costituito da più file di origine:
- Il testo normale
policy.confviene generato concatenandosecurity_classes,initial_sids, i file*.te,genfs_contextseport_contextsin questo ordine. - Per ogni file (ad esempio
security_classes), il contenuto è la concatenazione dei file con lo stesso nome insystem/sepolicy/eBOARDS_SEPOLICY_DIRS. - Il
policy.confviene inviato al compilatore SELinux per il controllo della sintassi e compilato in formato binario comesepolicysul dispositivo.
Figura 2. File della policy SELinux.
File SELinux
Dopo la compilazione, i dispositivi Android con 7.x e versioni precedenti in genere contengono i seguenti file correlati a SELinux:
selinux_versionsepolicy: output binario dopo la combinazione dei file di policy (ad esempiosecurity_classes,initial_sids, e*.te)file_contextsproperty_contextsseapp_contextsservice_contextssystem/etc/mac_permissions.xml
Per maggiori dettagli, vedi Implementare SELinux.
Inizializzazione di SELinux
All'avvio del sistema, SELinux è in modalità permissiva (e non in modalità di applicazione). Il processo di inizializzazione esegue le seguenti attività:
- Carica i file
sepolicydal ramdisk nel kernel tramite/sys/fs/selinux/load. - Imposta SELinux in modalità di applicazione.
- Esegue
re-exec()per applicare la regola del dominio SELinux a se stesso.
Per ridurre il tempo di avvio, esegui re-exec() sul processo init il prima possibile.
Android 8.0 e versioni successive
In Android 8.0, la policy SELinux è suddivisa in componenti della piattaforma e del fornitore per consentire aggiornamenti indipendenti della policy della piattaforma e del fornitore, mantenendo al contempo la compatibilità.
La sepolicy della piattaforma è ulteriormente suddivisa in parti private e pubbliche della piattaforma per esportare tipi e attributi specifici agli autori della policy del fornitore. È garantito che i tipi/attributi pubblici della piattaforma vengano mantenuti come API stabili per una determinata versione della piattaforma. La compatibilità con i tipi/attributi pubblici della piattaforma precedenti può essere garantita per diverse versioni utilizzando i file di mapping della piattaforma.
Processo di compilazione per Android 8.0
La policy SELinux in Android 8.0 viene creata combinando parti di /system e /vendor. La logica per configurarla
correttamente si trova in
/platform/system/sepolicy/Android.bp.
La policy esiste nelle seguenti posizioni:
| Località | Contiene |
|---|---|
system/sepolicy/public |
API sepolicy della piattaforma |
system/sepolicy/private |
Dettagli di implementazione della piattaforma (i fornitori possono ignorarli) |
system/sepolicy/vendor |
File di policy e di contesto che i fornitori possono utilizzare (i fornitori possono ignorarli) |
BOARD_SEPOLICY_DIRS |
Sepolicy del fornitore |
BOARD_ODM_SEPOLICY_DIRS (Android 9 e versioni successive) |
Sepolicy ODM |
SYSTEM_EXT_PUBLIC_SEPOLICY_DIRS (Android 11 e versioni successive) |
API sepolicy system_ext |
SYSTEM_EXT_PRIVATE_SEPOLICY_DIRS (Android 11 e versioni successive) |
Dettagli di implementazione di system_ext (i fornitori possono ignorarli) |
PRODUCT_PUBLIC_SEPOLICY_DIRS (Android 11 e versioni successive) |
API sepolicy del prodotto |
PRODUCT_PRIVATE_SEPOLICY_DIRS (Android 11 e versioni successive) |
Dettagli di implementazione del prodotto (i fornitori possono ignorarli) |
Il sistema di compilazione prende questa policy e produce i componenti della policy system, system_ext,
product, vendor e odm nella
partizione corrispondente. I passaggi includono:
- Converti le policy nel formato SELinux Common Intermediate Language (CIL)
, in particolare:
- Policy della piattaforma pubblica (
system,system_ext,product) - Policy privata e pubblica combinata
- Policy pubblica, del fornitore e
BOARD_SEPOLICY_DIRS
- Policy della piattaforma pubblica (
- Applica la versione della policy fornita come parte della policy del fornitore.
Utilizza la policy CIL pubblica prodotta per informare la policy combinata pubblica e
del fornitore e
BOARD_SEPOLICY_DIRSsu quali parti devono essere trasformate in attributi collegati alla policy della piattaforma. - Crea un file di mapping che colleghi le parti della piattaforma e del fornitore. Inizialmente, questo collega solo i tipi della policy pubblica con gli attributi corrispondenti nella policy del fornitore; in seguito fornisce anche la base per il file mantenuto nelle versioni future della piattaforma, consentendo la compatibilità con la policy del fornitore che ha come target questa versione della piattaforma.
- Combina i file di policy (descrivi le soluzioni on-device e precompilate).
- Combina la policy di mapping, della piattaforma e del fornitore.
- Compila il file della policy binaria di output.
Sepolicy pubblica della piattaforma
La sepolicy pubblica della piattaforma include tutto ciò che è definito in
system/sepolicy/public. La piattaforma può presupporre che i tipi e gli attributi definiti nella policy pubblica siano API stabili per una determinata versione della piattaforma. Questa costituisce la parte della sepolicy esportata dalla piattaforma su cui gli sviluppatori della policy del fornitore (ovvero del dispositivo) possono scrivere policy aggiuntive specifiche del dispositivo.
I tipi sono versionati in base alla versione della policy per cui vengono scritti i file del fornitore, definita dalla variabile di creazione PLATFORM_SEPOLICY_VERSION. La policy pubblica versionata viene quindi inclusa nella policy del fornitore e (nella sua forma originale) nella policy della piattaforma. Pertanto, la policy finale include la policy della piattaforma privata, la sepolicy pubblica della piattaforma corrente, la policy specifica del dispositivo e la policy pubblica versionata corrispondente alla versione della piattaforma per cui è stata scritta la policy del dispositivo.
Sepolicy privata della piattaforma
La sepolicy privata della piattaforma include tutto ciò che è definito in
/system/sepolicy/private. Questa parte della policy forma tipi, autorizzazioni e attributi solo della piattaforma necessari per la funzionalità della piattaforma. Questi non vengono esportati agli autori della policy del fornitore e del dispositivo. Gli autori della policy non della piattaforma non devono scrivere le proprie estensioni della policy in base a tipi, attributi e regole definiti nella sepolicy privata della piattaforma. Inoltre, queste regole possono essere modificate o potrebbero scomparire nell'ambito di un aggiornamento solo del framework.
Mapping privato della piattaforma
Il mapping privato della piattaforma include le istruzioni della policy che mappano gli attributi esposti nella policy pubblica della piattaforma delle versioni precedenti della piattaforma ai tipi concreti utilizzati nella sepolicy pubblica della piattaforma corrente. In questo modo, la policy del fornitore scritta in base agli attributi pubblici della piattaforma delle versioni precedenti della sepolicy pubblica della piattaforma continua a funzionare. Il versioning si basa sulla variabile di creazione PLATFORM_SEPOLICY_VERSION impostata in AOSP per una determinata versione della piattaforma. Esiste un file di mapping separato per ogni versione precedente della piattaforma da cui si prevede che questa piattaforma accetti la policy del fornitore. Per maggiori dettagli, vedi
Compatibilità delle policy.
Android 11 e versioni successive
Questa sezione spiega come viene creata la policy SELinux in Android 11 e versioni successive.
Sepolicy system_ext e del prodotto
In Android 11 vengono aggiunte la policy system_ext e la policy product. Come la sepolicy della piattaforma, la policy system_ext e la policy product sono suddivise in policy pubblica e policy privata.
La policy pubblica viene esportata al fornitore. I tipi e gli attributi diventano API stabili e la policy del fornitore può fare riferimento a tipi e attributi nella policy pubblica. I tipi sono versionati in base a PLATFORM_SEPOLICY_VERSION e la policy versionata viene inclusa nella policy del fornitore. La policy originale viene inclusa in ogni partizione system_ext e product.
La policy privata contiene tipi, autorizzazioni e attributi solo di system_ext e solo di product necessari per la funzionalità delle partizioni system_ext e product.
La policy privata non è visibile al fornitore, il che implica che queste regole sono interne e possono essere modificate.
Mapping system_ext e del prodotto
system_ext e product possono esportare i tipi pubblici designati al fornitore. Tuttavia, ogni partner ha la responsabilità di mantenere la compatibilità. Per la compatibilità, i partner possono fornire i propri file di mapping che mappano gli attributi versionati delle versioni precedenti ai tipi concreti utilizzati nella sepolicy pubblica corrente:
- Per installare un file di mapping per
system_ext, inserisci un file CIL contenente le informazioni di mapping desiderate in{SYSTEM_EXT_PRIVATE_SEPOLICY_DIRS}/compat/{ver}/{ver}.cil, quindi aggiungisystem_ext_{ver}.cilaPRODUCT_PACKAGES. - Per installare un file di mapping per
product, inserisci un file CIL contenente le informazioni di mapping desiderate in{PRODUCT_PRIVATE_SEPOLICY_DIRS}/compat/{ver}/{ver}.cil, quindi aggiungiproduct_{ver}.cilaPRODUCT_PACKAGES.
Fai riferimento a un
esempio
che aggiunge un file di mapping della partizione product di un dispositivo Redbull.
Policy SELinux precompilata
Prima che init attivi SELinux, init raccoglie tutti i file CIL dalle partizioni
(system, system_ext, product, vendor e
odm) e li compila in una policy binaria, il formato che può essere caricato nel kernel. Poiché la compilazione richiede tempo (in genere 1-2 secondi), i file CIL vengono precompilati in fase di compilazione e inseriti in /vendor/etc/selinux/precompiled_sepolicy o /odm/etc/selinux/precompiled_sepolicy, insieme agli hash sha256 dei file CIL di input. In fase di runtime, init verifica se uno dei file di policy è stato aggiornato confrontando gli hash. Se non sono state apportate modifiche, init carica la policy precompilata. In caso contrario, init compila al volo e la utilizza al posto di quella precompilata.
Più nello specifico, la policy precompilata viene utilizzata se sono soddisfatte tutte le seguenti condizioni. Qui, {partition} rappresenta la partizione in cui esiste la policy precompilata: vendor o odm.
- Esistono sia
/system/etc/selinux/plat_sepolicy_and_mapping.sha256sia/{partition}/etc/selinux/precompiled_sepolicy.plat_sepolicy_and_mapping.sha256e sono identici. - Non esistono sia
/system_ext/etc/selinux/system_ext_sepolicy_and_mapping.sha256sia/{partition}/etc/selinux/precompiled_sepolicy.system_ext_sepolicy_and_mapping.sha256. Oppure esistono entrambi e sono identici. - Non esistono sia
/product/etc/selinux/product_sepolicy_and_mapping.sha256sia/{partition}/etc/selinux/precompiled_sepolicy.product_sepolicy_and_mapping.sha256. Oppure esistono entrambi e sono identici.
Se uno di questi è diverso, init torna al percorso di compilazione on-device. Per maggiori dettagli, vedi
system/core/init/selinux.cpp.