Modem communications under Linux are powerful, but complex. Modems can be run as either standard terminal devices, or as network links that are directly maintained by the kernel.

One way to approach network communications under Linux is with the Point to Point Protocol (PPP). PPP can be used as a medium for TCP/IP (the protocol associated with the Internet) and IPX (used by Novell Netware).

The approach to PPP taken in this chapter will be one that is compatible with the methods used in Microsoft Windows. The approach used by Windows is not particularly secure, but it is ubiquitous.

Client PPP

Establishing a PPP client connection under Linux is rather simple.

The “Control Panel” application that runs under X Windows can be used to establish PPP connections. However, the shell scripting approach outlined below is much more flexible. It can be used in non-X environments and it does not require root access. For completeness, the method utilizing the control panel is addressed later.

Regardless of the method used to establish PPP, /etc/resolv.conf must be adjusted to allow Internet host names to be resolved. A Linux system can rely upon a remote DNS server for these functions, or it can run a caching-only server itself.

PPP - The Scripting Approach

To connect to a remote PPP server, the following three files should be placed on the local Linux system:

In the /bin/network file:

#!/bin/sh

exec /usr/sbin/pppd -detach lock modem crtscts \
	defaultroute user USERNAME /dev/ttyS1 57600 \
	connect "/usr/sbin/chat -f /bin/network.chat"

And in the /bin/network.chat file:

'ABORT' 'BUSY'
'ABORT' 'ERROR'
'ABORT' 'NO CARRIER'
'ABORT' 'NO DIALTONE'
'ABORT' 'Invalid Login'
'ABORT' 'Login incorrect'
'' 'ATZ'
'OK' 'ATDT 1234567'
'CONNECT' ''

And in the /etc/ppp/pap-secrets file:

# Secrets for authentication using PAP
# client    server              secret              IP addresses
USERNAME    ""                  PASSWORD

The scripts above will require some modifications:

  1. The correct serial port for the modem must be set in /bin/network.
  2. Replace 1234567 with the ISP telephone number in the /bin/network.chat script.
  3. Replace the USERNAME and PASSWORD in /etc/ppp/pap-secrets and /bin/network with the PPP account name and password on the Dial-Up server.
  4. Optionally, place the line “ogin:--ogin: ''” on the end of the /bin/network.chat file. This will cause the local Linux system to expect the remote server to issue a “login:” message before the PPP session commences. If such a message is not received, a carriage return will be sent in an effort to “prod” the remote server to supply it.
  5. Run the command “chmod 755 /bin/network” to enable the network script to be executed from the shell.
  6. Optionally, run the command “chmod u+s /usr/sbin/pppd” and change the permissions of the serial port device in the /dev directory to mode 666 (read and write access for everyone). This will allow all users on the system to bring the PPP link up or down. The root user might also create a “ppp group” to permit only trusted users to administer the interface.

The “demand” option to pppd is quite useful in establishing on-demand PPP connection. It allows for the link to be initiated only in the event of outbound network traffic, and has options for the termination of a PPP connection that is idle for a certain amount of time, and the reestablishment of the connection if traffic is generated on an inactive link. Finally, with Red Hat Linux 6.0, the kernel shipped contains a driver for this option of pppd (the option has been available but nonfunctional since a patch for version 5.0).

Following is a modified version of /bin/network that uses the demand-dialing approach:

#!/bin/sh

exec /usr/sbin/pppd demand idle 300 192.168.1.2:192.168.1.1 \
	-detach lock modem crtscts \
	defaultroute user USERNAME /dev/ttyS1 57600 \
	connect "/usr/sbin/chat -f /bin/network.chat"

The above script has the “demand” option, which will bring the link down after a period of inactivity. This period is defined by the argument to the “idle” parameter. This parameter is given in seconds, and is set to 5 minutes (300 seconds) in this case.

The main limitation to the “demand” parameter is that the IP address assigned to the device must be known before the connection is made. The manual page for pppd indicates that dynamically assigned IP addresses can be handled in a demand-dialing arrangement, but tests run by the author did not confirm this assertion. If the IP address assigned by the remote PPP server cannot be held constant, the diald demand-dialing daemon should be investigated as it is much more flexible in such an arrangement.

More information on attaching Linux to an ISP is available in the ISP-Hookup-HOWTO at ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO/ISP-Hookup-HOWTO.

PPP - From the Control Panel

To use the graphical PPP controls, X windows must be running correctly. From within X, open a terminal window and enter the command “control-panel” to launch it.

Before the control panel can launch a PPP session, a symbolic link must be set from /dev/modem to the actual serial port device. This can be done manually from a shell, or it can be accomplished through the control panel itself. To do so, click the Modem Configuration icon. It is not labeled, but it looks like this:

Select the serial port device for the modem from the list, and click “OK”.

From the control panel, open the “Network Configuration” dialog. The Network Configuration icon is not labeled, but it looks like this:

The Network Configuration dialog will be presented. Press the “Interfaces” button, and something like the following will appear:

Choose the “Add” option, and a menu of possible interface types will be displayed:

Ensure that “PPP” is selected, and click “OK.” A dialog to create the PPP interface will follow. Replace the relevant sections with settings for your own ISP:

Click done when the settings are correct. A confirmation dialog will appear:

After the settings are saved, the PPP device will be added in the Network Configuration dialog. Highlight it and click activate.

If all is correct, the modem should go off-hook and begin dialing.

A similar control interface for client PPP exists in the linuxconf utility, but it is not discussed here.

Name Resolution

On the Internet, there is no way to reach a host without its IP address. Regardless of the structure of a host name (such as host.foo.com), unless the hostname can be converted into an IP address (such as 1.2.3.4), the host is unreachable.

This conversion does not happen “by magic,” but is caused by Internet DNS servers (as is discussed in the DNS administration section of this text). A few name-IP translations can be entered into the /etc/hosts file, but such a lookup table becomes impractical for large numbers of hosts.

For a Linux system behind a PPP connection, there are two options in accomplishing DNS name resolution: either rely upon a remote DNS server on the far side of the PPP link, or run a local DNS server. There are advantages and drawbacks to each approach.

If a remote DNS server is used, configuration of the local Linux host is very simple. However, traffic will be generated for each hostname lookup which will consume a small portion of the PPP connection bandwidth.

If a local DNS server is configured and used, host name lookups are cached by the local DNS server. There is no further bandwidth consumption of the PPP connection after the first lookup of a remote host (until the caching period set by the remote authoritative DNS server expires). However, a caching-only name server running at boot time with no network access to the Internet can confuse some daemon processes (notably the Postgres SQL server, the Apache web server, and Sendmail). Also, the initial configuration of the name server is cumbersome.

To configure a Linux system to use remote DNS servers, the IP addresses of the servers will be required (up to three servers can be used). These addresses can be obtained from the remote ISP or system administrator. Please note that Linux will not accept DNS servers passed in the negotiation phase of the PPP connection (MSDNS is rejected for security reasons).

When the addresses of the remote servers have been obtained, the /etc/resolv.conf should be configured as follows:

search isp.net
nameserver 1.2.3.4
nameserver 5.6.7.8
nameserver 9.10.11.12

Replace the “isp.net” above with the domain name of the ISP or upstream authority. The secondary and tertiary nameserver entries may be omitted, but at least one operational server must be entered.

If a local caching-only server is preferred, the server must be loaded and configured. The DNS server and caching-only settings can be loaded at any time after installation by issuing the following commands from the RedHat/RPMS directory of the installation tree:

rpm -Uvh bind-8.2-6.i386.rpm
rpm -Uvh caching-nameserver-6.0-2.noarch.rpm

Installing the Bind package will automatically configure it to be launched at boot time through the /etc/rc.d/init.d/named startup script. If this is not the desired behavior, use the ntsysv utility to alter the boot status. The name server can also be manually started and stopped with this script.

Once the server is loaded, Linux must be instructed to use it. To specify the local host as the primary name server, make sure that the first nameserver directive in /etc/resolv.conf reads as follows:

nameserver 127.0.0.1

If the file does not exist, create it with permissions of 644.

Server PPP

The Linux pppd daemon has flexible configuration options and it can communicate with a variety of different TCP/IP protocol stacks. However, pppd has few options for controlling a modem. It does not send modem initialization strings and it does not answer ringing telephone lines.

The various getty implementations are usually responsible for controlling terminal hardware (which includes establishing modem sessions). mingetty is used on Red Hat Linux to control VGA console logins, but it has no options for manipulating a serial port. Some common getty implementations include mgetty, agetty, and uugetty. However, most of these know nothing about PPP network sessions.

There are two software components that will solve these problems. mgetty will be used to control the serial lines and answer the modems. mgetty will use the exec() system call to spawn pppd if it detects the start of a PPP session (which is a unique feature of the Linux getty implementations). pppd will then authenticate the user (using either the system password database, or its own database of valid users), and then start a network connection if access is granted.

Configuring mgetty

mgetty is not installed by default in Red Hat Linux; it must be explicitly loaded after installation has completed. This can be done by issuing the following command from the RedHat/RPMS directory of a Red Hat Linux installation tree:

rpm -Uvh mgetty-1.1.14-8.i386.rpm

The above command will install the mgetty binary and associated configuration and documentation files. For the most common PPP server configuration, modify the file /etc/mgetty+sendfax/mgetty.config so that the top two lines read:

speed 115200
modem-type data
rings 1

If you want to enable FAX transmissions with mgetty, you might want to use different options in this file. If so, consult the documentation at http://www.leo.org/~doering/mgetty/mgetty_toc.html for further information (additional RPM components will be required).

You should also modify the file /etc/mgetty+sendfax/login.config so that it contains the line:

