Description
Overview:
In the third part of assignment 1, you will implement the tool “4420_proctool_ps”. This tool is a reimplementation of the Unix tool “ps” which lists statistics for all the processes in the system. More
specifically, the “4420_proctools_ps” tool should produce (a subset of) all the information a call to “ps
aux” would produce. The tool has one required command argument and has the following syntax:
Shell> 4420_proctool_ps [-cpu|-mem|-pid|-com]
The tool will produce statistical information about all the process in the system. Specifically, it should
produce a table containing the following columns:
PID
(u_int)
Command
(string)
State
(char)
%CPU
(float)
%MEM
(float)
VSZ(virtual memory size)
(u_long; in bytes)
RSS (resident set size)
(u_long; in bytes)
In order to calculate the values in the different columns, you will need to access two different proc files:
• “/proc//stat”
• “/proc/uptime
Note that the difference between these two proc file locations is that each process has its own
“/proc//stat” file, while the system as a whole has only one “/proc/uptime” file. Also note that the
contents in these files constantly change. In other words, if you read the contents twice, at different points
in time, they will reflect the differences in the system between those two time points.
An important resource for you to understand the structure in both files is again the Linux man page for
proc (see Part I). It describes the format of both files in detail.
Most of the data needed in the different columns above can be directly read from “/proc//stat”.
Specifically, you can read the “PID”, the “Command” string (note that commands are stored in
parentheses, the “State”, the virtual memory size “VSZ”, and the resident set size “RSS”. It turns out that
the “%CPU” and “%MEM” field require a little bit extra work.
Let’s start with the “%MEM” field. Since we’re basically re-implementing the Unix “ps” command, we can
look at the definition of “%MEM” This field is defined as (see “man proc”) “ratio of the process’s resident
set size to the physical memory on the machine, expressed as a percentage”. Since we already know the
(RSS) resident set size (see above), all we need to calculate “%MEM” is the availability of physical memory
in the machine. There are different ways of doing it, but I suggest you use the “sysconf()” function. This
works as follows:
long phys_pages = sysconf(_SC_PHYS_PAGES);
long page_size = sysconf(_SC_PAGE_SIZE);
long phys_mem_size = phys_pages * page_size;
Next, the RSS is specified in units of numbers of “pages”. A “page” is a fixed size, basic management unit
in memory management. Different CPUs may use different page sizes. In order to calculate the actual
physical memory footprint of a process in bytes, the value of RSS (as read from “/proc//stat”, needs
to be multiplied with the (constant) value of the page size. This value can be obtained using the function
“getpagesize()” (see man getpagesize) or using “sysconf()” again (as shown above). Now you can calculate
the “%MEM” for each process by using the following equation:
( RSS * getpagesize() * 100 ) / phys_mem_size
The “%CPU” is a little bit more complicated. First note that the Unix commands “ps” and “top” use
different ways of calculating “%CPU”. In fact, “top” uses a more precise way of calculating this statistic.
Since we re-implement “ps” though, we will use its method. You should be able to verify the correctness
of your implementation by comparing your calculations to the ones done by the “ps” tool. Note that its
method is not very accurate. For example, it is possible (under certain circumstances) to obtain a %CPU
value for a process that exceeds 100%! The Unix tool “ps” defines %CPU (see man ps) as “cpu utilization
of the process in “##.#” format. Currently it is the CPU time used divided by the time the process has been
running (cputime/realtime ratio), expressed as percentage. It will not add up to 100% unless you are
lucky”
Here is how this value can be calculated. First extract the two fields “utime” and “stime” from
“/proc//stat” (see man -s5 proc). These two field represent the amount of time that a process has
been scheduled in user mode (“utime”) and in kernel mode (“stime”), measured in clock ticks. In order to
translate these values to seconds, you will need to divide them by system clock speed in HZ (divide by
“sysconf(_SC_CLK_TCK)”). In other words,
process_time = ( “utime” / sysconf(_SC_CLK_TCK) ) + ( “stime” / sysconf(_SC_ClK_TCK) )
is the total amount of time (in seconds) that a process has received.
Next, you will need to determine the time a process started after (i.e. relative to) system boot. This value,
“starttime” is also contained in the file “/proc//stat”.
Now you will need the total system “uptime”, which represents the total amount of “useful” time the CPU
has spent since boot. This value is stored in a per-system “/proc/uptime” (see man proc). This file contains
two numbers. The one you need is the first one. Note that this time is already given in units of seconds
(not clock ticks; you therefore don’t need to divide this value).
Now, you finally can calculate a process’s %CPU using the following formula:
real_time = “uptime” – ( “starttime” / sysconf(_SC_CLK_TCK) )
“%CPU” = real_time = process_time * 100 / real_time
Specific Requirements:
• Implement the above described tool “4420_proctools_ps”. The tool has one required argument
which is the sort order in which the process’s entries in the table (columns as described above)
are sorted. The following sort orders should be supported:
o 4420_proctools_ps -cpu
sort the rows based on “%CPU” (from highest to lowest)
o 4420_proctools_ps -mem
sort the rows based on ”%MEM” (from highest to lowest)
o 4420_proctools_ps -pid
sort the rows based on “PID” (from lowest to highest)
o 4420_proctools_ps -com
sort the rows lexicographically by command name
• You have to implement the tool either in C or C++. You need to use the proc filesystem (as
explained above) for this project. Do not use any other functions (example: system(), getrusage(),
etc.)
• Calling “4420_proctools_ps” witch an invalid argument (or without required argument) should
create some error message
• I put a reference implementation of “4420_proctools_ps” in my home directory on the prime
machines. You can access it in the folder “/home/drews/proctools”.
• The screenshot above shows a sample output of my reference tool.
• You will need to submit the source file(s), header files (if necessary), and you WILL NEED TO
SUBMIT A MAKEFILE. I will grade the project on “pu2.cs.ohio.edu”. I will type “make” to build the
executable tool (which, again, should be called “4420_proctools_ps”). If “make” fails (due to an
error), the GRADE FOR THE PROJECT WILL BE AN “F”!
• You will need to submit the program from “p2.cs.ohio.edu” (NOTE: THIS IS IMPORTANT. THE
SUBMISSION WILL NOT WORK FROM ANY OTHER (LAB)MACHINE OR SERVER!). The submission is
simple: “cd” into your project folder and type the following command (exactly as is shown here):
“bash> /home/drews/bin/442submit 3”. Should you need to re-submit your project
(due to changes), you will need to add an override switch “-f” to the submission: “bash>
/home/drews/bin/442submit -f 3”.
Deadline:
The project is due by 10/3/2018 (11.59pm). I will not accept any late submissions.
Additional Help and Resources:
You can use similar functions as in Parts I and II.
CS 4420/5420