Unix / Linux: différence entre l'ID utilisateur réel, l'ID utilisateur effectif et l'ID utilisateur enregistré

104

Je connais déjà le véritable identifiant d'utilisateur . C'est le numéro unique d'un utilisateur dans le système.

Dans mon système, mon uidest

$ echo $UID
1014
$                 

À quoi servent les deux autres supports d'identification?
Et à quoi sert un identifiant d'utilisateur efficace et un identifiant utilisateur enregistré et où nous les utilisons dans le système?

mrg
la source
Pour info - il y a aussi l'ID utilisateur du système de fichiers, comme indiqué sur la page Wikipedia: en.wikipedia.org/wiki/User_identifier
Willem van Ketwich
Je pense qu'il ne l'a pas mentionné parce que (à partir de votre lien wiki): "Depuis le noyau 2.0, l'existence de fsuid n'est plus nécessaire car Linux adhère aux règles SUSv3 pour l'envoi de signaux, mais fsuid reste pour des raisons de compatibilité."
RtmY du

Réponses:

148

La distinction entre un identifiant d'utilisateur réel et un identifiant effectif est faite parce que vous pourriez avoir besoin de prendre temporairement l'identité d'un autre utilisateur (la plupart du temps, ce serait le cas root, mais cela pourrait être n'importe quel utilisateur). Si vous n'aviez qu'un seul identifiant d'utilisateur, alors il n'y aurait aucun moyen de revenir à votre identifiant d'origine par la suite (autre que de prendre votre parole pour acquise, et au cas où vous l'auriez fait root, en utilisant rootles privilèges de pour passer à n'importe quel utilisateur).

Ainsi, l'ID utilisateur réel est qui vous êtes vraiment (celui qui possède le processus), et l'ID utilisateur effectif est ce que le système d'exploitation examine pour décider si vous êtes autorisé ou non à faire quelque chose (la plupart du temps , il y a quelques exceptions).

Lorsque vous vous connectez, le shell de connexion définit à la fois l'ID utilisateur réel et effectif sur la même valeur (votre ID utilisateur réel) que celle fournie par le fichier de mots de passe.

Maintenant, il arrive aussi que vous exécutiez un programme setuid, et en plus de s'exécuter en tant qu'un autre utilisateur (par exemple root), le programme setuid est également censé faire quelque chose en votre nom. Comment cela marche-t-il?
Après avoir exécuté le programme setuid, il aura votre véritable identifiant (puisque vous êtes le propriétaire du processus) et l'identifiant effectif du propriétaire du fichier (par exemple root) puisqu'il est setuid.

Le programme fait tout ce qu'il faut de magie avec les privilèges de superutilisateur et souhaite ensuite faire quelque chose en votre nom. Cela signifie que tenter de faire quelque chose que vous ne devriez pas pouvoir faire devrait échouer . Comment fait-il cela? Eh bien, évidemment en changeant son identifiant d'utilisateur effectif en l'identifiant réel de l'utilisateur!

Maintenant, ce programme setuid n'a aucun moyen de revenir en arrière puisque tout ce que le noyau sait, c'est votre identifiant et ... votre identifiant . Bang, tu es mort.

C'est à cela que sert l'ID utilisateur de l'ensemble enregistré.

Damon
la source
6
Pour plus de clarté sur ce dernier point concernant l'ID utilisateur enregistré, voir Wikipedia.
GDP2
Pouvez-vous m'indiquer quelques lectures où je peux trouver quel appel système vérifie le Real uid à la place? merci
mik1904
1
@ mik1904: Le plus important que vous êtes susceptible d'utiliser et qui vérifie vraiment l'UID réel est access. C'est 99,9% de celui-ci. Aussi setfsuid(mais rarement nécessaire), et quelques fonctions de très bas niveau, et vous avez besoin (mais pas vérifié) de l'ID utilisateur réel pour obtenir / définir les priorités ou le planificateur, et les ID passés aux gestionnaires de signaux ou renvoyés par waitet al. sont de vrais identifiants. execvene vérifie pas, mais peut échouer si vous avez changé l'ID utilisateur réel. Aussi forkne vérifie pas, mais peut échouer si vous atteignez le quota de processus maximum sur l'UID réel. Google avec site:man7.orgest votre ami ici.
Damon
"la commande ping doit ouvrir une socket et le noyau Linux demande le privilège root pour cela." ce n'est pas vraiment exact. pinga besoin d'une prise brute . tout utilisateur peut (généralement) ouvrir une socket, et pour l'écoute, au-dessus de 1024.
Daniel Farrell
39

