Chroot Umgebung für OpenSSH und sftp


chroot mit debian woody

Bisher waren FTPserver wie Proftp und Co. immer von Nöten wenn man einen upload Zugang z.B. zu einem Webserver anbieten wollte.
Mit sftp ist soetwas natürlich auch möglich nur muss im Gegensatz zu Proftp erst die Chroot Umgebung gestaltet werden.
Dafür kommt man dann aber in den genuss der sftp Vorteile.

Damit in der Chroot Umgebung nicht etliche Software zusätzlich installiert wird habe ich auf Busybox zurückgegriffen, was die meisten Kommandos für einen SSH Zugang beherscht.

Die Quellen zu Busybox gibt es unter
www.busybox.net

Desweiteren ist eine statische Version der bash hilfreich.
Dazu läd man sich den Quellcode der Bash bei:

www.gnu.org

herunter.

Für Debian gibt es unter:

apt-get.org eine bereits für Chroot Umgebungen gepatchte OpenSSH.

Als erstes nachdem man sich alle Quellen und die gepatchte OpenSSH heruntergeladen hat, installiert man die gepatchte OpenSSH.

Dann wird die statische Bash erstellt :


tar -xvzf bash-version.tar.gz

cd bash-version

export CFLAGS="--static -O2 -funroll-loops"

./configure

make

Mit ldd bash kann man nachschauen, ob die Bash keine Bibliotheken nachläd (was richtig wäre).

Und Busybox(auch statisch):


tar -xvzf busybox-0.60.3.tar.gz

cd busybox-0.60.3


im Makefile von Busybox müssen einige Einstellungen vorgenommen werden:


DOSTATIC = true # statisch

USE_SYSTEM_PWF_GRP = true # /etc/passwd group

DOLFS = true # grosses Dateisystem

in Config.h werden nun noch die Befehle die Busybox zur Verfügung stellen soll eingetragen (bzw. auskommentiert)

#define BB_BASENAME

#define BB_CAT

#define BB_CHMOD

#define BB_CLEAR

#define BB_CMP

#define BB_CP

#define BB_GREP

#define BB_GUNZIP

#define BB_GZIP

#define BB_HEAD

#define BB_ID

#define BB_KILL

#define BB_LN

#define BB_LOGGER

#define BB_LS

#define BB_MD5SUM

#define BB_MKDIR

#define BB_MORE

#define BB_MV

#define BB_NC

#define BB_NSLOOKUP

#define BB_PIDOF

#define BB_PING

#define BB_PS

#define BB_PWD

#define BB_RM

#define BB_RMDIR

#define BB_SED

#define BB_SLEEP

#define BB_SORT

#define BB_CUT

#define BB_DATE

#define BB_DD

#define BB_DF

#define BB_DIRNAME

#define BB_DOS2UNIX

#define BB_DU

#define BB_ECHO

#define BB_ENV

#define BB_EXPR

#define BB_FIND

#define BB_TAIL

#define BB_TAR

#define BB_TEST

#define BB_TELNET

#define BB_TOUCH

#define BB_TRACEROUTE

#define BB_TRUE_FALSE

#define BB_UNIQ

#define BB_UNAME

#define BB_UPTIME

#define BB_VI

#define BB_WC

#define BB_WGET

#define BB_WHICH

#define BB_WHOAMI

#define BB_XARGS

#define BB_YES

Dann wir Busybox mit :

make

Übersetzt.

Auch hier kann wieder mit
Mit ldd busybox getestet werden ob Busybox statisch vorliegt.


Nun kann ein
Benutzer fuer chroot-Zugang angelegt werden (z.B. Benutzer „bert“ User und Group ID 5000)


groupadd -g 5000 bert

useradd -u 5000 -g 5000 -d /home/bert/./ -s /bin/bash bert

chfn bert

passwd bert

Im Gegensatz zu normalen Homeverzeichnissen wir für ChrootHomeVerzeichnisse ein /./ angehangen.

Nun werden noch einige Verzeichnisse angelegt:


mkdir /home/bert

cd /home/bert

mkdir -p bin dev lib usr/lib usr/bin etc/ssh


