ssh
folgt der rsh
Tradition, indem das Shell-Programm des Benutzers aus der Kennwortdatei zum Ausführen von Befehlen verwendet wird.
Dies bedeutet, dass wir dies lösen können, ohne die ssh
Konfiguration in irgendeiner Weise einzubeziehen.
Wenn Sie nicht möchten, dass der Benutzer Shell-Zugriff hat, ersetzen Sie einfach die Shell dieses Benutzers durch ein Skript. Wenn Sie hineinschauen, werden /etc/passwd
Sie sehen, dass es ein Feld gibt, das jedem Benutzer einen Shell-Befehlsinterpreter zuweist. Das Skript wird sowohl für die interaktive Anmeldung ssh user@host
als auch für Befehle als Shell verwendet ssh user@host command arg ...
.
Hier ist ein Beispiel. Ich habe einen Benutzer erstellt, foo
dessen Shell ein Skript ist. Das Skript druckt die Nachricht my arguments are:
gefolgt von ihren Argumenten (jeweils in einer separaten Zeile und in spitzen Klammern) und wird beendet. Im Log-In-Fall gibt es keine Argumente. Folgendes passiert:
webserver:~# ssh foo@localhost
foo@localhost's password:
Linux webserver [ snip ]
[ snip ]
my arguments are:
Connection to localhost closed.
Wenn der Benutzer versucht, einen Befehl auszuführen, sieht dies folgendermaßen aus:
webserver:~# ssh foo@localhost cat /etc/passwd
foo@localhost's password:
my arguments are:
<-c>
<cat /etc/passwd>
Unsere "Shell" erhält einen -c
Stilaufruf mit dem gesamten Befehl als ein Argument, genauso wie er /bin/sh
ihn erhalten würde.
Wie Sie sehen, können wir das Skript jetzt weiterentwickeln, sodass es den Fall erkennt, wenn es mit einem -c
Argument aufgerufen wurde , und dann die Zeichenfolge analysiert (z. B. durch Mustervergleich). Die zulässigen Zeichenfolgen können durch rekursives Aufrufen an die reale Shell übergeben werden /bin/bash -c <string>
. Der Ablehnungsfall kann eine Fehlermeldung drucken und beenden (einschließlich des Falls, wenn er -c
fehlt).
Sie müssen vorsichtig sein, wie Sie dies schreiben. Ich empfehle, nur positive Übereinstimmungen zu schreiben, die nur sehr spezifische Dinge zulassen, und alles andere zu verbieten.
Hinweis: Wenn root
dies der Fall ist , können Sie sich weiterhin bei diesem Konto anmelden, indem Sie die Shell im su
Befehl wie folgt überschreiben su -s /bin/bash foo
. (Ersatzschale Ihrer Wahl.) Nicht-Root kann dies nicht.
Hier ist ein Beispielskript: Beschränken Sie den Benutzer darauf, nur ssh
für den git
Zugriff auf Repositorys unter zu verwenden /git
.
#!/bin/sh
if [ $# -ne 2 ] || [ "$1" != "-c" ] ; then
printf "interactive login not permitted\n"
exit 1
fi
set -- $2
if [ $# != 2 ] ; then
printf "wrong number of arguments\n"
exit 1
fi
case "$1" in
( git-upload-pack | git-receive-pack )
;; # continue execution
( * )
printf "command not allowed\n"
exit 1
;;
esac
# Canonicalize the path name: we don't want escape out of
# git via ../ path components.
gitpath=$(readlink -f "$2") # GNU Coreutils specific
case "$gitpath" in
( /git/* )
;; # continue execution
( * )
printf "access denied outside of /git\n"
exit 1
;;
esac
if ! [ -e "$gitpath" ] ; then
printf "that git repo doesn't exist\n"
exit 1
fi
"$1" "$gitpath"
Natürlich vertrauen wir , dass diese Programme Git git-upload-pack
und git-receive-pack
haben keine Löcher oder Luken zu entkommen , die Benutzer Zugriff auf das System erhalten.
Dies ist mit dieser Art von Beschränkungsschema verbunden. Der Benutzer ist authentifiziert, um Code in einer bestimmten Sicherheitsdomäne auszuführen, und wir beschränken uns darauf, diese Domäne auf eine Unterdomäne zu beschränken. Wenn Sie beispielsweise einem Benutzer erlauben, den vim
Befehl für eine bestimmte Datei auszuführen , um sie zu bearbeiten, kann der Benutzer einfach eine Shell mit abrufen :!sh[Enter]
.