Internet services on Linux

By Rainer Wichmann rainer@nullla-samhna.de    (last update: May 08, 2014)

The following is a short tutorial that explains how to determine which network services are active, and how to shutdown/disable unneccessary services. It is intended mainly for unexperienced Linux users, although not all of the information given here is Linux-specific.

Which services are active ?

Internet services are provided by processes that listen on one or more port(s) for incoming requests (e.g. the request to deliver email to your computer). You can determine the active internet services with netstat -pant. Below is some sample output (truncated to the relevant part). It shows a list of port numbers (22, 25, 80, ...) on which some process is listening.

bash$ netstat -pant
Active Internet connections (servers and established)
Proto Recv-Q Send-Q Local Address           Foreign Address         State       PID/Program name   
tcp        0      0   0.0.0.0:7             0.0.0.0:*               LISTEN     376/xinetd         
tcp        0      0   0.0.0.0:9             0.0.0.0:*               LISTEN     376/xinetd         
tcp        0      0   0.0.0.0:13            0.0.0.0:*               LISTEN     376/xinetd
tcp        0      0   0.0.0.0:19            0.0.0.0:*               LISTEN     376/xinetd         
tcp        0      0   0.0.0.0:37            0.0.0.0:*               LISTEN     376/xinetd         
tcp        0      0   0.0.0.0:3306          0.0.0.0:*               LISTEN     8439/mysqld         
tcp        0      0   0.0.0.0:80            0.0.0.0:*               LISTEN     11208/apache2       
tcp        0      0   0.0.0.0:22            0.0.0.0:*               LISTEN     8717/sshd           
tcp        0      0   0.0.0.0:631           0.0.0.0:*               LISTEN     11244/cupsd         
tcp        0      0   0.0.0.0:25            0.0.0.0:*               LISTEN     8527/master
tcp6       0      0   ::1:631               :::*                    LISTEN     11244/cupsd
tcp6       0      0   :::25                 :::*                    LISTEN     8527/master      

With netstat -pat, you will see the name of the protocol instead of the port number. E.g., 22 will become ssh, 25 = smtp (email), 80 = www-http, etc. The protocols corresponding to numerical port numbers are listed in /etc/services.

As you can see, some services may be offered both on IPv4 as well as on IPv6 (the latter being marked as 'tcp6' by netstat), e.g. in the example above the smtp (email) server and the cupsd (printer) server listen both on IPv4 as well as IPv6. Yoa also see that the printer server (cupsd) only liustens on the local IPv6 interface (::1) and therefore cannot be accessed from the outside.

If you want to disable a service, you need know which program provides this service. With netstat you need to specify the command line option -p to get the name of the command / executable listening on some port.

Alternatively, you can use another tool - lsof - that will tell you which program listens on which port. Below, you can see some sample output from lsof -i (this time with protocol names instead of port numbers):

bash$ lsof -i
COMMAND    PID   USER   FD   TYPE DEVICE SIZE NODE NAME
xinetd      376     root    5u  IPv6    265       UDP *:time
xinetd      376     root    6u  IPv6    266       TCP *:time (LISTEN)
xinetd      376     root    7u  IPv6    267       UDP *:daytime
xinetd      376     root    8u  IPv6    268       TCP *:daytime (LISTEN)
xinetd      376     root    9u  IPv6    269       UDP *:chargen
xinetd      376     root   10u  IPv6    270       TCP *:chargen (LISTEN)
xinetd      376     root   11u  IPv6    271       TCP *:echo (LISTEN)
xinetd      376     root   12u  IPv6    272       UDP *:echo
xinetd      376     root   13u  IPv6    273       TCP *:discard (LISTEN)
xinetd      376     root   14u  IPv6    274       UDP *:discard
mysqld     8439    mysql    3u  IPv4  12640       TCP *:mysql (LISTEN)
master     8527     root   11u  IPv4  12822       TCP *:smtp (LISTEN)
sshd       8717     root    3u  IPv4  13156       TCP *:ssh (LISTEN)
apache2   11208     root    4u  IPv4  25760       TCP *:www (LISTEN)
apache2   11209 www-data    4u  IPv4  25760       TCP *:www (LISTEN)
apache2   11210 www-data    4u  IPv4  25760       TCP *:www (LISTEN)
apache2   11211 www-data    4u  IPv4  25760       TCP *:www (LISTEN)
apache2   11212 www-data    4u  IPv4  25760       TCP *:www (LISTEN)
apache2   11215 www-data    4u  IPv4  25760       TCP *:www (LISTEN)
cupsd     11244   cupsys    0u  IPv4  25840       TCP *:ipp (LISTEN)

