typedef unsigned int reflectWidth;

#define POLYNOMIAL     0x1021

#define WIDTH   (8 * sizeof(resultType))
#define MSb     ((resultType)1 << (WIDTH - 1))
#define LSb     (1)

#define REFLECT_DATA(X)       ((readType) reflect((X), sizeof(readType) * 8))
#define REFLECT_REMAINDER(X)  (reflect((X), WIDTH))

// reflect the value passed, assuming nBits of this
// value are significant
reflectWidth
reflect(reflectWidth data, unsigned char nBits)
{
    reflectWidth reflection = 0;
    reflectWidth reflectMask = (reflectWidth)1 << nBits - 1;
    unsigned char bitp;

    for (bitp = 0; bitp != nBits; bitp++) {
        if (data & 0x01) {
            reflection |= reflectMask;
        }
        data >>= 1;
        reflectMask >>= 1;
    }

    return reflection;
}

resultType
crc_reflected_IO(const readType * data, unsigned n, resultType remainder) {
    unsigned pos;
    readType   reflected;
    unsigned char bitp;

    for (pos = 0; pos != n; pos ++) {
        reflected = REFLECT_DATA(data[pos]);
        remainder ^= ((resultType)reflected << (WIDTH - 8));

        for (bitp = 8; bitp > 0; bitp--) {
            if (remainder & MSb) {
                remainder = (remainder << 1) ^ POLYNOMIAL;
            } else {
                remainder <<= 1;
            }
        }
    }
    remainder = REFLECT_REMAINDER(remainder);

    return remainder;
}