Taco Steemers

A personal blog.
☼ / ☾

Setting up a Secure FTP server (SFTP)

We want to set up a secure FTP server (let us call this 'the service', to avoid confusion). This service will receive backups. The service (and it's clients) don't need access to any unrelated commands. So we will make an empty PATH and won't let the users perform a normal login. The service only needs to have access to one directory. We will attempt to restrict it to that directory by using the chroot utility ('change root') which will restrict the service's view of the server's filesystem. The service will need to be able to find all it's dependencies as well. One complication is that this will entail having to place the service and it's dependencies in a location that is not known to the normal system update service. I considered trying to fix this by automatically copying the updated versions over the new versions and restarting the service, until I realized a symlink would probably be much better.

As it turns out, there is a good but shallow tutorial over at Debian Administration . This tutorial shows the correct settings to set in /etc/ssh/sshd_config . These are 'Subsystem sftp internal-sftp' and

Match group sftponly
     ChrootDirectory /home/%u
     X11Forwarding no
     AllowTcpForwarding no
     ForceCommand internal-sftp

According to this tutorial, the system described there does not suffer from the mentioned update problems. We can use this tutorial. Be sure to set 'AllowTcpForwarding no' so that your service cannot be used as a proxy. Note that internal-sftp is not the binary that we run, that is still the regular ssh server. It is an instruction to use a version of the sftp service that can work in combination with chroot. Only that instruction will be run when a user in sftponly tries to use the service.

Unfortunately, there seems to be no way to have a user use a chrooted SFTP service while still allowing their accounts to easily be used for other services. This is because one will want to let these other services store files in the user's home directory, which the user will be able to access. This access is not always desired. The reason that one cannot constrain the SFTP user to a specific directory in the home directory of the user, has to do with the proper usage of access patterns when using chroot, and the access patterns enforced by sshd. If we want to use /home/%u as the chroot directory, we must allow only root to manipulate that directory. As a result, we need a directory that the user has privileges in, let's make that /home/%u/sftp . However, when the user connects to SFTP, they will be dropped into their home directory, /home/%u . We removed their privileges for this directory. To let the user be dropped into /home/%u/sftp instead, we need to make that their home directory. This makes it difficult to store files that should not be accessible over SFTP.

Let's start setting up the service. First, we create a group sftponly to which we will add the user accounts intended for sftp. We remove the users from other groups . From here, we can largely follow the other tutorial. To troubleshoot problems, stop the sshd service and use /usr/sbin/sshd -d which will give easy access to debug logging. To allow the sshd to do it's work, we have to set chmod 755 /home/myuser/ and chmod 755 /home/myuser/sftp . Preferable I would only have let the owners interact with the intended directories, using chmod -R o-rwx . on /home/myuser. However, this will cause SFTP to malfunction; it cannot drop the user in the user's directory, as it does not have access to it. We set the user's home directory to the files directory inside the user's SFTP root directory; usermod -d /sftp myuser . At this point, the user will be dropped in /home/%u/sftp/files when they have succesfully connected. To stop the user from logging in over SSH, we disable their shell; usermod -s /sbin/nologin myuser . If the user tries to SSH, they will be told that 'This service allows sftp connections only.'