Starting from:
$35

$29

Project 1: “Midday Commander” Solution

There are many ways you can interact with a computer, including a graphical user interface or a text-based SHELL where you can type commands at the command line. In this project, we’ll be creating another way to interact with the system: via text-based menu modeled after the once popular “Midnight Commander” file management application. Our program, called “Midday Commander,” will be implemented in three phases of increasing complexity, with each phase building on the prior one.




This project will allow students to learn about process creation, termination, and resource usage in the Linux operating system. All coding is to be done in the C programming language. We highly recommend implementing or testing the project on the Ubuntu virtual machine you created in Project 0. Projects that do not compile or run correctly on the Ubuntu virtual machines may be penalized.







Phase 1: Fixed Commands




Create a directory called “v0” and store your code and Makefile in this directory. The first phase program, called mc0, runs a fixed list of commands in a menu-driven manner, as depicted in the transcript below:




shepard@normandy:~ ./mc0




=====
Mid-Day
Commander, v0 =====


G’day, Commander! What command would you
like to run?
0.
whoami
: Prints out the result of
the whoamicommand
1.
last
: Prints out the result of
the last command
2.
ls
: Prints out the result of a listing on a user-specified path
Option?: 0




-- Who Am I? --


shepard




-- Statistics
---


Elapsed time:
1 milliseconds


Page Faults: 0




Page Faults (reclaimed): 0


G’day, Commander! What command would you
like to run?
0.
whoami
: Prints out the result of
the whoamicommand
1.
last
: Prints out the result of
the last command
2.
ls
: Prints out the result of
a listing on a user-specified path



Option?: 1




-- Last Logins --




shepard pts/1 1.2.3.4 Fri Jan 13 03:14 still logged in




-- Statistics ---




Elapsed time: 2 milliseconds




Page Faults: 0




Page Faults (reclaimed): 0







1



G’day, Commander! What command would you
like to run?
0.
whoami
: Prints out the result of
the whoamicommand
1.
last
: Prints out the result of
the last command
2.
ls
: Prints out the result of
a listing on a user-specified path



Option?: 2




-- Directory Listing --




Arguments?: -al




Path?: /home




total
132








drwxr-xr-x 33
root
root
4096 Oct
5 13:40 .
drwxr-xr-x 24
root
root
4096 Dec
6 09:20 ..
drwxr-xr-x 3
shepard
root
4096 Aug 31
2016 shepard
-- Statistics
---






Elapsed time:
7 milliseconds




Page Faults: 0








Page Faults (reclaimed): 0




G’day, Commander! What command would you like to run?
0.
whoami
: Prints out the result of the whoamicommand
1.
last
: Prints out the result of the last command
2.
ls
: Prints out the result of a listing on a user-specified path



Option?: ^C




shepard@normandy:~




Your program should call the appropriate command based on the selected option: whoami, last, or ls. Note, these commands are already built into the system and do not need to be re-implemented. Specifically, you must use OS system calls to fork() off a child process and execute the command and its arguments using the exec system call. The parent process should wait for completion and then print statistics about the child process’s execution. These statistics must include :




the elapsed “wall-clock” time for the command to execute in milliseconds,



the number of page faults, and



the number of page faults that could be satisfied using unreclaimed pages.



For the ls command, the program will execute the command with the indicated arguments (if any are specified) on the indicated path. Note that the printed output of a command may differ slightly from the given example. If the command is illegal, an error message must be generated. Finally, you are not allowed to use the system() system call. Satisfactory completion of this component is worth 20% of the project score.




Helpful Hints




One of the purposes of this assignment is for you to learn how to find information in the online documentation of Unix and Linux (called man pages) and, from that documentation, to learn how to invoke the various system facilities from your program. For example, to learn about the fork() function, type “man fork” in your favorite Unix or Linux shell. Manual pages are organized into sections. Section 1 is for commands to the shell, section 2 is for system calls, and section 3 is for library routines, etc. Some entries are contained in more than one section. For example, “man wait” will give you the manual page for the wait command







2



typed to a shell, while “man 2 wait” will give you the manual page for the wait() system call. Executing “man man” tells you how to use the man command to view and/or print manual pages. For this part of the assignment, the following systems calls and library functions may be needed:




fork() - create a new process by cloning an existing one



execvp() or one of its variants - execute a file. This is a front-end for the system call execve(), which replaces the current process with a new program to execute.



wait() - wait for a process to terminate.



getrusage() - get information about resource utilization.



gettimeofday() - get current time for calculation of wall-clock time.



Note: The getrusage() function returns a data structure with a lot of fields in it. However, the man pages say that only some of these fields are actually populated by the Linux kernel.







Phase 2: Extendable Commander