You can see that (e.g.) the ssh (secure shell) service is provided by the command sshd. Also, obviously there is one command xinetd that provides multiple services (time, daytime, chargen, echo, discard). xinetd (and inetd, which is a similar program) is a "super-daemon" that waits for requests on specified ports and then starts up the appropriate program to handle that request.

local services

Consider the following output of netstat -pant:

bash$ netstat -pant
Active Internet connections (servers and established)
Proto Recv-Q Send-Q Local Address           Foreign Address         State       PID/Program name   
tcp        0      0 127.0.0.1:3306          0.0.0.0:*               LISTEN     8439/mysqld         
tcp        0      0 127.0.0.1:80            0.0.0.0:*               LISTEN     11208/apache2       
tcp        0      0 127.0.0.1:22            0.0.0.0:*               LISTEN     8717/sshd           
tcp        0      0 127.0.0.1:631           0.0.0.0:*               LISTEN     11244/cupsd         
tcp        0      0 127.0.0.1:25            0.0.0.0:*               LISTEN     8527/master         

... and compare it to the following:

bash$ netstat -pant
Active Internet connections (servers and established)
Proto Recv-Q Send-Q Local Address           Foreign Address         State       PID/Program name   
tcp        0      0   0.0.0.0:3306          0.0.0.0:*               LISTEN     8439/mysqld         
tcp        0      0   0.0.0.0:80            0.0.0.0:*               LISTEN     11208/apache2       
tcp        0      0   0.0.0.0:22            0.0.0.0:*               LISTEN     8717/sshd           
tcp        0      0   0.0.0.0:631           0.0.0.0:*               LISTEN     11244/cupsd         
tcp        0      0   0.0.0.0:25            0.0.0.0:*               LISTEN     8527/master         

Did you spot the difference? In the first example, each service was listed with 127.0.0.1 as 'Local Address', while in the second example the 'Local Address' is always 0.0.0.0.

If a service shows 127.0.0.1 as 'Local Address', it can only be accessed from the local host, not by any remote host, i.e. it is pretty safe to keep it running.

However, if a service shows 0.0.0.0 as 'Local Address', it can be accessed from any remote host, and you should reconsider whether you really need to run it this way.

For IPv6, the equivalent of "127.0.0.1" is "::1", so any service showing up with this address is only accessible from the local host. The IPv6 equivalent of "0.0.0.0" is "::"

Here are a few tips to make a service local:

mysqld

In /etc/my.cnf (or /etc/mysql/my.cnf), set:

[mysqld]
bind-address            = 127.0.0.1

apache 2

