-rw-r--r-- 1806 libsecded-20220828/parity.c raw
#include <inttypes.h> #include "secded.h" #define BOTTOM 8 #define TWOBOTTOM 256 #define TWOPART 32 void secded_parity(void *parity_arg,const void *x_arg,long long n) { const uint8_t *x = (const uint8_t *) x_arg; uint8_t *parity = (uint8_t *) parity_arg; uint8_t sum; long long bits = 0; long long twobits = 1; long long bit = 0; long long twobit = 1; long long ntop = n>>BOTTOM; uint8_t prexor[TWOBOTTOM]; while (twobits < n) { ++bits; twobits += twobits; } for (long long j = 0;j < TWOBOTTOM;++j) prexor[j] = 0; for (long long j = 0;j < ntop;++j) for (long long k = 0;k < TWOBOTTOM;++k) prexor[k] ^= x[j*TWOBOTTOM+k]; for (long long j = ntop*TWOBOTTOM;j < n;++j) prexor[j%TWOBOTTOM] ^= x[j]; sum = 0; for (long long j = 0;j < TWOBOTTOM;++j) sum ^= prexor[j]; parity[bits] = sum; while (twobit < n && twobit < TWOBOTTOM) { sum = 0; for (long long j = 0;j < TWOBOTTOM;++j) if (j & twobit) sum ^= prexor[j]; parity[bit] = sum; ++bit; twobit += twobit; } for (bit = BOTTOM;bit < bits;++bit) parity[bit] = 0; for (long long j = 0;j < ntop;++j) { for (long long k = 0;k < TWOPART;++k) prexor[k] = x[j*TWOBOTTOM+k]; for (long long h = TWOPART;h < TWOBOTTOM;h += TWOPART) for (long long k = 0;k < TWOPART;++k) prexor[k] ^= x[j*TWOBOTTOM+h+k]; sum = 0; for (long long k = 0;k < TWOPART;++k) sum ^= prexor[k]; for (bit = BOTTOM;bit < bits;++bit) if (j&(1<<(bit-BOTTOM))) parity[bit] ^= sum; } for (long long j = ntop;j < ntop+1;++j) { sum = 0; for (long long k = 0;k < n-j*TWOBOTTOM;++k) sum ^= x[j*TWOBOTTOM+k]; for (bit = BOTTOM;bit < bits;++bit) if (j&(1<<(bit-BOTTOM))) parity[bit] ^= sum; } }