You can make the authentication/authorization even more secure by creating larger 4096-bit keys instead of the default 2048 bits. To do so, append –b 4096 to the ssh-keygen command. It will look like this:

ssh-keygen -t rsa -b 4096

Copying a Public Key

To use the key pair you created on your machine for SSH authentication, you need to place the public key on the desired server. The simplest way to do so is to use a tool available with OpenSSH: ssh-copy-id.

The procedure is easy:

  1. Type in ssh-copy-id username@host_address.
  2. If you are connecting for the first time to this host, you will get an authenticity message. Type Yes to continue.
  3. Input your password when asked, and the tool will copy the contents of ~/.ssh/ id_rsa.pub key to the authorized_keys file under the ~/.ssh home directory on the server.

Note: no characters will be visible while you are typing your password due to security purposes.

  1. You will get a message:
    Number of key(s) added: 1
    Now try logging into the machine, with: "ssh 'username@'"
    and check to make sure that only the key(s) you wanted were added.

    Your public key has been placed on the remote server, and now you can log into it without entering the account’s password.

  2. To test if the authentication with keys is working, connect to your server with ssh username@host_address. If successful, you will be automatically logged in. In case you have previously set up a passphrase, you will need to enter it first before you are granted access to the server.

    How do the keys work

    In simple terms, a public key is with security not a key. In fact, it behaves like a padlock that you can put on an SSH account on another machine. When you run the ‘ssh-keygen’ utility, you generate both the padlock and the key that opens it, id_rsa.pub and id_rsa respectively.

    You can make as many copies of the ‘padlock’ as necessary, distribute them to any server you need to, and only you will have the right key to unlock them. That is why it is important to keep the private key safe because it unlocks all copies of the ‘padlocks’ you handed out. It does not matter where you put your public key as long as the master key does not get compromised. Since nobody else possesses the private key, this method for authorization and authentication is probably the safest out there and highly recommended.

3. Disable server SSH root login.

Linux distributions have outside root access enabled by default which may be a serious security threat since hackers can try to crack the password with brute force attacks. It is recommended to disable root login and use a regular account and a su – command to switch to root user.

Before you disable root login, make sure that you have added an account that can gain root access and follow the steps below:

  1. Use SSH to log into the server as root.
  2. Use a text editor of your choice to open the main configuration file. This time, we will use the vi editor.
    vi /etc/ssh/sshd_config
  3. Find the line that says PermitRootLogin_yes and change to PermitRootLogin_no. You may need to scroll down a few lines to find it.
  4. It is important to add the user account you will use to log in. Just add another line with the username in question:
    AllowUsers your_username_here
  5. Save the changes you made and then exit the text editor.
  6. Restart the SSH service but do not close the root session yet. For Ubuntu/Debian use sudo service ssh restart and for Fedora/CentOS use service ssh restart command.
  7. Open a new terminal window and verify that you can now log in as the user you added. Once you confirm it works, exit the active root session.

4. Disable password-based logins on your server.

If you are using SSH keys for SSH authentication, you can disable server password authentication altogether. This is another way to prevent brute-force attacks and attempts to crack your password. Before you proceed, double check if SSH key-based authentication is working for the root account on the server or for an account with the sudo access.

When you are ready, complete these steps:

  1. Use SSH keys to log into the server as root or with sudo privileges.
  2. Use a text editor of your choice to open the sshd_config file. We will use vi:

vi /etc/ssh/sshd_config

  1. Look for the line that says PasswordAuthentication and change to PasswordAuthentication_no. Make sure to uncomment the line if the # is present.
  2. Save the changes you made and then exit the text editor.
  3. Restart the SSH service to apply the changes. For Ubuntu/Debian use sudo service ssh restart and for Fedora/CentOS use service ssh restart command.

Congratulations, you have successfully disabled the option to log in through SSH using account passwords. SSH Daemon will simply ignore any authentication requests which do not include private/public key pairs.

4. Restrict SSH Access using Iptables.

Iptables is a Linux utility used for configuring firewall rules and monitoring/filtering incoming and outgoing traffic to your server. It is included by default with most Linux distributions.

With iptables, you can define rules that limit or permit traffic for different kinds of services by IP address, port or network protocol and thus substantially improve the security of your server. In our case, we will set rules to restrict the incoming SSH traffic for everyone but one IP address or subnet.

This way, blocking port 22 will not only stop unauthorized access to your serves but can also stop some DDoS attacks.

While making this step, you should make sure you do not lock yourself out by completely blocking SSH traffic. You will need to use only a few commands to allow a specific IP address or subnet for incoming SSH connections.

Note: SSH Linux commands are case sensitive.

  1. This rule will whitelist the IP address that you typed in. Please replace the example IP in the command with your IP. You can also use a subnet, for example, iptables -A INPUT -p tcp -s 123.456.78.90 –dport 22 -j ACCEPT
  2. You need to save the rules, so you do not lose them after reboot:
    sudo iptables-save

If you want to view the list of all iptables rules, you can use the iptables –L command. To include more details such as packet, byte and target information, append –v to the command above. Add -n to all of it and output will be displayed in numeric format.

In case you want to reset all rules and start clean, use the flush command iptables –F. This will clear the iptables configuration which is useful if you are unsure if everything is set up as you want to.

Iptables parameters and Options Definitions

Here are some explanations for iptables parameters, options, and values used in the examples above, as well as a few of them not mentioned before.

>Parameter Description
-c counters allows setting the packet and byte counters of a specific rule
-d destination – can be an address, name of a host or address, etc.
-f fragment – applies the rule to the second and the fragments that follow it
-g goto chain – states that the action will continue in a user-specified chain
-i in-interface – states the name of the interface from where packets come
-j jump – specifies the action if a packet matches the rule
-o out-interface – the name of the interface of an outgoing package
-p protocol – any available protocol such as SSH, TCP, UDP, FTP.
-s source – can be an address, name of a host or address, etc.
Value Description
ACCEPT Allows the packets to pass through
DROP Blocks the packets
RETURN Tells to skip the current chain and resume at the next rule in the previous (calling) chain
Chain Description
INPUT Controls the incoming packets.
FORWARDS Forwards the packets coming to your server but destined for somewhere else
OUTPUT Filters packets going out of your server
Option Description
-A append adds one (or more) rules of the selected chain
-C check – checks for a rule that matches the criteria in the selected chain
-D delete – deletes only one rule from the selected chain
-F flush – deletes all defined iptables rules
-I insert – insert a rule into the selected chain
-L list – displays the rules of the selected chain
-n numeric – shows the IP address/hostname and return value in a numeric format
-N new-chain <name> – creates a new user-defined chain
-v verbose – used in the combination with -L to provide additional information
-X delete-chain <name> – deletes the user-defined chain.

Conclusion, ssh security best practices

Whether you are building a new server or a virtual machine, it is a good practice to implement multiple security layers within your environment. Businesses are usually keen on setting up their infrastructure as soon as possible, but necessary security measures have to be applied right from the start.

If you combine Linux SSH security methods listed in this article with security tips, you will make it hard for the hackers to penetrate your server(s) and cause any damage. Make sure you implement as many of them as possible before your server is available on the network.