Search for 'Listen' in /etc/apache2/*:

bash$ grep 'Listen' /etc/apache2/*
/etc/apache2/ports.conf:Listen 80

...and modify it to include the string '127.0.0.1:' before the port number:

bash$ grep 'Listen' /etc/apache2/*
/etc/apache2/ports.conf:Listen 127.0.0.1:80

sshd

In /etc/ssh/sshd_config, set:

ListenAddress 127.0.0.1

cupsd

In /etc/cups/cupsd.conf, search for 'Listen' and prefix the port number with '127.0.0.1:' as shown here:

Listen 127.0.0.1:631

postfix (master)

In /etc/postfix/main.cf, set:

inet_interfaces = loopback-only

switching off inetd/xinetd services

With the information you have gathered so far, you can shutdown and disable services that you don't need. First, let's discuss services run from the inetd or xinetd deamon. To switch these off, simply comment them out in the inetd / xinetd (whichever you use) configuration file.

inetd is configured by the file /etc/inetd.conf. To switch off services run from inetd, simply comment them out in the configuration file:

Before:

discard       stream  tcp     nowait  root    internal
discard       dgram   udp     wait    root    internal
daytime       stream  tcp     nowait  root    internal
daytime       dgram   udp     wait    root    internal
chargen       stream  tcp     nowait  root    internal
chargen       dgram   udp     wait    root    internal
time    stream  tcp     nowait  root    internal
time    dgram   udp     wait    root    internal

After:

#  discard       stream  tcp     nowait  root    internal
#  discard       dgram   udp     wait    root    internal
#  daytime       stream  tcp     nowait  root    internal
#  daytime       dgram   udp     wait    root    internal
#  chargen       stream  tcp     nowait  root    internal
#  chargen       dgram   udp     wait    root    internal
#  time    stream  tcp     nowait  root    internal
#  time    dgram   udp     wait    root    internal

You must send the SIGHUP signal to inetd for the changes to take effect. Use ps -aux | grep inetd to find the PID (process identification number):

# ps aux | grep inetd
root       376  0.0  0.6  1796  852 ?        S    00:43   0:00 /usr/sbin/inetd
root      3131  0.0  0.4  1272  520 pts/0    S    10:33   0:00 grep inetd
# kill -HUP 376

xinetd is configured by the file /etc/xinetd.conf. You can mark services as disabled in this file and send SIGUSR1 to the xinetd process to make the changes take effect:

Before:

defaults
{
        ....

}

After:

defaults
{
        ....

        disabled        = ftp
        disabled        = discard
        disabled        = chargen
        disabled        = daytime
        disabled        = time
        disabled        = echo
}

You must send the SIGHUP signal to xinetd for the changes to take effect. Use ps -aux | grep xinetd to find the PID (process identification number):

# ps aux | grep xinetd
root       376  0.0  0.6  1796  852 ?        S    00:43   0:00 /usr/sbin/xinetd
root      3131  0.0  0.4  1272  520 pts/0    S    10:33   0:00 grep xinetd
# kill -HUP 376

switching off standalone services - Ubuntu 'upstart'

This section explains how to switch off a service handled by the 'upstart' service which is used by Ubuntu Linux. For the traditional SYS V init method see next section.

Temporarily switching off/on a service

To switch off a service temporarily, use the command service servicename stop, e.g.
# service ssh stop
To switch on a service again, use the command service servicename start, e.g.
# service ssh start

Prevent a service from starting at boot

For every service handled by upstart, there exist an init script in the directory /etc/init which is named /etc/init/servicename.conf To prevent a service from starting at system boot, you could just remove that script or simply rename it to remove the .conf at the end. However, this isn't really a good idea because the next software update will likely restore it. You can also edit the file and comment out the line near the top starting with "start on". The recommended way (as of Ubuntu 11.10) is to create a file /etc/init/servicename.override with the single line manual:
# echo "manual" > /etc/init/servicename.override

switching off standalone services - tradidional SYS V

This section explains how to switch off a service handled by traditional SYS V init scripts.

runlevels

Services not run from inetd / xinetd are usually started at system boot. This is controlled by a group of directories named /etc/rc1.d, /etc/rc2.d, ... (Debian, Fedora) or /etc/init.d/rc1.d, /etc/init.d/rc2.d/, ... (SuSE) or /etc/runlevels/.../ (Gentoo).

The numbers in the directory names correspond to runlevels (on Gentoo, runlevels are named, not numbered), and scripts (or links to scripts) in such a directory identify the services that are active in the respective runlevel.

A runlevel is basically a software configuration of the system. E.g. there is a single-user runlevel, a runlevel with network, multi-user, and X, etc. On Linux, the present runlevel can be determined from the runlevel command (order: previous(N=none), current), so this is runlevel 3:

# runlevel
N 3

The default runlevel is configured in /etc/inittab. E.g. the following line in /etc/inittab selects 2 as the default runlevel.

# The default runlevel.
id:2:initdefault:

There is usually a main directory (/etc/init.d or /etc/rc.d) that holds startup scripts for each service. Each script is named after the respective command (e.g. for starting sshd there is a script that also is named sshd). In the individual runlevel directories there are links to that script which are named (e.g.) Sxxsshd, Kxxsshd.

# ls -l /etc/rc3.d/*sshd
lrwxrwxrwx  1 root  root   11 Jul 30 19:18 /etc/rc3.d/K20sshd -> ../init.d/sshd
lrwxrwxrwx  1 root  root   11 Jul 30 19:18 /etc/rc3.d/S20sshd -> ../init.d/sshd

The links starting with "S" are for starting the service, and those with "K" are for stopping the service. The "xx" is a number indicating the order in which the startup/stop scripts are executed.

stopping a service

To stop the service immediately, execute the startup/stop script manually, using stop as argument:

# /etc/init.d/sshd stop

preventing a service from startup at system boot

To prevent a service from becoming active at system boot, simply remove the corresponding link for the runlevel into which your system boots by default (should you ever want to run the service again, just recreate the links).

Most Linux distributions provide tools to handle this. For all of them, the argument service-name is the name of the script in /etc/init.d that starts the respective service:
Debian, Ubuntu: update-rc.d -f service-name remove
SuSE: insserv -r service-name
Fedora: chkconfig --del service-name
Gentoo: rc-update del service-name

Of course, you can also just delete the symlinks manually. E.g. the following commands disable ssh in runlevel 2 on Debian:

# rm /etc/rc2.d/S20sshd
# rm /etc/rc2.d/K20sshd
Creative Commons License
This work is licensed under a Creative Commons Attribution-NonCommercial-ShareAlike 2.0 Germany License.