CSCI.4220 Network Programming
Spring, 2005
Programming Assignment 1
For this assignment you will write a simple ftp client and server
which conforms to the following specification.
- The client connects to the server on a different machine.
Any client should be able to connect to any server.
- The server should be able to handle multiple simultaneous
connections.
- There will be two connections between the client and the server:
the initial connection, initiated by the client, on which the client
sends requests, and a second connection on which files are
transferred. These will be referred to as the request connection and
the data connection respectively. (Note: this is more or less how the
real ftp protocol works). On the data connection, the roles
of client and server are reversed. When the client establishes a
connection, it sends port number as a character string on the request
line which means that it is listening on that port, and the server
then connects to that port.
- There are four commands that the client can issue.
- the port number (only sent once and must be the first request)
- dir The server sends the names of all files in its
current directory, delimited by a newline char.
- get followed by a file name. Server sends the contents of
the file. The client creates a file of the same name in its
current directory and copies the contents to this file.
- quit Client is terminating.
- All commands sent from the client to the server should
be terminated with a null char (ascii 0).
- All requests from the client must be acknowledged by the server on the
request connection.
The reply from the server
to the client on the request line is always exactly eight bytes (no null terminator).
The first must be either a 'y', indicating that the request
was successful, or an 'n', indicating that the server
could not honor the request. In the former case, the remaining
seven characters must be all digits, and indicate the number
of bytes that will be returned to the client on the data
line. It will then send the data. When the reply is an
'n', the remaining seven bytes should be all zeros (ascii 48).
Even requests that do not ask for data (the port number and quit)
should be acknowledged with an 8 byte message. The last seven
bytes should be all zeros.
All requests and acknowledgment should be human readable. That is,
the numbers should be sent as a character string. If the server is
about to send a file of 34 bytes, here is its eight bytes
| y | 0 | 0 | 0 | 0 | 0 | 3 | 4 |
---------------------------------
The first byte is ascii 'y, (121) the second through sixth bytes are
ascii '0' (48), the seventh byte is ascii '3' (51), and the last byte
is ascii '4' (52).
Hint: You might want to use the function sprintf to write digits
to a string. The format string %07d write a seven char string
with leading zeros.
Here is a sample run stream
- Server starts, listens on port 12345
- Client starts, connects to server (the request connection)
- Client listens on port 54321
- Client sends the string "54321" to server (6 bytes including terminal null char)
- Server connects to client on port 54321 (the data connection)
- Server acknowledges by sending "y0000000" on request connection
- Client sends dir to server on request connection (4 bytes)
- Server acknowledges by sending "y0000345" on the request connection
- Server sends the list of files on the data connection, a total of 345 bytes
- Client sends "get file1" on the request connection (10 bytes)
- Server acknowledges by sending "y0000678" on the request connection
- Server sends the contents of file1 (678 bytes) to the client on the data connection
- Client sends "dri" to the server on the request connection (bad command)
- Server acknowledges by sending "n0000000" on the request connection
- Client sends "quit" on the request connection (5 bytes)
- Server acknowledges by sending "y0000000" on the request connection.
Here are some constraints.
- The server should be run in a directory with several files, but
no subdirectories. No file should be larger than 9,999,999 bytes.
- All requested files should be relative file names. For security
reasons, any request for a file name where the first character is a
. (dot), a slash, a backslash, or a tilde should be rejected. Your
program must check for this.
- When the server is started, it should take one argument, the
port number that it will listen on.
- When the client is started, it should take three arguments. The
first is the name of the host on which the server is running, the
second is the port number on which the server is listening, and the
third is the port number on which the client will listen for the data.
- File names should not have spaces. The only valid characters
allowed in a file name are letters, digits, dot, hyphen, tilde and
underscore. File names are case sensitive.
You must submit four separate source files, a unix client and server
and a windows client and server.
When compiling the server on solaris, you should use the following command line
gcc -g -Wall -o server server.c -lnsl -lsocket -lphread
When compiling on FreeBSD, use this command line
gcc -g -Wall -o server server.c -pthread
When compiling on Windows in the .NET compiler, you have to link to the wsock32 library. To do
this, choose Properties from the Project menu. The Properties page will appear.
Choose Linker from the Configuration Properties, and then choose Input.
The first line will read Additional Dependencies. Type wsock32.lib, and hit
the OK button.
On Windows, to pass command line arguments from within the .NET
development environment, choose Properties from the Project menu. Then choose debugging from the Configuration
Properties. One of the lines will be labeled Command Arguments.
Type in the arguments, delimited by spaces. Then hit the OK
button.
The project is due at midnight on Tuesday, Feb. 8.