Restricting public keys

It may be the case that while you’re happy to allow a user or process to have public key authentication access to your server via the ~/.ssh/authorized_keys file, you don’t necessarily want to give them a full shell, or you may want to restrict them from doing things like SSH port forwarding or X11 forwarding.

One method that’s supposed to prevent users from accessing a shell is by defining their shell in /etc/passwd as /bin/false, which does indeed prevent them from logging in with the usual ssh or ssh command syntax. This isn’t a good approach because it still allows port forwarding and other SSH-enabled services.

If you want to restrict the use of logins with a public key, you can prepend option pairs to its line in the authorized_keys file. Some of the most useful options here include:

  • from="<hostname/ip>" — Prepending from="*" to the key line would only allow public-key authenticated login if the connection was coming from some host with a reverse DNS of You can also put IP addresses in here. This is particularly useful for setting up automated processes through keys with null passphrases.
  • command="<command>" — Means that once authenticated, the command specified is run, and the connection is closed. Again, this is useful in automated setups for running only a certain script on successful authentication, and nothing else.
  • no-agent-forwarding — Prevents the key user from forwarding authentication requests to an SSH agent on their client, using the -A or ForwardAgent option to ssh.
  • no-port-forwarding — Prevents the key user from forwarding ports using -L and -R.
  • no-X11-forwarding — Prevents the key user from forwarding X11 processes.
  • no-pty — Prevents the key user from being allocated a tty device at all.

So, for example, a public key that is only used to run a script called runscript on the server by the client runscript@client.example:

command="runscript",client="client.example",no-pty,no-agent-forwarding,no-port-forwarding ssh-rsa AAAAB2....19Q runscript@client.example

A public key for a user whom you were happy to allow to log in from anywhere with a full shell, but did not want to allow agent, port, or X11 forwarding:

no-agent-forwarding,no-port-forwarding,no-X11-forwarding ssh-rsa AAAAD3....19Q user@client.example

Use of these options goes a long way to making your public key authentication setup harder to exploit, and is very consistent with the principle of least privilege. To see a complete list of the options available, check out the man page for sshd.

6 thoughts on “Restricting public keys

  1. Pingback: Quickies: restricting SSH public keys « 0ddn1x: tricks with *nix

  2. Pingback: Jail (Chroot) SSH Users | The Brainwrecked Tech

  3. I believe that the use of no-port-forwarding also blocks dynamic port forwarding (-D).

    Once you close port forwarding with no-port-forwarding, you can open specific ports with permitopen. In addition, I believe that use of permitopen implies no-port-forwarding. For example:: no-pty,permitopen=”localhost:143″,permitopen=”localhost:25″ ssh-rsa AAAAB3Nz… prevents use of any ports except 25 and 143. Unfortunately, it is my experience that once you cannot use permitopen to open reverse or dynamic ports, so with any restriction of ports using either no-port-forwarding or permitopen you lose the ability to do reverse or dynamic port forwarding.

  4. Pingback: Monitor the status of a GitHub Enterprise replica | Clifford Sanders

Leave a Reply

Your email address will not be published. Required fields are marked *

You can use Markdown if you want.