mirror of
https://github.com/EQEmu/Server.git
synced 2025-12-12 05:21:29 +00:00
* Update zlibng * Set cmake path more directly in zlibng to hopefully fix an issue with the build on drone * I'm dumb, missing / in path * Mackal helps with a dumb gitignore issue * Adding all the files, not sure what's ignoring them and im tired of looking * Some tweaks to zlibng build to hopefully get it to build properly. works on msvc now
178 lines
6.5 KiB
C
178 lines
6.5 KiB
C
/* crc32.c -- output crc32 tables
|
|
* Copyright (C) 1995-2006, 2010, 2011, 2012, 2016, 2018 Mark Adler
|
|
* For conditions of distribution and use, see copyright notice in zlib.h
|
|
*/
|
|
|
|
#include <stdio.h>
|
|
#include <inttypes.h>
|
|
#include "zbuild.h"
|
|
#include "deflate.h"
|
|
#include "crc32_p.h"
|
|
|
|
static uint32_t crc_table[8][256];
|
|
static uint32_t crc_comb[GF2_DIM][GF2_DIM];
|
|
|
|
static void gf2_matrix_square(uint32_t *square, const uint32_t *mat);
|
|
static void make_crc_table(void);
|
|
static void make_crc_combine_table(void);
|
|
static void print_crc_table(void);
|
|
static void print_crc_combine_table(void);
|
|
static void write_table(const uint32_t *, int);
|
|
|
|
|
|
/* ========================================================================= */
|
|
static void gf2_matrix_square(uint32_t *square, const uint32_t *mat) {
|
|
int n;
|
|
|
|
for (n = 0; n < GF2_DIM; n++)
|
|
square[n] = gf2_matrix_times(mat, mat[n]);
|
|
}
|
|
|
|
/* =========================================================================
|
|
Generate tables for a byte-wise 32-bit CRC calculation on the polynomial:
|
|
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.
|
|
|
|
Polynomials over GF(2) are represented in binary, one bit per coefficient,
|
|
with the lowest powers in the most significant bit. Then adding polynomials
|
|
is just exclusive-or, and multiplying a polynomial by x is a right shift by
|
|
one. If we call the above polynomial p, and represent a byte as the
|
|
polynomial q, also with the lowest power in the most significant bit (so the
|
|
byte 0xb1 is the polynomial x^7+x^3+x+1), then the CRC is (q*x^32) mod p,
|
|
where a mod b means the remainder after dividing a by b.
|
|
|
|
This calculation is done using the shift-register method of multiplying and
|
|
taking the remainder. The register is initialized to zero, and for each
|
|
incoming bit, x^32 is added mod p to the register if the bit is a one (where
|
|
x^32 mod p is p+x^32 = x^26+...+1), and the register is multiplied mod p by
|
|
x (which is shifting right by one and adding x^32 mod p if the bit shifted
|
|
out is a one). We start with the highest power (least significant bit) of
|
|
q and repeat for all eight bits of q.
|
|
|
|
The first table is simply the CRC of all possible eight bit values. This is
|
|
all the information needed to generate CRCs on data a byte at a time for all
|
|
combinations of CRC register values and incoming bytes. The remaining tables
|
|
allow for word-at-a-time CRC calculation for both big-endian and little-
|
|
endian machines, where a word is four bytes.
|
|
*/
|
|
static void make_crc_table(void) {
|
|
int n, k;
|
|
uint32_t c;
|
|
uint32_t poly; /* polynomial exclusive-or pattern */
|
|
/* terms of polynomial defining this crc (except x^32): */
|
|
static const unsigned char p[] = {0, 1, 2, 4, 5, 7, 8, 10, 11, 12, 16, 22, 23, 26};
|
|
|
|
/* make exclusive-or pattern from polynomial (0xedb88320) */
|
|
poly = 0;
|
|
for (n = 0; n < (int)(sizeof(p)/sizeof(unsigned char)); n++)
|
|
poly |= (uint32_t)1 << (31 - p[n]);
|
|
|
|
/* generate a crc for every 8-bit value */
|
|
for (n = 0; n < 256; n++) {
|
|
c = (uint32_t)n;
|
|
for (k = 0; k < 8; k++)
|
|
c = c & 1 ? poly ^ (c >> 1) : c >> 1;
|
|
crc_table[0][n] = c;
|
|
}
|
|
|
|
/* generate crc for each value followed by one, two, and three zeros,
|
|
and then the byte reversal of those as well as the first table */
|
|
for (n = 0; n < 256; n++) {
|
|
c = crc_table[0][n];
|
|
crc_table[4][n] = ZSWAP32(c);
|
|
for (k = 1; k < 4; k++) {
|
|
c = crc_table[0][c & 0xff] ^ (c >> 8);
|
|
crc_table[k][n] = c;
|
|
crc_table[k + 4][n] = ZSWAP32(c);
|
|
}
|
|
}
|
|
}
|
|
|
|
static void make_crc_combine_table(void) {
|
|
int n, k;
|
|
/* generate zero operators table for crc32_combine() */
|
|
|
|
/* generate the operator to apply a single zero bit to a CRC -- the
|
|
first row adds the polynomial if the low bit is a 1, and the
|
|
remaining rows shift the CRC right one bit */
|
|
k = GF2_DIM - 3;
|
|
crc_comb[k][0] = 0xedb88320UL; /* CRC-32 polynomial */
|
|
uint32_t row = 1;
|
|
for (n = 1; n < GF2_DIM; n++) {
|
|
crc_comb[k][n] = row;
|
|
row <<= 1;
|
|
}
|
|
/* generate operators that apply 2, 4, and 8 zeros to a CRC, putting
|
|
the last one, the operator for one zero byte, at the 0 position */
|
|
gf2_matrix_square(crc_comb[k + 1], crc_comb[k]);
|
|
gf2_matrix_square(crc_comb[k + 2], crc_comb[k + 1]);
|
|
gf2_matrix_square(crc_comb[0], crc_comb[k + 2]);
|
|
|
|
/* generate operators for applying 2^n zero bytes to a CRC, filling out
|
|
the remainder of the table -- the operators repeat after GF2_DIM
|
|
values of n, so the table only needs GF2_DIM entries, regardless of
|
|
the size of the length being processed */
|
|
for (n = 1; n < k; n++)
|
|
gf2_matrix_square(crc_comb[n], crc_comb[n - 1]);
|
|
}
|
|
|
|
static void write_table(const uint32_t *table, int k) {
|
|
int n;
|
|
|
|
for (n = 0; n < k; n++)
|
|
printf("%s0x%08" PRIx32 "%s", n % 5 ? "" : " ",
|
|
(uint32_t)(table[n]),
|
|
n == k - 1 ? "\n" : (n % 5 == 4 ? ",\n" : ", "));
|
|
}
|
|
|
|
static void print_crc_table(void) {
|
|
int k;
|
|
printf("#ifndef CRC32_TBL_H_\n");
|
|
printf("#define CRC32_TBL_H_\n\n");
|
|
printf("/* crc32_tbl.h -- tables for rapid CRC calculation\n");
|
|
printf(" * Generated automatically by makecrct.c\n */\n\n");
|
|
|
|
/* print CRC table */
|
|
printf("static const uint32_t ");
|
|
printf("crc_table[8][256] =\n{\n {\n");
|
|
write_table(crc_table[0], 256);
|
|
for (k = 1; k < 8; k++) {
|
|
printf(" },\n {\n");
|
|
write_table(crc_table[k], 256);
|
|
}
|
|
printf(" }\n};\n\n");
|
|
|
|
printf("#endif /* CRC32_TBL_H_ */\n");
|
|
}
|
|
|
|
static void print_crc_combine_table(void) {
|
|
int k;
|
|
printf("#ifndef CRC32_COMB_TBL_H_\n");
|
|
printf("#define CRC32_COMB_TBL_H_\n\n");
|
|
printf("/* crc32_comb_tbl.h -- zero operators table for CRC combine\n");
|
|
printf(" * Generated automatically by makecrct.c\n */\n\n");
|
|
|
|
/* print zero operator table */
|
|
printf("static const uint32_t ");
|
|
printf("crc_comb[%d][%d] =\n{\n {\n", GF2_DIM, GF2_DIM);
|
|
write_table(crc_comb[0], GF2_DIM);
|
|
for (k = 1; k < GF2_DIM; k++) {
|
|
printf(" },\n {\n");
|
|
write_table(crc_comb[k], GF2_DIM);
|
|
}
|
|
printf(" }\n};\n\n");
|
|
|
|
printf("#endif /* CRC32_COMB_TBL_H_ */\n");
|
|
}
|
|
|
|
// The output of this application can be piped out to recreate crc32.h
|
|
int main(int argc, char *argv[]) {
|
|
if (argc > 1 && strcmp(argv[1], "-c") == 0) {
|
|
make_crc_combine_table();
|
|
print_crc_combine_table();
|
|
} else {
|
|
make_crc_table();
|
|
print_crc_table();
|
|
}
|
|
return 0;
|
|
}
|