1. Goals for this week

  1. Learn about command line arguments in C and the atoi function

  1. Practice with an example visualization program that uses the ParaVisi visualization library.

  2. Some reminders about dynamically allocated 2-D arrays in C, and about using gdb and valgrind for debugging C programs

  3. Introduction to Lab 7.

2. Starting Point Code

Start by creating the week08 directory in your WeeklyLabs subdirectory and copying over some files:

$ cd ~/cs31/WeeklyLabs
$ mkdir week08
$ cd week08
$ pwd
/home/you/cs31/WeeklyLabs/week08
$ cp ~sukrit/public/cs31/week08/* ./
$ ls
Makefile  colors.h  commandlineargs.c  fileio.c  students.txt
twoDarray.c  visi_example.c  bad_cells.txt

3. C command line arguments and atoi

Let’s look at an example C program that takes command line arguments. Start by opening commandlineargs.c in an editor:

$ code commandlineargs.c

The first thing to note is the change in the definition of main:

int main(int argc, char **argv) { ...

The first parameter to main, argc, is the number of command line arguments. For example, if the user enters:

$ ./a.out 10 11 200

argc will be 4 (a.out counts as one of the command line arguments, and 10, 11, and 200 as three more). Each command line argument is passed to main in the second parameter, argv, as a string (argv is an array of strings):

        -----
argv[0]:| *-|-----> "./a.out"
        -----
argv[1]:| *-|-----> "10"
        -----
argv[2]:| *-|-----> "11"
        -----
argv[3]:| *-|-----> "200"
        -----
argv[4]:| *-|-----| (NULL pointer: indicates no more command line strings)
        -----

C has functions that can convert strings of numeric characters to their int, float, and other basic types, values. For example, atoi converts a string to an int:

int x = atoi(argv[1]);  // x gets the int value 10

See the man page for atoi for more information

$ man atoi

Let’s try compiling and running this program with different command line arguments and see what happens.

4. File I/O in C

Here’s an example of file I/O in C (fileio.c), using C’s stream interface for file I/O (fopen, fclose, fscanf, fprintf, etc.). Remember, we covered this in Lab 4.

You can find more extensive documentation about file I/O in C in the textbook.

Open the fileio.c program and see what this code is doing to read from a file. Here, the file has multiple items per line that is being read in and you may want to take a closer look at it for your lab.

Try running it with the students.txt file as a command line argument:

$ ./fileio students.txt

5. Reminder about gdb and valgrind for C program debugging

We’re back to C programming this week, with pointers and functions. Remember to use layout src to view C source code and navigate using next, step, and cont.

You are all experts at using GDB to debug at the assembly level, but remember that you also know how to use GDB (and Valgrind) to debug programs at the C code level.

Previously in lab, we looked at some examples of using both gdb and valgrind. Take a look at the Weekly Lab Meeting 2 page and the examples we talked about as a reminder of how to use gdb and the Weekly Lab Meeting 5 page for how to use valgrind.

6. Dynamically Allocated 2-D Arrays in C

We are not going to look at this program together in lab today, but the twoDarray.c program contains examples of C statically declared 2D arrays and dynamically allocated 2D arrays (using a single malloc).

As you work on Lab 7, you can refer to this example program dynamically allocate and accesses a 2D array.

7. Lab 7

Finally, let’s take a look at Lab 7.

8. Part 2: ParaVisi Visualization Library

You will implement two different animations/visualizations of the solution to your Lab 7 assignment. One of these will be a GUI (Graphical User Interface) visualization that uses the ParaVisi library.

With the files you copied over is an example program that uses the ParaVisi library. Let’s first try running it to see what it does:

$ ./visi_example 200 200 50

Then, let’s open up the source file and examine the code together:

$ code visi_example.c

At the top of the file is a long comment about the steps a program needs to take to initialize and use the ParaVisi library to visualize their program. Let’s first read through these, and then look at this code together, starting with main.

As we look at it, note how the struct appl_data is being used as an argument to the ParaVisi library functions. It defines the key information that the library needs to know.

Let’s also look at the simulation function that performs the updates to the image buffer based on updates to application program state. Note that after each call to the ParaVisi draw_ready function, the program calls usleep to slow down the animation:

usleep(SLEEP_USECS);   // otherwise animation moves too fast

Looking in the update_colors function, you can see how the program updates the color of each pixel based on some the program data. A line such as the one below says that the buffer buff, indexed at buff_i, should be set to the color red:

buff[buff_i] = c3_red;

The colors are defined in the colors.h file: c3_black, c3_red, c3_orange, c3_yellow, c3_green, c3_blue, c3_purple, c3_white, c3_pink, c3_teal, c3_brown. If you want to define your own colors, you can specify the red, green and blue values as follows:

// This is "garnet" according the College's style guide
buff[buff_i] = (color3){99, 25, 25};

There are a lot of websites that will give you the RGB values for different colors. Here is one example.

Documentation about using the ParaVisi interface is available as a comment at the top of the visi_example.c program. Also, more detailed documentation is available in the pthreadGridVisi.h header file:

$ code /usr/local/include/qtvis/pthreadGridVisi.h

9. Handy References