Create a directory called “v1” and store your code and Makefile in this directory for the second phase. Make a copy of your mc0 program and call it mc1.




The mc1 command allows users to begin adding their own commands to the menu. By pressing the ‘a’ key, the user will be able to add a new command and parameters to the menu. Your program will prompts for and read a new line of text from stdin. It stores this line in a data structure in memory and adds an option for the command to the menu by incrementing the last available option number and displaying it in order, as shown in the following transcript:




shepard@normandy:~ ./mc1


===== Mid-Day Commander, v1 =====


G’day, Commander! What command would you
like to run?
0.
whoami
: Prints out the result of
the whoamicommand
1.
last
: Prints out the result of
the last command
2.
ls
: Prints out the result of
a listing on a user-specified path



a. add command : Adds a new command to the menu.




c. change directory : Changes process working directory




e. exit : Leave Mid-Day Commander




p. pwd : Prints working directory




Option?: a




-- Add a command --




Command to add?: free -m




Okay, added with ID 3!




G’day, Commander! What
command
would you
like to run?
0.
whoami
: Prints
out the
result of
the whoamicommand
1.
last
: Prints
out the
result of
the last command
2.
ls
: Prints out the result of a listing on a user-specified path
3.
free -m : User added command





a. add command : Adds a new command to the menu.




c. change directory : Changes process working directory




e. exit : Leave Mid-Day Commander




p. pwd : Prints working directory




Option?: 3







3



-- Command: free -m --














total
used
free
shared
buff/cache
available
Mem:


64414
9988
381
54
54044
53564
Swap:


65524
3272
62252






-- Statistics
---










Elapsed time:
4
milliseconds








Page Faults: 0














Page Faults (reclaimed): 0










G’day, Commander! What command would you like to run?




0.
whoami
: Prints out the result of the whoamicommand


1.
last
: Prints out the result of the last command




2.
ls
: Prints out the result of a listing on a user-specified path
3.
free -m : User added command








a. add command : Adds a new command to the menu.




c. change directory : Changes process working directory


e. exit : Leave Mid-Day Commander








p. pwd : Prints working directory








Option?: p














-- Current Directory --










Directory: /home/shepard/project1/mc1/








G’day, Commander! What command would you like to run?




0.
whoami
: Prints out the result of the whoamicommand


1.
last
: Prints out the result of the last command




2.
ls
: Prints out the result of a listing on a user-specified path
3.
free -m : User added command








a. add command : Adds a new command to the menu.




c. change directory : Changes process working directory


e. exit : Leave Mid-Day Commander








p. pwd : Prints working directory








Option?: c














-- Change Directory --










New Directory?: /










G’day, Commander! What command would you like to run?




0.
whoami
: Prints out the result of the whoamicommand


1.
last
: Prints out the result of the last command




2.
ls
: Prints out the result of a listing on a user-specified path
3.
free -m
: User added command











a. add command : Adds a new command to the menu.




c. change directory : Changes process working directory




e. exit : Leave Mid-Day Commander




p. pwd : Prints working directory




Option?: p




-- Current Directory --




Directory: /




G’day, Commander! What command would you like to run?







4



0.
whoami
:
Prints out the result of the whoamicommand
1.
last
:
Prints out the result of the last command
2.
ls
:
Prints out the result of a listing on a user-specified path
3.
free -m :
User added command



a. add command : Adds a new command to the menu.




c. change directory : Changes process working directory




e. exit : Leave Mid-Day Commander




p. pwd : Prints working directory




Option?: e




Logging you out, Commander.




shepard@normandy:~




When processing a user-added command, you will need to tokenize the string into an argument vector. Under normal conditions, mc1 should fork() a new child process to execute that command with the accu-mulated arguments. It should then wait for that child to terminate and print statistics about that child in the same way that mc0 did.




However, three new “built-in” commands are treated differently. These are:




a - Add: adds a new command to the menu.



c - Change Directory: causes your program to change the working directory to the specified directory



e - Exit: causes your shell to terminate.



p - Print Working Directory: prints the directory associated with your process.



These must not be forked and executed in child processes. Instead, they must be executed “in line” in the mc1 process itself, because their effects need to persist to subsequent commands. For example, if you change the working directory, all children processes should run from that working directory (e.g., “rm” should remove files in the current working directory). It is not correct to tracking the variable locally and use it only for printing out via the ‘p’ option.




A requirement of this assignment (to assist the grader) is that shell must be capable of accepting its input from the standard input stream stdin. Normally, stdin is connected to the keyboard input of the terminal window. However, it is also possible in Linux to pipe a file to stdin as follows:




shepard@normandy:~ ./mc1 < file.txt




This exposes the need to handle the end-of-file condition. When the end of file is detected in stdin, mc1 should act as if e had been typed.




