web-dev-qa-db-fra.com

Exécuter une commande spécifique avec une invite de mot de passe root, même si elle est exécutée en tant que root

Je souhaite exécuter une commande spécifique, telle que rm, tout en étant connecté en tant que root, mais je souhaite que l'invite de mot de passe root soit affichée à chaque fois. Lorsque j'exécute su -c "command" en tant que root, aucun mot de passe ne m'a été demandé.

4
fdsfad

Spécifiquement pour su, un mot de passe n'est pas demandé à la racine car les règles PAM de su le permettent:

$ grep root /etc/pam.d/su
# This allows root to su without passwords (normal operation)
auth       sufficient pam_rootok.so
# Uncomment this to force users to be a member of group root
# than the default "root" (but this may have side effect of
# denying "root" user, unless she's a member of "foo" or explicitly
# permitted earlier by e.g. "sufficient pam_rootok.so").

Si vous voulez que su demande un mot de passe pour root, commentez l'utilisation de pam_rootok. Bien sûr, su ne se soucie pas des commandes, toute utilisation de su par root demandera alors le mot de passe.

Vous ne pouvez pas protéger des commandes individuelles de la racine sans risquer beaucoup de problèmes. Verrouillez simplement votre terminal lorsque vous le quittez. N'exécutez pas de sessions root.

10
muru

Vous pouvez utiliser ce code pour le script wrapper rm, mais vous pouvez également créer des versions similaires pour mv et find.


Modifier 5 mars 2017 - Changer la méthode de vérification lors de l'exécution dans le terminal.


Cette réponse vérifie si elle est exécutée sur le terminal et ne demande pas de mot de passe si elle est exécutée dans un script en arrière-plan tel que démarrage, cron ou interface graphique. Le script peut être amélioré pour s'assurer que rm a été saisi directement dans le terminal. Ensuite, si un autre script tel que Sudo update-grub ou Sudo apt update appelé rm, un deuxième mot de passe ne serait pas nécessaire.

J'ai écrit un script pour protéger par mot de passe rm comme l'OP demandé et le code ci-dessous est le même, sauf qu'il exige un mot de passe de l'utilisateur Sudo/root. Il a également des modifications pour vous empêcher de supprimer accidentellement:

  • /
  • /domicile
  • /poubelle

Créer le script

Utilisez gksu gedit /usr/local/bin/rm et copiez-le dans ces lignes:

#!/bin/bash

tty -s;
if [ "0" == "$?" ]; then Terminal="Y"; else Terminal="N"; fi

if [ $Terminal == "Y" ] ; then    

    # Running from terminal don't allow delete of / or /toplevel directory even if Sudo
    for i in ${@:1}
    do
        # Skip options -i -r -v -d 
        if [[ ${i:0:1} != "-" ]] ; then
            # if parameter doesn't begin with '-' it's file or directory, so get real path.
            fullname=$(realpath "$i" 2>&1) # No error messages if file doens't exist
            # We must have at least two `/` in the full path
            levels=$(echo "$fullname" | tr -cd '/' | wc -c)
            if (( $levels == 1 )); then # Test for 1, will be zero when file doesn't exist.
                echo "Attempting to remove top level directory '$fullname'"
                echo "Use 'Sudo /bin/rm $@' instead."
                exit 1 # error
            fi
        fi
    done
fi


if [ $Terminal == "Y" ] ; then    
# Only running from a terminal needs password (ie not cron)

    # log rm usage to /var/log/syslog
    PARENT_COMMAND="$(ps -o comm= $PPID)"   
    logger "$PARENT_COMMAND"" - rm command was used on file: ""$fullname"

    # Get password
    Password=$(zenity --password --title="Password for rm")
    encryptPassword=$(echo -n "$Password" | md5sum)

echo "md5sum: $encryptPassword" # Comment out after viewing one time and updating line below.

    if [[ "$encryptPassword" != "d2c30dc65e59558c852ea30b7338abbe  -" ]]; then
        echo "Invalid password!"
        exit 1
    fi

fi # non-terminals can't enter password.

# Call REAL rm command with parameters passed to this wrapper sript
/bin/rm "$@"

exit 0

Remplacez le mot de passe "WE2U" par tout ce que vous voulez et enregistrez le fichier.

Marquer le nouveau script rm comme exécutable

Marquer le nouveau script rm comme exécutable à l'aide de:

Sudo chmod +x /usr/local/bin/rm

Comment ça fonctionne

rm password

Sauf si le mot de passe est WE2U , la première fois que vous exécutez le script, vous obtiendrez un "mot de passe invalide". et la clé de cryptage du mot de passe que vous avez entré s’affiche. Copiez et collez cette clé de chiffrement du terminal dans le script. Puis commentez la ligne avec l'écho qui affiche la clé de cryptage sur le terminal.

Parce que le chemin /usr/local/bin est plus élevé dans la liste que /bin notre commande rm est appelée. Après avoir obtenu un mot de passe valide, il appelle /bin/rm pour effectuer la suppression réelle.

Le script appelle logger pour enregistrer chaque fois que rm a été appelé manuellement à l'aide du terminal. L'utilisation de la commande est enregistrée dans /var/log/syslog.

Tiré de la réponse postée à l'adresse ( Comment puis-je configurer un mot de passe pour la commande 'rm'? ) et modifié pour exiger également un mot de passe de l'utilisateur root.

8
WinEunuuchs2Unix

La solution la plus simple à laquelle je puisse penser est de su à un autre utilisateur, puis de nouveau à root:

su userx -c 'su -c "ls"'

Un inconvénient de cela est que si vous avez besoin de caractères spéciaux dans la commande, l'échappement devient délicat.

0
kasperd