/AutoPPP/ -     a_ppp   /usr/sbin/pppd 115200

There will be another commented AutoPPP line that passes many more options to pppd. It is more convenient to place these switches in /etc/ppp/options (so “ps aux” listings remain uncluttered), so these options are removed here.

When mgetty is running, it will place log files in /var/log. You may want to either clean them out manually from time to time, or put the log files on automatic rotation.

Options in /etc/ppp

After you have installed mgetty, run the following command to configure your /etc/ppp/pap-secrets file to allow PAM logins:

echo '* * "" *' >> /etc/ppp/pap-secrets

At this point, IP addresses must be assigned to each of the modem lines that will be providing PPP services. These IP addresses will be recorded in the /etc/ppp/options* files.

Your /etc/ppp/options file contains control parameters for all pppd sessions that run on your system. It should contain the following:

auth
login
modem
crtscts
lock
proxyarp
ms-dns x.x.x.x
ms-dns y.y.y.y

All of these options are discussed in the pppd man page, but below is a quick synopsis:

auth
Force the remote PPP system to authenticate.
login
Authenticate against the system password database (/etc/password, /etc/shadow or whatever else PAM is configured to use), and record the session in the wtmp file.
proxyarp
Configure the Ethernet card to respond to ARP requests for the IP address of the remote PPP system.
ms-dns x.x.x.x
Pass the IP address of a DNS server to the client. This only works for Windows clients. You should have no more than two of these entries in the options file. This option won't work unless your pppd was compiled with -DUSE_MS_DNS, but it makes the configuration of the client much easier.

Each serial device that will support dialup PPP must have a unique option file. If you plan to attach a modem to /dev/ttyS1 (DOS COM1:), the file /etc/ppp/options.ttyS1 will contain parameters specific to that modem.

For example, a PPP server at IP address 1.2.3.1 might allocate 1.2.3.4 as the IP address for the PPP dialup. This configuration would require the file /etc/ppp/options.ttyR1 to contain the single line:

1.2.3.1:1.2.3.4

The first parameter above is the IP address of the dialup server. The second parameter is the IP assigned for that line. Each serial line must have a different IP address.

The “proxyarp” option listed above deserves greater attention. If proxyarp is excluded, the serial devices will be able to transmit network data to the server, but they will not be able to communicate with any other machine. (The proxyarp option configures the Ethernet devices to answer ARP requests for the PPP IP addresses.) Specific dialup lines that are intended for local access only might require that the proxyarp parameter be moved out of /etc/ppp/options and into the device-specific options files for the lines that will receive total network access.

In addition to “proxyarp,” one other step is required to allow the PPP device to exchange data with the LAN device: forwarding of packets across the networking interfaces must be enabled. To accomplish this, a modification must be made to the /etc/sysconfig/network file. If forwarding is disabled (which is the default), there is a line in the file that reads:

FORWARD_IPV4=false

To enable forwarding, change the line to:

FORWARD_IPV4=true

The instructions in this file are only executed at boot time. To enable forwarding without rebooting the system, enter the command:

echo 1 > /proc/sys/net/ipv4/ip_forward

If no IP addresses are available to allocate for serial devices, one might consider using bogus IP addresses in the 192.168.x.x range, and proxy software like the free TIS FireWall ToolKit discussed in Chapter 4. Normally, proxyarp cannot be used in such a situation. Information on IP Masquerade (discussed in the firewall section of this text) might also be helpful.

Adding mgetty to /etc/inittab

Each serial line will be controlled by an entry in /etc/inittab. An entry for ttyS1 might look like:

S1:345:respawn:/sbin/mgetty ttyS1

Similar lines must be added describing each serial device on the system that is participating in the mgetty/pppd arrangement.

After the changes to /etc/inittab are complete, the Linux system must be rebooted or the shell command “init q” must be entered while logged in as root. The lights on any external modems will flash (if external modems are present).

Inactive modems can be reinitialized at any time by entering the command “killall mgetty” (be cautious of this command on non-Red Hat systems).

Additional Logging Information

Most system services send activity logs to the syslog daemon. The syslog daemon records most of this information in /var/log/messages (mail system log data goes to /var/log/maillog, other logging locations can be found by examining /etc/syslog.conf).

It is relatively simple to copy this logging information to an inactive virtual console so that it might be examined in real time. To do so, enter the following command:

echo '*.*		/dev/tty9' >> /etc/syslog.conf

Then, reboot the system (or send a HUP signal to the syslog daemon).

If the CTRL-ALT-F9 keys are pressed simultaneously, virtual console number nine should come into view. It should contain the complete output of the syslog daemon. Any PPP activity should be immediately logged to this screen, as well as activity from other major system services (such as DHCP, the mail transport utilities, DNS, etc.).

To return to the login on virtual console number one, press CTRL-ALT-F1. To return to the X-Windows session (if one is running), press CTRL-ALT-F7.