Allow Ubuntu Server Access only from specific IP's

How I can allow only my own ip to login for my ubuntu server ? Yesterday got 1500 unwanted failed login attempts.

Allowing only my own IP, could be the most secure from hackers ? I use Postfix only for sending, so that wont need to allow any incoming connections.


Solution 1:

You can use ufw

When you enable ufw with any rules to allow some traffic all is in deny state.

sudo ufw enable

with this command you will enable Ubuntu Firewall

To see status use

sudo ufw status

Status: active

To                         Action      From
--                         ------      ----
69                         ALLOW       Anywhere
53                         ALLOW       Anywhere
22                         ALLOW       213.xxx.xxx.xxx
80/tcp                     ALLOW       194.247.xxx.xxx
21/tcp                     ALLOW       194.247.xxx.xxx
69 (v6)                    ALLOW       Anywhere (v6)
80 (v6)                    ALLOW       Anywhere (v6)

This rules accept any on port 69, any on port 53, ssh from 213.xxx.xxx.xxx, 80 and 21 from 194.247.xxx.xxx ... and deny any other inbound traffic

Complete command for rule in ufw is

sudo ufw [--dry-run] [delete] [insert NUM]  allow|deny|reject|limit  [in|out on INTERFACE] [log|log-all] [proto protocol] [from ADDRESS [port PORT]][to ADDRESS [port PORT]]

Based on this rule template you can allow from xxx.xxx.xxx.xxx on port 80 with this rule

for specific host

sudo ufw allow proto tcp from xxx.xxx.xxx.xxx to any port 80

if you want to allow any to access your web server

sudo ufw allow proto tcp from any to any port 80

if you wish to allow access from specific network

sudo ufw allow proto tcp from xxx.xxx.xxx.xxx/yy to any port 80

where

xxx.xxx.xxx.xxx - represent network ip

yy - represent network mask

Solution 2:

If you don't use (or don't want to use) ufw and instead need an iptables answer, here's the gist of how to do it. Note you also have to adapt to IPv4 and IPv6.


IPv4

First, examine your iptables rules (iptables -L -n). Assuming a default installation, then you'll have no rules.

iptables -A INPUT -s SOURCEIP/CIDR -p tcp --dport PORTNUM -j ACCEPT is the general syntax to add a rule to the end of the INPUT table, specifically stating that "I want to permit the source IP adddress (and range of IPs, if a CIDR suffix is provided - it's not necessary) access to my server when requests come to port PORTNUM via TCP". If you want to only permit one IP address, then omit the /CIDR part with SOURCEIP.

If you have any rules in the INPUT table to deny access (at the end) you will need to use iptables -I INPUT RULENUMBER (where RULENUMBER is the line number in the INPUT table where you want to insert this rule).

Make sure, however, that you also add rules such as these:
iptables -A INPUT -i lo -j ACCEPT - Accept anything over the localhost loopback (127.0.0.1, etc.)
iptables -A INPUT -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT - Accept traffic related to already established connections (required to make sure communication back to your server and your remote client works)

After that configuration is done, you now need to add a rule to deny all other connections. Such a rule would be this, added to the end of the INPUT table:
iptables -A INPUT -j REJECT --reject-with icmp-host-unreachable.


IPv6

First, examine your ip6tables rules (ip6tables -L -n). Assuming a default installation, then you'll have no rules.

ip6tables -A INPUT -s SOURCEIP/CIDR -p tcp --dport PORTNUM -j ACCEPT is the general syntax to add a rule to the end of the INPUT table, specifically stating that "I want to permit the source IP adddress (and range of IPs, if a CIDR suffix is provided - it's not necessary) access to my server when requests come to port PORTNUM via TCP". If you want to only permit one IP address, then omit the /CIDR part with SOURCEIP.

If you have any rules in the INPUT table to deny access (at the end) you will need to use ip6tables -I INPUT RULENUMBER (where RULENUMBER is the line number in the INPUT table where you want to insert this rule).

Make sure, however, that you also add rules such as these:
ip6tables -A INPUT -i lo -j ACCEPT - Accept anything over the localhost loopback (127.0.0.1, etc.)
ip6tables -A INPUT -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT - Accept traffic related to already established connections (required to make sure communication back to your server and your remote client works)

Additionally with IPv6, you need to actually accept pretty much every ICMPv6 packet as it's far more required than in IPv4. This would achieve that:
ip6tables -A INPUT -p ipv6-icmp -j ACCPET

After that configuration is done, you now need to add a rule to deny all other connections. Such a rule would be this, added to the end of the INPUT table:
ip6tables -A INPUT -j REJECT --reject-with icmp6-addr-unreachable.


Make these rules persistent (`iptables` only solutions need this)

Time to make the rules stick persistently. Lets install iptables-persistent. apt-get install iptables-persistent.

The installation will ask if you want to save your current rules. Tell it "yes" for both IPv4 and IPv6 prompts. The ruleset we just 'added' to or created will now be persistently available.

(If you use ufw instead of iptables, you will not need to install this package)


While ufw will automatically manage the ruleset to make sure it's in the right order, iptables is the 'sysadmin' way of doing advanced firewalling. UFW just does easy rules and functions - complex ones you have to do with iptables or add manually to the configuration files for ufw with iptables syntax.