category-group: math
layer: 1
header file(s): z_math.h
libraries: libz00.lib libz01.lib

synopsis.
the few math functions found here at layer 1 were originally categorized as string functions in layer 1. It was decided to categorize them under the "mathematics" umbrella. The CRC calculation function is used by the hash class objects (found at higher layers).

[C] functions (aka subroutines):

CRC32_checksum()
SIGNATURE: u_long CRC32_checksum (const byte_t *data, size_t n, u_long *ans, flag_o *pf, int *pe = NULL)
SYNOPSIS:
calculates the CRC (Cyclic Redundancy Check) value of a "string" block (The string is of type "byte_t", an alias for "u_char").
PARAMETERS
  • data: points to a block of data. This "block" can be a char[]. It must be properly casted (see example).
  • n: number of bytes to process. Note that this has nothing to do with a null-terminated string. "n" can be less than the length of the string - in which case, only the first 4 n bytes will be processed. It is your responsibility to correctly set this parameter value.
  • ans: initial value (can be any), and also output value. the final-resultant value of this parameter is identical to the return value (eg, you have 2 routes to getting the CRC value). This parameter is not initialized internally. Thus, repeated calls to CRC32_checksum() will update "ans", continuing with its last value.
    recommended initial value: 0, or 0xffffffff (for compatibility with PKZIP)
  • pe: error indicator [output] variable. can have 2 values: 0 {success} or 1 {data was a null pointer}.
DESCRIPTION:
sample usage:
    char *my_datas[4];
    my_data[0] = "Four score and seven years ago";
    my_data[1] = "To be, or not to be; that is the question";
    my_data[2] = "The only thing we have to fear is fear itself";
    my_data[3] = "Hi dee-dee; Hi dee-do.";
    int ie, i;
    u_long answer, x = 0xffffffff;
    size_t n_bytes = z_strlen (my_data);
    for (i = 0; i < 4; i++)
      answer = CRC32_checksum ((const byte_t *) my_data[i], n_bytes, &x);
In this case "x" will have the cumulative CRC value for all 4 strings (as if they were concatenated).
There are 2 algorithms for calculating a CRC value ("Method 1" & "Method 2"). They both use a 256-element array of values, and both shift the value over 8 places and X-ORing the current value with a lookup from the tables. They are almost the same, but for Method 1, the length of the block is included in the CRC computation (after the block is processed). The default method is Method 1. To use Method 2, set the first bit (bit 0) of the [optianal] flag object to 1:
  char *my_fluff[] = "Do you know the way to San Jose?";
  u_long x = 0xffffffff;
  size_t n_bytes = z_strlen (my_fluff);
  flag_o myflag = z_CRC_METHOD_2;
  CRC32_checksum ((const byte_t *) my_data[i], n_bytes, &x, &myflag);
Bit 1 (the 2nd bit; if set, value is 2), if set, adds the block length to the CRC value. This is probably useful only when doing a single block of bytes. Thus, if you want to use method 2 and include a file size, in the above example set the flag value to 3:
    flag_o myflag = 3;
The remainder of the flags in the rather excessive use of a flag object are reserved for future use.
RETURNS: {number >= 0} the CRC value