Project #1

Assigned: September 9
Due: September 30, 2:00pm, in class


(100 points) Develop a UNIX shell in C.


  1. The command-line prompt must be a dollar sign followed by a single space character (e.g., $ ).
  2. Your shell must support the following builtin commands:
    1. cd <directory>: change the current directory to <directory> and change the value of the PWD variable appropriately. If the <directory> argument is not present, write the current directory to standard output. If the directory does not exist an appropriate error should be reported.
    2. environ: write all of the environment strings to standard output.
    3. print <comment>: write <comment> to standard output followed by a newline.
    4. pause: pause operation of the shell until Enter is pressed.
    5. quit: quit the shell.
  3. All other command line input must be interpreted as UNIX program invocation (i.e., not builtin), which must be done by the shell forking and execing the program as its own child process.
  4. Your shell must support standard I/O redirection. For instance, $ pgm arg1 arg2 < in > out must execute the program pgm with arguments arg1 and arg2, the stdin FILE stream replaced by in, and the stdout FILE stream replaced by out. Your shell must support <, >, and >>.
  5. Your shell must be capable of file I/O (in addition to standard I/O), e.g., $ mysh scriptfile.
  6. Your shell must not use its parent shell to provide any functionality since the idea of your shell is to potentially replace your login shell. In other words, assume that your shell is not running as a child on top of your login shell. This also means that you must not use the system call system anywhere in your program.
  7. Your implementation must be distributed across more than one source code file, in some sensible manner which reflects the logical purpose of the various components of your desgin, to encourage problem decomposition and modular design.
  8. Your submission must include a Makefile. Your Makefile must include target directives for every derived file produced during the compilation process (i.e., each program, each object file, and any other intermediate files produced during code compilation). Make sure that each directive also lists all files on which the derived file depends in its dependency list. Also, your Makefile must be written so carries out only the commands necessary to bring any produced file up-to-date. Your Makefile must do just enough, but no extra, work to bring the final executable mysh for your shell up-to-date every time make is invoked. In addition, it must have an all directive and a clean directive to remove all generated files Use variables where appropriate in your Makefile to improve its readability. Your Makefile must bring everything up-to-date, using only gcc, without any warnings or errors, when make is invoked on our system.


If designed properly, the program required for this project should occupy between 200-300 lines of code. You are encouraged to use the makeargv function available in /home/perugini/C/makeargv.c to build an argument array which can be passed to execv.

You are encouraged to develop your shell iteratively. Specifically,
  1. start by implementing the execution of non-shell builtin UNIX commands, e.g., ls;
  2. then implememnt I/O redirection for non-shell builtin commands, e.g., ls > outfile and cat < infile;
  3. then implement the shell builtin commands, e.g., environ or quit; and
  4. finally, implement I/O redirection for the shell builtin commands, e.g., environ >> outfile.

Sample test data

There is a transcript of a UNIX session here which illustrates the execution our solution on several representative test cases. The input files used in the examples actually live on our UNIX system (see the particular computer on which they were run at the top of the file) and you are encouraged to test your program with them for purposes of comparison. These test cases are not exhaustive.

How to submit

Note: All directory and filenames below are case-sensitive. You must use the directory and filenames exactly as shown below, i.e., all lower case.

Prepare your submission file as /home/<logname>/projects/p1/p1.tar. This archive must contain only the most minimal set of files necessary to build your shell from scratch. Only the file /home/<logname>/projects/p1/p1.tar will be electronically collected from your account on the deadline.

Submit a pretty-printed listing using a2ps of all your source code files (except for makeargv.c, if used) as well as your Makefile in class.

Failure to follow these submission requirements will result in a 10% penalty.


Ninety percent of your score will come from correctness and 10% of your score will come from following our programming style guide. Applicable submission penalties will then be applied.

Eighty of the 90 possible points for correctness are for the correctness of the program, while the other 10 are for the correctness of the Makefile. Students earn up to four different portions of the 80 possible points for program correctness:

  • If your program meets all requirements above, you can earn up to 80 points.
  • If your program meets all requirements above with the exception of I/O redirection for shell builtins, you can only earn up to 60 points.
  • If your program meets all requirements above with the exception of shell builtins, you can only earn up to 40 points.
  • If your program meets all requirements above with the exception of shell builtins and I/O rediction for non-builtin commands, you can only earn up to 20 points.
  • If your program does not implement execution of non-builtin commands, you will not earn any points.
  • If your program does not compile with gcc when make is invoked on our system or execute without errors or warnings, you will not earn any points.

Return Home