# SELinux: Gestion d'un système SELinux (avancé) SELinux (Security Enhanced Linux) est un système de contrôle d'accès obligatoire (Mandatory Access Control) qui s'appuie sur l'interface Linux Security Modules fournie par le noyau Linux. Concrètement, le noyau interroge SELinux avant chaque appel système pour savoir si le processus est autorisé à effectuer l'opération concernée. SELinux s'appuie sur un ensemble de règles (policy) pour autoriser ou interdire une opération. Ces règles sont assez délicates à créer, mais heureusement deux jeux de règles standards (targeted et strict) sont fournies pour éviter le plus gros du travail de configuration. Le système de permissions de SELinux est totalement différent de ce qu'offre un système Unix traditionnel. Les droits d'un processus dépendent de son contexte de sécurité. Le contexte est défini par l'identité de celui qui a démarré le processus, le rôle et le domaine qu'il avait à ce moment. Les permissions proprement dites dépendent du domaine, mais les transitions entre les domaines sont contrôlées par les rôles. Enfin, les transitions autorisées entre rôles dépendent de l'identité. # Mise en route Le code de SELinux est intégré dans les noyaux standards fournis par Debian et les programmes Unix de base le gèrent sans modification. Il est donc relativement simple d'activer SELinux. La commande **apt install selinux-basics selinux-policy-default** installera automatiquement les paquets nécessaires pour configurer un système SELinux. Le paquet **selinux-policy-default** contient un ensemble de règles standards. Par défaut, l'ensemble de règles ne restreint les accès que pour certains services très exposés. Les sessions utilisateur ne sont pas restreintes et il n'y a donc que peu de risques que SELinux bloque des opérations légitimes des utilisateurs. En revanche, cela permet d'apporter un surcroît de sécurité pour les services système fonctionnant sur la machine. Pour obtenir l'équivalent des anciennes règles « strictes », il faut simplement désactiver le module unconfined (la gestion des modules est détaillée plus loin). Une fois les règles installées, il reste à étiqueter tous les fichiers disponibles (il s'agit de leur affecter un type). C'est une opération qu'il faut déclencher manuellement avec **fixfiles relabel**. Le système SELinux est prêt, il ne reste plus qu'à l'activer. Pour cela, il faut passer le paramètre **selinux=1 security=selinux** au noyau Linux. Le paramètre **audit=1** active les traces SELinux qui enregistrent les différentes opérations qui ont été refusées. Enfin, le paramètre **enforcing=1** permet de mettre en application l'ensemble des règles : en effet, par défaut SELinux fonctionne en mode permissive où les actions interdites sont tracées mais malgré tout autorisées. Il faut donc modifier le fichier de configuration du chargeur de démarrage GRUB pour ajouter les paramètres désirés. Le plus simple pour cela est de modifier la variable **GRUB\_CMDLINE\_LINUX** dans `/etc/default/grub` et d'exécuter **update-grub**. Au démarrage suivant, SELinux sera actif. Le script **selinux-activate** automatise ces opérations et permet de forcer un étiquetage au prochain redémarrage, ce qui évite d'avoir des fichiers non étiquetés créés alors que SELinux n'était pas encore actif et que l'étiquetage était en cours. # Gestion d'un système SELinux L'ensemble de règles SELinux est modulaire et son installation détecte et active automatiquement tous les modules pertinents en fonction des services déjà installés. Ainsi, le système est immédiatement fonctionnel. Toutefois, lorsqu'un service est installé après les règles SELinux, il faut pouvoir activer manuellement un module de règles. C'est le rôle de la commande semodule. En outre, il faut pouvoir définir les rôles accessibles à chaque utilisateur ; pour cela c'est la commande semanage qu'il faudra utiliser. Ces deux commandes modifient donc la configuration SELinux courante qui est stockée dans /etc/selinux/default/. Contrairement à ce qui se pratique d'habitude avec les fichiers de configuration de /etc/, ces fichiers ne doivent pas être modifiés manuellement. Il faut les manipuler en utilisant les programmes prévus pour cela. # Gestion des modules SELinux Les modules SELinux disponibles sont stockés dans le répertoire /usr/share/selinux/default/. Pour activer un de ces modules dans la configuration courante, il faut employer **semodule -i module.pp.bz2**. L'extension pp.bz2 signifie policy package que l'on pourrait traduire par « paquet de règles » (comprimé avec bzip2). À l'inverse, la commande **semodule -r module** retire un module de la configuration courante. Enfin, la commande **semodule -l** liste les modules qui sont actuellement installés. La commande inclut également le numéro de version du module. # semodule -i /usr/share/selinux/default/abrt.pp.bz2 # semodule -l abrt 1.5.0 Disabled accountsd 1.1.0 acct 1.6.0 [...] # semodule -e abrt # semodule -d accountsd # semodule -l abrt 1.5.0 accountsd 1.1.0 Disabled acct 1.6.0 [...] # semodule -r abrt # semodule -l accountsd 1.1.0 Disabled acct 1.6.0 [...] **semodule** recharge immédiatement la nouvelle configuration, sauf si l'on utilise l'option -n. Signalons également que le programme modifie par défaut la configuration courante (celle indiquée par la variable SELINUXTYPE dans `/etc/selinux/config`) mais qu'on peut en modifier une autre grâce à l'option -s. # Gestion des identités Chaque fois qu'un utilisateur se connecte, il se voit attribuer une identité SELinux, qui va définir les rôles qu'il va pouvoir assumer. Ces deux correspondances (de l'utilisateur vers l'identité SELinux et de cette identité vers les rôles) se configurent grâce à la commande semanage. On retrouvera des options communes aux différentes sous-commandes : * -a pour ajouter: **semanage login -a -s user\_u utilisateur** va associer l'identité user\_u à l'utilisateur * -d pour supprimer : **semanage login -d utilisateur** va retirer la correspondance affectée à l'utilisateur * -m pour modifier * -l pour lister : **semanage login -l** liste les correspondances existantes entre identifiants d'utilisateurs et identités SELinux. Si un utilisateur n'a pas de correspondance explicite, il aura l'identité indiquée en face de \_\_default\_\_. **semanage user -l** liste les correspondances entre identité SELinux et rôles possibles. * -t pour indiquer un type (ou domaine). # Gestion des contextes de fichiers, des ports et des booléens Chaque module SELinux fournit un ensemble de règles d'étiquetage des fichiers, mais il est également possible de rajouter des règles d'étiquetage spécifiques afin de les adapter à un cas particulier. Ainsi, pour rendre toute l'arborescence /srv/www/ accessible au serveur web, on pourrait exécuter **semanage fcontext -a -t httpd\_sys\_content\_t "/srv/www(/.\*)\?"** , puis **restorecon -R /srv/www/**. * La première commande enregistre la nouvelle règle d'étiquetage * la seconde restaure les bonnes étiquettes en fonction des règles enregistrées. D'une manière similaire, les ports TCP/UDP sont étiquetés afin que seuls les démons correspondants puissent y écouter. Ainsi, si l'on veut que le serveur web puisse également écouter sur le port 8080, il faut exécuter la commande **semanage port -m -t http\_port\_t -p tcp 8080**. Les modules SELinux exportent parfois des options booléennes qui influencent le comportement des règles. L'utilitaire **getsebool** permet de consulter l'état de ces options (**getsebool booléen** affiche une option et **getsebool -a** les affiche toutes). La commande **setsebool booléen valeur** change la valeur courante d'une option. L'option -P rend le changement permanent, autrement dit la nouvelle valeur sera celle par défaut et sera conservée au prochain redémarrage. L'exemple ci-dessous permet au serveur web d'accéder aux répertoires personnels des utilisateurs (utile dans le cas où ils ont des sites web personnels dans ~/public_html/ par exemple). # getsebool httpd_enable_homedirs httpd_enable_homedirs --> off # setsebool -P httpd_enable_homedirs on # getsebool httpd_enable_homedirs httpd_enable_homedirs --> on # Adaptation des règles Comme l'ensemble des règles (que l'on nomme policy) est modulaire, on peut développer de nouveaux modules pour les applications (éventuellement spécifiques) qui n'en disposent pas encore, ces nouveaux modules venant alors compléter la reference policy. Trois fichiers permettent de définir un nouveau module (Le paquet selinux-policy-dev sera également nécessaire) : * **Le fichier .fc** définit les « contextes des fichiers », autrement dit les types affectés aux fichiers relatifs à ce module. Les informations du .fc sont utilisées lors de l'étiquetage des fichiers sur le disque. * **Le fichier .if** définit l'interface du module ; il s'agit d'un ensemble de « fonctions publiques » qui permettent à d'autres modules de s'interfacer proprement avec celui en cours de création. * **Le fichier .te** est le plus important : il définit les règles à proprement parler. ## Rédiger un fichier .fc La lecture de l'exemple qui suit suffit à comprendre la structure d'un tel fichier. Il est possible d'employer une expression rationnelle pour affecter le même contexte à plusieurs fichiers, voire à toute une arborescence. # myapp executable will have: # label: system_u:object_r:myapp_exec_t # MLS sensitivity: s0 # MCS categories: /usr/sbin/myapp -- gen_context(system_u:object_r:myapp_exec_t,s0) ## Rédiger un fichier .if Dans l'exemple suivant, la première interface (myapp\_domtrans) sert à contrôler qui a le droit d'exécuter l'application et la seconde (myapp\_read\_log) fournit un droit de lecture sur les fichiers de logs de l'application. Chaque interface doit générer un ensemble correct de règles comme s'il était directement placé dans un fichier .te. Il faut donc déclarer tous les types employés (avec la macro gen\_require) et employer les directives standards pour attribuer des droits. Notons toutefois qu'il est possible d'employer des interfaces fournies par d'autres modules. ## Myapp example policy ## ##

## More descriptive text about myapp. The ## tag can also use

,