AnsweredAssumed Answered

LPC824 Hardware Modbus CRC calculation

Question asked by David Kaplan on Nov 16, 2016

I am interested in trying to use the LPC824 CRC hardware to calculate the CRC for the Modbus protocol.

I use a 512 byte CRC lookup table for the fastest software calculations but now am using a little slower version that uses only a 16 byte table, all to save on the limited flash. It would be much better to use the hardware somehow and Modbus is a very popular serial protocol used on micro controllers.

 

 I have seen that it may be possible on other hardware CRC blocks such as below

 

void ModbusSlave::_crc_append(uint8_t* buffer, uint8_t* length)
{
    CRC0->GPOLY_ACCESS16BIT.GPOLYL = 0x8005;
    CRC0->CTRL = CRC_CTRL_WAS_MASK | CRC_CTRL_TOT(1) | CRC_CTRL_TOTR(1);
    CRC0->ACCESS16BIT.DATAL = 0xFFFF;
    CRC0->CTRL &= ~CRC_CTRL_WAS_MASK;
    for (int i=0; i<(*length); i++) {
        CRC0->ACCESS8BIT.DATALL = buffer[i];
    }
    buffer[*length] = CRC0->ACCESS8BIT.DATALU;
    buffer[*length+1] = CRC0->ACCESS8BIT.DATALL;
    *length = *length + 2;
}

 

My feeble attempt to duplicate this does not work

 

uint16_t CalcModbusChecksum(uint8_t* buffer, uint8_t* length)
{
  uint16_t ret;
  uint8_t  len = *length;
  Chip_Clock_EnablePeriphClock(SYSCTL_CLOCK_CRC);
  Chip_CRC_SetPoly(CRC_MODE_POLY_CRC32,CRC_MODE_WRDATA_BIT_RVS|CRC_MODE_SUM_BIT_RVS);
  Chip_CRC_SetSeed(0x8005);
  Chip_CRC_Write16(0xFFFF);
  while (len--){
      *((uint8_t *)&LPC_CRC->WRDATA32) = *buffer++;
  }
  ret = (uint16_t)Chip_CRC_Sum();
  return ret;
} // CalcModbusChecksum

 

Any help would be appreciated.

This would be very useful to add in the LPC Open code.

 

Thanks

Outcomes