B09 Lab week 6

This lab is an exercise on file I/O in C, including opening, closing, binary I/O, formatted input, and detecting how much valid data you actually get.

Starter file saveload.c is provided, along with support files and sample inputs.

A struct point is defined in point.h; here it is again:

typedef struct point {
  int x, y;
} point;

Your job is to implement the following functions for writing and reading an array of these points to/from a file, given pathname, array address, and how many points. There are a binary version and a formatted (human-readable) version.

// write and read binary
ssize_t save_points(const char *pathname, const point *a, size_t n);
ssize_t load_points(const char *pathname, point *a, size_t n);

// read free-formatted
ssize_t scan_points(const char *pathname, point *a, size_t n);

In all cases, n is how many points to write/read, a is the address of the array of points. You may assume that the array is large enough.

In the reading cases, read n complete points or as many as possible, whichever happens first. There are extra elaborations below.

Assumptions and responsibilities for all functions:

Binary

A single use of fwrite() or fread() suffices to conform to the binary format if used correctly.

The only scenerio you need to handle when reading does not get n complete points is when the file is too small. But it is trivial to find out from the return value of fread().

You can use the od program to visualize binary files. The option -t dI (interpret every 4 bytes as an int) is most suitable for this lab, e.g.,

od -t dI sample-binary

The sample file sample-binary has 3 points: (3, 14), (-5, 7), (45, -34).

Free-Formatted

For scan_points(), the format is: Each point is 2 integers in the order x, y; integer is as in %d; integers and points are separated by spaces and/or newlines; spaces and newlines can also appear before and after. Such spacing rules should be trivial to handle if you truly understand fscanf().

The scenerios you need to handle when fewer than n complete points can be read are:

In those cases, read until you encounter end of file or invalid data before completing one point. Disregard the incomplete point (and any remaining data). If you understand the return value of fscanf(), it should be easy to know when to stop.

The sample file sample-free.txt is an example of having at most 3 complete points; afterwards it’s an incomplete point and invalid data.

Testing And Handing In

Please hand in a completed saveload.c only. Please do not put main() in it.

Please make your own C file for tests and main(), like in basictest.c. Then you can compile by, e.g.,

gcc -O2 -Wall saveload.c basictest.c

(Auto-marking will compile with -O2 -Wall.)