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.

CRC-32 with 0x4C11DB7 polynomial

I am trying to use the CRC module to calculate the CRC-32 using the polynomial above. I have another software based implementation I am using to compare the results, with no success so far. I have tried several combinations of seed, bit reversal, endiannes etc. but so far I do not get the same results for the same input data.

The software version of the CRC-32 was taken from FreeBSD code (github.com/.../crc32.c)

I used the first table as well as the code on the comment right bellow it. I compared the outputs with those of online crc calculators (http://www.zorc.breitbandkatze.de/crc.html

I tried changing configurations on the fly (i.e. changing the config registers before calling CRCDataProcess() without success.

What am I doing wrong?

uint32_t calc_crc32 (uint32_t * buf, uint32_t length)
{
	uint32_t config = CRC_CFG_INIT_SEED | CRC_CFG_TYPE_P4C11DB7 | CRC_CFG_SIZE_8BIT;
	uint32_t seed = ~0U;

	// Reset
    SysCtlPeripheralReset(SYSCTL_PERIPH_CCM0);
    while(!SysCtlPeripheralReady(SYSCTL_PERIPH_CCM0)) {}

    // Set operation mode
    CRCConfigSet(CCM0_BASE, config);

    CRCSeedSet(CCM0_BASE, seed);

	uint32_t result = CRCDataProcess (CCM0_BASE, buf, length, false);
	return result;
}

  • Hello Elder

    Did you try CRC_CFG_SIZE_32BIT instead of CRC_CFG_SIZE_8BIT?
  • Yes. No match either.
  • Hello Elder

    Can you please send the following information for me to recreate the issue and investigate.,

    1. Sample sequence you are sending,
    2. Init Seed (I believe you are using 0)
    3. Expected and Actual CRC result.
  • Hi Amit,

    The first two I can answer now, the third I will be able to answer only on thursday when I am back to the office.

    1- Sample sequence: "0123" (ascii). I discard the trailing null character so four characters.

    2- Actually ~0U or 0xFFFFFFFF (line 4 of the code excerpt). I tried with 0 too and it did not match either.

    3- Expected: 0xA6669D7D, actual: TBD.

    You may try other sequences and check on the online calculator bellow:

    https://www.lammertbies.nl/comm/info/crc-calculation.html

    The soft version adapted from FreeBSD code (mentioned in my first post) returns the same CRC as the online calculator above.

  • Hello Elder

    Sure. I will check it up as well in the meantime.
  • Hello Elder

    I had to dig into the CRC32 mechanism and the correct configuration that matches the web page is the following.

    CRCConfigSet(CCM0_BASE, (CRC_CFG_INIT_1 | CRC_CFG_RESINV | CRC_CFG_TYPE_P4C11DB7 | CRC_CFG_OBR | CRC_CFG_IBR |
    CRC_CFG_SIZE_32BIT));
  • Greetings Amit,

    Somehow poster chose:
    uint32_t config = CRC_CFG_INIT_SEED | CRC_CFG_TYPE_P4C11DB7 | CRC_CFG_SIZE_8BIT;

    And your "Config" FILLED the entire page. (possibly the entire forum!)

    Is the write-up so bad that posters MISS so many parameters?

    And - why did YOU have to "dig" - should not so elementary a function be made "crystal clear" - so that even (we posters) may find & exploit w/out "digging?"

    I do recognize that poster's use may be unexpected - non-standard - and if that's the case - perhaps that should have been mentioned.   (reflects better upon your firm)

  • Hello cb1

    cb1 said:
    And - why did YOU have to "dig" - should not so elementary a function be made "crystal clear" - so that even (we posters) may find & exploit w/out "digging?"

    There are quite some options and it should have been made cleared in the datasheet chapter in terms of the Initialization and Configuration, what these settings should be for different CRC types.

  • Hello Amit. I will try it tomorrow when I am back to the office. I expect it works with the 8 bits mode though.
  • Hello Elder

    I have only checked the 32-bit mode. Please note that the ASCII text '0123' is in big endian format. So that the data register is to be fed in 0x33323130. Similarly the output from the CRC module is in little endian format, so the output bytes from the module and the web page need to be adjusted for the endianess.
  • Hello Amit.

    First, thank you for taking the time to figure this out.

    It does work with bytes too, I tested with several sequences of different sizes comparing with the online calculators.

    Thanks for the heads up on byte order of the result (it would take eons before I would notice it).

    It seems to me the CRC engine delivers the result in big endian though, which is funny as it gets the input in little endian (if I understand it right - the ENDIAN field of CRCCTRL is not altered.)

    The final version of the function is as follows:

    uint32_t calc_crc32 (uint32_t * buf, uint32_t length)
    {
    	uint32_t config = CRC_CFG_INIT_SEED | CRC_CFG_RESINV | CRC_CFG_TYPE_P4C11DB7 |
    			CRC_CFG_OBR | CRC_CFG_IBR |	CRC_CFG_SIZE_8BIT;
    	uint32_t seed = ~0U;
    
        // Set operation mode and seed
        CRCConfigSet(CCM0_BASE, config);
        CRCSeedSet(CCM0_BASE, seed);
    
        // Compute CRC
    	uint32_t result = CRCDataProcess (CCM0_BASE, buf, length, true);
    	result = __REV(result);
    	return result;
    }
    

    The __REV() intrinsic function swaps the bytes. It requires <intrinsics.h>. This is for IAR, other tools must have equivalent functions. The alternative would be shifting/masking/oring the output which the compiler would probably optimize anyway (if optimization is set).

    I wonder why this issue has not been raised before. At least I could not find any post about it or I did not use the search tool properly.

    Once again, thank you very much for your support.


    Elder.

  • PS: I kept the seed configuration of my oritinal code but the CRC_CFG_INIT_1 works fine too. I was playing with an idea to optimize computation for odd streams by mixing word and byte configurations but in hindsight it would probably not work. As my streams are not long, I will probably keep the byte version. I could check if the stream length is multiple of a word and call different versions with the function according with the result but probably is not worth it.
  • Hello Elder,

    We have had similar posts on the AES, DES and SHA in the past where users wanted to key in Strings and get the result.
  • May firm/I express praise for poster's persistence and care/effort in presenting his solution? Excellent.

    And also (and always) to Amit for his "digging" to gather the (somewhat) obscured data required to aid this poster...
  • cb1 said:

    And also (and always) to Amit for his "digging" to gather the (somewhat) obscured data required to aid this poster...

    I second that. :)

  • Hello cb1 and Elder

    It seems that a short application note on the settings of the CRC32 viz-a-viz web implementations would be useful.