Description
1. Overview
This project will implement a client/server application using sockets.Adaemon (cixd)listens on a socket for client connection requests.Eachconnection will cause the server to fork a child process to serve the client. The daemon runs in an infinite loop listening.The server exits when the client disconnects.Aclient (cix)connects to a server and can send files,receive files,and get a summary listing of all files present.
Asocket is a two-way means of communication between processes,not necessarily running on the same host. An IPv4 host is know by a 4-octet sequence suchas 128.114.108.152, and a port is an unsigned 16-bit number (0 to 65535). Communication will be done via TCP/IP over IPv4 sockets.
2. Programs
In this project, two main programs are to be written for the three parts of the project : the daemon and server,and the client. There will also be several library files written to be used by the programs.The general function is similar to sftp(1).
cixd
Usage : cixd [port]
Creates a server socket and goes into an infinite loop:When it accepts a client socket, it uses fork(2) to create a child process,whichfunctions as the server to communicate with the client.
The daemon listens for connections on the given port, if specified. If not, the environment variable CIX_SERVER_PORT is used to determine the port. There is no default port.
The server is forked with an open socket communicating with the client. Its loop repeatedly reads commands and information from the client and acts on those commands,returning information backtothe client. Its loop will be a receive followed by a send, responding to client requests.Itexits when the client closes the socket. It does no terminal I/O except possibly for debugging purposes.
cix
Usage : cix [host][port]
The client interacts with the user.Commands are read from the terminal (or redirect), eachofwhichisexecuted one at a time by communicating with the server.Results are then displayed at the terminal.
The client connects to the given host, if specified. If not specified, the environment variable CIX_SERVER_HOST is used as the host to connect to.Ifnot specified, localhost is used. It tries to connect to the given port, if specified. If not, the environment variable CIX_SERVER_PORT is used to determine the port. There is no default port.
CMPS-109 • Spring 2015 • Program 5 • Client/Server and Sockets 2 of 5
3. Interactive Commands
The cix-client responds to commands read from the standard output and writes output to the standard output and error and accesses files.Inthe syntax below, Courier Bold are literal characters actually typed in, while Roman Italic stands for appropriate substitutions.
exit
Quit the program. An end of file marker or Control/D is equivalent.
get filename Copy the file named filename on the remote server and create or overwrite a file of the same name in the current directory.
help
Asummary of available commands is printed.
ls
Causes the remote server to execute the command ls -l and prints the output to the user’sterminal.
put filename Copies a local file into the socket and causes the remote server to create that file in its directory.
rm filename Causes the remote server to remove the file.
4. Protocol used by the cix* programs
In order for the client and server to communicate,aprotocol needs to be established. This means that eachmessage needs to be framed in terms of a header and a payload. The header alwaysconsists of a struct of size 64 bytes.All messages between client and server consist of these 64 bytes,possibly followed by a payload. For alignment purposes,the nbytes field is first. Before filling in the fields, use memset(3) to clear the struct.
enum cix_command {CIX_ERROR = 0, CIX_EXIT, CIX_GET, CIX_HELP, CIX_LS, CIX_PUT, CIX_RM, CIX_FILE, CIX_LSOUT, CIX_ACK, CIX_NAK}; struct cix_header { uint32_t cix_nbytes; uint8_t cix_command; char cix_filename[59]; };
The purposes of the fields are as follows:
uint32_t cix_nbytes; The number of bytes in the payload if there is any payload. Otherwise it must be zero (MBZ). This field is sent in network byte order and so must use the functions ntohl(3) and htonl(3) when loading and storing data.
uint8_t cix_command; Asingle byte containing one of the cix_command constants.
CMPS-109 • Spring 2015 • Program 5 • Client/Server and Sockets 3 of 5
char cix_filename[59]; The name of the file being transferred or removed. The filename may not have any slash (’/’)characters in it and must be null-terminated (with ’\0’). All bytes following the null must also be null. Pathnames with slashes and filenames longer than 58 characters are prohibited.
Following are the meanings of eachofthe cix_command values.Eachiseither client to server (C→S) or server to client (S→C), but never both.
CIX_ERROR An error flag to indicate an invalid header.Used internally.
CIX_EXIT Internal to cix-client,not used in communication.
CIX_GET (C→S) Request a file from the server.The filename is used both remotely and locally. The payload length is 0.
CIX_HELP Internal to cix-client,not used in communication.
CIX_LS (C→S) Request file (ls)information. The payload length and filename are zeroed.
CIX_PUT (C→S) The length of the payload is the number of bytes in the file.The contents of the file immediately follow the header.The bytes of the payload are unstructured and maycontain null bytes.Binary files are acceptable.
CIX_RM (C→S) Request to remove a file.The payload length is 0.
CIX_FILE (S→C) Response to a CIX_GET.The filename is the same as in the request and the payload length reflects the number of bytes in the file.The payload consists of the bytes of the file.
CIX_LSOUT (S→C) Response to a CIX_LS.The filename is zeroed and the payload length is the number of bytes sent in the payload. The payload is the output of the command ls -l.
CIX_ACK (S→C) Response to either a CIX_PUT or a CIX_RM indicating that the request was successfully completed.
CIX_NAK (S→C) Response to any request that fails.There is no payload. The filename field is the same as was in the original request.The payload field is set to the value of errno in the server’sattempt to preform a task.
5. Procedures
Eachofthe above commands requires procedures for accessing files,including reading files from disk and writing files to disk, as well as accessing directories.When
CMPS-109 • Spring 2015 • Program 5 • Client/Server and Sockets 4 of 5
any of the system calls fails in the server,the server immediately terminates the operation and sends the value of errno backtothe client in a CIX_NAK message.
(a) For the client or server to send a file it must first be read into a buffer.Binary files must be properly handled, so protocols whichassume text files won’t work. Toload a file from disk, use istream::read(),collecting characters into abuffer.Read the entire file into a buffer then close it. After that, it maybe sent down the socket. Alternatively, stat(2) the file to see how large it is,and send the file down the socket piecemeal.
(b) When receiving a file from the socket, Receive the header and determine the size of the file.Create an ostream and use ostream::write() to write the parts of the file as they are received from the socket. A C++ stream is closed when the variable goes out of scope,oryou can call close.
(c) Todelete a file for the CIX_RM command, use unlink(2) : rc = unlink (filename);
(d) Toexecute the CIX_LS command use popen(2) and pclose(2) to create a pipe stream from the ls(1) command FILE* pipe = popen (“ls -l”, “r”); Then read the characters from the pipe in the easiest way,probably by using fgets(3). Finally, pclose(pipe).Then send the output backthe client in a CIX_ LSOUT message.
6. Modules
There will need to be several modules in this suite of programs.Eachofthe programs,ofcourse,will have its own source file with a main function in it.
The sockets module will be a useful inclusion into the program as its own module.
There should also be a cix_protocol module to implement the protocols and contain code for accessing files and sockets,since these will be used by both the client and the server.
7. Use of ports
If your daemon listens on a port that has been bound by another process,you will get the message ‘‘Address already in use’’because only one process at any given time is allowed to listen on a particular process.Toavoid this,choose a port number not being used by anyone else on the same server.
To avoid having to type in a port number every time you start your server,put the following line in your .bashrc or .bash_profile file : export CIX_CLIENT_PORT 60000 except that eachperson in class should use a different number.You should picka dynamic or private port number from the range 49152 through 65535 (0xC000 through 0xFFFF).
8. Runaway Processes
Be careful in using fork(2) so that you don’t accidentally create a fork-bomb.The command pkill(1) can be used to kill all processes matching a particular pattern. So the command
CMPS-109 • Spring 2015 • Program 5 • Client/Server and Sockets 5 of 5
pkill cix will kill all of your processes whose executables contain the string ‘‘cix’’.Areally quickway tolog out is to use kill(1) : kill -9 -1 kill -s KILL -1 will send SIGKILL to all of your processes,thus logging you out.
9. What to Submit
Submit Makefile whichbuilds the three programs,all necessary C++ header and implementation files.And if doing pair programming,the PARTNER file.When the grader uses the command make in the submit directory,the three binaries should be built