cancel
Showing results for 
Search instead for 
Did you mean: 

How to generate CRC-16 in javascript and validate the checksum on STM32F373

LMorr.3
Senior II

I need to generate a simple CRC16 checksum from a unit8_t array[64] in javascript and validate the checksum on the STM32F373.

I have been looking at the CRC unit and all of its options.  I see STM32 use a non-standard scheme.

Does anyone know of a sample library or function examples showing how it can be done in javascript with matching c function?  

Here is the javascript function i could potentially use if I can match up a c function or STM32 CRC config settings to match:

function calculateCRC(data) {
    const polynomial = 0xEDB88320;
    let crc = 0xFFFFFFFF;
    // Iterate through each character in the data
    for (let i = 0; i < data.length; i++) {
        // XOR the current character
        // with the current CRC value
        crc ^= data.charCodeAt(i);
 
        // Perform bitwise operations
        // to calculate the new CRC value
        for (let j = 0; j < 8; j++) {
            crc = (crc >>> 1) ^ (crc & 1 ? polynomial : 0);
        }
    }
    // Perform a final XOR operation and return the CRC value
    return crc ^ 0xFFFFFFFF;
}
 
1 ACCEPTED SOLUTION

Accepted Solutions
JamesHome
Associate

The CRC16 checksum calculation is commonly used for error-checking purposes. The JavaScript function you provided is a CRC32 implementation, not CRC16. Here's a CRC16 implementation in JavaScript that matches a common CRC16-CCITT polynomial (0x1021) and its corresponding C function:

Javascript&colon;

 

function calculateCRC16(data) {
    const polynomial = 0x1021;
    let crc = 0xFFFF;

    for (let i = 0; i < data.length; i++) {
        crc ^= (data[i] << 8);

        for (let j = 0; j < 8; j++) {
            crc = (crc & 0x8000) ? ((crc << 1) ^ polynomial) : (crc << 1);
        }
    }

    return crc & 0xFFFF;
}

 

You can use this JavaScript function to calculate the CRC16 checksum for your unit8_t array[64] in JavaScript. Now, let's create a corresponding C function for STM32.

C (STM32):

 

#include <stdint.h>

uint16_t calculateCRC16(const uint8_t *data, uint32_t length) {
    const uint16_t polynomial = 0x1021;
    uint16_t crc = 0xFFFF;

    for (uint32_t i = 0; i < length; i++) {
        crc ^= (data[i] << 8);

        for (uint8_t j = 0; j < 8; j++) {
            crc = (crc & 0x8000) ? ((crc << 1) ^ polynomial) : (crc << 1);
        }
    }

    return crc & 0xFFFF;
}

 

You can use this C function on your STM32F373 to validate the CRC16 checksum. Make sure to pass the same array of data and its length to both the JavaScript and C functions.

Note: CRC16 settings can vary, so it's important to ensure that both the JavaScript and C implementations use the same polynomial and initial CRC value for compatibility. The implementations provided use the common CRC16-CCITT polynomial (0x1021) and initial value (0xFFFF).

 

View solution in original post

3 REPLIES 3

Depends on the polynomial, shift direction, endianess, etc there are lots of ways to implement a 16-bit CRC, even a "standard" one

// left shift, 0x1021 polynomial
uint16_t crc16_byte(uint16_t crc, uint8_t data)
{
	int i;
	crc ^= (uint16_t)crc << 8; // Apply byte to high order

	for(i=0; i<8; i++)
		crc = (crc << 1) ^ ((crc & 0x8000) ? 0x1021 : 0);

	return(crc);
}

 

ST's 32-bit uses a "standard" polynomial, but assumes data is applied 32-bit at a time in Big Endian

uint32_t crc32_word(uint32_t crc, uint32_t data)
{
	int i;
	crc ^= data;

	for(i=0; i<32; i++)
		crc = (crc << 1) ^ ((crc & 0x80000000) ? 0x04C11DB7 : 0);

	return(crc);
}
Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..
JamesHome
Associate

The CRC16 checksum calculation is commonly used for error-checking purposes. The JavaScript function you provided is a CRC32 implementation, not CRC16. Here's a CRC16 implementation in JavaScript that matches a common CRC16-CCITT polynomial (0x1021) and its corresponding C function:

Javascript&colon;

 

function calculateCRC16(data) {
    const polynomial = 0x1021;
    let crc = 0xFFFF;

    for (let i = 0; i < data.length; i++) {
        crc ^= (data[i] << 8);

        for (let j = 0; j < 8; j++) {
            crc = (crc & 0x8000) ? ((crc << 1) ^ polynomial) : (crc << 1);
        }
    }

    return crc & 0xFFFF;
}

 

You can use this JavaScript function to calculate the CRC16 checksum for your unit8_t array[64] in JavaScript. Now, let's create a corresponding C function for STM32.

C (STM32):

 

#include <stdint.h>

uint16_t calculateCRC16(const uint8_t *data, uint32_t length) {
    const uint16_t polynomial = 0x1021;
    uint16_t crc = 0xFFFF;

    for (uint32_t i = 0; i < length; i++) {
        crc ^= (data[i] << 8);

        for (uint8_t j = 0; j < 8; j++) {
            crc = (crc & 0x8000) ? ((crc << 1) ^ polynomial) : (crc << 1);
        }
    }

    return crc & 0xFFFF;
}

 

You can use this C function on your STM32F373 to validate the CRC16 checksum. Make sure to pass the same array of data and its length to both the JavaScript and C functions.

Note: CRC16 settings can vary, so it's important to ensure that both the JavaScript and C implementations use the same polynomial and initial CRC value for compatibility. The implementations provided use the common CRC16-CCITT polynomial (0x1021) and initial value (0xFFFF).

 

Thank you!