Cette page explique comment la règle SELinux est créée. La règle SELinux est créée à partir de la combinaison de la règle AOSP de base (plate-forme) et de la règle spécifique à l'appareil (fournisseur). Le flux de compilation des règles SELinux pour Android 4.4 à Android 7.0 fusionnait tous les fragments sepolicy, puis générait des fichiers monolithiques dans le répertoire racine. Cela signifiait que les fournisseurs de SoC et les fabricants d'ODM modifiaient boot.img
(pour les appareils non A/B) ou system.img
(pour les appareils A/B) chaque fois que la règle était modifiée.
Dans Android 8.0 et versions ultérieures, les règles de la plate-forme et du fournisseur sont créées séparément.
Les SoC et les OEM peuvent mettre à jour leurs sections de la règle, créer leurs images (par exemple, vendor.img
et boot.img
), puis mettre à jour ces images indépendamment des mises à jour de la plate-forme.
Toutefois, comme les fichiers de règles SELinux modularisés sont stockés sur les partitions /vendor
, le processus init
doit monter les partitions système et fournisseur plus tôt afin de pouvoir lire les fichiers SELinux de ces partitions et les fusionner avec les fichiers SELinux principaux du répertoire système (avant de les charger dans le noyau).
Fichiers sources
La logique de création de SELinux se trouve dans les fichiers suivants :
-
external/selinux
: projet SELinux externe, utilisé pour créer des utilitaires de ligne de commande HOST afin de compiler les règles et les libellés SELinux.-
external/selinux/libselinux
: Android n'utilise qu'un sous-ensemble du projetlibselinux
externe, ainsi que certaines personnalisations spécifiques à Android. Pour en savoir plus, consultezexternal/selinux/README.android
. -
external/selinux/libsepol
: -
external/selinux/checkpolicy
: compilateur de règles SELinux (exécutables hôtes :checkpolicy
,checkmodule
, etdispol
). Dépend delibsepol
.
-
-
system/sepolicy
: configurations de la stratégie SELinux Android de base, y compris les contextes et les fichiers de stratégie. La logique de compilation sepolicy majeure se trouve également ici (system/sepolicy/Android.mk
).
Pour en savoir plus sur les fichiers dans system/sepolicy
, consultez Implémenter SELinux.
Android 7.x et versions antérieures
Cette section explique comment la règle SELinux est créée dans Android 7.x et versions antérieures.
Processus de compilation pour Android 7.x et versions antérieures
La règle SELinux est créée en combinant la règle AOSP de base avec des personnalisations spécifiques à l'appareil. La règle combinée est ensuite transmise au compilateur de règles et à différents vérificateurs. La personnalisation spécifique à l'appareil s'effectue via la variable BOARD_SEPOLICY_DIRS
définie dans le fichier Boardconfig.mk
spécifique à l'appareil. Cette variable de compilation globale contient une liste de répertoires qui spécifient l'ordre dans lequel rechercher des fichiers de règles supplémentaires.
Par exemple, un fournisseur de SoC et un ODM peuvent chacun ajouter un répertoire, l'un pour les paramètres spécifiques au SoC et l'autre pour les paramètres spécifiques à l'appareil, afin de générer les configurations SELinux finales pour un appareil donné :
BOARD_SEPOLICY_DIRS += device/SOC/common/sepolicy
BOARD_SEPOLICY_DIRS += device/SoC/DEVICE/sepolicy
Le contenu des fichiers file_contexts dans system/sepolicy
et BOARD_SEPOLICY_DIRS
est concaténé pour générer le fichier file_contexts.bin
sur l'appareil :