Das sieht dann folgendermassen aus:

     /home/os
     |-- bin
     |-- dev
     |-- etc
     |   `-- ssh
     |-- lib
     `-- usr
         |-- bin
         `-- lib

Im Homeverzeichnis werden nun die benötigten Devices angelegt :


mknod dev/null c 1 3

mknod dev/random c 1 8

mknod dev/tty c 5 0

mknod dev/urandom c 1 9

mknod dev/zero c 13 12

Und Busybox und Bash installiert:


cd ...../busybox-version

sh install.sh /home/bert

cd ...../bash-version

cp bash /home/bert/bin



Als nächstes werden einige Softwarebibliotheken in /lib/ installiert:

export FOLDER=/home/bert

cd $FOLDER"/lib"

for i in libdl libnss_compat libnss_dns libnss_files libresolv; do
    cp $(ls /lib/$i-*.so) .
    LNAME=$(ls /lib/$i-*.so | cut -d / -f 3)
    ln -s $LNAME $i.so.2
done

cp -v "/lib/"$(ls /lib/libc-*.so | cut -d / -f 3) .
ln -s $(ls libc-* ) libc.so.6

cp -v "/lib/"$(ls /lib/libnsl-*.so | cut -d / -f 3) .
ln -s $(ls libnsl-* ) libnsl.so.1

cp -v "/lib/"$(ls /lib/libutil*.so | cut -d / -f 3) .
ln -s $(ls libutil* ) libutil.so.1

cp -v "/lib/"$(ls /lib/ld-*.so | cut -d / -f 3) .
ln -s $(ls ld-*.so ) ld-linux.so.2

cp -v "/lib/"$(ls /lib/libdl*.so | cut -d / -f 3) .
ln -s $(ls libdl*.so ) libdl.so.2

Und einige Softwarebibliotheken in /usr/lib/ :

cd $FOLDER"/usr/lib"

cp -v "/usr/lib/"$(ls -r /usr/lib/libcrypto* | cut -d / -f 4) .
ln -s $(ls libcrypto* ) libcrypto.so

cp -v "/usr/lib/"$(ls -mr /usr/lib/libz* | cut -d, -f 1  |cut -d / -f 4 ) .
ln -s $(ls libz* ) libz.so.1

Es werden noch zwei links angelegt (ob die wirklich nötig sind ist mir nicht ganz klar, waren aber auch im Basisdebiansystem vorhanden)

ln -s $FOLDER"/lib/libdl.so.2" libdl.so
ln -s $FOLDER"/lib/libnsl.so.1" libnsl.so

Dann werden die SSH Binaries kopiert:

cp -v /usr/bin/ssh    $FOLDER"/usr/bin/"
cp -v /usr/bin/scp    $FOLDER"/usr/bin/"
cp -v /usr/bin/sftp    $FOLDER"/usr/bin/"
cp -v /usr/lib/sftp-server    $FOLDER"/usr/lib/"

Es werden noch einige Dateien für etc angelegt:

export USER=bert

grep root /etc/passwd >> $FOLDER"/etc/passwd"
grep www-data   /etc/passwd >> $FOLDER"/etc/passwd"
grep $USER   /etc/passwd >> $FOLDER"/etc/passwd"

grep root /etc/group  >> $FOLDER"/etc/group"
grep www-data   /etc/group  >> $FOLDER"/etc/group"
grep $USER   /etc/group  >> $FOLDER"/etc/group"

cp -v /etc/nsswitch.conf $FOLDER"/etc/nsswitch.conf"
cp -v /etc/resolv.conf   $FOLDER"/etc/resolv.conf"

echo "/bin/bash"   >  $FOLDER"/etc/shells"

cp -v /etc/ssh/moduli      $FOLDER"/etc/ssh"
cp -v /etc/ssh/ssh_config $FOLDER"/etc/ssh"

Jetzt werden noch einige Rechte gesetzt:

cd $FOLDER
chmod a=x bin/bash
chmod a=x bin/busybox
chmod a=x usr/bin/ssh
chmod a=x usr/bin/scp
chmod a=x usr/bin/sftp

chown $USER.$USER $FOLDER
chattr -R +i dev bin usr etc lib

und dann sollte
.das Filesystem in etwa so aussehen:

|-- bin/
|   |-- bash*
|   |-- busybox*
|   |-- cat -> busybox*
|   |-- chmod -> busybox*
|   |-- cp -> busybox*
|   |-- date -> busybox*
|   |-- dd -> busybox*
|   |-- df -> busybox*
|   |-- echo -> busybox*
|   |-- false -> busybox*
|   |-- grep -> busybox*
|   |-- gunzip -> busybox*
|   |-- gzip -> busybox*
|   |-- kill -> busybox*
|   |-- ln -> busybox*
|   |-- ls -> busybox*
|   |-- mkdir -> busybox*
|   |-- more -> busybox*
|   |-- mv -> busybox*
|   |-- pidof -> busybox*
|   |-- ping -> busybox*
|   |-- ps -> busybox*
|   |-- pwd -> busybox*
|   |-- rm -> busybox*
|   |-- rmdir -> busybox*
|   |-- sed -> busybox*
|   |-- sleep -> busybox*
|   |-- tar -> busybox*
|   |-- touch -> busybox*
|   |-- true -> busybox*
|   |-- uname -> busybox*
|   |-- vi -> busybox*
|   `-- zcat -> busybox*
|-- dev/
|   |-- null
|   |-- random
|   |-- tty
|   |-- urandom
|   `-- zero
|-- etc/
|   |-- group
|   |-- nsswitch.conf
|   |-- passwd
|   |-- resolv.conf
|   |-- shells
|   `-- ssh/
|       |-- moduli
|       `-- ssh_config
|-- lib/
|   |-- ld-2.2.5.so*
|   |-- ld-linux.so.2 -> ld-2.2.5.so*
|   |-- libc-2.2.5.so*
|   |-- libc.so.6 -> libc-2.2.5.so*
|   |-- libdl-2.2.5.so
|   |-- libdl.so.2 -> libdl-2.2.5.so
|   |-- libnsl-2.2.5.so
|   |-- libnsl.so.1 -> libnsl-2.2.5.so
|   |-- libnss_compat-2.2.5.so
|   |-- libnss_compat.so.2 -> libnss_compat-2.2.5.so
|   |-- libnss_dns-2.2.5.so
|   |-- libnss_dns.so.2 -> libnss_dns-2.2.5.so
|   |-- libnss_files-2.2.5.so
|   |-- libnss_files.so.2 -> libnss_files-2.2.5.so
|   |-- libresolv-2.2.5.so
|   |-- libresolv.so.2 -> libresolv-2.2.5.so
|   |-- libutil-2.2.5.so
|   `-- libutil.so.1 -> libutil-2.2.5.so
`-- usr/
    |-- bin/
    |   |-- [ -> ../../bin/busybox*
    |   |-- basename -> ../../bin/busybox*
    |   |-- clear -> ../../bin/busybox*
    |   |-- cmp -> ../../bin/busybox*
    |   |-- cut -> ../../bin/busybox*
    |   |-- dirname -> ../../bin/busybox*
    |   |-- dos2unix -> ../../bin/busybox*
    |   |-- du -> ../../bin/busybox*
    |   |-- env -> ../../bin/busybox*
    |   |-- expr -> ../../bin/busybox*
    |   |-- find -> ../../bin/busybox*
    |   |-- head -> ../../bin/busybox*
    |   |-- id -> ../../bin/busybox*
    |   |-- linux_logo*
    |   |-- logger -> ../../bin/busybox*
    |   |-- md5sum -> ../../bin/busybox*
    |   |-- nc -> ../../bin/busybox*
    |   |-- nslookup -> ../../bin/busybox*
    |   |-- scp*
    |   |-- sftp*
    |   |-- sort -> ../../bin/busybox*
    |   |-- ssh*
    |   |-- tail -> ../../bin/busybox*
    |   |-- telnet -> ../../bin/busybox*
    |   |-- test -> ../../bin/busybox*
    |   |-- traceroute -> ../../bin/busybox*
    |   |-- uniq -> ../../bin/busybox*
    |   |-- uptime -> ../../bin/busybox*
    |   |-- wc -> ../../bin/busybox*
    |   |-- wget -> ../../bin/busybox*
    |   |-- which -> ../../bin/busybox*
    |   |-- whoami -> ../../bin/busybox*
    |   |-- xargs -> ../../bin/busybox*
    |   `-- yes -> ../../bin/busybox*
    `-- lib/
        |-- libcrypto.so -> libcrypto.so.0.9.6
        |-- libcrypto.so.0.9.6
        |-- libdl.so -> libdl.so.2
        |-- libnsl.so -> libnsl.so.1
        |-- libz.so.1 -> libz.so.1.1.4
        |-- libz.so.1.1.4
        `-- sftp-server*


