Utilisez find avec sudo en toute sécurité

10

Sur un serveur Linux, je dois supprimer les privilèges root d'un groupe d'utilisateurs. Mais ces utilisateurs ont des raisons légitimes de pouvoir utiliser l'utilitaire "find" pour rechercher des fichiers en fonction des noms de fichiers, des dates de modification et d'autres métadonnées.

Sur le serveur, les noms de fichiers ne sont pas sensibles, mais le contenu du fichier peut l'être.

Je voudrais utiliser sudo pour permettre aux utilisateurs de rechercher des fichiers n'importe où sur le serveur. L'utilitaire "find" est génial, mais il permet toutes sortes d'effets secondaires, comme l'utilisation de "-exec" pour générer des commandes arbitraires.

Puis - je obtenir findde travailler avec mes restrictions?

Troels Arvin
la source
14
En général , vous ne voulez que les résultats de la recherche pour modèles de nom de fichier pour contenir les fichiers que vous ne pouvez pas réellement accès. À cet égard, votre exigence est un peu étrange.
HBruijn
2
Personne ne vous oblige à vous engager dans la question. Je pense que l'un des objectifs de Server Fault est de servir de forum pour des situations étranges.
Troels Arvin
2
Server Fault n'est pas un forum, et les tentatives de psychologie inverse ne changent pas la validité de l'observation de HBruijn (qui était, j'en suis sûr, posée dans une tentative de vous aider).
Courses de légèreté en orbite

Réponses:

19

Et localiser ?

Locate lit une ou plusieurs bases de données préparées par updatedb (8) et écrit des noms de fichiers correspondant à au moins un des MOTIFS dans la sortie standard, un par ligne. Si --regex n'est pas spécifié, les MOTIFS peuvent contenir des caractères globbing. Si un MOTIF ne contient aucun caractère de remplacement, la localisation se comporte comme si le motif était un MOTIF .

Par défaut, Locate ne vérifie pas si les fichiers trouvés dans la base de données existent toujours. Locate ne peut jamais signaler les fichiers créés après la dernière mise à jour de la base de données concernée.

Ou peut-être même slocate :

Secure Locate fournit un moyen sécurisé d'indexer et de rechercher rapidement des fichiers sur votre système. Il utilise un codage incrémentiel tout comme GNU Locate pour compresser sa base de données pour accélérer la recherche, mais il stockera également les autorisations et la propriété des fichiers afin que les utilisateurs ne voient pas les fichiers auxquels ils n'ont pas accès.

Cette page de manuel documente la version GNU de slocate. slocate Permet aux utilisateurs du système de rechercher des systèmes de fichiers entiers sans afficher les fichiers non autorisés.

Lenniey
la source
Bonne idée. Je ne sais pas pourquoi je n'y ai pas pensé. Mais j'ai peur que le paramètre "-d" puisse être utilisé d'une manière ou d'une autre pour lire des fichiers arbitraires, si les règles sudo permettent à l'utilisateur d'exécuter n'importe quelle commande "Locate"?
Troels Arvin
2
@TroelsArvin: locaten'a pas besoin sudo; seul son updatedbtravail requiert des privilèges spéciaux. Vos utilisateurs ne devraient donc jamais être en cours d'exécution ou pouvoir s'exécuter sudo locate.
jwodder
1
@jwodder: Sur un serveur RHEL 7: Disons que l'utilisateur u n'a pas accès à / data / foo. Dans / data / foo, il y a un fichier "somefile.csv". Maintenant, lorsque u exécute "Locate somefile.csv", la sortie de "Locate" n'inclut pas /data/foo/somefile.csv - sauf si l'utilisateur u exécute "Locate" via sudo. (L'utilisation de l'argument "--nofollow" n'aide pas.)
Troels Arvin
1
@TroelsArvin mais le -ddrapeau ne définit que le chemin de la base de données? Je vous ai peut-être mal compris.
Lenniey
21

Selon man 7 capabilities

   CAP_DAC_READ_SEARCH
          * Bypass file read permission checks and directory read and execute permission checks;
          * Invoke open_by_handle_at(2).

Cela a fonctionné pour moi. (les lignes commençant par '#' sont root, celles avec '$' ne sont pas root) dans ce cas, l'utilisateur non root est dans le wheelgroupe.

# cp /usr/bin/find /usr/bin/sudofind
# chmod 710 /usr/bin/sudofind
# chown root:wheel /usr/bin/sudofind
# setcap cap_dac_read_search+ep /usr/bin/sudofind
# exit
$ find /root 
find: ‘/root’: Permission denied
$ sudofind /root
/root /root 
/root/Testbed 
...
... 
$ sudofind /root -exec cat {} \;
cat: /root: Permission denied 
cat: /root/Testbed: Permission denied
$ sudofind /root -printf "%u %g %m %c %p\n"
root root 644 Mon Apr 20 09:20:48.0457518493 2015 /root
root root 755 Fri Dec  4 02:34:03.0016294644 2015 /root/Testbed
...
...
$ # Capability inheritance test..
$ sudofind /root -exec /bin/sleep 10 \; &
[1] 17017
$ getpcaps $(pgrep find)
Capabilities for `17017': = cap_dac_read_search+ep
$ getpcaps $(pgrep sleep)
Capabilities for `17019': =

Compte tenu de ce que la capacité accorde, elle correspond exactement à ce que vous voulez. Je n'ai pas vérifié de manière exhaustive si findune fonctionnalité vous permet de lire des octets à l'intérieur des fichiers, mais des choses évidentes comme les LD_PRELOADattaques de cales de bibliothèque ne devraient pas fonctionner en raison de la nature des vérifications de setuid sous Linux, et les bits de capacité ne sont pas hérité par les processus enfants non plus (contrairement au setuid brut), c'est donc un autre bonus.

Gardez à l'esprit que ce que vous voulez faire soulève des problèmes de confidentialité potentiels en ce qui concerne la création de fichiers temporaires ou l'accès, et le programme pourrait être utilisé comme base pour monter une condition de concurrence critique / tentative d'escalade de privilèges (contre les programmes qui créent des noms de fichiers bien connus mais ne faites pas les contrôles de sécurité corrects).

De plus, certaines applications mal écrites peuvent s'appuyer sur des métadonnées de fichier ou une structure arborescente pour transmettre du sens ou masquer des données. Cela pourrait provoquer la divulgation d'informations restreintes ou révéler des documents privilégiés inconnus autrement (la sécurité par l'obscurité, je sais, mais c'est une chose que les fournisseurs de sources fermées en particulier aiment faire, malheureusement).

Par conséquent, soyez prudent et méfiez-vous de le faire et comprenez qu'il y a toujours un risque associé à cela, même si les choses évidentes ne fonctionnent pas.

Oh, et je serais intéressé de voir si quelqu'un a une attaque de preuve de concept qui utilise ce mécanisme comme base pour une élévation de privilèges dans les commentaires!

Matthew Ife
la source
5
Cela semble en effet assez intéressant!
Sven
Comme ça? Eh bien, pas de PoC, mais néanmoins intéressant: forums.grsecurity.net/…
Lenniey
J'aime cette idée, mais elle a un inconvénient important: sudofind est maintenant un binaire qui ne fait partie d'aucun logiciel (par exemple RPM) sur le système. Donc, si la distribution envoie un patch pour "find", sudofind ne sera pas mis à jour.
Troels Arvin
2
@TroelsArvin Ce n'est pas nécessairement une mauvaise chose. Si vous ajoutez des fonctionnalités de type setuid à un utilitaire existant qui n'a pas été conçu pour ces fonctionnalités, vous ne voudriez aucune mise à jour de l'utilitaire sous-jacent avant de vérifier que l'utilitaire mis à jour peut être utilisé en toute sécurité avec votre non standard capacités. Imaginez dans ce cas si une mise à jour devait donner findla possibilité d'exécuter directement du code fourni par l'utilisateur, similaire à ce qui awkpeut faire.
Andrew Henle
4
Le plus gros problème que je peux voir avec cela est que les répertoires accessibles en écriture qui se trouvent sous des répertoires non consultables peuvent soudainement être écrits.
Tavian Barnes
2

Je donnerais aux utilisateurs les autorisations appropriées.

Par défaut, si umask l'est 022, des répertoires sont créés pour que tout le monde puisse y lister et statuer les fichiers. Sinon, vous pouvez modifier manuellement l'autorisation du répertoire pour qu'elle soit au niveau du bit ou de ses anciennes autorisations et 0555:

chmod +0555 foo

Et si ces utilisateurs ne disposent pas de l'autorisation d'exécution sur tous les parents de ce répertoire (par exemple, le répertoire personnel d'un autre utilisateur), cela signifie probablement que vous devriez placer le premier répertoire ailleurs.

Si vous souhaitez autoriser uniquement certains utilisateurs à lire et exécuter ce répertoire, vous pouvez modifier son mode en 0750, placer ces utilisateurs dans un groupe et modifier le propriétaire du groupe du répertoire dans ce groupe:

groupadd can_read_foo
chmod 0750 foo
chgrp can_read_foo foo
gpasswd -a alice can_read_foo
gpasswd -a bob can_read_foo
yt7b97q-
la source