Figure 1 : Logique de compilation SELinux.
Le fichier sepolicy
se compose de plusieurs fichiers sources :
- Le fichier
policy.conf
en texte brut est généré en concaténant les fichierssecurity_classes
,initial_sids
,*.te
,genfs_contexts
etport_contexts
dans cet ordre. - Pour chaque fichier (par exemple,
security_classes
), son contenu correspond à la concaténation des fichiers portant le même nom soussystem/sepolicy/
etBOARDS_SEPOLICY_DIRS
. - Le fichier
policy.conf
est envoyé au compilateur SELinux pour vérification de la syntaxe et compilé au format binaire en tant quesepolicy
sur l'appareil.Figure 2. Fichier de règles SELinux.
Fichiers SELinux
Après compilation, les appareils Android 7.x et versions antérieures contiennent généralement les fichiers SELinux suivants :
selinux_version
- sepolicy : sortie binaire après la combinaison des fichiers de règles (par exemple,
security_classes
,initial_sids
et*.te
) file_contexts
property_contexts
seapp_contexts
service_contexts
system/etc/mac_permissions.xml
Pour en savoir plus, consultez Implémenter SELinux.
Initialisation de SELinux
Au démarrage du système, SELinux est en mode permissif (et non en mode d'application forcée). Le processus init effectue les tâches suivantes :
- Charge les fichiers
sepolicy
du disque RAM dans le noyau via/sys/fs/selinux/load
. - Passe SELinux en mode d'application.
- Exécute
re-exec()
pour appliquer la règle de domaine SELinux à lui-même.
Pour réduire le temps de démarrage, effectuez le re-exec()
sur le processus init
dès que possible.
Android 8.0 ou version ultérieure
Dans Android 8.0, la règle SELinux est divisée en composants de plate-forme et de fournisseur pour permettre des mises à jour indépendantes des règles de plate-forme/fournisseur tout en maintenant la compatibilité.
La plate-forme sepolicy est en outre divisée en parties privées et publiques pour exporter des types et des attributs spécifiques vers les rédacteurs de règles du fournisseur. Les types/attributs publics de la plate-forme sont garantis comme étant des API stables pour une version donnée de la plate-forme. La compatibilité avec les types/attributs publics de la plate-forme précédente peut être garantie pour plusieurs versions à l'aide de fichiers de mappage de plate-forme.
Processus de compilation pour Android 8.0
La règle SELinux dans Android 8.0 est créée en combinant des éléments de /system
et /vendor
. La logique pour configurer cela correctement se trouve dans
/platform/system/sepolicy/Android.mk
.
La règle existe aux emplacements suivants :
Position | Contient |
---|---|
system/sepolicy/public |
API sepolicy de la plate-forme |
system/sepolicy/private |
Détails de l'implémentation de la plate-forme (les fournisseurs peuvent les ignorer) |
system/sepolicy/vendor |
Fichiers de règles et de contexte que les fournisseurs peuvent utiliser (ils peuvent les ignorer s'ils le souhaitent) |
BOARD_SEPOLICY_DIRS |
sepolicy du fournisseur |
BOARD_ODM_SEPOLICY_DIRS (Android 9 ou version ultérieure) |
Odm sepolicy |
SYSTEM_EXT_PUBLIC_SEPOLICY_DIRS (Android 11 et versions ultérieures) |
API sepolicy de system_ext |
SYSTEM_EXT_PRIVATE_SEPOLICY_DIRS (Android 11 et versions ultérieures) |
Détails d'implémentation de system_ext (les fournisseurs peuvent les ignorer) |
PRODUCT_PUBLIC_SEPOLICY_DIRS (Android 11 et versions ultérieures) |
API sepolicy du produit |
PRODUCT_PRIVATE_SEPOLICY_DIRS (Android 11 et versions ultérieures) |
Informations sur l'implémentation du produit (les fournisseurs peuvent les ignorer) |
Le système de compilation prend cette stratégie et produit des composants de stratégie système, system_ext, produit, fournisseur et odm sur la partition correspondante. Voici les étapes à suivre :
- Conversion des règles au format SELinux Common Intermediate Language (CIL), plus précisément :
- Règles publiques de la plate-forme (système + extension système + produit)
- Règles combinées (privées et publiques)
BOARD_SEPOLICY_DIRS
: règles publiques et relatives aux fournisseurs
- Gestion des versions de la règle fournie par le public dans le cadre de la règle du fournisseur.
Pour ce faire, la règle CIL publique produite est utilisée pour informer la règle combinée publique + fournisseur +
BOARD_SEPOLICY_DIRS
sur les parties qui doivent être transformées en attributs qui seront liés à la règle de la plate-forme. - Créer un fichier de mappage qui associe les parties de la plate-forme et du fournisseur. Dans un premier temps, cela associe simplement les types de la règle publique aux attributs correspondants de la règle du fournisseur. Par la suite, cela servira également de base au fichier conservé dans les futures versions de la plate-forme, ce qui permettra la compatibilité avec la règle du fournisseur ciblant cette version de la plate-forme.
- Combiner des fichiers de règles (décrivez les solutions sur l'appareil et précompilées).
- Combinez les règles de mappage, de plate-forme et du fournisseur.
- Compilez le fichier de stratégie binaire de sortie.
Stratégie de sécurité publique de la plate-forme
La règle de sécurité publique de la plate-forme inclut tout ce qui est défini sous
system/sepolicy/public
. La plate-forme peut supposer que les types et les attributs définis dans le règlement sont des API stables pour une version donnée de la plate-forme. Cela constitue la partie de la stratégie SELinux qui est exportée par la plate-forme sur laquelle les développeurs de stratégies de fournisseur (c'est-à-dire d'appareil) peuvent écrire des stratégies supplémentaires spécifiques à l'appareil.
Les types sont versionnés en fonction de la version de la règle par rapport à laquelle les fichiers du fournisseur sont écrits, définie par la variable de compilation PLATFORM_SEPOLICY_VERSION
. La version de la règle publique est ensuite incluse dans la règle du fournisseur et (dans sa forme d'origine) dans la règle de la plate-forme. Ainsi, la règle finale inclut la règle de plate-forme privée, la règle sepolicy publique de la plate-forme actuelle, la règle spécifique à l'appareil et la règle publique versionnée correspondant à la version de la plate-forme pour laquelle la règle de l'appareil a été rédigée.
sepolicy privé de la plate-forme
La stratégie SE privée de la plate-forme inclut tout ce qui est défini sous
/system/sepolicy/private
. Cette partie du règlement définit les types, les autorisations et les attributs propres à la plate-forme requis pour la fonctionnalité de la plate-forme. Ces informations ne sont pas exportées vers les rédacteurs du règlement vendor/device
. Les rédacteurs de règles non liés à la plate-forme ne doivent pas rédiger leurs extensions de règles en fonction des types/attributs/règles définis dans la stratégie SE privée de la plate-forme. De plus, ces règles peuvent être modifiées ou disparaître dans le cadre d'une mise à jour du framework uniquement.
Mappage privé de la plate-forme
Le mappage privé de la plate-forme inclut des instructions de règles qui mappent les attributs exposés dans les règles publiques de la plate-forme des versions précédentes de la plate-forme aux types concrets utilisés dans les règles publiques de la plate-forme actuelle. Cela garantit que la règle du fournisseur qui a été rédigée en fonction des attributs publics de la plate-forme à partir des versions précédentes de la stratégie de sécurité publique de la plate-forme continue de fonctionner. La gestion des versions est basée sur la variable de compilation PLATFORM_SEPOLICY_VERSION
définie dans AOSP pour une version de plate-forme donnée. Un fichier de mappage distinct existe pour chaque version précédente de la plate-forme à partir de laquelle cette plate-forme est censée accepter les règles du fournisseur. Pour en savoir plus, consultez Compatibilité.
Android 11 ou version ultérieure
system_ext et sepolicy du produit
Dans Android 11, les règles system_ext et produit sont ajoutées. Comme la stratégie sepolicy de la plate-forme, les stratégies system_ext et produit sont divisées en stratégies publiques et privées.
Les règles publiques sont exportées vers le fournisseur. Les types et les attributs deviennent une API stable, et le règlement du fournisseur peut faire référence aux types et aux attributs dans le règlement public. Les types sont versionnés selon PLATFORM_SEPOLICY_VERSION
, et la règle versionnée est incluse dans la règle du fournisseur. La stratégie d'origine est incluse dans chaque partition system_ext et produit.
La politique de confidentialité contient des types, des autorisations et des attributs system_ext et produit uniquement, qui sont nécessaires au fonctionnement des partitions system_ext et produit. Les règles privées ne sont pas visibles par le fournisseur, ce qui implique qu'elles sont internes et peuvent être modifiées.
Mappage system_ext et produit
system_ext et product sont autorisés à exporter leurs types publics désignés vers vendor. Toutefois, chaque partenaire est responsable du maintien de la compatibilité. Pour assurer la compatibilité, les partenaires peuvent fournir leurs propres fichiers de mappage qui associent les attributs versionnés des versions précédentes aux types concrets utilisés dans la stratégie SELinux publique actuelle.
- Pour installer un fichier de mappage pour system_ext, placez un fichier cil contenant les informations de mappage souhaitées dans
{SYSTEM_EXT_PRIVATE_SEPOLICY_DIRS}/compat/{ver}/{ver}.cil
, puis ajoutezsystem_ext_{ver}.cil
àPRODUCT_PACKAGES
. - Pour installer un fichier de mappage pour un produit, placez un fichier cil contenant les informations de mappage souhaitées dans
{PRODUCT_PRIVATE_SEPOLICY_DIRS}/compat/{ver}/{ver}.cil
, puis ajoutezproduct_{ver}.cil
àPRODUCT_PACKAGES
.
Consultez cet exemple qui ajoute un fichier de mappage de la partition produit de l'appareil Red Bull.
Règle SELinux précompilée
Avant d'activer SELinux, init
collecte tous les fichiers CIL des partitions (system
, system_ext
, product
, vendor
et odm
) et les compile en une règle binaire, le format qui peut être chargé dans le noyau.init
Comme la compilation prend du temps (généralement une à deux secondes), les fichiers CIL sont précompilés au moment de la compilation et placés dans /vendor/etc/selinux/precompiled_sepolicy
ou /odm/etc/selinux/precompiled_sepolicy
, avec les hachages sha256 des fichiers CIL d'entrée. Lors de l'exécution, init
vérifie si l'un des fichiers de règles a été mis à jour en comparant les hachages. Si rien n'a changé, init
charge la stratégie précompilée. Sinon, init
compile à la volée et l'utilise à la place de celui précompilé.
Plus précisément, une règle précompilée est utilisée si toutes les conditions suivantes sont remplies. Ici, {partition}
représente la partition dans laquelle la règle précompilée existe : vendor
ou odm
.
-
/system/etc/selinux/plat_sepolicy_and_mapping.sha256
et/{partition}/etc/selinux/precompiled_sepolicy.plat_sepolicy_and_mapping.sha256
existent et sont identiques. -
/system_ext/etc/selinux/system_ext_sepolicy_and_mapping.sha256
et/{partition}/etc/selinux/precompiled_sepolicy.system_ext_sepolicy_and_mapping.sha256
n'existent pas. Ou les deux existent et sont identiques. -
/product/etc/selinux/product_sepolicy_and_mapping.sha256
et/{partition}/etc/selinux/precompiled_sepolicy.product_sepolicy_and_mapping.sha256
n'existent pas. Ou les deux existent et sont identiques.
Si l'une d'elles est différente, init
revient au chemin de compilation sur l'appareil. Pour en savoir plus, consultez
system/core/init/selinux.cpp
.