Note that the Linux man pages explicitly state that getrusage() returns the cumulative statistics for all children of a process, not just the statistics for the most recent child. Therefore, you must keep a record of the statistics of previous children. When you call getrusage() after a particular child has terminated, you must subtract the previous statistics from the most recent ones returned by getrusage() in order to find out how many resources that the particular child used.




To keep things simple, you may design your program for lines of input containing not more than 128 characters and not more than 32 distinct arguments. You should print an error if this condition is violated. Further, you do not need to support stdout redirection and pipes for the user-provided commands, i.e., the user will not add a command such as cat foo | less .




Helpful hints




You may need the following two functions:




chdir() - change working directory



strtok() - search for tokens in the input string



5
Phase 3: Commander with Background Execution




Create a directory called “v2” and store your code and Makefile in this directory for the third phase. Make a copy of your mc1 program and call it mc2.




You must modify shell2 to handle background tasks, which are indicated by ampersand (‘&’) characters at the ends of input lines when adding new commands. When a task is run in background, mc2 should not block until the child process completes. Instead, it prompts the user for another command. As a result, there may be multiple child processes active at once, even while mc2 is reading additional commands. Moreover, a background task can terminate at any time. In this case, mc2 should display a message that the particular task has terminated, and it should follow that message with the statistics about the command of that task.




In addition to the built-in commands of mc1, shell2 must also handle the following built-in command:




r - Running processes list. Lists all background processes currently active



Note that output from background commands that is directed to the terminal window may intermingle with the output of other commands and with the output from your mc2.




A sample session with background tasks is given below.




shepard@normandy:~ ./mc2




===== Mid-Day Commander, v2 =====




G’day, Commander! What command would you like to run?




0.
whoami
: Prints out
the result of the
whoamicommand
1.
last
: Prints out
the result of the
last command
2.
ls
: Prints out
the result of a listing on a user-specified path
a. add command : Adds a
new command to the menu.



c. change directory : Changes process working directory




e. exit : Leave Mid-Day Commander




p. pwd : Prints working directory




r. running processes : Print list of running processes




Option?: r




-- Background Processes --




G’day, Commander! What command would you like to run?




0.
whoami
: Prints out the result of the
whoamicommand
1.
last
: Prints out the result of the
last command
2.
ls
: Prints out the result of a listing on a user-specified path



a. add command : Adds a new command to the menu.




c. change directory : Changes process working directory




e. exit : Leave Mid-Day Commander




p. pwd : Prints working directory




r. running processes : Print list of running processes




Option?: a




Command to add?: make -j4 O=~/kernelDst &




Okay, added with ID 3!




G’day, Commander! What command would you like to run?




0.
whoami
: Prints out the result of the
whoamicommand
1.
last
: Prints out the result of the
last command
2.
ls
: Prints out the result of a listing on a user-specified path



make -j4 O=~/kernelDst & : User added command a. add command : Adds a new command to the menu.



6



c. change directory : Changes process working directory




e. exit : Leave Mid-Day Commander




p. pwd : Prints working directory




r. running processes : Print list of running processes




Option?: 3




-- Command: make -j4 O=~/kernelDst & --




[1] 12345 /* indicate
background task #1 and process id */
G’day, Commander! What
command would you like to run?
0.
whoami
: Prints
out the result of the whoamicommand
1.
last
: Prints
out the result of the last command
2.
ls
: Prints
out the result of a listing on a user-specified path



make -j4 O=~/kernelDst & : User added command a. add command : Adds a new command to the menu.
c. change directory : Changes process working directory




e. exit : Leave Mid-Day Commander




p. pwd : Prints working directory




Option?: 1




-- Last Logins --




shepard pts/1 1.2.3.4 Fri Jan 13 03:14 still logged in




-- Statistics ---




Elapsed time: 2 milliseconds




Page Faults: 0




Page Faults (reclaimed): 0




G’day, Commander! What command would you like to run?




0.
whoami
: Prints out
the result of the whoamicommand
1.
last
: Prints out
the result of the last command
2.
ls
: Prints out
the result of a listing on a user-specified path
3.
free -m : User added
command
a. add command : Adds a
new command to the menu.



c. change directory : Changes process working directory




e. exit : Leave Mid-Day Commander




p. pwd : Prints working directory




Option?:




-- Job Complete [1] --




Process ID: 12345




[ Output ]




-- Statistics ---




Elapsed time: 2 milliseconds




Page Faults: 0




Page Faults (reclaimed): 0




e




Logging you out, Commander.




shepard@normandy:~




If the user tries to exit mc2 before all background tasks have completed, then mc2 should refuse to exit, print a message, and wait() for those tasks to be completed. As part of the write-up describing your program, you must explain how you keep track of outstanding processes in mc2 - i.e., the data structures







