InformIT

Linux Thin Clients: The Server

Date: Mar 18, 2005

Sample Chapter is provided courtesy of Addison-Wesley Professional.

Return to the article

Linux offers an excellent alternative for businesses looking for something different in an OS. However, Linux with all of its components and options installed can be a massive resource hog. Enter "thin clients," pared-down Linux installations, which offer a streamlined OS for lighter system usage.

For many companies and individuals looking for alternatives to their desktop operating system, Linux is the natural choice and offers many relatively painless ways to make that switch. Unfortunately, modern Linux distributions running KDE and GNOME can demand a great deal of resources, and in some cases, companies looking to make a switch have been holding on to fairly modest PC hardware. Luckily, Linux enables you to set up workstations with minimal Linux installations that offload most of the work to a powerful, central server.

This is the thin-client approach. Just how thin this client can be is a matter of which approach you choose. In fact, it can all be done without even reinstalling the client PCs.

How Thin Clients Work

Linux thin clients typically are PCs booting from an Ethernet card with a chip that asks for an address from the server, or they are PCs with a specially prepared boot diskette that performs the same network boot function. Thin-client PCs don't even need a hard drive to provide a user with all of the functions they need. Companies may also choose to use a dedicated thin-client PC built for that purpose.

After boot, the unit—whether a PC or dedicated thin-client unit—requests an IP address, netmask, and default route from the thin-client server via DHCP (Dynamic Host Configuration Protocol). As part of the network settings package that gets sent back, the thin client is told which kernel to load and where to find it. The kernel is then downloaded via TFTP (Trivial File Transfer Protocol).