Ich habe mir ein Shellscript erstellt was mir automatisiert ChrootUser anlegt -an dem Script gibt es sicherlich einiges zu verbessern und es muss auch stark an jeweilige Bedürfnisse angepasst werden. Ich werde es trotzdem hier veröffentlichen vieleicht ist es ja doch für den ein oder anderen hilfreich.

Falls es dazu Anmerkungen oder Erweiterungen gibt, bitte melden dann kann ich das Skript ergänzen..

Hier nun das Skript:

[code lang=“bash“]
#!/bin/bash

# Username @ Domain
echo „Chroot User anlegen“
echo -e “ Benutzername@Domain: n“
read LOCATION

USER=$(echo $LOCATION | cut -d @ -f 1)
echo $USER
FOLDER=“/var/www/virtual/“$(echo $LOCATION | cut -d @ -f 2)
echo $FOLDER

[ -d $FOLDER ] || (echo „Verzeichnis existiert nicht“ && exit 0)

echo „Die letzen 5 Accounts im virtualfolder“
grep virtual /etc/passwd | cut -d : -f 3 | sort -g |tail -n 5

echo „UID und GID : (ab 5000)“
read ID

groupadd -g $ID $USER
useradd -u $ID -g $ID -d $FOLDER“/./“ -s /bin/bash $USER
echo „Userinformationen setzen“
chfn $USER
echo „Userpasswort setzen“
passwd $USER

