Overview
This semester you will be writing a program to synchronize directories
on two machines. You will transfer files from the source machine to
the destination machine. A file will be transferred if either it is
not on the destination machine, or the copy on the destination machine
is older than the one on the source machine.
In this assignment you will be writing a function that will be useful for the final assignment. Given two arrays of strings, each representing the files on a directorry of a machine, we want to be able to divide the strings into three groups:
We will need to allocate memory for the three arrays that we create. We will do this in such a way that the three arrays can be freed individually when they are no longer needed.
In C, an array of strings is just an array of pointers, each of which is assumed to be pointing to a string. A string is a sequence of bytes terminated by the string terminator, a null byte. For this assignment we assume that the arrays of string are NULL-terminated, meaning that a NULL pointer terminates the array of pointers.
Please read the entire assignment, especially the part on turning in the assignment, before writing any code.
Use the programming style described here.
None of the functions below modify memory referenced (directly or indirectly) by a parameter of type char **.
Part 0:
This is actually part of Assignment 0.
Part 1:
Write a function:
int null_terminated_size(char **array);
that returns the number of pointers in array before a NULL pointer.
Part 2:
In order to allocate space for the three arrays, we will need to know the
size of each array. Write a function:
int num_in_both(char **first, char **second);
You may assume that neither parameter is NULL and that each points
to a NULL-terminated array of strings. This function returns the number
of strings that appear in both arrays.
Two strings are identical if they contain exactly the same characters
(in the same order). Your comparison should be case sensitive.
Consider using strcmp.
You may assume that neither array contains duplicate strings.
Note that you are comparing the strings, and not just the pointers.
Part 3:
Write a function:
int num_only_in_first(char **first, char **second);
that returns the number of strings that appear in the first array
but not in the second one.
You can do this by calling the functions in Part 1 and Part 2 appropriately.
Note: Since the arrays contain unique strings, a string in the first array
is either also in the second array or it is only in the first array.
Part 4
Write a function:
int create_lists(char **first, char **second, char ***only_first,
      char ***only_second, char ***both);
It allocates three NULL-terminated arrays of pointers that point to
strings only in the first array, only in the second array, and those
in both arrays. Use your functions in Parts 1-3 to determine the sizes of
the arrays needed, allocate the arrays and fill them appropriately.
Set the last three parameters to point to these allocated arrays.
The pointers in the last array should be identical to pointers in the
first array. Return 0 on success (all memory allocations successful)
and -1 on error (a memory allocation was not successful). If an error
occurs, be sure to free all memory allocated by the function and set
the last three parameters to NULL. If 0 is returned, none of three
final parameters should be set to NULL.
Be sure you handle the cases in which the created arrays are empty (first entry is a NULL pointer).
If you can successfully do Part 4, you can consider yourself a 3-star programmer.
Note added 9/12/06:
Each of the three arrays you create contains pointers.
Each of the pointers in the first and last array you create should be
identical to a pointer in the first array. Each of the pointers
in the second array you create should be identical to a pointer in the
second array. In other words, do not allocate space for the
strings, only for the arrays of pointers.
Turning in your assignment
You should do the parts of this assignment sequentially.
Each time you write a function, you need to test it and convince me
that you tested in thoroughly.
This means that for each part of the assignment (aside from Part 0)
you will write a main program that tests the corresponding function
and produce output from that test. If the output is not self-explanatory,
you need to comment the generated output.
Each time you start a new part of this assignment, create a new directly which will contain all of the code from the previous part and the new code for that part. This will give you a backup if something gets inadvertently deleted.
You should also run lint on each main program. Unfortunately, lint is not available under Linux, so you will need to remotely log into one of the Solaris machines to run lint. You will not need to make a new copy of your code for this since your home directory is shared on all of the machines in the CS labs. Read about using lint here.
Use this cover sheet in handing in your assignment. Consecutively number each page of your assignment that you hand in. Fill in each lined space on the cover sheet with the appropriate page number. Be sure to answer each question on the cover sheet. (Sometimes there will be questions on the reverse side of a cover sheet.) Only check the "all correct" box if you think you did everything perfectly. Otherwise, give an explanation of what you did that was not working. No credit will be given for a part of an assignment unless the corresponding description indicates in detail what progress you made on that part.
For each part of the assignment in which you create code, use a makefile to compile and lint the programs. You can find a discussion of using makefiles in Appendix A of USP. The programs from USP for each chapter are available on the web and provide examples of compile using make.
Assignments are generally due at the start of class on the due date.