The kernel loads, and the thin-client workstation boots. As with any Linux system boot, in this scenario the kernel takes control and configures all attached hardware. A file system image is then loaded into memory and becomes a temporary root file system. Additional modules are loaded and some further network configuration takes place to prepare the system. After a few seconds, a new root file system is mounted via NFS (you'll see a “pivot_root” message as this happens). At this point, the thin client is live, and it begins the final states of boot. The /tmp, /proc, and other file systems are created and mounted. Swap space is activated. Soon after, the graphical display starts. The workstation queries the server for a graphical login.

Although a rather simplified explanation of the process, this is essentially it. A user can now log in at the thin-client workstation and start using Linux. All this magic takes place courtesy of the Linux Terminal Server Project (LTSP). To make this magic happen, however, there are a few prerequisites that we need to visit on the server side. Via NFS, thin-client servers use shared drive space across the local network. (See Chapter 19, “Linux File System (NFS),” for more on NFS.) Even before we get to that stage, the PC or thin client needs to get an IP address from the network. To do that, it uses DHCP (Dynamic Host Configuration Protocol).

DHCP

Most people who use the Internet regularly probably use DHCP on a daily basis—even if they don't know it.

In a classic office network that does not use DHCP, each PC needs to be configured with a static IP address and all of the appropriate network settings: name servers, default routes, and so on. Once configured, the device reads its own local network settings when it boots and never forgets it. A DHCP-connected device, on the other hand, asks a central DHCP server for all that information each time it boots and leases an IP address from the server. From the perspective of the user, the PC automatically configures itself. That's what happens at home when you dial in to your ISP and are assigned an address.

Setting Up DHCP

For starters, you need to install the DHCP package on your system. Be aware that many distributions break up the DHCP package into a dhcp-server and a dhcp-client, though the names can vary. Debian's DHCP server package is called just dhcp, for example.

The server gets its information from the /etc/dhcpd.conf configuration file. Take a look at this very basic configuration file that I created on my test server, being sure to note the semicolons at the end of each entry:

#
# My DHCP configuration file
#

ddns-update-style            none;

default-lease-time           21600;
max-lease-time               21600;

option subnet-mask           255.255.255.0;
option broadcast-address     192.168.22.255;
option routers               192.168.22.10;
option domain-name-servers   192.168.22.10, 192.168.22.11;
option domain-name           "mydomain.dom";
option root-path             "192.168.22.6:/opt/ltsp/i386";
filename                     "/lts/vmlinuz-2.4.24-ltsp-1";

subnet 192.168.22.0 netmask 255.255.255.0 {
    range dynamic-bootp 192.168.22.70 192.168.22.90;
}

When I start a thin client or even a regular PC with this configuration file in place, the unit is assigned an IP address between 192.168.22.70 and 192.168.22.90—that's the meaning behind the range dynamic-bootp parameter near the bottom. Take a look at the rest of these settings in turn, starting from the top:

All that brings us back around to the paragraph that started it all.

subnet 192.168.22.0 netmask 255.255.255.0 {
    range dynamic-bootp 192.168.22.70 192.168.22.90;
    range dynamic-bootp 192.168.22.120 192.168.22.150;
}

Here, we are essentially defining a dynamic network and specifying the addresses available for DHCP clients just logging on. Before moving on, I should tell you that the range I've defined above is a little different than the one I showed you just a couple of paragraphs back. In this example, there are actually two ranges of IP addresses up for grabs, and you could include more, depending on how you, as the systems administrator, decided to partition out IPs.

One of the reasons I've separated this out is that everything above the subnet paragraph is considered global. There can be many different subnet paragraphs (as in a Class A or B private network). That said, some of the globals start with the word “option”. All of these options you see can be applied to the subnet you defined (a different default DNS address perhaps). Unless you include a different parameter, the global parameters apply.

The Webmin Approach

Configuring DHCP from the command line is actually fairly easy. Should you prefer a more graphical approach, Webmin provides a module with everything you need to configure and maintain your DHCP server. You can find DHCP configuration under Servers in Webmin, or you can just jump to it by entering the URL in your browser's location bar:

http://your_server:10000/dhcpd/

Assigning Fixed DHCP Addresses

As a longtime systems administrator, I always have had a love/hate relationship with DHCP. These feelings come from trying to work on a site where every PC in the entire organization is assigned an IP dynamically. When troubleshooting problems on the network, I also had the additional burden of trying to figure out which workstation belonged to a particular IP address.

Luckily, DHCP does allow for host-specific IP addresses. To me, if a workstation is always sitting in a fixed location—on someone's desk, for example—then a fixed IP is more than desirable. Configuring fixed DHCP addresses does require an additional step, but it's not that complicated. Have a look at the following additional paragraph in my DHCP configuration file:

host thinclient1 {
    hardware ethernet       00:50:41:01:82:35;
    fixed-address           192.168.22.51;
    filename                "/lts/vmlinuz-2.4.24-ltsp-1";
}

Because this requires more work than assigning a range of addresses, why would you want to do this? Well, for one, this is more secure, because any host authenticating through your DHCP server is going to assign addresses only to those cards it knows about. For another, you know which workstation has which address, so support is easier, because you always know which unit you are talking about.

The host parameter represents the host name (thinclient1, in this case) for this client and should have an equivalent either configured on your name server or in your /etc/hosts file. Next, the hardware ethernet address is the unique hardware address (or MAC address) that I've mentioned in the past. You can get this information in a variety of ways. Dedicated thin-client units probably have it stamped on their backs. Ethernet cards have small labels identifying their MAC addresses. You can also see the MAC address by using the ifconfig command. The hardware ethernet address is the HWaddr information that you see on the second line below.

$ /sbin/ifconfig eth0
eth0      Link encap:Ethernet HWaddr 00:04:5A:5A:A8:2B
          inet addr:192.168.22.100 Bcast:192.168.22.255
Mask:255.255.255.0

Let's get back to the dhcpd.conf file segment we were looking at and continue with the fixed-address parameter. This is, quite simply, the IP address that you want to assign to that client. Finally, the last line (the filename parameter) is the TFTP download path to the kernel that the thin client loads when it boots from the network. And that, my friends, is the perfect segue to a discussion of TFTP.

A Trivial Primer On TFTP

Once connected with a proper IP address in hand, your thin client will download a Linux kernel from the server using a protocol called TFTP (Trivial File Transfer Protocol). The package that contains this server may be called tftp-server, which is the name the Red Hat and Mandrake systems I have used here, or tftp, as on my Debian system.

There's not much to getting TFTP running and no real configuration file to speak of. Just make sure the protocol is active. Look in your /etc/xinetd.d directory, and make sure that disable is set to no in the tftp file.

service tftp
{
        disable = no
        socket_type             = dgram
        protocol                = udp
        wait                    = yes
        user                    = root
        server                  = /usr/sbin/in.tftpd
        server_args             = -s /var/lib/tftpboot
        per_source              = 11
        cps                     = 100 2
        flags                   = IPv4
}

It's all very nice and easy (trivial?), but beware of one possible gotcha with the kernel installation. By default, the LTSP kernel, which I will cover shortly, is placed in /tftpboot/lts, whereas some TFTP installations may use a different directory for the TFTP files. For instance, my Mandrake test machine uses /var/lib/tftpboot as the TFTP transfer directory. This will make it impossible for the workstations booting up to download.

You have two choices. The first is to move the lts directory (installed under /tftpboot into your system's official TFTP download directory. Use the line:

mv /tftpboot/lts /var/lib/tftpboot/

The second way is to modify the /etc/xinetd.d/tftp paragraph to reflect the location of the LTSP kernel files.

The line you need to change is the server_args line, substituting /var/lib/tftpboot with /tftpboot. Once the change has been made, restart the xinetd daemon. Which of these two options you choose depends somewhat on whether TFTP is used for anything else on your system. If you are setting it up for LTSP only, it's just as easy to change the xinetd configuration file. Furthermore, it will make it easier to change things when newer kernels become available. The downside is that you have to move any other TFTP files into the new directory. If, instead, you choose to modify the location of the kernel files, then you have to move new kernel files into place each time you upgrade the packages. My personal choice is usually to change the xinetd configuration file.

LTSP 4.0 Installation Procedures

We now have all of the pieces we need to install the heart of a Linux thin-client installation. That heart is the Linux Terminal Server Project packages available at www.ltsp.org. To install the LTSP 4.0 packages, you need to switch to the root user first.

su - root

Running as the root user, use this command to begin the LTSP server installation:

wget -q -O - http://www.ltsp.org/ltsp_installer | sh

After you press <Enter>, you will see a menu much like this one:

LTSP Installer - v0.06
Welcome to the LTSP Installer.

This program will retrieve the LTSP packages and install them
for you.

Please select where you want to retrieve the packages from:

  1) http://www.ltsp.org
  2) Local disk (current directory)
  q) Quit installation

