11e9a6b47SJoerg Sonnenberger /* crc32.c -- compute the CRC-32 of a data stream
2*e041647aSSascha Wildner * Copyright (C) 1995-2006, 2010, 2011, 2012, 2016 Mark Adler
31e9a6b47SJoerg Sonnenberger * For conditions of distribution and use, see copyright notice in zlib.h
41e9a6b47SJoerg Sonnenberger *
51e9a6b47SJoerg Sonnenberger * Thanks to Rodney Brown <rbrown64@csc.com.au> for his contribution of faster
61e9a6b47SJoerg Sonnenberger * CRC methods: exclusive-oring 32 bits of data at a time, and pre-computing
71e9a6b47SJoerg Sonnenberger * tables for updating the shift register in one step with three exclusive-ors
81e9a6b47SJoerg Sonnenberger * instead of four steps with four exclusive-ors. This results in about a
91e9a6b47SJoerg Sonnenberger * factor of two increase in speed on a Power PC G4 (PPC7455) using gcc -O3.
101e9a6b47SJoerg Sonnenberger */
111e9a6b47SJoerg Sonnenberger
121e9a6b47SJoerg Sonnenberger /* @(#) $Id$ */
131e9a6b47SJoerg Sonnenberger
141e9a6b47SJoerg Sonnenberger /*
151e9a6b47SJoerg Sonnenberger Note on the use of DYNAMIC_CRC_TABLE: there is no mutex or semaphore
161e9a6b47SJoerg Sonnenberger protection on the static variables used to control the first-use generation
171e9a6b47SJoerg Sonnenberger of the crc tables. Therefore, if you #define DYNAMIC_CRC_TABLE, you should
181e9a6b47SJoerg Sonnenberger first call get_crc_table() to initialize the tables before allowing more than
191e9a6b47SJoerg Sonnenberger one thread to use crc32().
20712f98b7SJohn Marino
21712f98b7SJohn Marino DYNAMIC_CRC_TABLE and MAKECRCH can be #defined to write out crc32.h.
221e9a6b47SJoerg Sonnenberger */
231e9a6b47SJoerg Sonnenberger
241e9a6b47SJoerg Sonnenberger #ifdef MAKECRCH
251e9a6b47SJoerg Sonnenberger # include <stdio.h>
261e9a6b47SJoerg Sonnenberger # ifndef DYNAMIC_CRC_TABLE
271e9a6b47SJoerg Sonnenberger # define DYNAMIC_CRC_TABLE
281e9a6b47SJoerg Sonnenberger # endif /* !DYNAMIC_CRC_TABLE */
291e9a6b47SJoerg Sonnenberger #endif /* MAKECRCH */
301e9a6b47SJoerg Sonnenberger
311e9a6b47SJoerg Sonnenberger #include "zutil.h" /* for STDC and FAR definitions */
321e9a6b47SJoerg Sonnenberger
331e9a6b47SJoerg Sonnenberger /* Definitions for doing the crc four data bytes at a time. */
34712f98b7SJohn Marino #if !defined(NOBYFOUR) && defined(Z_U4)
35712f98b7SJohn Marino # define BYFOUR
36712f98b7SJohn Marino #endif
371e9a6b47SJoerg Sonnenberger #ifdef BYFOUR
381e9a6b47SJoerg Sonnenberger local unsigned long crc32_little OF((unsigned long,
39*e041647aSSascha Wildner const unsigned char FAR *, z_size_t));
401e9a6b47SJoerg Sonnenberger local unsigned long crc32_big OF((unsigned long,
41*e041647aSSascha Wildner const unsigned char FAR *, z_size_t));
421e9a6b47SJoerg Sonnenberger # define TBLS 8
431e9a6b47SJoerg Sonnenberger #else
441e9a6b47SJoerg Sonnenberger # define TBLS 1
451e9a6b47SJoerg Sonnenberger #endif /* BYFOUR */
461e9a6b47SJoerg Sonnenberger
471e9a6b47SJoerg Sonnenberger /* Local functions for crc concatenation */
481e9a6b47SJoerg Sonnenberger local unsigned long gf2_matrix_times OF((unsigned long *mat,
491e9a6b47SJoerg Sonnenberger unsigned long vec));
501e9a6b47SJoerg Sonnenberger local void gf2_matrix_square OF((unsigned long *square, unsigned long *mat));
51712f98b7SJohn Marino local uLong crc32_combine_ OF((uLong crc1, uLong crc2, z_off64_t len2));
52fe927c51SPeter Avalos
531e9a6b47SJoerg Sonnenberger
541e9a6b47SJoerg Sonnenberger #ifdef DYNAMIC_CRC_TABLE
551e9a6b47SJoerg Sonnenberger
561e9a6b47SJoerg Sonnenberger local volatile int crc_table_empty = 1;
57712f98b7SJohn Marino local z_crc_t FAR crc_table[TBLS][256];
581e9a6b47SJoerg Sonnenberger local void make_crc_table OF((void));
591e9a6b47SJoerg Sonnenberger #ifdef MAKECRCH
60712f98b7SJohn Marino local void write_table OF((FILE *, const z_crc_t FAR *));
611e9a6b47SJoerg Sonnenberger #endif /* MAKECRCH */
621e9a6b47SJoerg Sonnenberger /*
631e9a6b47SJoerg Sonnenberger Generate tables for a byte-wise 32-bit CRC calculation on the polynomial:
641e9a6b47SJoerg Sonnenberger x^32+x^26+x^23+x^22+x^16+x^12+x^11+x^10+x^8+x^7+x^5+x^4+x^2+x+1.
651e9a6b47SJoerg Sonnenberger
661e9a6b47SJoerg Sonnenberger Polynomials over GF(2) are represented in binary, one bit per coefficient,
671e9a6b47SJoerg Sonnenberger with the lowest powers in the most significant bit. Then adding polynomials
681e9a6b47SJoerg Sonnenberger is just exclusive-or, and multiplying a polynomial by x is a right shift by
691e9a6b47SJoerg Sonnenberger one. If we call the above polynomial p, and represent a byte as the
701e9a6b47SJoerg Sonnenberger polynomial q, also with the lowest power in the most significant bit (so the
711e9a6b47SJoerg Sonnenberger byte 0xb1 is the polynomial x^7+x^3+x+1), then the CRC is (q*x^32) mod p,
721e9a6b47SJoerg Sonnenberger where a mod b means the remainder after dividing a by b.
731e9a6b47SJoerg Sonnenberger
741e9a6b47SJoerg Sonnenberger This calculation is done using the shift-register method of multiplying and
751e9a6b47SJoerg Sonnenberger taking the remainder. The register is initialized to zero, and for each
761e9a6b47SJoerg Sonnenberger incoming bit, x^32 is added mod p to the register if the bit is a one (where
771e9a6b47SJoerg Sonnenberger x^32 mod p is p+x^32 = x^26+...+1), and the register is multiplied mod p by
781e9a6b47SJoerg Sonnenberger x (which is shifting right by one and adding x^32 mod p if the bit shifted
791e9a6b47SJoerg Sonnenberger out is a one). We start with the highest power (least significant bit) of
801e9a6b47SJoerg Sonnenberger q and repeat for all eight bits of q.
811e9a6b47SJoerg Sonnenberger
821e9a6b47SJoerg Sonnenberger The first table is simply the CRC of all possible eight bit values. This is
831e9a6b47SJoerg Sonnenberger all the information needed to generate CRCs on data a byte at a time for all
841e9a6b47SJoerg Sonnenberger combinations of CRC register values and incoming bytes. The remaining tables
851e9a6b47SJoerg Sonnenberger allow for word-at-a-time CRC calculation for both big-endian and little-
861e9a6b47SJoerg Sonnenberger endian machines, where a word is four bytes.
871e9a6b47SJoerg Sonnenberger */
make_crc_table()881e9a6b47SJoerg Sonnenberger local void make_crc_table()
891e9a6b47SJoerg Sonnenberger {
90712f98b7SJohn Marino z_crc_t c;
911e9a6b47SJoerg Sonnenberger int n, k;
92712f98b7SJohn Marino z_crc_t poly; /* polynomial exclusive-or pattern */
931e9a6b47SJoerg Sonnenberger /* terms of polynomial defining this crc (except x^32): */
941e9a6b47SJoerg Sonnenberger static volatile int first = 1; /* flag to limit concurrent making */
951e9a6b47SJoerg Sonnenberger static const unsigned char p[] = {0,1,2,4,5,7,8,10,11,12,16,22,23,26};
961e9a6b47SJoerg Sonnenberger
971e9a6b47SJoerg Sonnenberger /* See if another task is already doing this (not thread-safe, but better
981e9a6b47SJoerg Sonnenberger than nothing -- significantly reduces duration of vulnerability in
991e9a6b47SJoerg Sonnenberger case the advice about DYNAMIC_CRC_TABLE is ignored) */
1001e9a6b47SJoerg Sonnenberger if (first) {
1011e9a6b47SJoerg Sonnenberger first = 0;
1021e9a6b47SJoerg Sonnenberger
1031e9a6b47SJoerg Sonnenberger /* make exclusive-or pattern from polynomial (0xedb88320UL) */
104712f98b7SJohn Marino poly = 0;
105712f98b7SJohn Marino for (n = 0; n < (int)(sizeof(p)/sizeof(unsigned char)); n++)
106712f98b7SJohn Marino poly |= (z_crc_t)1 << (31 - p[n]);
1071e9a6b47SJoerg Sonnenberger
1081e9a6b47SJoerg Sonnenberger /* generate a crc for every 8-bit value */
1091e9a6b47SJoerg Sonnenberger for (n = 0; n < 256; n++) {
110712f98b7SJohn Marino c = (z_crc_t)n;
1111e9a6b47SJoerg Sonnenberger for (k = 0; k < 8; k++)
1121e9a6b47SJoerg Sonnenberger c = c & 1 ? poly ^ (c >> 1) : c >> 1;
1131e9a6b47SJoerg Sonnenberger crc_table[0][n] = c;
1141e9a6b47SJoerg Sonnenberger }
1151e9a6b47SJoerg Sonnenberger
1161e9a6b47SJoerg Sonnenberger #ifdef BYFOUR
1171e9a6b47SJoerg Sonnenberger /* generate crc for each value followed by one, two, and three zeros,
1181e9a6b47SJoerg Sonnenberger and then the byte reversal of those as well as the first table */
1191e9a6b47SJoerg Sonnenberger for (n = 0; n < 256; n++) {
1201e9a6b47SJoerg Sonnenberger c = crc_table[0][n];
121712f98b7SJohn Marino crc_table[4][n] = ZSWAP32(c);
1221e9a6b47SJoerg Sonnenberger for (k = 1; k < 4; k++) {
1231e9a6b47SJoerg Sonnenberger c = crc_table[0][c & 0xff] ^ (c >> 8);
1241e9a6b47SJoerg Sonnenberger crc_table[k][n] = c;
125712f98b7SJohn Marino crc_table[k + 4][n] = ZSWAP32(c);
1261e9a6b47SJoerg Sonnenberger }
1271e9a6b47SJoerg Sonnenberger }
1281e9a6b47SJoerg Sonnenberger #endif /* BYFOUR */
1291e9a6b47SJoerg Sonnenberger
1301e9a6b47SJoerg Sonnenberger crc_table_empty = 0;
1311e9a6b47SJoerg Sonnenberger }
1321e9a6b47SJoerg Sonnenberger else { /* not first */
1331e9a6b47SJoerg Sonnenberger /* wait for the other guy to finish (not efficient, but rare) */
1341e9a6b47SJoerg Sonnenberger while (crc_table_empty)
1351e9a6b47SJoerg Sonnenberger ;
1361e9a6b47SJoerg Sonnenberger }
1371e9a6b47SJoerg Sonnenberger
1381e9a6b47SJoerg Sonnenberger #ifdef MAKECRCH
1391e9a6b47SJoerg Sonnenberger /* write out CRC tables to crc32.h */
1401e9a6b47SJoerg Sonnenberger {
1411e9a6b47SJoerg Sonnenberger FILE *out;
1421e9a6b47SJoerg Sonnenberger
1431e9a6b47SJoerg Sonnenberger out = fopen("crc32.h", "w");
1441e9a6b47SJoerg Sonnenberger if (out == NULL) return;
1451e9a6b47SJoerg Sonnenberger fprintf(out, "/* crc32.h -- tables for rapid CRC calculation\n");
1461e9a6b47SJoerg Sonnenberger fprintf(out, " * Generated automatically by crc32.c\n */\n\n");
147712f98b7SJohn Marino fprintf(out, "local const z_crc_t FAR ");
1481e9a6b47SJoerg Sonnenberger fprintf(out, "crc_table[TBLS][256] =\n{\n {\n");
1491e9a6b47SJoerg Sonnenberger write_table(out, crc_table[0]);
1501e9a6b47SJoerg Sonnenberger # ifdef BYFOUR
1511e9a6b47SJoerg Sonnenberger fprintf(out, "#ifdef BYFOUR\n");
1521e9a6b47SJoerg Sonnenberger for (k = 1; k < 8; k++) {
1531e9a6b47SJoerg Sonnenberger fprintf(out, " },\n {\n");
1541e9a6b47SJoerg Sonnenberger write_table(out, crc_table[k]);
1551e9a6b47SJoerg Sonnenberger }
1561e9a6b47SJoerg Sonnenberger fprintf(out, "#endif\n");
1571e9a6b47SJoerg Sonnenberger # endif /* BYFOUR */
1581e9a6b47SJoerg Sonnenberger fprintf(out, " }\n};\n");
1591e9a6b47SJoerg Sonnenberger fclose(out);
1601e9a6b47SJoerg Sonnenberger }
1611e9a6b47SJoerg Sonnenberger #endif /* MAKECRCH */
1621e9a6b47SJoerg Sonnenberger }
1631e9a6b47SJoerg Sonnenberger
1641e9a6b47SJoerg Sonnenberger #ifdef MAKECRCH
write_table(out,table)1651e9a6b47SJoerg Sonnenberger local void write_table(out, table)
1661e9a6b47SJoerg Sonnenberger FILE *out;
167712f98b7SJohn Marino const z_crc_t FAR *table;
1681e9a6b47SJoerg Sonnenberger {
1691e9a6b47SJoerg Sonnenberger int n;
1701e9a6b47SJoerg Sonnenberger
1711e9a6b47SJoerg Sonnenberger for (n = 0; n < 256; n++)
172712f98b7SJohn Marino fprintf(out, "%s0x%08lxUL%s", n % 5 ? "" : " ",
173712f98b7SJohn Marino (unsigned long)(table[n]),
1741e9a6b47SJoerg Sonnenberger n == 255 ? "\n" : (n % 5 == 4 ? ",\n" : ", "));
1751e9a6b47SJoerg Sonnenberger }
1761e9a6b47SJoerg Sonnenberger #endif /* MAKECRCH */
1771e9a6b47SJoerg Sonnenberger
1781e9a6b47SJoerg Sonnenberger #else /* !DYNAMIC_CRC_TABLE */
1791e9a6b47SJoerg Sonnenberger /* ========================================================================
1801e9a6b47SJoerg Sonnenberger * Tables of CRC-32s of all single-byte values, made by make_crc_table().
1811e9a6b47SJoerg Sonnenberger */
1821e9a6b47SJoerg Sonnenberger #include "crc32.h"
1831e9a6b47SJoerg Sonnenberger #endif /* DYNAMIC_CRC_TABLE */
1841e9a6b47SJoerg Sonnenberger
1851e9a6b47SJoerg Sonnenberger /* =========================================================================
1861e9a6b47SJoerg Sonnenberger * This function can be used by asm versions of crc32()
1871e9a6b47SJoerg Sonnenberger */
get_crc_table()188712f98b7SJohn Marino const z_crc_t FAR * ZEXPORT get_crc_table()
1891e9a6b47SJoerg Sonnenberger {
1901e9a6b47SJoerg Sonnenberger #ifdef DYNAMIC_CRC_TABLE
1911e9a6b47SJoerg Sonnenberger if (crc_table_empty)
1921e9a6b47SJoerg Sonnenberger make_crc_table();
1931e9a6b47SJoerg Sonnenberger #endif /* DYNAMIC_CRC_TABLE */
194712f98b7SJohn Marino return (const z_crc_t FAR *)crc_table;
1951e9a6b47SJoerg Sonnenberger }
1961e9a6b47SJoerg Sonnenberger
1971e9a6b47SJoerg Sonnenberger /* ========================================================================= */
1981e9a6b47SJoerg Sonnenberger #define DO1 crc = crc_table[0][((int)crc ^ (*buf++)) & 0xff] ^ (crc >> 8)
1991e9a6b47SJoerg Sonnenberger #define DO8 DO1; DO1; DO1; DO1; DO1; DO1; DO1; DO1
2001e9a6b47SJoerg Sonnenberger
2011e9a6b47SJoerg Sonnenberger /* ========================================================================= */
crc32_z(crc,buf,len)202*e041647aSSascha Wildner unsigned long ZEXPORT crc32_z(crc, buf, len)
2031e9a6b47SJoerg Sonnenberger unsigned long crc;
2041e9a6b47SJoerg Sonnenberger const unsigned char FAR *buf;
205*e041647aSSascha Wildner z_size_t len;
2061e9a6b47SJoerg Sonnenberger {
2071e9a6b47SJoerg Sonnenberger if (buf == Z_NULL) return 0UL;
2081e9a6b47SJoerg Sonnenberger
2091e9a6b47SJoerg Sonnenberger #ifdef DYNAMIC_CRC_TABLE
2101e9a6b47SJoerg Sonnenberger if (crc_table_empty)
2111e9a6b47SJoerg Sonnenberger make_crc_table();
2121e9a6b47SJoerg Sonnenberger #endif /* DYNAMIC_CRC_TABLE */
2131e9a6b47SJoerg Sonnenberger
2141e9a6b47SJoerg Sonnenberger #ifdef BYFOUR
2151e9a6b47SJoerg Sonnenberger if (sizeof(void *) == sizeof(ptrdiff_t)) {
216712f98b7SJohn Marino z_crc_t endian;
2171e9a6b47SJoerg Sonnenberger
2181e9a6b47SJoerg Sonnenberger endian = 1;
2191e9a6b47SJoerg Sonnenberger if (*((unsigned char *)(&endian)))
2201e9a6b47SJoerg Sonnenberger return crc32_little(crc, buf, len);
2211e9a6b47SJoerg Sonnenberger else
2221e9a6b47SJoerg Sonnenberger return crc32_big(crc, buf, len);
2231e9a6b47SJoerg Sonnenberger }
2241e9a6b47SJoerg Sonnenberger #endif /* BYFOUR */
2251e9a6b47SJoerg Sonnenberger crc = crc ^ 0xffffffffUL;
2261e9a6b47SJoerg Sonnenberger while (len >= 8) {
2271e9a6b47SJoerg Sonnenberger DO8;
2281e9a6b47SJoerg Sonnenberger len -= 8;
2291e9a6b47SJoerg Sonnenberger }
2301e9a6b47SJoerg Sonnenberger if (len) do {
2311e9a6b47SJoerg Sonnenberger DO1;
2321e9a6b47SJoerg Sonnenberger } while (--len);
2331e9a6b47SJoerg Sonnenberger return crc ^ 0xffffffffUL;
2341e9a6b47SJoerg Sonnenberger }
2351e9a6b47SJoerg Sonnenberger
236*e041647aSSascha Wildner /* ========================================================================= */
crc32(crc,buf,len)237*e041647aSSascha Wildner unsigned long ZEXPORT crc32(crc, buf, len)
238*e041647aSSascha Wildner unsigned long crc;
239*e041647aSSascha Wildner const unsigned char FAR *buf;
240*e041647aSSascha Wildner uInt len;
241*e041647aSSascha Wildner {
242*e041647aSSascha Wildner return crc32_z(crc, buf, len);
243*e041647aSSascha Wildner }
244*e041647aSSascha Wildner
2451e9a6b47SJoerg Sonnenberger #ifdef BYFOUR
2461e9a6b47SJoerg Sonnenberger
247*e041647aSSascha Wildner /*
248*e041647aSSascha Wildner This BYFOUR code accesses the passed unsigned char * buffer with a 32-bit
249*e041647aSSascha Wildner integer pointer type. This violates the strict aliasing rule, where a
250*e041647aSSascha Wildner compiler can assume, for optimization purposes, that two pointers to
251*e041647aSSascha Wildner fundamentally different types won't ever point to the same memory. This can
252*e041647aSSascha Wildner manifest as a problem only if one of the pointers is written to. This code
253*e041647aSSascha Wildner only reads from those pointers. So long as this code remains isolated in
254*e041647aSSascha Wildner this compilation unit, there won't be a problem. For this reason, this code
255*e041647aSSascha Wildner should not be copied and pasted into a compilation unit in which other code
256*e041647aSSascha Wildner writes to the buffer that is passed to these routines.
257*e041647aSSascha Wildner */
258*e041647aSSascha Wildner
2591e9a6b47SJoerg Sonnenberger /* ========================================================================= */
2601e9a6b47SJoerg Sonnenberger #define DOLIT4 c ^= *buf4++; \
2611e9a6b47SJoerg Sonnenberger c = crc_table[3][c & 0xff] ^ crc_table[2][(c >> 8) & 0xff] ^ \
2621e9a6b47SJoerg Sonnenberger crc_table[1][(c >> 16) & 0xff] ^ crc_table[0][c >> 24]
2631e9a6b47SJoerg Sonnenberger #define DOLIT32 DOLIT4; DOLIT4; DOLIT4; DOLIT4; DOLIT4; DOLIT4; DOLIT4; DOLIT4
2641e9a6b47SJoerg Sonnenberger
2651e9a6b47SJoerg Sonnenberger /* ========================================================================= */
crc32_little(crc,buf,len)2661e9a6b47SJoerg Sonnenberger local unsigned long crc32_little(crc, buf, len)
2671e9a6b47SJoerg Sonnenberger unsigned long crc;
2681e9a6b47SJoerg Sonnenberger const unsigned char FAR *buf;
269*e041647aSSascha Wildner z_size_t len;
2701e9a6b47SJoerg Sonnenberger {
271712f98b7SJohn Marino register z_crc_t c;
272712f98b7SJohn Marino register const z_crc_t FAR *buf4;
2731e9a6b47SJoerg Sonnenberger
274712f98b7SJohn Marino c = (z_crc_t)crc;
2751e9a6b47SJoerg Sonnenberger c = ~c;
2761e9a6b47SJoerg Sonnenberger while (len && ((ptrdiff_t)buf & 3)) {
2771e9a6b47SJoerg Sonnenberger c = crc_table[0][(c ^ *buf++) & 0xff] ^ (c >> 8);
2781e9a6b47SJoerg Sonnenberger len--;
2791e9a6b47SJoerg Sonnenberger }
2801e9a6b47SJoerg Sonnenberger
281712f98b7SJohn Marino buf4 = (const z_crc_t FAR *)(const void FAR *)buf;
2821e9a6b47SJoerg Sonnenberger while (len >= 32) {
2831e9a6b47SJoerg Sonnenberger DOLIT32;
2841e9a6b47SJoerg Sonnenberger len -= 32;
2851e9a6b47SJoerg Sonnenberger }
2861e9a6b47SJoerg Sonnenberger while (len >= 4) {
2871e9a6b47SJoerg Sonnenberger DOLIT4;
2881e9a6b47SJoerg Sonnenberger len -= 4;
2891e9a6b47SJoerg Sonnenberger }
2901e9a6b47SJoerg Sonnenberger buf = (const unsigned char FAR *)buf4;
2911e9a6b47SJoerg Sonnenberger
2921e9a6b47SJoerg Sonnenberger if (len) do {
2931e9a6b47SJoerg Sonnenberger c = crc_table[0][(c ^ *buf++) & 0xff] ^ (c >> 8);
2941e9a6b47SJoerg Sonnenberger } while (--len);
2951e9a6b47SJoerg Sonnenberger c = ~c;
2961e9a6b47SJoerg Sonnenberger return (unsigned long)c;
2971e9a6b47SJoerg Sonnenberger }
2981e9a6b47SJoerg Sonnenberger
2991e9a6b47SJoerg Sonnenberger /* ========================================================================= */
300*e041647aSSascha Wildner #define DOBIG4 c ^= *buf4++; \
3011e9a6b47SJoerg Sonnenberger c = crc_table[4][c & 0xff] ^ crc_table[5][(c >> 8) & 0xff] ^ \
3021e9a6b47SJoerg Sonnenberger crc_table[6][(c >> 16) & 0xff] ^ crc_table[7][c >> 24]
3031e9a6b47SJoerg Sonnenberger #define DOBIG32 DOBIG4; DOBIG4; DOBIG4; DOBIG4; DOBIG4; DOBIG4; DOBIG4; DOBIG4
3041e9a6b47SJoerg Sonnenberger
3051e9a6b47SJoerg Sonnenberger /* ========================================================================= */
crc32_big(crc,buf,len)3061e9a6b47SJoerg Sonnenberger local unsigned long crc32_big(crc, buf, len)
3071e9a6b47SJoerg Sonnenberger unsigned long crc;
3081e9a6b47SJoerg Sonnenberger const unsigned char FAR *buf;
309*e041647aSSascha Wildner z_size_t len;
3101e9a6b47SJoerg Sonnenberger {
311712f98b7SJohn Marino register z_crc_t c;
312712f98b7SJohn Marino register const z_crc_t FAR *buf4;
3131e9a6b47SJoerg Sonnenberger
314712f98b7SJohn Marino c = ZSWAP32((z_crc_t)crc);
3151e9a6b47SJoerg Sonnenberger c = ~c;
3161e9a6b47SJoerg Sonnenberger while (len && ((ptrdiff_t)buf & 3)) {
3171e9a6b47SJoerg Sonnenberger c = crc_table[4][(c >> 24) ^ *buf++] ^ (c << 8);
3181e9a6b47SJoerg Sonnenberger len--;
3191e9a6b47SJoerg Sonnenberger }
3201e9a6b47SJoerg Sonnenberger
321712f98b7SJohn Marino buf4 = (const z_crc_t FAR *)(const void FAR *)buf;
3221e9a6b47SJoerg Sonnenberger while (len >= 32) {
3231e9a6b47SJoerg Sonnenberger DOBIG32;
3241e9a6b47SJoerg Sonnenberger len -= 32;
3251e9a6b47SJoerg Sonnenberger }
3261e9a6b47SJoerg Sonnenberger while (len >= 4) {
3271e9a6b47SJoerg Sonnenberger DOBIG4;
3281e9a6b47SJoerg Sonnenberger len -= 4;
3291e9a6b47SJoerg Sonnenberger }
3301e9a6b47SJoerg Sonnenberger buf = (const unsigned char FAR *)buf4;
3311e9a6b47SJoerg Sonnenberger
3321e9a6b47SJoerg Sonnenberger if (len) do {
3331e9a6b47SJoerg Sonnenberger c = crc_table[4][(c >> 24) ^ *buf++] ^ (c << 8);
3341e9a6b47SJoerg Sonnenberger } while (--len);
3351e9a6b47SJoerg Sonnenberger c = ~c;
336712f98b7SJohn Marino return (unsigned long)(ZSWAP32(c));
3371e9a6b47SJoerg Sonnenberger }
3381e9a6b47SJoerg Sonnenberger
3391e9a6b47SJoerg Sonnenberger #endif /* BYFOUR */
3401e9a6b47SJoerg Sonnenberger
3411e9a6b47SJoerg Sonnenberger #define GF2_DIM 32 /* dimension of GF(2) vectors (length of CRC) */
3421e9a6b47SJoerg Sonnenberger
3431e9a6b47SJoerg Sonnenberger /* ========================================================================= */
gf2_matrix_times(mat,vec)3441e9a6b47SJoerg Sonnenberger local unsigned long gf2_matrix_times(mat, vec)
3451e9a6b47SJoerg Sonnenberger unsigned long *mat;
3461e9a6b47SJoerg Sonnenberger unsigned long vec;
3471e9a6b47SJoerg Sonnenberger {
3481e9a6b47SJoerg Sonnenberger unsigned long sum;
3491e9a6b47SJoerg Sonnenberger
3501e9a6b47SJoerg Sonnenberger sum = 0;
3511e9a6b47SJoerg Sonnenberger while (vec) {
3521e9a6b47SJoerg Sonnenberger if (vec & 1)
3531e9a6b47SJoerg Sonnenberger sum ^= *mat;
3541e9a6b47SJoerg Sonnenberger vec >>= 1;
3551e9a6b47SJoerg Sonnenberger mat++;
3561e9a6b47SJoerg Sonnenberger }
3571e9a6b47SJoerg Sonnenberger return sum;
3581e9a6b47SJoerg Sonnenberger }
3591e9a6b47SJoerg Sonnenberger
3601e9a6b47SJoerg Sonnenberger /* ========================================================================= */
gf2_matrix_square(square,mat)3611e9a6b47SJoerg Sonnenberger local void gf2_matrix_square(square, mat)
3621e9a6b47SJoerg Sonnenberger unsigned long *square;
3631e9a6b47SJoerg Sonnenberger unsigned long *mat;
3641e9a6b47SJoerg Sonnenberger {
3651e9a6b47SJoerg Sonnenberger int n;
3661e9a6b47SJoerg Sonnenberger
3671e9a6b47SJoerg Sonnenberger for (n = 0; n < GF2_DIM; n++)
3681e9a6b47SJoerg Sonnenberger square[n] = gf2_matrix_times(mat, mat[n]);
3691e9a6b47SJoerg Sonnenberger }
3701e9a6b47SJoerg Sonnenberger
3711e9a6b47SJoerg Sonnenberger /* ========================================================================= */
crc32_combine_(crc1,crc2,len2)372fe927c51SPeter Avalos local uLong crc32_combine_(crc1, crc2, len2)
3731e9a6b47SJoerg Sonnenberger uLong crc1;
3741e9a6b47SJoerg Sonnenberger uLong crc2;
375fe927c51SPeter Avalos z_off64_t len2;
3761e9a6b47SJoerg Sonnenberger {
3771e9a6b47SJoerg Sonnenberger int n;
3781e9a6b47SJoerg Sonnenberger unsigned long row;
3791e9a6b47SJoerg Sonnenberger unsigned long even[GF2_DIM]; /* even-power-of-two zeros operator */
3801e9a6b47SJoerg Sonnenberger unsigned long odd[GF2_DIM]; /* odd-power-of-two zeros operator */
3811e9a6b47SJoerg Sonnenberger
382fe927c51SPeter Avalos /* degenerate case (also disallow negative lengths) */
383fe927c51SPeter Avalos if (len2 <= 0)
3841e9a6b47SJoerg Sonnenberger return crc1;
3851e9a6b47SJoerg Sonnenberger
3861e9a6b47SJoerg Sonnenberger /* put operator for one zero bit in odd */
387fe927c51SPeter Avalos odd[0] = 0xedb88320UL; /* CRC-32 polynomial */
3881e9a6b47SJoerg Sonnenberger row = 1;
3891e9a6b47SJoerg Sonnenberger for (n = 1; n < GF2_DIM; n++) {
3901e9a6b47SJoerg Sonnenberger odd[n] = row;
3911e9a6b47SJoerg Sonnenberger row <<= 1;
3921e9a6b47SJoerg Sonnenberger }
3931e9a6b47SJoerg Sonnenberger
3941e9a6b47SJoerg Sonnenberger /* put operator for two zero bits in even */
3951e9a6b47SJoerg Sonnenberger gf2_matrix_square(even, odd);
3961e9a6b47SJoerg Sonnenberger
3971e9a6b47SJoerg Sonnenberger /* put operator for four zero bits in odd */
3981e9a6b47SJoerg Sonnenberger gf2_matrix_square(odd, even);
3991e9a6b47SJoerg Sonnenberger
4001e9a6b47SJoerg Sonnenberger /* apply len2 zeros to crc1 (first square will put the operator for one
4011e9a6b47SJoerg Sonnenberger zero byte, eight zero bits, in even) */
4021e9a6b47SJoerg Sonnenberger do {
4031e9a6b47SJoerg Sonnenberger /* apply zeros operator for this bit of len2 */
4041e9a6b47SJoerg Sonnenberger gf2_matrix_square(even, odd);
4051e9a6b47SJoerg Sonnenberger if (len2 & 1)
4061e9a6b47SJoerg Sonnenberger crc1 = gf2_matrix_times(even, crc1);
4071e9a6b47SJoerg Sonnenberger len2 >>= 1;
4081e9a6b47SJoerg Sonnenberger
4091e9a6b47SJoerg Sonnenberger /* if no more bits set, then done */
4101e9a6b47SJoerg Sonnenberger if (len2 == 0)
4111e9a6b47SJoerg Sonnenberger break;
4121e9a6b47SJoerg Sonnenberger
4131e9a6b47SJoerg Sonnenberger /* another iteration of the loop with odd and even swapped */
4141e9a6b47SJoerg Sonnenberger gf2_matrix_square(odd, even);
4151e9a6b47SJoerg Sonnenberger if (len2 & 1)
4161e9a6b47SJoerg Sonnenberger crc1 = gf2_matrix_times(odd, crc1);
4171e9a6b47SJoerg Sonnenberger len2 >>= 1;
4181e9a6b47SJoerg Sonnenberger
4191e9a6b47SJoerg Sonnenberger /* if no more bits set, then done */
4201e9a6b47SJoerg Sonnenberger } while (len2 != 0);
4211e9a6b47SJoerg Sonnenberger
4221e9a6b47SJoerg Sonnenberger /* return combined crc */
4231e9a6b47SJoerg Sonnenberger crc1 ^= crc2;
4241e9a6b47SJoerg Sonnenberger return crc1;
4251e9a6b47SJoerg Sonnenberger }
426fe927c51SPeter Avalos
427fe927c51SPeter Avalos /* ========================================================================= */
crc32_combine(crc1,crc2,len2)428fe927c51SPeter Avalos uLong ZEXPORT crc32_combine(crc1, crc2, len2)
429fe927c51SPeter Avalos uLong crc1;
430fe927c51SPeter Avalos uLong crc2;
431fe927c51SPeter Avalos z_off_t len2;
432fe927c51SPeter Avalos {
433fe927c51SPeter Avalos return crc32_combine_(crc1, crc2, len2);
434fe927c51SPeter Avalos }
435fe927c51SPeter Avalos
crc32_combine64(crc1,crc2,len2)436fe927c51SPeter Avalos uLong ZEXPORT crc32_combine64(crc1, crc2, len2)
437fe927c51SPeter Avalos uLong crc1;
438fe927c51SPeter Avalos uLong crc2;
439fe927c51SPeter Avalos z_off64_t len2;
440fe927c51SPeter Avalos {
441fe927c51SPeter Avalos return crc32_combine_(crc1, crc2, len2);
442fe927c51SPeter Avalos }
443