Creating a service to be managed by xinted super-server
Refer to the slide presentation entitled "socket demo."

[ Color-coding note: this exercise involves a client and a server machine. Some commands below are to be executed on the client, others on the server, as follows:
 blue - on client
 red - on server

1) prepare a directory to house the executable file that will perform the service:

    mkdir /opt/socketdemo/
    chmod 755 /opt/socketdemo/

2) we're going to set it up so this file gets executed by user "nobody," when run as a service for some remote client. First obtain the file:

    [ grab file "byteme" by ftp from instructor's anonymous ftp server, pub directory ]

The byteme program is a simple script:

#!/bin/bash
/bin/echo "GIGA-BYTE ME!" | /usr/bin/tee /tmp/bytelog.txt
/bin/date >> /tmp/bytelog.txt

so you can read it and run it to note what it does. Do so. You are running it as an ordinary local program. But we are now going to install it as a managed service for xinetd to run when called upon by clients instead. Give byteme user and group ownership by "nobody," and permissions that let "nobody" read and execute it:

    cd /opt/socketdemo/
    chown nobody.nobody /opt/socketdemo/byteme
    chmod 500 /opt/socketdemo/byteme

3) the executable is written to employ a logfile. The logfile is /tmp/bytelog.txt. Create this file, give it user and group ownership by "nobody," and permissions that let "nobody" read and write it.

    touch /tmp/bytelog.txt
    chown nobody.nobody /tmp/bytelog.txt
    chmod 600 /tmp/bytelog.txt

4) this program will need a port number. That number will be inserted in the /etc/services file, also in a configuration file for this service that we're going to place in /etc/xinetd.d/. We need to avoid choosing a port number already in use by some other service. Choose your number, then search for it in those two places. If you find it, move on to some other choice till you find a number that's unused. For example:

    grep 54321 /etc/services

5) xinetd will need a name by which to know this service. Use "chomper." Reflect the new service in /etc/services (see the slide presentation for the line you need to add or model it after the existing lines). Also reflect it with a service configuration file under /etc/xinetd.d/:

    vi /etc/services
    cd /etc/xinetd.d/

    [ grab file "chomper" by ftp from instructor's anonymous ftp server, pub directory ]

Because file "chomper" contains a line reading "service chomper", it will map into a line in /etc/services that starts with "chomper..." followed by a port number. That causes this service to use that port number. Edit /etc/xinetd.d/chomper to enable this service, by making sure you have "disable = no."

6) restart xinetd to recognize, respect, and implement the new configuration information:

    service xinetd restart
    netstat  -pant

netstat should show that xinetd is now listening on port 54321.

7) run byteme as a service from another station with telnet, or equivalently but without extraneous screen messages, with nc ("net cat"):

    nc [or telnet] <address of server> <port number you picked>

Observe the screen output on the client, and view the content of the log file on the server. Run it twice more, while at the server running tcpdump 2 different ways:

    tcpdump  -ti  eth0
    tcpdump  -nnti  eth0

Note the difference in output, which is due to the change you made in /etc/services. tcpdump is one of many programs that perform lookups in that file.

8) transform byteme into an echo server. A managed server like byteme inherits the xinetd-provided network connection on its ordinary standard input and standard output. That is, xinetd gives the server as standard input whatever it takes in through the connection, and xinetd takes any standard output from the server and puts it out the connection. If the far-side client sends anything, it will reach the server's standard input. And if the server produces any standard output, the client will receive it (we've already seen the second part).

Modify byteme to absorb a line of its standard input into a variable, then echo that variable (instead of the constant "GIGA-BYTE ME!") to its standard output.

#!/bin/bash
read INCOMING
/bin/echo "$INCOMING" | /usr/bin/tee /tmp/bytelog.txt
/bin/date >> /tmp/bytelog.txt

Modify the client to actively send something:

    echo hello | nc <address of server> <port number you picked>

Repeat, changing "hello" to "goodbye".

    echo goodbye | nc <address of server> <port number you picked>

Repeat again, sending both words, separated by a newline:

    echo -e "hello\ngoodbye" | nc <address of server> <port number you picked>

If you didn't get the full echo of everything you sent, modify the server again:

#!/bin/bash
while read INCOMING
do
  /bin/echo "$INCOMING" | /usr/bin/tee /tmp/bytelog.txt
  /bin/date >> /tmp/bytelog.txt
done

Try the previous command again:

    echo -e "hello\ngoodbye" | nc <address of server> <port number you picked>

Now echo a whole lot of stuff:

    nc <address of server> <port number you picked>     <     /etc/services

Anybody can use xinetd to start arbitrary special purpose servers. Servers can participate is full bi-directional use of the network connection as if they'd utilized the socket API directly, and they can be written in any language.


With the server on 164.67.79.151 and client on 164.67.79.150, here is the network traffic captured by ethereal/wireshark on the server while running the baseline byteme. Here is the same wireshark/tcpdump capture file zipped for download, if you wish to load it into wireshark and examine it live yourself (unzip first).