Make a selection: 1

Because you are going to be installing from the web site, selecting Option 1 probably makes sense. This also ensures that you will be running from the latest version. After a few seconds (or minutes), the install script finishes downloading and the following menu will appear:

LTSP Installer - v0.06
Select which group of packages you want to install:

1)   ltsp       Linux Terminal Server Project - Version 4

Make a selection (Q=Quit):

Given that we have only one option here, the choice is simple. Type 1, and press <Enter>.

LTSP Installer - v0.06

This group contains more than 1 component, which component
do you want to install:

   1) ltsp_core
      Core packages of LTSP

   2) ltsp_debug_tools
      Debugging tools for LTSP

   3) ltsp_x_core
      XFree86 packages

   4) ltsp_x_addtl_fonts
      Additional fonts

   5) ltsp_x336
      Older XFree86 version 3.3.6 Xservers

   6) ltsp_rdesktop
      Rdesktop setup as a Screen Script

Make a selection (Q=Quit, A=All):

Unless you have good reason to do otherwise, select A for All and press <Enter>.

Are you sure you want to install ALL components?

The answer is Y for Yes. After you press <Enter> one more time, you are asked for the LTSP installation directory. The default is /opt/ltsp, but you can select any part of the system where you have sufficient space. I'll continue the installation information using the default directory structure. Should you choose otherwise, take this into consideration as you read on.

One by one, each of the component packages is downloaded and installed. How long this takes depends largely on the speed of your Internet connection.

And Then… The Kernel

This download step provides you with most of the pieces you need, but it does leave out one very important one: the kernel. Your best bet is to select the latest kernel from the LTSP Sourceforge download page. As I write this, the latest package is ltsp_kernel-3.0.13-0.i386.rpm. The package is a simple RPM install, but Debian and TGZ format packages are available as well. On my current, RPM-based test system, I installed the kernel like this:

# rpm -Uvh ltsp_kernel-3.0.13-0.i386.rpm
Preparing...
########################################### [100%]
   1:ltsp_kernel
########################################### [100%]

