ArchWiki / SFTP chroot
ArchWiki / SFTP chroot
ja:SFTP chroot zh-hans:SFTP chroot
OpenSSH 4.9+ includes a built-in chroot for SFTP, but requires a few tweaks to the normal install.
Installation
Install and configure OpenSSH. Once running, make sure sftp-server has been set correctly:
Subsystem sftp /usr/lib/ssh/sftp-server/etc/ssh/sshd_configAccess files with sftp or SSHFS. Many standard FTP clients should work as well.
Configuration
Setup the filesystem
* Readers may select a file access scheme on their own. For example, optionally create a subdirectory for an incoming (writable) space and/or a read-only space. This need not be done directly under /srv/ssh/jail - it can be accomplished on the live partition which will be mounted via a bind mount as well.
* It is also possible chrooting into /home directory thus skipping the usage of bind, however the desired user home directory should be owned by root:
# chown root:root /home/<username>
# chmod 0755 /home/<username>
Bind mount the live filesystem to be shared to this directory. In this example, /mnt/data/share is to be used, owned by user root and has octal permissions of 755:
# chown root:root /mnt/data/share
# chmod 755 /mnt/data/share
# mkdir -p /srv/ssh/jail
# mount -o bind /mnt/data/share /srv/ssh/jailAdd entries to fstab to make the bind mount survive on a reboot:
/mnt/data/share /srv/ssh/jail none bind 0 0/etc/fstabCreate an unprivileged user
You do not need to create a group, it is possible to use Match User instead of Match Group.
Create the sftponly user group:
# groupadd sftponlyCreate a user who is a member of the sftponly group and has shell login access denied:
# useradd -G sftponly -s /usr/bin/nologin -d /srv/ssh/jail usernameSSH authentication by password (not recommended) only works if users have access to a login shell (i.e. -s /usr/bin/nologin not set).
Set a (complex) password to prevent account is locked error (may appear even with key authentication):
# passwd usernameConfigure OpenSSH
You may want to use Match User instead of Match Group as been given in the previous step.
Subsystem sftp /usr/lib/ssh/sftp-server
Match Group sftponly
ChrootDirectory %h
ForceCommand internal-sftp
AllowTcpForwarding no
X11Forwarding no
PasswordAuthentication no
/etc/ssh/sshd_configRestart sshd.service to confirm the changes.
Fixing path for authorized_keys
Use the debug mode of OpenSSH on the client and server in case of (pre)auth error(s).
With the standard path of AuthorizedKeysFile, the SSH keys authentication will fail for chrooted-users. To fix this, append a root-owned directory on AuthorizedKeysFile to /etc/ssh/sshd_config e.g. /etc/ssh/authorized_keys, as example:
AuthorizedKeysFile /etc/ssh/authorized_keys/%u .ssh/authorized_keys
PermitRootLogin no
PasswordAuthentication no
PermitEmptyPasswords no
Subsystem sftp /usr/lib/ssh/sftp-server/etc/ssh/sshd_configCreate authorized_keys folder, generate a SSH-key on the client, copy the contents of the key to /etc/ssh/authorized_keys (or any other preferred method) of the server and set correct permissions:
# mkdir /etc/ssh/authorized_keys
# chown root:root /etc/ssh/authorized_keys
# chmod 755 /etc/ssh/authorized_keys
# echo 'ssh-rsa <key> <username@host>' >> /etc/ssh/authorized_keys/username
# chmod 644 /etc/ssh/authorized_keys/usernameRestart sshd.service.
Tips and tricks
Write permissions
The bind path needs to be fully owned by root, however files and/or subdirectories do not have to be.
In the following example the user www-demo uses /srv/ssh/www/demo as the jail-directory:
# mkdir /srv/ssh/www/demo/public_html
# chown www-demo:sftponly /srv/ssh/www/demo/public_html
# chmod 755 /srv/ssh/www/demo/public_htmlThe user should now be able to create files/subdirectories inside this directory. See File permissions and attributes for more information.
Allow upload only
To allow only uploading files via sftp and deny downloading files, change the ForceCommand internal-sftp line:
Match Group sftponly
ForceCommand internal-sftp -u 0666 -p realpath,open,write,close,lstat
/etc/ssh/sshd_configLogging
The user will not be able to access /dev/log. This can be seen by running strace on the process once the user connects and attempts to download a file.
Create sub directory
Create the sub-directory dev in the ChrootDirectory, for example:
# mkdir /usr/local/chroot/user/dev
# chmod 755 /usr/local/chroot/user/devNow you should create socket at /usr/local/chroot/user/dev/log which will be used by openssh. You may directly bind this socket to /dev/log (or /run/systemd/journal/dev-log in case you are using journald) or create using syslog-ng/rsyslog.
Bind to journald
# touch /usr/local/chroot/user/dev/log
# mount --bind /run/systemd/journal/dev-log /usr/local/chroot/user/dev/logTo make it permanent, add an entry to fstab:
/run/systemd/journal/dev-log /usr/local/chroot/user/dev/log none bind,nofail,x-systemd.requires=sshd.service/etc/fstabSyslog-ng configuration
Add to /etc/syslog-ng/syslog-ng.conf a new source for the log and add the configuration, for example change the section:
source src {
unix-dgram("/dev/log");
internal();
file("/proc/kmsg");
};to:
source src {
unix-dgram("/dev/log");
internal();
file("/proc/kmsg");
unix-dgram("/usr/local/chroot/theuser/dev/log");
};and append:
#sftp configuration
destination sftp { file("/var/log/sftp.log"); };
filter f_sftp { program("internal-sftp"); };
log { source(src); filter(f_sftp); destination(sftp); };(Optional) If you would like to similarly log SSH messages to its own file:
#sshd configuration
destination ssh { file("/var/log/ssh.log"); };
filter f_ssh { program("sshd"); };
log { source(src); filter(f_ssh); destination(ssh); };(From Syslog-ng#Move log to another file)
OpenSSH configuration
Edit /etc/ssh/sshd_config to replace all instances of internal-sftp with internal-sftp -f AUTH -l VERBOSE.
Restart service
Restart service syslog-ng and sshd.
/usr/local/chroot/theuser/dev/log should now exist.
Alternatives to SFTP
Secure copy protocol (SCP)
Installing openssh provides the scp command to transfer files. SCP may be faster than using SFTP https://superuser.com/questions/134901/whats-the-difference-between-scp-and-sftp.
Install rssh or scponly as alternative shell solutions.
Scponly
For existing users, simply set the user's shell to scponly:
# usermod -s /usr/bin/scponly usernameSee the Scponly Wiki for more details.
Adding a chroot jail
The package comes with a script to create a chroot. To use it, run:
# /usr/share/doc/scponly/setup_chroot.shProvide answers.
Check that
/path/to/chroothasroot:rootowner andr-xfor others.Change the shell for selected user to
/usr/bin/scponlyc.sftp-server may require some libnss modules such as libnss_files. Copy them to chroot's
/libpath.
See also
https://www.minstrel.org.uk/papers/sftp/