7



and algorithms for maintain information about outstanding commands that have not been completed.




Helpful hints




The following two functions may be useful:




wait3() - lets you wait for any child process; returns rusage statistics



wait4() - lets you wait for a specific child process; returns rusage statistics



Either of these functions can be called with the WNOHANG option, which causes the wait() function to not block but rather return with an error code (e.g., “nobody is ready to be waited on yet”).




A suggested approach to handling background tasks is as follows. After forking a child process to invoke a background command (i.e., with a ‘&’ character at the end), go into a loop using wait3(WNOHANG) to wait for any child to finish. If wait3() returns information about a child process that has finished, print its statistics and repeat the loop. However, if wait3() indicates that no child process has finished lately, exit the loop and prompt for the next command. In the case that a command is not a background process (i.e., does not end with a ‘&’ character), then you should use a wait3() loop without the WNOHANG argument. This will pick up any previous background commands that may have completed. Once the non-background task has been waited for, loop again using wait3(WNOHANG) to pick up any remaining tasks that have finished. When wait3(WNOHANG) returns with an error, then prompt for the next command.







Checkpoint Contributions




Students must submit work that demonstrates substantial progress towards completing the project on the checkpoint date. Substantial progress is judged at the discretion of the grader to allow students flexibility in prioritizing their efforts. However, as an example, any assignment in which the first phase is completed and has a partial implementation of the second phase will be considered as making substantial progress. Projects that fail to submit a checkpoint demonstrating significant progress will incur a 10% penalty during final project grading.







Deliverables and Grading




When submitting your project, please include the following:




All of the files containing the code for all parts of the assignment.



One file called Makefile that can be used by the make command for building the three executable programs. It should support the “make clean” command, “make all” and make each of the three programs individually.



The test files or input that you use to convince yourself (and others) that your programs actually work.



Output from your tests.



A document called README.txt explaining your project and anything that you feel the instructor should know when grading the project. In particular, describe the data structure and algorithm you used to keep track of background jobs. Also, explain how you tested your programs. Only plaintext write-ups are accepted.



Please compress all the files together as a single .zip archive for submission. As with all projects, please only standard zip files for compression; .rar, .7z, and other custom file formats will not be accepted.




8



The project programming is only a portion of the project. Students should use the following checklist in turning in their projects to avoid forgetting any deliverables:




Sign up for a project partner or have one assigned (URL: https://ia.wpi.edu/cs3013/request_ teammate.php),



Submit the project code and documentation via InstructAssist (URL: https://ia.wpi.edu/cs3013/ files.php),



Complete your Partner Evaluation (URL: https://ia.wpi.edu/cs3013/evals.php), and



Schedule your Project Demonstration (URL: https://ia.wpi.edu/cs3013/demos.php), which may be posted slightly after the submission deadline.



A grading rubric has been provided at the end of this specification to give you a guide for how the project will be graded. No points can be earned for a task that has a prerequisite unless that prerequisite is working well enough to support the dependent task. Students will receive a scanned markup of this rubric as part of their project grading feedback.




Groups must schedule an appointment to demonstrate their project to the teaching assistants. Groups that fail to demonstrate their project will not receive credit for the project. If a group member fails to attend his or her scheduled demonstration time slot, he or she will receive a 10 point reduction on his or her project grade.




During the demonstrations, the TAs will be evaluating the contributions of group members. We will use this evaluation, along with partner evaluations, to determine contributions. If contributions are not equal, under-contributing students may be penalized.
















































































































9
Project 1 – Midday Commander – Grading Sheet/Rubric












Evaluation?
Grader:


Student Name:






Date/Time:


Student Name:






Team ID:


Student Name:









Late?:




















Checkpoint?:










Project Score:




Earned


Weight


Task ID


Description




















_____


5%


1


Phase 1 – Correct execution on student test cases.
_____
10%
2


Phase 1 – Correct execution on grader test cases. Prerequisite: Task 1.
_____
5%
3


Phase 2 – Correct execution on student test cases. Prerequisite: Task 2.
_____
10%
4


Phase 2 – Suitable student test cases. Prerequisite: Task 3.
_____
20%
5


Phase 2 – Correct execution on grader’s test cases. Prerequisite: Task 3.
_____
15%
6


Phase 3 – Supports background commands and jobs. Prerequisite: Task














3.






_____
10%
7


Phase 3 – Handles out-of-order commands. Prerequisite: Task 6.
_____
5%
8


Phase 3 – Comprehensive student test cases for out-of-order execution.
















Prerequisite: Task 7.
_____
20%
9


Phase 3 – Correct execution on student and grader tests. Prerequisite:
















Task 8.



Grader Notes:

More products