That pretty much covers all of the pieces necessary for a working LTSP installation. By this point, you should have a working NFS, DHCP, and TFTP server running on what will be your LTSP server. On to the next step.

Configuring LTSP 4

Once everything is installed, it's time to configure your system. There is no part of the LTSP configuration that cannot be done manually, but the people working on the Linux Terminal Server Project have tried to simplify that process as well by providing the ltspcfg configuration utility. This is separate from the main LTSP distribution, and you must install it separately. Download the package from the LTSP web site, then install it using:

rpm -Uvh ltspcfg-0.5-0.i386.rpm

After the installation completes, run the utility by opening a root shell and typing ltspcfg.

# ltspcfg

ltspcfg - Version 0.5

Checking Runlevel....: 5
Checking Ethernet Interfaces
Checking Dhcpd....
Checking Tftpd....
Checking Portmapper...
Checking nfs....
Checking xdmcp...........Found: xdm, gdm, [kdm]
Checking /etc/hosts.
Checking /etc/hosts.allow.
Checking /etc/exports.
Checking lts.conf.

Press <enter> to continue..

When you press <Enter>, a ncurses-based administration interface appears (Figure 20-1). In order to run thin clients using LTSP, several services need to be running: DHCP, TFTP, NFS (which includes the portmapper), and a login manager (most likely KDM). Look at the top part of the ltspcfg window to check whether the services are installed, enabled, and running.

20fig01.gifFigure 20-1 Checking the status of your LTSP configuration.

If there are things that still need to be installed (your TFTP server, for instance), simply quit the configuration utility, make your changes and run it again until you are ready to proceed. When everything is ready, choose C from the main ltspcfg menu to manually configure various services. When you press <Enter>, you'll see the various options laid out as in Figure 20-2.

20fig02.gifFigure 20-2 The main LTSP configuration menu.

Take a look at item number 1. To serve up the graphical login manager, your system should be running at level 5. This modifies the initdefault line in your /etc/inittab file to 5 (should you prefer to do this manually).

id:5:initdefault:

So what does this really do? Well, if you aren't booting up into a graphical desktop, the 5 above will be a 3, which tells the system to boot up in text-only mode. To see where that happens and what that has to do with runlevels, scroll down in your /etc/inittab file and look near the bottom. You should see something like this:

# Run xdm in runlevel 5
# xdm is now a seperate service
x:5:respawn:/etc/X11/prefdm -nodaemon

The second item on the configuration menu is Interface Selection. If your system has more than one network interface card, you need to identify which of those interfaces the thin-client workstations will be connected to. My test system had three interfaces configured (Figure 20-3). On systems with both inside and outside interfaces, you'll most likely want to configure the private subnet interface.

20fig03.gifFigure 20-3 Which interface will your thin clients connect to?

You may be interested where this information is used. Much of LTSP's internal configurations are handled in an lts.conf file, which is created at this time under the /etc directory. If you look at the file at this point, you'll notice that it is still pretty light, containing only two important parameters:

# Configuration variables for LTSP
#
LTSP_DIR=/opt/ltsp
LTSP_ETH_INTERFACE=eth1

I'm making a point of mentioning this now, because there are two lts.conf files. The first, /etc/lts.conf, is used by the ltspcfg tool to keep information about the server while you configure the system. The second is /opt/ltsp/i386/etc/ltsp.conf, which is the one used by the thin clients. It contains parameters and settings that the thin clients need to operate.

Once this is written, we move on to Step 3, which creates a sample DHCP configuration file. If you used my examples earlier in this chapter, you can leave this part alone. Otherwise, go ahead and let the ltspcfg tool install a default /etc/dhcpd.conf file for you. Be aware that it is only a basic, sample file and that you will have to tweak it for your own network.

Making any changes to your NFS exports file or your DHCP configuration file (/etc/dhcpd.conf) does require that you restart those services. I have more than once found myself wondering why a new workstation wasn't coming online, only to remember that I had not reset the dhcpd daemon. It sounds obvious, but it is also surprisingly easy to forget.

Option 4 on the menu enables TFTP, if it hasn't already been activated, as shown in the status screen (Figure 20-1). Similarly, Option 5 activates the portmap daemon (which we covered earlier when discussing NFS). And speaking of NFS, Option 6 turns on the NFS daemons if they haven't already been activated.