Je vais essayer d'expliquer étape par étape avec quelques exemples.

Bref historique

Chaque processus a ses propres « pouvoirs de processus » qui comprend des attributs tels que PID, les PPID, PGID, session IDainsi que les utilisateurs réels et efficaces et des ID de groupe: RUID, EUID, RGID, EGID.

Nous allons nous concentrer sur ceux-ci.


Partie 1: Comprendre l'UID et le GID

Maintenant, je vais me connecter à un shell avec mes informations d'identification et exécuter:

$ grep $LOGNAME /etc/passwd
rotem:x:1000:1000:rotem,,,:/home/rotem:/bin/bash

Vous pouvez voir mon nom de journal (rotem), l' UID et le GID qui sont tous deux 1000, et d'autres détails comme le shell auquel je suis connecté.


Partie 2: Comprendre RUID et RGID

Chaque processus a un propriétaire et appartient à un groupe .
Dans notre shell, chaque processus que nous allons maintenant exécuter héritera des privilèges de mon compte utilisateur et fonctionnera avec le même UID et GID.

Permet d'exécuter une commande simple pour le vérifier:

$ sleep 10 & ps aux | grep 'sleep'

Et vérifiez l'UID et le GID du processus:

$ stat -c "%u %g" /proc/$pid/
1000 1000

Ce sont l' ID utilisateur réel ( ) et l' ID de groupe réel ( ) du processus .RUIDRGID

(*) Cochez les autres options pour afficher l'UID et le GID et les moyens d'obtenir cela en une seule ligne .

Pour l'instant, acceptez le fait que les attributs EUIDet EGIDsont «redondants» et sont juste égaux à RUIDet RGIDen coulisses.

Partie 3: Comprendre l'EUID et l'EGID

Prenons la pingcommande comme exemple.

Recherchez l'emplacement binaire avec la whichcommande puis exécutez ls -la:

-rwsr-xr-x  1 root root   64424 Mar 10  2017  ping

Vous pouvez voir que le propriétaire et le groupe du fichier sont root. C'est parce que la pingcommande doit ouvrir une socket et que le noyau Linux demande des rootprivilèges pour cela.

Mais comment puis-je utiliser pingsi je n'ai pas de rootprivilège?
Notez la lettre «s» au lieu de «x» dans la partie propriétaire de l'autorisation de fichier.
Il s'agit d'un bit d'autorisation spécial pour des fichiers exécutables binaires spécifiques (comme pinget sudo) qui est connu sous le nom de setuid .

C'est là EUIDet EGIDentre en jeu.
Ce qui se passera, c'est lorsqu'un binaire setuid comme pings'exécute, le processus change son ID utilisateur effectif ( EUID) de la valeur par défaut RUIDau propriétaire de ce fichier exécutable binaire spécial qui dans ce cas est -root .
Tout cela est fait par le simple fait que ce fichier a le setuidbit.

Le noyau décide si ce processus a le privilège en regardant sur EUIDle processus. Parce que maintenant le EUIDpoint sur root, l'opération ne sera pas rejetée par le noyau.

Remarque : Sur les dernières versions de Linux, la sortie de la pingcommande sera différente du fait qu'elle a adopté l' approche des capacités Linux au lieu de cette approche setuid - pour ceux qui ne sont pas familiers - lisez ici .

Partie 4: Qu'en est-il du SUID et du SGID?

L'ID utilisateur enregistré ( SUID) est utilisé lorsqu'un processus privilégié est en cours d'exécution (comme rootpar exemple) et qu'il doit effectuer des tâches non privilégiées.

Dans ce cas, l'UID effectif ( EUID) d'avant sera enregistré à l'intérieur SUIDpuis changé en une tâche sans privilège. Une fois la tâche non privilégiée terminée, la valeur de EUIDsera prise en SUIDcompte et reviendra au compte privilégié.


RtmY
la source
1
Réponse claire sauf pour le dernier paragraphe sur SUID. J'ai été confondu avec les tâches privilégiées et privilégiées. Utile si un exemple est fourni. Merci.
Upendra
2
Réponse très précise. Merci!!
user37416