This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

TMAG5170: TMAG5170 CRC Algorithm

Part Number: TMAG5170

There have been a lot of questions about the CRC on this part. Most of the recommendations are to send a command to disable the CRC or alternatively use a slow, bit-by-bit algorithm. The below code implements the CRC for this part using a byte-by-byte algorithm. It is based on a state machine approach where the present state is the current CRC and the input data is eight bits of data.

static const uint8_t crc_lut[16][128] = {
{48, 86, 252, 154, 139, 237, 71, 33, 101, 3, 169, 207, 222, 184, 18, 116, 154, 252, 86, 48, 33, 71, 237, 139, 207, 169, 3, 101, 116, 18, 184, 222, 71, 33, 139, 237, 252, 154, 48, 86, 18, 116, 222, 184, 169, 207, 101, 3, 237, 139, 33, 71, 86, 48, 154, 252, 184, 222, 116, 18, 3, 101, 207, 169, 222, 184, 18, 116, 101, 3, 169, 207, 139, 237, 71, 33, 48, 86, 252, 154, 116, 18, 184, 222, 207, 169, 3, 101, 33, 71, 237, 139, 154, 252, 86, 48, 169, 207, 101, 3, 18, 116, 222, 184, 252, 154, 48, 86, 71, 33, 139, 237, 3, 101, 207, 169, 184, 222, 116, 18, 86, 48, 154, 252, 237, 139, 33, 71},
{101, 3, 169, 207, 222, 184, 18, 116, 48, 86, 252, 154, 139, 237, 71, 33, 207, 169, 3, 101, 116, 18, 184, 222, 154, 252, 86, 48, 33, 71, 237, 139, 18, 116, 222, 184, 169, 207, 101, 3, 71, 33, 139, 237, 252, 154, 48, 86, 184, 222, 116, 18, 3, 101, 207, 169, 237, 139, 33, 71, 86, 48, 154, 252, 139, 237, 71, 33, 48, 86, 252, 154, 222, 184, 18, 116, 101, 3, 169, 207, 33, 71, 237, 139, 154, 252, 86, 48, 116, 18, 184, 222, 207, 169, 3, 101, 252, 154, 48, 86, 71, 33, 139, 237, 169, 207, 101, 3, 18, 116, 222, 184, 86, 48, 154, 252, 237, 139, 33, 71, 3, 101, 207, 169, 184, 222, 116, 18},
{154, 252, 86, 48, 33, 71, 237, 139, 207, 169, 3, 101, 116, 18, 184, 222, 48, 86, 252, 154, 139, 237, 71, 33, 101, 3, 169, 207, 222, 184, 18, 116, 237, 139, 33, 71, 86, 48, 154, 252, 184, 222, 116, 18, 3, 101, 207, 169, 71, 33, 139, 237, 252, 154, 48, 86, 18, 116, 222, 184, 169, 207, 101, 3, 116, 18, 184, 222, 207, 169, 3, 101, 33, 71, 237, 139, 154, 252, 86, 48, 222, 184, 18, 116, 101, 3, 169, 207, 139, 237, 71, 33, 48, 86, 252, 154, 3, 101, 207, 169, 184, 222, 116, 18, 86, 48, 154, 252, 237, 139, 33, 71, 169, 207, 101, 3, 18, 116, 222, 184, 252, 154, 48, 86, 71, 33, 139, 237},
{207, 169, 3, 101, 116, 18, 184, 222, 154, 252, 86, 48, 33, 71, 237, 139, 101, 3, 169, 207, 222, 184, 18, 116, 48, 86, 252, 154, 139, 237, 71, 33, 184, 222, 116, 18, 3, 101, 207, 169, 237, 139, 33, 71, 86, 48, 154, 252, 18, 116, 222, 184, 169, 207, 101, 3, 71, 33, 139, 237, 252, 154, 48, 86, 33, 71, 237, 139, 154, 252, 86, 48, 116, 18, 184, 222, 207, 169, 3, 101, 139, 237, 71, 33, 48, 86, 252, 154, 222, 184, 18, 116, 101, 3, 169, 207, 86, 48, 154, 252, 237, 139, 33, 71, 3, 101, 207, 169, 184, 222, 116, 18, 252, 154, 48, 86, 71, 33, 139, 237, 169, 207, 101, 3, 18, 116, 222, 184},
{71, 33, 139, 237, 252, 154, 48, 86, 18, 116, 222, 184, 169, 207, 101, 3, 237, 139, 33, 71, 86, 48, 154, 252, 184, 222, 116, 18, 3, 101, 207, 169, 48, 86, 252, 154, 139, 237, 71, 33, 101, 3, 169, 207, 222, 184, 18, 116, 154, 252, 86, 48, 33, 71, 237, 139, 207, 169, 3, 101, 116, 18, 184, 222, 169, 207, 101, 3, 18, 116, 222, 184, 252, 154, 48, 86, 71, 33, 139, 237, 3, 101, 207, 169, 184, 222, 116, 18, 86, 48, 154, 252, 237, 139, 33, 71, 222, 184, 18, 116, 101, 3, 169, 207, 139, 237, 71, 33, 48, 86, 252, 154, 116, 18, 184, 222, 207, 169, 3, 101, 33, 71, 237, 139, 154, 252, 86, 48},
{18, 116, 222, 184, 169, 207, 101, 3, 71, 33, 139, 237, 252, 154, 48, 86, 184, 222, 116, 18, 3, 101, 207, 169, 237, 139, 33, 71, 86, 48, 154, 252, 101, 3, 169, 207, 222, 184, 18, 116, 48, 86, 252, 154, 139, 237, 71, 33, 207, 169, 3, 101, 116, 18, 184, 222, 154, 252, 86, 48, 33, 71, 237, 139, 252, 154, 48, 86, 71, 33, 139, 237, 169, 207, 101, 3, 18, 116, 222, 184, 86, 48, 154, 252, 237, 139, 33, 71, 3, 101, 207, 169, 184, 222, 116, 18, 139, 237, 71, 33, 48, 86, 252, 154, 222, 184, 18, 116, 101, 3, 169, 207, 33, 71, 237, 139, 154, 252, 86, 48, 116, 18, 184, 222, 207, 169, 3, 101},
{237, 139, 33, 71, 86, 48, 154, 252, 184, 222, 116, 18, 3, 101, 207, 169, 71, 33, 139, 237, 252, 154, 48, 86, 18, 116, 222, 184, 169, 207, 101, 3, 154, 252, 86, 48, 33, 71, 237, 139, 207, 169, 3, 101, 116, 18, 184, 222, 48, 86, 252, 154, 139, 237, 71, 33, 101, 3, 169, 207, 222, 184, 18, 116, 3, 101, 207, 169, 184, 222, 116, 18, 86, 48, 154, 252, 237, 139, 33, 71, 169, 207, 101, 3, 18, 116, 222, 184, 252, 154, 48, 86, 71, 33, 139, 237, 116, 18, 184, 222, 207, 169, 3, 101, 33, 71, 237, 139, 154, 252, 86, 48, 222, 184, 18, 116, 101, 3, 169, 207, 139, 237, 71, 33, 48, 86, 252, 154},
{184, 222, 116, 18, 3, 101, 207, 169, 237, 139, 33, 71, 86, 48, 154, 252, 18, 116, 222, 184, 169, 207, 101, 3, 71, 33, 139, 237, 252, 154, 48, 86, 207, 169, 3, 101, 116, 18, 184, 222, 154, 252, 86, 48, 33, 71, 237, 139, 101, 3, 169, 207, 222, 184, 18, 116, 48, 86, 252, 154, 139, 237, 71, 33, 86, 48, 154, 252, 237, 139, 33, 71, 3, 101, 207, 169, 184, 222, 116, 18, 252, 154, 48, 86, 71, 33, 139, 237, 169, 207, 101, 3, 18, 116, 222, 184, 33, 71, 237, 139, 154, 252, 86, 48, 116, 18, 184, 222, 207, 169, 3, 101, 139, 237, 71, 33, 48, 86, 252, 154, 222, 184, 18, 116, 101, 3, 169, 207},
{222, 184, 18, 116, 101, 3, 169, 207, 139, 237, 71, 33, 48, 86, 252, 154, 116, 18, 184, 222, 207, 169, 3, 101, 33, 71, 237, 139, 154, 252, 86, 48, 169, 207, 101, 3, 18, 116, 222, 184, 252, 154, 48, 86, 71, 33, 139, 237, 3, 101, 207, 169, 184, 222, 116, 18, 86, 48, 154, 252, 237, 139, 33, 71, 48, 86, 252, 154, 139, 237, 71, 33, 101, 3, 169, 207, 222, 184, 18, 116, 154, 252, 86, 48, 33, 71, 237, 139, 207, 169, 3, 101, 116, 18, 184, 222, 71, 33, 139, 237, 252, 154, 48, 86, 18, 116, 222, 184, 169, 207, 101, 3, 237, 139, 33, 71, 86, 48, 154, 252, 184, 222, 116, 18, 3, 101, 207, 169},
{139, 237, 71, 33, 48, 86, 252, 154, 222, 184, 18, 116, 101, 3, 169, 207, 33, 71, 237, 139, 154, 252, 86, 48, 116, 18, 184, 222, 207, 169, 3, 101, 252, 154, 48, 86, 71, 33, 139, 237, 169, 207, 101, 3, 18, 116, 222, 184, 86, 48, 154, 252, 237, 139, 33, 71, 3, 101, 207, 169, 184, 222, 116, 18, 101, 3, 169, 207, 222, 184, 18, 116, 48, 86, 252, 154, 139, 237, 71, 33, 207, 169, 3, 101, 116, 18, 184, 222, 154, 252, 86, 48, 33, 71, 237, 139, 18, 116, 222, 184, 169, 207, 101, 3, 71, 33, 139, 237, 252, 154, 48, 86, 184, 222, 116, 18, 3, 101, 207, 169, 237, 139, 33, 71, 86, 48, 154, 252},
{116, 18, 184, 222, 207, 169, 3, 101, 33, 71, 237, 139, 154, 252, 86, 48, 222, 184, 18, 116, 101, 3, 169, 207, 139, 237, 71, 33, 48, 86, 252, 154, 3, 101, 207, 169, 184, 222, 116, 18, 86, 48, 154, 252, 237, 139, 33, 71, 169, 207, 101, 3, 18, 116, 222, 184, 252, 154, 48, 86, 71, 33, 139, 237, 154, 252, 86, 48, 33, 71, 237, 139, 207, 169, 3, 101, 116, 18, 184, 222, 48, 86, 252, 154, 139, 237, 71, 33, 101, 3, 169, 207, 222, 184, 18, 116, 237, 139, 33, 71, 86, 48, 154, 252, 184, 222, 116, 18, 3, 101, 207, 169, 71, 33, 139, 237, 252, 154, 48, 86, 18, 116, 222, 184, 169, 207, 101, 3},
{33, 71, 237, 139, 154, 252, 86, 48, 116, 18, 184, 222, 207, 169, 3, 101, 139, 237, 71, 33, 48, 86, 252, 154, 222, 184, 18, 116, 101, 3, 169, 207, 86, 48, 154, 252, 237, 139, 33, 71, 3, 101, 207, 169, 184, 222, 116, 18, 252, 154, 48, 86, 71, 33, 139, 237, 169, 207, 101, 3, 18, 116, 222, 184, 207, 169, 3, 101, 116, 18, 184, 222, 154, 252, 86, 48, 33, 71, 237, 139, 101, 3, 169, 207, 222, 184, 18, 116, 48, 86, 252, 154, 139, 237, 71, 33, 184, 222, 116, 18, 3, 101, 207, 169, 237, 139, 33, 71, 86, 48, 154, 252, 18, 116, 222, 184, 169, 207, 101, 3, 71, 33, 139, 237, 252, 154, 48, 86},
{169, 207, 101, 3, 18, 116, 222, 184, 252, 154, 48, 86, 71, 33, 139, 237, 3, 101, 207, 169, 184, 222, 116, 18, 86, 48, 154, 252, 237, 139, 33, 71, 222, 184, 18, 116, 101, 3, 169, 207, 139, 237, 71, 33, 48, 86, 252, 154, 116, 18, 184, 222, 207, 169, 3, 101, 33, 71, 237, 139, 154, 252, 86, 48, 71, 33, 139, 237, 252, 154, 48, 86, 18, 116, 222, 184, 169, 207, 101, 3, 237, 139, 33, 71, 86, 48, 154, 252, 184, 222, 116, 18, 3, 101, 207, 169, 48, 86, 252, 154, 139, 237, 71, 33, 101, 3, 169, 207, 222, 184, 18, 116, 154, 252, 86, 48, 33, 71, 237, 139, 207, 169, 3, 101, 116, 18, 184, 222},
{252, 154, 48, 86, 71, 33, 139, 237, 169, 207, 101, 3, 18, 116, 222, 184, 86, 48, 154, 252, 237, 139, 33, 71, 3, 101, 207, 169, 184, 222, 116, 18, 139, 237, 71, 33, 48, 86, 252, 154, 222, 184, 18, 116, 101, 3, 169, 207, 33, 71, 237, 139, 154, 252, 86, 48, 116, 18, 184, 222, 207, 169, 3, 101, 18, 116, 222, 184, 169, 207, 101, 3, 71, 33, 139, 237, 252, 154, 48, 86, 184, 222, 116, 18, 3, 101, 207, 169, 237, 139, 33, 71, 86, 48, 154, 252, 101, 3, 169, 207, 222, 184, 18, 116, 48, 86, 252, 154, 139, 237, 71, 33, 207, 169, 3, 101, 116, 18, 184, 222, 154, 252, 86, 48, 33, 71, 237, 139},
{3, 101, 207, 169, 184, 222, 116, 18, 86, 48, 154, 252, 237, 139, 33, 71, 169, 207, 101, 3, 18, 116, 222, 184, 252, 154, 48, 86, 71, 33, 139, 237, 116, 18, 184, 222, 207, 169, 3, 101, 33, 71, 237, 139, 154, 252, 86, 48, 222, 184, 18, 116, 101, 3, 169, 207, 139, 237, 71, 33, 48, 86, 252, 154, 237, 139, 33, 71, 86, 48, 154, 252, 184, 222, 116, 18, 3, 101, 207, 169, 71, 33, 139, 237, 252, 154, 48, 86, 18, 116, 222, 184, 169, 207, 101, 3, 154, 252, 86, 48, 33, 71, 237, 139, 207, 169, 3, 101, 116, 18, 184, 222, 48, 86, 252, 154, 139, 237, 71, 33, 101, 3, 169, 207, 222, 184, 18, 116},
{86, 48, 154, 252, 237, 139, 33, 71, 3, 101, 207, 169, 184, 222, 116, 18, 252, 154, 48, 86, 71, 33, 139, 237, 169, 207, 101, 3, 18, 116, 222, 184, 33, 71, 237, 139, 154, 252, 86, 48, 116, 18, 184, 222, 207, 169, 3, 101, 139, 237, 71, 33, 48, 86, 252, 154, 222, 184, 18, 116, 101, 3, 169, 207, 184, 222, 116, 18, 3, 101, 207, 169, 237, 139, 33, 71, 86, 48, 154, 252, 18, 116, 222, 184, 169, 207, 101, 3, 71, 33, 139, 237, 252, 154, 48, 86, 207, 169, 3, 101, 116, 18, 184, 222, 154, 252, 86, 48, 33, 71, 237, 139, 101, 3, 169, 207, 222, 184, 18, 116, 48, 86, 252, 154, 139, 237, 71, 33},
};

static inline uint8_t get_next_crc(uint8_t crc, uint8_t data) {

uint8_t crc_hl = crc_lut[crc][data / 2];
return (data & 1) ? (crc_hl >> 4) : (crc_hl & 0xF);
}


static uint8_t calc_crc(uint32_t data) {
uint8_t crc;

crc = get_next_crc(0xF, (data >> 24) & 0xFF); // first CRC value is 0xF (the initial value)
crc = get_next_crc(crc, (data >> 16) & 0xFF);
crc = get_next_crc(crc, (data >> 8) & 0xFF);
crc = get_next_crc(crc, (data >> 0) & 0xF0); // note the 0xF0 for the zero padding
return crc;
}

If anyone can think of a way to reduce the table size further, let me know.