CS 536 Spring 2024

Lab 1: System Programming Review [150 pts]

Due: 01/31/2024 (Wed), 11:59 PM

Objective

The objective of this introductory lab is to review C system programming which is the foundation for network/socket programming. If you are rusty, please use this practice period to bring yourself up-to-speed on system level C programming. Utilize the PSOs and office hours to resolve any questions. The goal of this lab is to understand the structure and implementation of concurrent client/server apps which comprise the bulk of networked applications in the real-world. This lab is an individual effort. Please note the lab assignment policy specified on the course home page.


Reading

Read chapter 1 from Peterson & Davie (textbook).


Problem 1 [50 pts]

The directory

/homes/cs536 (symbolic link currently pointing to /u/u3/cs536)

accessible from our lab machines in HAAS G050 contains mysh.c which implements a prototypical concurrent server: a simple, minimalist shell. A concurrent server receives and parses a client request -- in this case, from stdin (by default the keyboard attached to a PC in the lab) -- then delegates the actual execution of a requested task to a worker process or thread. Many apps in the real-world, including network software, follow the general structure of concurrent client/server code which are multithreaded programs. They constitute a baseline for implementing network software.

Create a directory, lab1/, somewhere under your home directory, and a subdirectory v1/ therein. Copy mysh.c to v1/, compile, run and check that you understand how it works. Run the shell with command "ls -l" and explain why it does not work. Put your answer in lab1.pdf and place the pdf file under lab1/. Modify mysh.c, call it newsh.c, that accepts command-line arguments. That is, whereas mysh.c can handle "ls" and "ps", it cannot handle "ls -l -a" and "ps -gaux". Your modified code, newsh.c, handles command-line arguments by parsing "ls -l -a" into string tokens "ls", "-l", "-a" and passing them to execvp() as its second argument which is an array of pointers to the parsed tokens. Also, modify the format of the prompt so that it outputs the hostname, colon character, PID, space, then character %. Use the system call gethostname() to access the hostname of a machine.

Make your code modular by performing the parsing task in a separate function that is placed in its own file. Provide a Makefile in v1/ that compiles your code and generates a binary executable newsh.bin. Compile, test, and verify that your code works correctly. Annotate your code so that a competent C programmer can understand what your code is doing.


Problem 2 [100 pts]

Create a subdirectory v2/ under lab1. Modify your code newsh.c, call it remotecmd.bin whose driver code main() should be placed in v2/remotecmd.c, so that instead of accepting client requests from stdin (i.e., human typing on keyboard in v1/) the request is communicated from a client process. The server process running remotecmds.bin creates a FIFO (i.e., named pipe) to be used as a communication channel where clients can submit requests. Call the FIFO "cmdfifo" which is hardcoded into both server and client code. Place the driver code of the client in v2/remotecmdc.c. A client running remotecmdc.bin should be started after the server process has started executing. If the client cannot write to cmdfifo, it terminates after printing a suitable error message to stderr. When testing, run the server and client processes in separate windows for ease of observation.

The client, remotecmdc, uses system call open() to open the FIFO and sends its request using write(). The client's request is provided by a human through stdin. Hence, the client is itself a server who prints a prompt '? ' to stdout and accepts command requests from stdin. The input string may be contain command-line arguments. Total length of the input string may not exceed 30 characters including end-of-string character '\0'. If it does, the client outputs an error message to stdout and outputs a fresh prompt. Describe in lab1.pdf your method for determining if an input exceeds the length limit. To support multiple client processes, we will use a message format where a request ends with the newline character. That is, we are using '\n' as a delimiter which overwrites the end-of-string character '\0'. When using FIFO to receive multiple client requests, the potential for interleaving of characters belonging to two or more requests must be considered. Check up to how many bytes in a write() system call Linux FIFOs guarantee interleaving will not occur -- i.e., write() behaves atomically -- and note the answer in lab1.pdf. Although your client will reject command strings exceeding 30 characters, the server remotecmds.bin will not rely on correctness of clients. Instead, when remotecmds.bin reads a command from cmdfifo it will check that a command terminated by '\n' does not exceed 30 characters inclusive newline. If so, it ignores the command by discarding characters in cmdfifo until '\n' is reached. Then the next command is parsed.

Implement your client/server app in a modular fashion. Provide a Makefile in v2/ to compile and generate remotecmds.bin and remotecmdc.bin. Create README under v2/ that specifies the files and functions of your code, and a brief description of their roles. Test your client/server app with multiple client processes and verify correctness.


Bonus problem [20 pts]

Reimplement newsh.bin of Problem 1 so that it calls system call execve() instead of execvp(). Explain in lab1.pdf the main difference between the two versions and any restrictions you place on how to use newsh.bin. Code this version in a new directory v3/.

The Bonus Problem is completely optional. It serves to provide additional exercises to understand material. Bonus problems help more readily reach the 45% contributed by lab component to the course grade.


Turn-in instructions

Electronic turn-in instructions:

We will use turnin to manage lab assignment submissions. Go to the parent directory of the directory lab1/ where you deposited the submissions and type the command

turnin -c cs536 -p lab1 lab1

You can check/list the submitted files using

turnin -c cs536 -p lab1 -v

This lab is individual effort. Please note the assignment submission policy specified on the course home page.


Back to the CS 536 web page