We are now at Option 7, which means it's time for a discussion of XDMCP.

XDMCP

When your Linux system comes up, you are either looking at a graphical login screen, or a simple text login prompt. The graphical login, or login manager, can also be used by remote thin-client units or PCs. XDMCP (X Display Manager Control Protocol) is the protocol that allows thin clients to login via the graphical login manager (kdm). Option 7 asks whether you want to start the protocol. The answer here is yes.

There are other login managers. GDM is popular with GNOME users and the classic XDM is still in use. Since we are concentrating on KDE, I'll cover KDM.

Immediately thereafter, you are asked another very interesting question: Do you want the graphical login manager running on the console as well? In my own office, I tend to keep the console terminal more or less permanently logged out. Consequently, a graphical login on the console isn't necessary (even though graphical logins are provided to the thin clients). The decision here is yours.

The magic that happens in the background takes place in two files, kdmrc and Xaccess. To get a graphical login screen presented to a querying host, you need to uncomment the following lines in the /etc/X11/xdm/Xaccess file:

*                      #any host can get a login window
*    CHOOSER BROADCAST #any indirect host can get a chooser

Next, the configuration utility makes changes to the kdmrc file. On one of my systems, it is located in /etc/kde/kdm. On the other, it is in /usr/share/kde/kdm. Look for the following lines and make sure that the Enable parameter in the [Xdmcp] section is set to true.

[Xdmcp]
# Whether KDM should listen to XDMCP requests.
Enable=true

When you restart the window manager, you should then be able to get a remote graphical login. One way to reset the environment is to take the system down to runlevel 3 and then back to runlevel 5; this works for most systems.

init 3
init 5

If you are anxious to test this out right now, you can. All you need is a Linux client. For this example, I'll assume that you are already running in a graphical desktop. I'm going to have you type a command, but before you do, I should probably tell you what is going to happen. Your graphical KDE session is running on virtual terminal number seven. You can test this by pressing <Ctrl+Alt+F1>. You should drop out of your graphical session and back to a text screen. To get to the second, nongraphical desktop, press <Ctrl+Alt+F2> and so on, right up to virtual terminal number six. When you press <Ctrl+Alt+F7>(as in virtual terminal number seven), you'll be back to the graphical screen. The following command will start another graphical screen, but on virtual terminal eight! Assuming that your thin-client server is called your_tcserver, you would type:

X -query your_tcserver :1

Your X workstation queries your thin-client server for a login. The :1 at the end of the command specifies the second graphical display on your PC (the first is :0). If all has gone well up to this point, you should find yourself with a nice, graphical login screen. To switch back to your regular session, just press<Ctrl+Alt+F7>. To go back to the new session, press <Ctrl+Alt+F8>.

Back to Our Configuration

For each thin-client workstation you define, there should be an entry in your DNS tables or in your /etc/hosts file. If you are planning on providing entries on your name server zone files, you can skip this step. The same is true for a small handful of entries in your /etc/hosts file. Manually creating a handful of entries is easy, but Option 8 can create the hosts file entries for you. If you choose to let ltspcfg create entries for your /etc/hosts file, be aware that the entries will be generated as ws001 through ws254 (with IP addresses for your subnet) and a domain extension will be set to ltsp. You will probably want to do a global substitution in the file to change ltsp to your own domain name.

The next item on the menu, Option 9, has to do with system security. One way to provide or deny access is through the /etc/hosts.allow and /etc/hosts.deny files. Because some of these services, which may be controlled by the TCP wrapper, are needed by all thin-client workstations, it makes sense to put them in the /etc/hosts.allow file. These additions will be in a paragraph preceded by an ##LTSP-begin## comment line and closed with the ##LTSP-end## comment line.

bootpd:      0.0.0.0
in.tftpd:    192.168.22.
portmap:     192.168.22.

By the way, take note that the private Class C network used in this example may not be the same as in your office. Option 10 brings us back to NFS by defining those file systems that need to be exported for the thin-client workstations. By default, the entry created looks like this:

/opt/ltsp
192.168.22.0/255.255.255.0(ro,no_root_squash,sync)
/var/opt/ltsp/swapfiles
192.168.22.0/255.255.255.0(rw,no_root_squash,async)

The paths mentioned are probably fine. The first entry should not be a problem at all. I do want you to think about the second, however. If you are using NFS swap (most likely), the amount of space you allow per workstation may impact on where you store this information. Imagine 50 thin-client workstations logging in, each with 64 megabytes of swap space. That starts to add up. Make sure that the file system you choose here has the capacity to handle the load.

This brings us to the last option in the menu, and that means that it's time to talk about the lts.conf file.

The lts.conf File

When you choose to execute Option 11 and write the lts.conf file, you may get a message telling you that the file is already there. That's because by this point, you have probably effected enough changes to your system's configuration that the lts.conf file has been written. There's no harm in rewriting it, so go ahead. The file, by the way, lives in /opt/ltsp/i386/ltsp/etc, assuming you chose the recommended default installation. Aside from a few comments at the beginning of the file, this is the basic information you can expect to see:

[Default]
        SERVER             = 192.168.22.6
        XSERVER            = auto
        X_MOUSE_PROTOCOL   = "PS/2"
        X_MOUSE_DEVICE     = "/dev/psaux"
        X_MOUSE_RESOLUTION = 400
        X_MOUSE_BUTTONS    = 3
        USE_XFS            = N
        SCREEN_01          = startx

Let's look at the various parameters and what each means. The SERVER variable is the IP address of the machine on which your LTSP server will run. Nothing complicated here.

Pretty much every other variable that follows has to do with the graphical displays on the thin-client PCs or units. XSERVER generally is set to auto, but this is something you could hard code for individual workstations. The settings could be nv, vesa, ati, or any of the X servers supported by XFree86 version 4. We'll look at selecting parameters for individual thin clients in more detail when we discuss workstations in the next chapter. The next four variables (all prefixed with X_MOUSE_) are all pretty self-explanatory and relate to configuring the mouse. Meanwhile, the USE_XFS variable specifies whether the workstation will handle its own fonts or pull the information from the server's own font server.

The most interesting parameter here is SCREEN_01. The default is startx, which specifies that the workstation should boot up in a graphical X display, but there are a number of interesting possibilities. The other options are:

How Many SCREENs?

Of course, the fact that this last variable is labeled SCREEN_01 leads up to the obvious question: What about SCREEN_02? Or SCREEN_03?

Earlier on in this chapter, I told you about running your main X session on virtual terminal session 7, while the second X session (started with an X -query) ran on virtual terminal 8. You can do something similar with thin-client workstations by modifying the lts.conf file to include more than one SCREEN definition. Here's the example from my own server:

SCREEN_01         = startx
SCREEN_02         = telnet
SCREEN_03         = shell

The first virtual terminal (accessible by pressing <Ctrl+Alt+F1>) runs the graphical login served up via XDMCP. The second virtual terminal (<Ctrl+Alt+F2>) runs a TELNET session with a prompt saying “Screen:2 – Press <Enter> to establish a connection to the server…” Finally, the third screen (<Ctrl+Alt+F3>) sits at a shell prompt.

In a default LTSP installation, all these screen definitions can be found in the /opt/ltsp/i386/etc/screen.d directory. Each is a shell script and easy to read and understand. You could, if you so wish, create your own screen definitions to better suit your own environment.

These types of screen modifications can be done globally or on a client-by-client basis. In the next chapter, you're going to look at just what sorts of things you can do with workstations. I'm also going to show you how you can run a not quite so thin, Linux thin client from a Windows desktop.

But first, what if you need extra help?

Help Me!

As complex as this whole operation sounds, it's not that difficult. That said, I've gone through this process many times now and I still miss things, usually something as silly as a typo. Thin-client computing does bring some interesting challenges into the picture, however, especially when dealing with devices connected to the thin clients themselves. Add to that the fact that a thin-client device can be anything from a vintage PC with any number of different network or video cards or any of several different types of hardware, and it's possible to run into the odd snag.

I'm going to talk about thin clients in a moment, but for now, I want to tell you about a great resource, the #ltsp IRC channel on irc.freenode.net. Many people who frequent this channel are either developers on the project or just plain enthusiastic users. If you run into problems, this is always a great place to ask questions.

Resources

Linux Terminal Server Project

800 East 96th Street, Indianapolis, Indiana 46240