Administration Unix - CM séance 13
12. Droits étendus : les ACLs
On a vu au 1er semestre la gestion des droits avec chmod
.
Problème : on veut donner à des utilisateurs des droits sur certains fichiers. Une solution est de créer un groupe, de le rendre propriétaire des fichiers, et de rajouter ce groupe aux utilisateurs. L'inconvénient, lorsqu'il y a beaucoup d'utilisateurs, est une multiplication des groupes.
Une autre solution, plus souple, est d'utiliser les "droits étendus" : les ACL (Access Control List).
Les ACL ont été inventées dans le système Multics en 1965, et existent sous différentes formes : dans les systèmes Unix, sous MacOS, Windows, Active Directory, NFSv4, et même SQL !
En ce qui concerne les fichiers Unix, les ACL sont normalisés POSIX, et sont disponibles dans la plupart des systèmes de fichiers récents.
12.1. Gestion des droits étendus
L'idée consiste à rajouter les mêmes triplets (rwx
) de droits, mais pour
d'autres utilisateurs ou d'autres groupes que les propriétaires du fichier.
La lecture étendue habituelle d'un répertoire (ls -l
) indiquera seulement qu'il
existe des ACLs avec un "+
" à la fin : (exemple plus loin)
$ ls -l toto
-rw-rwx---+ 1 thiel thiel 8 sept. 25 14:37 toto*
Les ACLs seront représentées sous l'une des formes suivantes :
u:username:rwx ou user:username:rwx
g:groupname:rwx ou group:groupname:rwx
o:rwx ou other:rwx
m:rwx ou mask:rwx
Deux commandes permettent de manipuler les ACLs :
getfacl
pour lister les ACLs ;setfacl
pour les positionner (ou les effacer).
Leurs options principales sont les suivantes :
-
getfacl
:-n affiche les uid et gid au lieu des noms -t affiche les informations tabulées -R réalise un affichage récursif sur un répertoire.
-
setfacl
:-x acl file supprime l'acl de file -b file supprime toutes les acls de file -m acl file modifie (ou ajoute acl) à file –h affiche une aide
Exemple :
$ umask 027
$ echo "bonjour" > toto
$ ls -l toto
-rw-r----- 1 thiel thiel 8 sept. 25 14:37 toto
$ getfacl toto
# file: toto
# owner: thiel
# group: thiel
user::rw-
group::r--
other::---
# On rajoute un utilisateur dupond
$ sudo adduser dupond
...
# On rajoute des droits pour l'utilisateur dupond
$ setfacl -m u:dupond:rwx toto
# Remarque : si l'utilisateur n'existe pas on aurait eu
$ setfacl -m u:bidon:rwx toto
setfacl : Option -m : Argument invalide près du caractère 3
$ ls -l toto
-rw-rwx---+ 1 thiel thiel 8 sept. 25 14:37 toto*
# le + signifie qu'il y a des ACL
# le * signifie que c'est un exécutable (car on a rajouté x avec setfacl)
$ getfacl toto
# file: toto
# owner: thiel
# group: thiel
user::rw-
user:dupond:rwx # ça a marché
group::r--
mask::rwx
other::---
On peut aussi préciser un "masque de droits effectifs", qui définit quels sont les droits maximaux pour tous les groupes et utilisateurs (sauf pour le propriétaire) :
$ setfacl -m m::w toto # le masque est après ::, ici w
$ getfacl toto
# file: toto
# owner: thiel
# group: thiel
user::rw-
user:dupond:rwx #effective:-w-
group::r-- #effective:---
mask::-w-
other::---
Maintenant dupond
ne peut plus lire le fichier, mais il peut le modifier :
thiel:~$ cat toto
bonjour
thiel:~$ sudo su dupond # on change d'utilisateur
[sudo] Mot de passe de thiel :
dupond:/home/thiel$ cat toto
cat: toto: Permission non accordée # dupond n'a pas le droit r
dupond:/home/thiel$ echo "hop" >> toto # on modifie toto, droit w
dupond:/home/thiel$ cat toto
cat: toto: Permission non accordée
dupond:/home/thiel$ exit # retour à l'utilisateur précédent
déconnexion
thiel:~$ cat toto
bonjour
hop # la modification a marché
Défaire le masque = donner les droits maximaux
$ setfacl -m m::rwx toto
Archives tar
: par défaut la commande tar
ne conserve pas les ACL, il faut
rajouter l'option --acls
$ tar cvf essai.tar toto
toto
$ tar tvf essai.tar
-rw--w---- thiel/thiel 12 2021-01-29 15:35 toto
$ tar cvf essai.tar --acls toto # on recrée le tarball avec --acls
toto
$ tar tvf essai.tar --acls # il y a le '+' qui signale les ACLs
-rw--w----+ thiel/thiel 12 2021-01-29 15:35 toto
La commande mv
préserve les ACLs. Pour copier un fichier avec ses ACLs,
utiliser cp -p
12.2. Droits étendus par défaut
On peut donner des ACL par défaut à un répertoire ; tout ce qui sera créé dedans recevra des droits par défaut.
Options de setfacl
:
-d
donne des droits par défaut-k
supprime les droits par défaut
Exemple :
$ umask
0027
$ mkdir rep1 # Création d'un répertoire
$ touch rep1/fic1 # et d'un fichier avec le umask
$ ls -laR rep1
rep1:
total 8
drwxr-x--- 2 thiel thiel 4096 janv. 24 11:37 .
drwxr-xr-x 16 thiel thiel 4096 janv. 24 11:37 ..
-rw-r----- 1 thiel thiel 0 janv. 24 11:37 fic1
$ setfacl -d -m u:dupond:rwx rep1 # ajout d'ACLs par défaut
$ getfacl -R rep1
# file: rep1
# owner: thiel
# group: thiel
user::rwx # ça n'a pas ajouté d'ACL ici (pour
group::r-x # les rajouter, setfacl sans -d)
other::---
default:user::rwx # mais ça a ajouté les ACL par
default:user:dupond:rwx # défaut
default:group::r-x
default:mask::rwx
default:other::---
# file: rep1/fic1 # ça n'a pas modifié fic1
# owner: thiel # qui existait déjà
# group: thiel
user::rw-
group::r--
other::---
$ touch rep1/fic2 # Création d'un répertoire et d'un
$ mkdir rep1/rep2 # fichier avec les ACLs par défaut
$ getfacl rep1/{fic2,rep2}
# file: rep1/fic2
# owner: thiel
# group: thiel
user::rw-
user:dupond:rwx #effective:rw- # ça a créé les ACLs pour fic1
group::r-x #effective:r--
mask::rw- # avec un masque pour enlever x
other::---
# file: rep1/rep2
# owner: thiel
# group: thiel
user::rwx
user:dupond:rwx # ça a créé les ACLs pour rep1
group::r-x
mask::rwx
other::---
default:user::rwx # et recopié les ACLs par défaut
default:user:dupond:rwx
default:group::r-x
default:mask::rwx
default:other::---
$ setfacl -k rep1 # pour supprimer les ACLs par défaut
$ setfacl -kR rep1 # idem récursivement sur les rep
Pour aller plus loin : lire le document sur les ACLs POSIX.
13. Élévation de privilèges
C'est un mécanisme qui permet à un utilisateur d'accéder à des privilèges supérieurs à ceux qu'il possède habituellement.
13.1. Commande sudo (superuser do)
Elle permet d'exécuter une commande en changeant temporairement le user et le groupe.
Un utilisateur peut utiliser sudo
s'il est dans le groupe :
- sur Debian et Ubuntu :
sudo
- Fedora et CentOS :
wheel
Configuration : voir
man sudo.conf
; fichier/etc/sudo.conf
man sudoers
; fichiers/etc/sudoers
,/etc/sudoers.d/*.conf
Le système lui demande ensuite son propre mot de passe. Ensuite, pendant 5 minutes, on peut utiliser sudo sans mot de passe.
$ sudo commande... # exécute commande par root
$ sudo -u user commande... # exécute commande par le user
Exemples :
thiel@xubu1:~$ groups
thiel adm cdrom sudo ... # est dans le groupe sudo
thiel@xubu1:~$ sudo id
[sudo] Mot de passe de thiel :
uid=0(root) gid=0(root) groupes=0(root)
thiel@xubu1:~$ sudo addgroup boulga
Ajout du groupe « boulga » (GID 1007)...
Fait.
thiel@xubu1:~$ sudo -u dupond id
uid=1006(dupond) gid=1006(dupond) groupes=1006(dupond)
Test avec un utilisateur qui n'est pas dans le group sudo
:
thiel@xubu1:~$ sudo su dupond # on devient dupont
dupond@xubu1:/home/thiel$ groups
dupond # n'est pas dans le groupe sudo
dupond@xubu1:/home/thiel$ sudo id
[sudo] Mot de passe de dupond :
dupond n'apparaît pas dans le fichier sudoers. Cet incident sera signalé.
13.2. Commande su (substitute user)
Usage :
su [options] [-] [user [argument...]]
Elle permet de changer le user et le groupe. En principe, elle commence par demander le mot de passe du nouvel utilisateur. Elle démarre ensuite le shell par défaut de l'utilisateur.
Devenir root : su
thiel@debian:~$ su
Mot de passe : # mot de passe de root
root@debian:/home/thiel$ id # on n'a pas changé de répertoire
uid=0(root) gid=0(root) groupes=0(root) # on est bien devenu root
root@debian:/home/thiel$ exit # retour à l'utilisateur
thiel@debian:~$
Pour que ce soit possible il faut que root
ait un mot de passe.
Ce n'est pas le cas par défaut sur Ubuntu ; une solution est d'utiliser sudo
:
thiel@xubu1:~$ sudo su
[sudo] Mot de passe de thiel :
root@xubu1:/home/thiel# id
uid=0(root) gid=0(root) groupes=0(root)
root@xubu1:/home/thiel# exit
exit
thiel@xubu1:~$
Changer d'utilisateur : su user
thiel@xubu1:~$ su dupond
Mot de passe : # mot de passe de dupond
dupond@xubu1:/home/thiel$ id # on n'a pas changé de répertoire
uid=1006(dupond) gid=1006(dupond) groupes=1006(dupond)
dupond@xubu1:/home/thiel$ exit
thiel@xubu1:~$
Changer d'utilisateur et démarrer un login shell dans son homedir : su - [user]
thiel@xubu1:~$ su - dupond
Mot de passe : # mot de passe de dupond
dupond@xubu1:~$ id # on est dans son home
uid=1006(dupond) gid=1006(dupond) groupes=1006(dupond)
dupond@xubu1:~$ exit
déconnexion
thiel@xubu1:~$
Changer d'utilisateur et de groupe (réservé à root
) : su -g groupe [user]
thiel@xubu1:~$ sudo su
[sudo] Mot de passe de thiel :
root@xubu1:/home/thiel# su -g boulga dupond
dupond@xubu1:/home/thiel$ id
uid=1006(dupond) gid=1007(boulga) groupes=1007(boulga)
dupond@xubu1:/home/thiel$ exit
root@xubu1:/home/thiel# exit
thiel@xubu1:~$
Changer d'utilisateur pour exécuter une commande : su -c "commande" [user]
thiel@xubu1:~$ su -c "id ; pwd" dupond
Mot de passe : # mot de passe de dupond
uid=1006(dupond) gid=1006(dupond) groupes=1006(dupond)
/home/thiel
thiel@xubu1:~$
Pour aller plus loin :
- commande
sg
pour changer de groupe - utilisateurs réel, effectif, sauvegardé :
man 7 credentials
,/real
- commandes
runuser
,setpriv
(man
) - capabilities (
man
)
13.3. Droits spéciaux : setuid, setgid, sticky bit
Flags setuid et setgid
Ils signifient : "set user ID", "set group ID"
Les droits d'accès setuid
et setgid
sont placés sur un fichier ou un répertoire
avec chmod
:
-
sur un fichier régulier exécutable :
n'importe quel utilisateur qui a les droits d'exécution l'exécutera avec les privilèges :
- du propriétaire du fichier s'il y a le flag
setuid
, - du groupe du fichier s'il y a le flag
setgid
.
- du propriétaire du fichier s'il y a le flag
-
sur un fichier régulier non exécutable :
aucun effet
-
sur un répertoires :
- flag
setuid
: aucun effet (sauf FreeBSD). - flag
setgid
: les fichiers et répertoires créés dans ce répertoire héritent dugid
du répertoire.
- flag
Affichage étendu : ls -l
affiche
..s ... ... fichier exécutable + setuid
..S ... ... fichier non exécutable + setuid
... ..s ... fichier exécutable + setgid
... ..S ... fichier non exécutable + setgid
Exemples :
$ ls -l /bin/su /usr/bin/sudo /usr/bin/passwd /bin/ping /bin/bash /usr/bin/at
-rwxr-xr-x 1 root root 1037528 juil. 12 2019 /bin/bash*
-rwsr-xr-x 1 root root 44168 mai 7 2014 /bin/ping*
-rwsr-xr-x 1 root root 40128 mars 26 2019 /bin/su*
-rwsr-sr-x 1 daemon daemon 51464 janv. 14 2016 /usr/bin/at*
-rwsr-xr-x 1 root root 54256 mars 26 2019 /usr/bin/passwd*
-rwsr-xr-x 1 root root 136808 janv. 31 2020 /usr/bin/sudo*
Donner les droits à un fichier :
$ chmod u+s # donne le setuid
$ chmod g+s # donne le setgid
$ chmod ug+s # donne le setuid et le setgid
En octal, u+s
est codé 4000
, et g+s
est codé 2000
, aucun 0000
.
Par exemple :
$ touch ga
$ chmod 0755 ga # pas de setuid/setgid
$ ls -l ga
-rwxr-xr-x 1 thiel thiel 0 janv. 25 11:22 ga
$ chmod 4755 ga # setuid
$ ls -l ga
-rwsr-xr-x 1 thiel thiel 0 janv. 25 11:22 ga
$ chmod 2755 ga # setgid
$ ls -l ga
-rwxr-sr-x 1 thiel thiel 0 janv. 25 11:22 ga
$ chmod 6644 ga # setuid+setgid mais non-
$ ls -l ga # exécutable
-rwSr-Sr-- 1 thiel thiel 0 janv. 25 11:22 ga
Au niveau de la sécurité, l'emploi inconsidéré de ces droits est un réel danger.
C'est pourquoi la plupart des unix modernes (dont Linux) ignorent setuid
et
setgid
lorsque l'exécutable est un script (voir tests en TP).
Le sticky bit
Il s'agit d'un droit que l'on peut donner à un répertoire avec chmod
.
En général il est ignoré pour les fichiers.
Lorsqu'un répertoire rep
possède le sticky bit, les fichiers et répertoires qui
sont dans rep
ne peuvent être renommés ou effacés que par leur propriétaire,
ou par le propriétaire de rep
, ou par root
.
C'est typiquement ce qui se passe pour /tmp
.
Affichage étendu : ls -l
affiche
... ... ..t répertoire traversable par les users (x) + sticky bit
... ... ..T répertoire non traversable par les users + sticky bit
Exemple :
$ ls -l / | grep tmp
drwxrwxrwt 14 root root 4096 janv. 25 14:03 tmp
Donner le sticky bit à un répertoire :
$ chmod +t rep # donne le sticky bit
En octal, +t
est codé 1000
.
$ umask
0027
$ mkdir rep1
$ ls -l | grep rep1
drwxr-x--- 2 thiel thiel 4096 janv. 25 14:56 rep1
$ chmod 1755 rep1
$ ls -l | grep rep1
drwxr-xr-t 2 thiel thiel 4096 janv. 25 14:56 rep1