cd $FOLDER

mkdir -p bin dev etc lib usr usr/lib usr/bin etc/ssh

mknod dev/null c 1 3 # /home darf nicht mit nodev
mknod dev/random c 1 8 # gemountet sein!
mknod dev/tty c 5 0
mknod dev/urandom c 1 9
mknod dev/zero c 13 12

cd /root/busybox # Busybox-Binaries installieren
sh install.sh $FOLDER # Prima!

cd /root/bash # Bash installieren
cp bash $FOLDER“/bin“

# Minimal benoetigte Bibliotheken installieren
cd $FOLDER“/lib“
for i in libdl libnss_compat libnss_dns libnss_files libresolv; do

cp $(ls /lib/$i-*.so) .
LNAME=$(ls /lib/$i-*.so | cut -d / -f 3)
ln -s $LNAME $i.so.2
done

cp -v „/lib/“$(ls /lib/libc-*.so | cut -d / -f 3) .
ln -s $(ls libc-* ) libc.so.6

cp -v „/lib/“$(ls /lib/libnsl-*.so | cut -d / -f 3) .
ln -s $(ls libnsl-* ) libnsl.so.1

cp -v „/lib/“$(ls /lib/libutil*.so | cut -d / -f 3) .
ln -s $(ls libutil* ) libutil.so.1

cp -v „/lib/“$(ls /lib/ld-*.so | cut -d / -f 3) .
ln -s $(ls ld-*.so ) ld-linux.so.2

cp -v „/lib/“$(ls /lib/libdl*.so | cut -d / -f 3) .
ln -s $(ls libdl*.so ) libdl.so.2

cd $FOLDER“/usr/lib“

cp -v „/usr/lib/“$(ls -r /usr/lib/libcrypto* | cut -d / -f 4) .
ln -s $(ls libcrypto* ) libcrypto.so

cp -v „/usr/lib/“$(ls -mr /usr/lib/libz* | cut -d, -f 1 |cut -d / -f 4 ) .
ln -s $(ls libz* ) libz.so.1

ln -s $FOLDER“/lib/libdl.so.2″ libdl.so
ln -s $FOLDER“/lib/libnsl.so.1″ libnsl.so

cp -v /usr/bin/linux_logo $FOLDER“/usr/bin/“

cp -v /usr/bin/ssh $FOLDER“/usr/bin/“
cp -v /usr/bin/scp $FOLDER“/usr/bin/“
cp -v /usr/bin/sftp $FOLDER“/usr/bin/“
cp -v /usr/lib/sftp-server $FOLDER“/usr/lib/“

# Benoetigte Daten in etc
grep root /etc/passwd >> $FOLDER“/etc/passwd“
grep www-data /etc/passwd >> $FOLDER“/etc/passwd“
grep $USER /etc/passwd >> $FOLDER“/etc/passwd“

grep root /etc/group >> $FOLDER“/etc/group“
grep www-data /etc/group >> $FOLDER“/etc/group“
grep $USER /etc/group >> $FOLDER“/etc/group“

cp -v /etc/nsswitch.conf $FOLDER“/etc/nsswitch.conf“

cp -v /etc/resolv.conf $FOLDER“/etc/resolv.conf“

echo „/bin/bash“ > $FOLDER“/etc/shells“

cp -v /etc/ssh/moduli $FOLDER“/etc/ssh“
cp -v /etc/ssh/ssh_config $FOLDER“/etc/ssh“

cd $FOLDER
chmod a=x bin/bash
chmod a=x bin/busybox
chmod a=x usr/bin/ssh
chmod a=x usr/bin/scp
chmod a=x usr/bin/sftp

# eigentuemer ID.www-data -> Web

cd $FOLDER
chown $ID.$ID $FOLDER

for i in cgi-bin html logs tmp; do
chown -R $ID“.www-data“ $i
chmod 775 $i
done

# user files

cp /root/chrootfiles/.bash_profile .
cp /root/chrootfiles/.bashrc .
cp /root/chrootfiles/.profile .

chown $ID.$ID .bash*
chown $ID.$ID .profile

# damit kann nix mehr veraendert werden in dem bereich
chattr -R +i dev bin usr etc lib
[/code]

Zum Schluss noch ein paar weiterführende Links:


chrootssh.sourceforge.net

sshchroot

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert.