Add CRC stack for testing (Currently unused)

This commit is contained in:
Josh Stewart 2017-05-05 08:52:10 +10:00
parent bae708a4d6
commit 2004034674
16 changed files with 25627 additions and 0 deletions

File diff suppressed because it is too large Load Diff

155
speeduino/src/FastCRC/FastCRC.h Executable file
View File

@ -0,0 +1,155 @@
/* FastCRC library code is placed under the MIT license
* Copyright (c) 2014,2015 Frank Bösing
*
* Permission is hereby granted, free of charge, to any person obtaining
* a copy of this software and associated documentation files (the
* "Software"), to deal in the Software without restriction, including
* without limitation the rights to use, copy, modify, merge, publish,
* distribute, sublicense, and/or sell copies of the Software, and to
* permit persons to whom the Software is furnished to do so, subject to
* the following conditions:
*
* The above copyright notice and this permission notice shall be
* included in all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
* BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
* ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
// Teensy 3.0, Teensy 3.1:
// See K20P64M72SF1RM.pdf (Kinetis), Pages 638 - 641 for documentation of CRC Device
// See KINETIS_4N30D.pdf for Errata (Errata ID 2776)
//
// So, ALL HW-calculations are done as 32 bit.
//
//
//
// Thanks to:
// - Catalogue of parametrised CRC algorithms, CRC RevEng
// http://reveng.sourceforge.net/crc-catalogue/
//
// - Danjel McGougan (CRC-Table-Generator)
//
// Set this to 0 for smaller 32BIT-CRC-Tables:
#define CRC_BIGTABLES 1
#if !defined(FastCRC_h)
#define FastCRC_h
#include "inttypes.h"
// ================= DEFINES ===================
#if defined(KINETISK)
#define CRC_SW 0
#define CRC_FLAG_NOREFLECT (((1<<31) | (1<<30)) | ((0<<29) | (0<<28))) //refin=false refout=false
#define CRC_FLAG_REFLECT (((1<<31) | (0<<30)) | ((1<<29) | (0<<28))) //Reflect in- and outgoing bytes (refin=true refout=true)
#define CRC_FLAG_XOR (1<<26) //Perform XOR on result
#define CRC_FLAG_NOREFLECT_8 (0) //For 8-Bit CRC
#define CRC_FLAG_REFLECT_SWAP (((1<<31) | (0<<30)) | ((0<<29) | (1<<28))) //For 16-Bit CRC (byteswap)
#else
#define CRC_SW 1
#endif
// ================= 7-BIT CRC ===================
class FastCRC7
{
public:
FastCRC7();
uint8_t crc7(const uint8_t *data, const uint16_t datalen); // (MultiMediaCard interface)
uint8_t crc7_upd(const uint8_t *data, const uint16_t datalen); // Call for subsequent calculations with previous seed.
#if !CRC_SW
uint8_t generic(const uint8_t polyom, const uint8_t seed, const uint32_t flags, const uint8_t *data, const uint16_t datalen); //Not available in non-hw-variant (not T3.x)
#endif
private:
#if CRC_SW
uint8_t seed;
#else
uint8_t update(const uint8_t *data, const uint16_t datalen);
#endif
};
// ================= 8-BIT CRC ===================
class FastCRC8
{
public:
FastCRC8();
uint8_t smbus(const uint8_t *data, const uint16_t datalen); // Alias CRC-8
uint8_t maxim(const uint8_t *data, const uint16_t datalen); // Equivalent to _crc_ibutton_update() in crc16.h from avr_libc
uint8_t smbus_upd(const uint8_t *data, uint16_t datalen); // Call for subsequent calculations with previous seed.
uint8_t maxim_upd(const uint8_t *data, uint16_t datalen); // Call for subsequent calculations with previous seed.
#if !CRC_SW
uint8_t generic(const uint8_t polyom, const uint8_t seed, const uint32_t flags, const uint8_t *data, const uint16_t datalen); //Not available in non-hw-variant (not T3.x)
#endif
private:
#if CRC_SW
uint8_t seed;
#else
uint8_t update(const uint8_t *data, const uint16_t datalen);
#endif
};
// ================= 16-BIT CRC ===================
class FastCRC16
{
public:
FastCRC16();
uint16_t ccitt(const uint8_t *data, const uint16_t datalen); // Alias "false CCITT"
uint16_t mcrf4xx(const uint8_t *data,const uint16_t datalen); // Equivalent to _crc_ccitt_update() in crc16.h from avr_libc
uint16_t kermit(const uint8_t *data, const uint16_t datalen); // Alias CRC-16/CCITT, CRC-16/CCITT-TRUE, CRC-CCITT
uint16_t modbus(const uint8_t *data, const uint16_t datalen); // Equivalent to _crc_16_update() in crc16.h from avr_libc
uint16_t xmodem(const uint8_t *data, const uint16_t datalen); // Alias ZMODEM, CRC-16/ACORN
uint16_t x25(const uint8_t *data, const uint16_t datalen); // Alias CRC-16/IBM-SDLC, CRC-16/ISO-HDLC, CRC-B
uint16_t ccitt_upd(const uint8_t *data, uint16_t len); // Call for subsequent calculations with previous seed
uint16_t mcrf4xx_upd(const uint8_t *data, uint16_t len); // Call for subsequent calculations with previous seed
uint16_t kermit_upd(const uint8_t *data, uint16_t len); // Call for subsequent calculations with previous seed
uint16_t modbus_upd(const uint8_t *data, uint16_t len); // Call for subsequent calculations with previous seed
uint16_t xmodem_upd(const uint8_t *data, uint16_t len); // Call for subsequent calculations with previous seed
uint16_t x25_upd(const uint8_t *data, uint16_t len); // Call for subsequent calculations with previous seed
#if !CRC_SW
uint16_t generic(const uint16_t polyom, const uint16_t seed, const uint32_t flags, const uint8_t *data, const uint16_t datalen); //Not available in non-hw-variant (not T3.x)
#endif
private:
#if CRC_SW
uint16_t seed;
#else
uint16_t update(const uint8_t *data, const uint16_t datalen);
#endif
};
// ================= 32-BIT CRC ===================
class FastCRC32
{
public:
FastCRC32();
uint32_t crc32(const uint8_t *data, const uint16_t datalen); // Alias CRC-32/ADCCP, PKZIP, Ethernet, 802.3
uint32_t cksum(const uint8_t *data, const uint16_t datalen); // Alias CRC-32/POSIX
uint32_t crc32_upd(const uint8_t *data, uint16_t len); // Call for subsequent calculations with previous seed
uint32_t cksum_upd(const uint8_t *data, uint16_t len); // Call for subsequent calculations with previous seed
#if !CRC_SW
uint32_t generic(const uint32_t polyom, const uint32_t seed, const uint32_t flags, const uint8_t *data, const uint16_t datalen); //Not available in non-hw-variant (not T3.x)
#endif
private:
#if CRC_SW
uint32_t seed;
#else
uint32_t update(const uint8_t *data, const uint16_t datalen);
#endif
};
#endif

View File

@ -0,0 +1,71 @@
/* FastCRC library code is placed under the MIT license
* Copyright (c) 2014,2015,2016 Frank Bösing
*
* Permission is hereby granted, free of charge, to any person obtaining
* a copy of this software and associated documentation files (the
* "Software"), to deal in the Software without restriction, including
* without limitation the rights to use, copy, modify, merge, publish,
* distribute, sublicense, and/or sell copies of the Software, and to
* permit persons to whom the Software is furnished to do so, subject to
* the following conditions:
*
* The above copyright notice and this permission notice shall be
* included in all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
* BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
* ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
// CPU-specific implementations of helper functions
#if !defined(KINETISK)
#if !defined(FastCRC_cpu)
#define FastCRC_cpu
//Reverse byte order (16 bit)
#if defined(__thumb__)
static inline __attribute__((always_inline))
uint32_t REV16( uint32_t value) //ARM-THUMB
{
asm ("rev16 %0, %1" : "=r" (value) : "r" (value) );
return(value);
}
#else
static inline __attribute__((always_inline))
uint32_t REV16( uint32_t value) //generic
{
return (value >> 8) | ((value & 0xff) << 8);
}
#endif
//Reverse byte order (32 bit)
#if defined(__thumb__)
static inline __attribute__((always_inline))
uint32_t REV32( uint32_t value) //ARM-THUMB
{
asm ("rev %0, %1" : "=r" (value) : "r" (value) );
return(value);
}
#else
static inline __attribute__((always_inline))
uint32_t REV32( uint32_t value) //generic
{
value = (value >> 16) | ((value & 0xffff) << 16);
return ((value >> 8) & 0xff00ff) | ((value & 0xff00ff) << 8);
}
#endif
#endif
#endif

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,453 @@
/* FastCRC library code is placed under the MIT license
* Copyright (c) 2014,2015 Frank Bösing
*
* Permission is hereby granted, free of charge, to any person obtaining
* a copy of this software and associated documentation files (the
* "Software"), to deal in the Software without restriction, including
* without limitation the rights to use, copy, modify, merge, publish,
* distribute, sublicense, and/or sell copies of the Software, and to
* permit persons to whom the Software is furnished to do so, subject to
* the following conditions:
*
* The above copyright notice and this permission notice shall be
* included in all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
* BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
* ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
//
// HW-calculations are 32BIT
//
// Thanks to:
// - Catalogue of parametrised CRC algorithms, CRC RevEng
// http://reveng.sourceforge.net/crc-catalogue/
//
// - Danjel McGougan (CRC-Table-Generator)
//
#include "Arduino.h"
#if defined(KINETISK)
#include "mk20dx128.h"
#include "FastCRC.h"
// ===============================================
typedef struct {
union {
uint32_t CRC; //CRC Data register
struct {
uint16_t CRC16;
uint16_t CRC16_1;
};
struct {
uint8_t CRC8;
uint8_t CRC8_1;
uint8_t CRC8_2;
uint8_t CRC8_3;
};
};
uint32_t GPOLY; //CRC Polynomial register
uint32_t CTRL; //CRC Control register
} CRC_T;
static volatile CRC_T * const rCRC = (CRC_T *)0x40032000;
#define CRC_CTRL_WAS 25 // Write CRC Data Register As Seed(1) / Data(0)
#define CRC_CTRL_TCRC 24 // Width of CRC protocol (0=16 BIT, 1=32 BIT)
#define CRC_CTRL_TOTR1 29 // TOTR[1]
// ================= 7-BIT CRC ===================
/** Constructor
* Enables CRC-clock
*/
FastCRC7::FastCRC7(){
SIM_SCGC6 |= SIM_SCGC6_CRC;
}
/** CRC 7
* MultiMediaCard interface
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint8_t FastCRC7::crc7(const uint8_t *data, const uint16_t datalen)
{
// poly=0x09 init=0x00 refin=false refout=false xorout=0x00 check=0x75
return (generic(0x09, 0, CRC_FLAG_NOREFLECT, data, datalen));
}
/** Update
* Call for subsequent calculations with previous seed
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint8_t FastCRC7::update(const uint8_t *data, const uint16_t datalen)
{
const uint8_t *src = data;
const uint8_t *target = src + datalen;
while (((uintptr_t)src & 0x03) != 0 && (src < target)) {
rCRC->CRC8_3 = *src++; //Write 8 BIT
}
while (src <= target-4) {
rCRC->CRC = *( uint32_t *)src; //Write 32 BIT
src += 4;
}
while (src < target) {
rCRC->CRC8_3 = *src++; //Write 8 Bit
}
//TODO: Check handling of CRC_CTRL_TOTR1 for other CRC7s
/*
if (rCRC->CTRL & (1<<CRC_CTRL_TOTR1))
return rCRC->CRC8 >> 1;
else
*/
return rCRC->CRC8_3 >> 1;
}
/** generic function for all 7-Bit CRCs
* @param polynom Polynom
* @param seed Seed
* @param flags Flags
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint8_t FastCRC7::generic(const uint8_t polynom, const uint8_t seed, const uint32_t flags, const uint8_t *data,const uint16_t datalen)
{
rCRC->CTRL = flags | (1<<CRC_CTRL_TCRC) | (1<<CRC_CTRL_WAS); // 32Bit Mode, Prepare to write seed(25)
rCRC->GPOLY = ((uint32_t)polynom)<<(24 + 1); // Set polynom
rCRC->CRC = ((uint32_t)seed<<(24 + 1)); // Write seed
rCRC->CTRL = flags | (1<<CRC_CTRL_TCRC); // Clear WAS Bit - prepare to write data
return update(data, datalen);
}
uint8_t FastCRC7::crc7_upd(const uint8_t *data, uint16_t datalen){return update(data, datalen);}
// ================= 8-BIT CRC ===================
/** Constructor
* Enables CRC-clock
*/
FastCRC8::FastCRC8(){
SIM_SCGC6 |= SIM_SCGC6_CRC;
}
/** SMBUS CRC
* aka CRC-8
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint8_t FastCRC8::smbus(const uint8_t *data, const uint16_t datalen)
{
// poly=0x07 init=0x00 refin=false refout=false xorout=0x00 check=0xf4
return generic(0x07, 0, CRC_FLAG_NOREFLECT, data, datalen);
}
/** MAXIM 8-Bit CRC
* equivalent to _crc_ibutton_update() in crc16.h from avr_libc
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint8_t FastCRC8::maxim(const uint8_t *data, const uint16_t datalen)
{
// poly=0x31 init=0x00 refin=true refout=true xorout=0x00 check=0xa1
return generic(0x31, 0, CRC_FLAG_REFLECT, data, datalen);
}
/** Update
* Call for subsequent calculations with previous seed
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint8_t FastCRC8::update(const uint8_t *data, const uint16_t datalen)
{
const uint8_t *src = data;
const uint8_t *target = src + datalen;
while (((uintptr_t)src & 0x03) != 0 && (src < target)) {
rCRC->CRC8_3 = *src++; //Write 8 BIT
}
while (src <= target-4) {
rCRC->CRC = *( uint32_t *)src; //Write 32 BIT
src += 4;
}
while (src < target) {
rCRC->CRC8_3 = *src++; //Write 8 Bit
}
if (rCRC->CTRL & (1<<CRC_CTRL_TOTR1))
return rCRC->CRC8;
else
return rCRC->CRC8_3;
}
/** generic function for all 8-Bit CRCs
* @param polynom Polynom
* @param seed Seed
* @param flags Flags
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint8_t FastCRC8::generic(const uint8_t polynom, const uint8_t seed, const uint32_t flags, const uint8_t *data,const uint16_t datalen)
{
rCRC->CTRL = flags | (1<<CRC_CTRL_TCRC) | (1<<CRC_CTRL_WAS); // 32Bit Mode, Prepare to write seed(25)
rCRC->GPOLY = ((uint32_t)polynom)<<24; // Set polynom
rCRC->CRC = ((uint32_t)seed<<24); // Write seed
rCRC->CTRL = flags | (1<<CRC_CTRL_TCRC); // Clear WAS Bit - prepare to write data
return update(data, datalen);
}
uint8_t FastCRC8::smbus_upd(const uint8_t *data, uint16_t datalen){return update(data, datalen);}
uint8_t FastCRC8::maxim_upd(const uint8_t *data, uint16_t datalen){return update(data, datalen);}
// ================= 16-BIT CRC ===================
/** Constructor
* Enables CRC-clock
*/
FastCRC16::FastCRC16(){
SIM_SCGC6 |= SIM_SCGC6_CRC;
}
/** CCITT
* Alias "false CCITT"
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint16_t FastCRC16::ccitt(const uint8_t *data,const uint16_t datalen)
{
// poly=0x1021 init=0xffff refin=false refout=false xorout=0x0000 check=0x29b1
return generic(0x1021, 0XFFFF, CRC_FLAG_NOREFLECT, data, datalen);
}
/** MCRF4XX
* equivalent to _crc_ccitt_update() in crc16.h from avr_libc
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint16_t FastCRC16::mcrf4xx(const uint8_t *data,const uint16_t datalen)
{
// poly=0x1021 init=0xffff refin=true refout=true xorout=0x0000 check=0x6f91
return generic(0x1021, 0XFFFF, CRC_FLAG_REFLECT, data, datalen);
}
/** MODBUS
* equivalent to _crc_16_update() in crc16.h from avr_libc
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint16_t FastCRC16::modbus(const uint8_t *data, const uint16_t datalen)
{
// poly=0x8005 init=0xffff refin=true refout=true xorout=0x0000 check=0x4b37
return generic(0x8005, 0XFFFF, CRC_FLAG_REFLECT, data, datalen);
}
/** KERMIT
* Alias CRC-16/CCITT, CRC-16/CCITT-TRUE, CRC-CCITT
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint16_t FastCRC16::kermit(const uint8_t *data, const uint16_t datalen)
{
// poly=0x1021 init=0x0000 refin=true refout=true xorout=0x0000 check=0x2189
// sometimes byteswapped presentation of result
return generic(0x1021, 0x00, CRC_FLAG_REFLECT, data, datalen);
}
/** XMODEM
* Alias ZMODEM, CRC-16/ACORN
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint16_t FastCRC16::xmodem(const uint8_t *data, const uint16_t datalen)
{
//width=16 poly=0x1021 init=0x0000 refin=false refout=false xorout=0x0000 check=0x31c3
return generic(0x1021, 0, CRC_FLAG_NOREFLECT, data, datalen);
}
/** X25
* Alias CRC-16/IBM-SDLC, CRC-16/ISO-HDLC, CRC-B
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint16_t FastCRC16::x25(const uint8_t *data, const uint16_t datalen)
{
// poly=0x1021 init=0xffff refin=true refout=true xorout=0xffff check=0x906e
return generic(0x1021, 0XFFFF, CRC_FLAG_REFLECT | CRC_FLAG_XOR, data, datalen);
}
/** Update
* Call for subsequent calculations with previous seed
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint16_t FastCRC16::update(const uint8_t *data, const uint16_t datalen)
{
const uint8_t *src = data;
const uint8_t *target = src + datalen;
while (((uintptr_t)src & 0x03) !=0 && (src < target)) {
rCRC->CRC8_3 = *src++; //Write 8 BIT
}
while (src <= target-4) {
rCRC->CRC = *( uint32_t *)src; //Write 32 BIT
src += 4;
}
while (src < target) {
rCRC->CRC8_3 = *src++; //Write 8 Bit
}
if (rCRC->CTRL & (1<<CRC_CTRL_TOTR1))
return rCRC->CRC16;
else
return rCRC->CRC16_1;
}
/** generic function for all 16-Bit CRCs
* @param polynom Polynom
* @param seed Seed
* @param flags Flags
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint16_t FastCRC16::generic(const uint16_t polynom, const uint16_t seed, const uint32_t flags, const uint8_t *data, const uint16_t datalen)
{
rCRC->CTRL = flags | (1<<CRC_CTRL_TCRC) | (1<<CRC_CTRL_WAS);// 32-Bit Mode, prepare to write seed(25)
rCRC->GPOLY = ((uint32_t)polynom)<<16; // set polynom
rCRC->CRC = ((uint32_t)seed<<16); // this is the seed
rCRC->CTRL = flags | (1<<CRC_CTRL_TCRC); // Clear WAS Bit - prepare to write data
return update(data, datalen);
}
uint16_t FastCRC16::ccitt_upd(const uint8_t *data, uint16_t len) {return update(data, len);}
uint16_t FastCRC16::mcrf4xx_upd(const uint8_t *data, uint16_t len){return update(data, len);}
uint16_t FastCRC16::kermit_upd(const uint8_t *data, uint16_t len) {return update(data, len);}
uint16_t FastCRC16::modbus_upd(const uint8_t *data, uint16_t len) {return update(data, len);}
uint16_t FastCRC16::xmodem_upd(const uint8_t *data, uint16_t len) {return update(data, len);}
uint16_t FastCRC16::x25_upd(const uint8_t *data, uint16_t len) {return update(data, len);}
// ================= 32-BIT CRC ===================
/** Constructor
* Enables CRC-clock
*/
FastCRC32::FastCRC32(){
SIM_SCGC6 |= SIM_SCGC6_CRC;
}
/** CRC32
* Alias CRC-32/ADCCP, PKZIP, Ethernet, 802.3
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint32_t FastCRC32::crc32(const uint8_t *data, const uint16_t datalen)
{
// poly=0x04c11db7 init=0xffffffff refin=true refout=true xorout=0xffffffff check=0xcbf43926
return generic(0x04C11DB7L, 0XFFFFFFFFL, CRC_FLAG_REFLECT | CRC_FLAG_XOR, data, datalen);
}
/** CKSUM
* Alias CRC-32/POSIX
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint32_t FastCRC32::cksum(const uint8_t *data, const uint16_t datalen)
{
// width=32 poly=0x04c11db7 init=0x00000000 refin=false refout=false xorout=0xffffffff check=0x765e7680
return generic(0x04C11DB7L, 0, CRC_FLAG_NOREFLECT | CRC_FLAG_XOR, data, datalen);
}
/** Update
* Call for subsequent calculations with previous seed
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
//#pragma GCC diagnostic ignored "-Wpointer-arith"
uint32_t FastCRC32::update(const uint8_t *data, const uint16_t datalen)
{
const uint8_t *src = data;
const uint8_t *target = src + datalen;
while (((uintptr_t)src & 0x03) != 0 && (src < target)) {
rCRC->CRC8_3 = *src++; //Write 8 BIT
}
while (src <= target-4) {
rCRC->CRC = *( uint32_t *)src; //Write 32 BIT
src += 4;
}
while (src < target) {
rCRC->CRC8_3 = *src++; //Write 8 Bit
}
return rCRC->CRC;
}
/** generic function for all 32-Bit CRCs
* @param polynom Polynom
* @param seed Seed
* @param flags Flags
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint32_t FastCRC32::generic(const uint32_t polynom, const uint32_t seed, const uint32_t flags, const uint8_t *data, const uint16_t datalen)
{
rCRC->CTRL = flags | (1<<CRC_CTRL_TCRC) | (1<<CRC_CTRL_WAS); // 32Bit Mode, prepare to write seed(25)
rCRC->GPOLY = polynom; // Set polynom
rCRC->CRC = seed; // This is the seed
rCRC->CTRL = flags | (1<<CRC_CTRL_TCRC); // Clear WAS Bit - prepare to write data
return update(data, datalen);
}
uint32_t FastCRC32::crc32_upd(const uint8_t *data, uint16_t len){return update(data, len);}
uint32_t FastCRC32::cksum_upd(const uint8_t *data, uint16_t len){return update(data, len);}
#endif // #if defined(KINETISK)

View File

@ -0,0 +1,509 @@
/* FastCRC library code is placed under the MIT license
* Copyright (c) 2014,2015,2016 Frank Bösing
*
* Permission is hereby granted, free of charge, to any person obtaining
* a copy of this software and associated documentation files (the
* "Software"), to deal in the Software without restriction, including
* without limitation the rights to use, copy, modify, merge, publish,
* distribute, sublicense, and/or sell copies of the Software, and to
* permit persons to whom the Software is furnished to do so, subject to
* the following conditions:
*
* The above copyright notice and this permission notice shall be
* included in all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
* BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
* ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
//
// Thanks to:
// - Catalogue of parametrised CRC algorithms, CRC RevEng
// http://reveng.sourceforge.net/crc-catalogue/
//
// - Danjel McGougan (CRC-Table-Generator)
//
#include "Arduino.h"
#if !defined(KINETISK)
#include "FastCRC.h"
#include "FastCRC_cpu.h"
#include "FastCRC_tables.h"
// ================= 7-BIT CRC ===================
/** Constructor
*/
FastCRC7::FastCRC7(){}
/** SMBUS CRC
* aka CRC-8
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint8_t FastCRC7::crc7_upd(const uint8_t *data, uint16_t datalen)
{
uint8_t crc = seed;
if (datalen) do {
crc = pgm_read_byte(&crc_table_crc7[crc ^ *data]);
data++;
} while (--datalen);
seed = crc;
return crc >> 1;
}
uint8_t FastCRC7::crc7(const uint8_t *data, const uint16_t datalen)
{
// poly=0x09 init=0x00 refin=false refout=false xorout=0x00 check=0x75
seed = 0x00;
return crc7_upd(data, datalen);
}
// ================= 8-BIT CRC ===================
/** Constructor
*/
FastCRC8::FastCRC8(){}
/** SMBUS CRC
* aka CRC-8
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint8_t FastCRC8::smbus_upd(const uint8_t *data, uint16_t datalen)
{
uint8_t crc = seed;
if (datalen) do {
crc = pgm_read_byte(&crc_table_smbus[crc ^ *data]);
data++;
} while (--datalen);
seed = crc;
return crc;
}
uint8_t FastCRC8::smbus(const uint8_t *data, const uint16_t datalen)
{
// poly=0x07 init=0x00 refin=false refout=false xorout=0x00 check=0xf4
seed = 0x00;
return smbus_upd(data, datalen);
}
/** MAXIM 8-Bit CRC
* equivalent to _crc_ibutton_update() in crc16.h from avr_libc
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint8_t FastCRC8::maxim_upd(const uint8_t *data, uint16_t datalen)
{
uint8_t crc = seed;
if (datalen) do {
crc = pgm_read_byte(&crc_table_maxim[crc ^ *data]);
data++;
} while (--datalen);
seed = crc;
return crc;
}
uint8_t FastCRC8::maxim(const uint8_t *data, const uint16_t datalen)
{
// poly=0x31 init=0x00 refin=true refout=true xorout=0x00 check=0xa1
seed = 0x00;
return maxim_upd(data, datalen);
}
// ================= 16-BIT CRC ===================
/** Constructor
*/
FastCRC16::FastCRC16(){}
#define crc_n4(crc, data, table) crc ^= data; \
crc = pgm_read_word(&table[(crc & 0xff) + 0x300]) ^ \
pgm_read_word(&table[((crc >> 8) & 0xff) + 0x200]) ^ \
pgm_read_word(&table[((data >> 16) & 0xff) + 0x100]) ^ \
pgm_read_word(&table[data >> 24]);
/** CCITT
* Alias "false CCITT"
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint16_t FastCRC16::ccitt_upd(const uint8_t *data, uint16_t len)
{
uint16_t crc = seed;
while (((uintptr_t)data & 3) && len) {
crc = (crc >> 8) ^ pgm_read_word(&crc_table_ccitt[(crc & 0xff) ^ *data++]);
len--;
}
while (len >= 16) {
len -= 16;
crc_n4(crc, ((uint32_t *)data)[0], crc_table_ccitt);
crc_n4(crc, ((uint32_t *)data)[1], crc_table_ccitt);
crc_n4(crc, ((uint32_t *)data)[2], crc_table_ccitt);
crc_n4(crc, ((uint32_t *)data)[3], crc_table_ccitt);
data += 16;
}
while (len--) {
crc = (crc >> 8) ^ pgm_read_word(&crc_table_ccitt[(crc & 0xff) ^ *data++]);
}
seed = crc;
crc = REV16(crc);
return crc;
}
uint16_t FastCRC16::ccitt(const uint8_t *data,const uint16_t datalen)
{
// poly=0x1021 init=0xffff refin=false refout=false xorout=0x0000 check=0x29b1
seed = 0xffff;
return ccitt_upd(data, datalen);
}
/** MCRF4XX
* equivalent to _crc_ccitt_update() in crc16.h from avr_libc
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint16_t FastCRC16::mcrf4xx_upd(const uint8_t *data, uint16_t len)
{
uint16_t crc = seed;
while (((uintptr_t)data & 3) && len) {
crc = (crc >> 8) ^ pgm_read_word(&crc_table_mcrf4xx[(crc & 0xff) ^ *data++]);
len--;
}
while (len >= 16) {
len -= 16;
crc_n4(crc, ((uint32_t *)data)[0], crc_table_mcrf4xx);
crc_n4(crc, ((uint32_t *)data)[1], crc_table_mcrf4xx);
crc_n4(crc, ((uint32_t *)data)[2], crc_table_mcrf4xx);
crc_n4(crc, ((uint32_t *)data)[3], crc_table_mcrf4xx);
data += 16;
}
while (len--) {
crc = (crc >> 8) ^ pgm_read_word(&crc_table_mcrf4xx[(crc & 0xff) ^ *data++]);
}
seed = crc;
return crc;
}
uint16_t FastCRC16::mcrf4xx(const uint8_t *data,const uint16_t datalen)
{
// poly=0x1021 init=0xffff refin=true refout=true xorout=0x0000 check=0x6f91
seed = 0xffff;
return mcrf4xx_upd(data, datalen);
}
/** MODBUS
* equivalent to _crc_16_update() in crc16.h from avr_libc
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint16_t FastCRC16::modbus_upd(const uint8_t *data, uint16_t len)
{
uint16_t crc = seed;
while (((uintptr_t)data & 3) && len) {
crc = (crc >> 8) ^ pgm_read_word(&crc_table_modbus[(crc & 0xff) ^ *data++]);
len--;
}
while (len >= 16) {
len -= 16;
crc_n4(crc, ((uint32_t *)data)[0], crc_table_modbus);
crc_n4(crc, ((uint32_t *)data)[1], crc_table_modbus);
crc_n4(crc, ((uint32_t *)data)[2], crc_table_modbus);
crc_n4(crc, ((uint32_t *)data)[3], crc_table_modbus);
data += 16;
}
while (len--) {
crc = (crc >> 8) ^ pgm_read_word(&crc_table_modbus[(crc & 0xff) ^ *data++]);
}
seed = crc;
return crc;
}
uint16_t FastCRC16::modbus(const uint8_t *data, const uint16_t datalen)
{
// poly=0x8005 init=0xffff refin=true refout=true xorout=0x0000 check=0x4b37
seed = 0xffff;
return modbus_upd(data, datalen);
}
/** KERMIT
* Alias CRC-16/CCITT, CRC-16/CCITT-TRUE, CRC-CCITT
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint16_t FastCRC16::kermit_upd(const uint8_t *data, uint16_t len)
{
uint16_t crc = seed;
while (((uintptr_t)data & 3) && len) {
crc = (crc >> 8) ^ pgm_read_word(&crc_table_kermit[(crc & 0xff) ^ *data++]);
len--;
}
while (len >= 16) {
len -= 16;
crc_n4(crc, ((uint32_t *)data)[0], crc_table_kermit);
crc_n4(crc, ((uint32_t *)data)[1], crc_table_kermit);
crc_n4(crc, ((uint32_t *)data)[2], crc_table_kermit);
crc_n4(crc, ((uint32_t *)data)[3], crc_table_kermit);
data += 16;
}
while (len--) {
crc = (crc >> 8) ^ pgm_read_word(&crc_table_kermit[(crc & 0xff) ^ *data++]);
}
seed = crc;
return crc;
}
uint16_t FastCRC16::kermit(const uint8_t *data, const uint16_t datalen)
{
// poly=0x1021 init=0x0000 refin=true refout=true xorout=0x0000 check=0x2189
// sometimes byteswapped presentation of result
seed = 0x0000;
return kermit_upd(data, datalen);
}
/** XMODEM
* Alias ZMODEM, CRC-16/ACORN
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint16_t FastCRC16::xmodem_upd(const uint8_t *data, uint16_t len)
{
uint16_t crc = seed;
while (((uintptr_t)data & 3) && len) {
crc = (crc >> 8) ^ pgm_read_word(&crc_table_xmodem[(crc & 0xff) ^ *data++]);
len--;
}
while (len >= 16) {
len -= 16;
crc_n4(crc, ((uint32_t *)data)[0], crc_table_xmodem);
crc_n4(crc, ((uint32_t *)data)[1], crc_table_xmodem);
crc_n4(crc, ((uint32_t *)data)[2], crc_table_xmodem);
crc_n4(crc, ((uint32_t *)data)[3], crc_table_xmodem);
data += 16;
}
while (len--) {
crc = (crc >> 8) ^ pgm_read_word(&crc_table_xmodem[(crc & 0xff) ^ *data++]);
}
seed = crc;
crc = REV16(crc);
return crc;
}
uint16_t FastCRC16::xmodem(const uint8_t *data, const uint16_t datalen)
{
//width=16 poly=0x1021 init=0x0000 refin=false refout=false xorout=0x0000 check=0x31c3
seed = 0x0000;
return xmodem_upd(data, datalen);
}
/** X25
* Alias CRC-16/IBM-SDLC, CRC-16/ISO-HDLC, CRC-B
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
uint16_t FastCRC16::x25_upd(const uint8_t *data, uint16_t len)
{
uint16_t crc = seed;
while (((uintptr_t)data & 3) && len) {
crc = (crc >> 8) ^ pgm_read_word(&crc_table_x25[(crc & 0xff) ^ *data++]);
len--;
}
while (len >= 16) {
len -= 16;
crc_n4(crc, ((uint32_t *)data)[0], crc_table_x25);
crc_n4(crc, ((uint32_t *)data)[1], crc_table_x25);
crc_n4(crc, ((uint32_t *)data)[2], crc_table_x25);
crc_n4(crc, ((uint32_t *)data)[3], crc_table_x25);
data += 16;
}
while (len--) {
crc = (crc >> 8) ^ pgm_read_word(&crc_table_x25[(crc & 0xff) ^ *data++]);
}
crc = ~crc;
seed = crc;
return crc;
}
uint16_t FastCRC16::x25(const uint8_t *data, const uint16_t datalen)
{
// poly=0x1021 init=0xffff refin=true refout=true xorout=0xffff check=0x906e
seed = 0xffff;
return x25_upd(data, datalen);
}
// ================= 32-BIT CRC ===================
/** Constructor
*/
FastCRC32::FastCRC32(){}
#define crc_n4d(crc, data, table) crc ^= data; \
crc = pgm_read_dword(&table[(crc & 0xff) + 0x300]) ^ \
pgm_read_dword(&table[((crc >> 8) & 0xff) + 0x200]) ^ \
pgm_read_dword(&table[((crc >> 16) & 0xff) + 0x100]) ^ \
pgm_read_dword(&table[(crc >> 24) & 0xff]);
#define crcsm_n4d(crc, data, table) crc ^= data; \
crc = (crc >> 8) ^ pgm_read_dword(&table[crc & 0xff]); \
crc = (crc >> 8) ^ pgm_read_dword(&table[crc & 0xff]); \
crc = (crc >> 8) ^ pgm_read_dword(&table[crc & 0xff]); \
crc = (crc >> 8) ^ pgm_read_dword(&table[crc & 0xff]);
/** CRC32
* Alias CRC-32/ADCCP, PKZIP, Ethernet, 802.3
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
#if CRC_BIGTABLES
#define CRC_TABLE_CRC32 crc_table_crc32_big
#else
#define CRC_TABLE_CRC32 crc_table_crc32
#endif
uint32_t FastCRC32::crc32_upd(const uint8_t *data, uint16_t len)
{
uint32_t crc = seed;
while (((uintptr_t)data & 3) && len) {
crc = (crc >> 8) ^ pgm_read_dword(&CRC_TABLE_CRC32[(crc & 0xff) ^ *data++]);
len--;
}
while (len >= 16) {
len -= 16;
#if CRC_BIGTABLES
crc_n4d(crc, ((uint32_t *)data)[0], CRC_TABLE_CRC32);
crc_n4d(crc, ((uint32_t *)data)[1], CRC_TABLE_CRC32);
crc_n4d(crc, ((uint32_t *)data)[2], CRC_TABLE_CRC32);
crc_n4d(crc, ((uint32_t *)data)[3], CRC_TABLE_CRC32);
#else
crcsm_n4d(crc, ((uint32_t *)data)[0], CRC_TABLE_CRC32);
crcsm_n4d(crc, ((uint32_t *)data)[1], CRC_TABLE_CRC32);
crcsm_n4d(crc, ((uint32_t *)data)[2], CRC_TABLE_CRC32);
crcsm_n4d(crc, ((uint32_t *)data)[3], CRC_TABLE_CRC32);
#endif
data += 16;
}
while (len--) {
crc = (crc >> 8) ^ pgm_read_dword(&CRC_TABLE_CRC32[(crc & 0xff) ^ *data++]);
}
crc = ~crc;
seed = crc;
return crc;
}
uint32_t FastCRC32::crc32(const uint8_t *data, const uint16_t datalen)
{
// poly=0x04c11db7 init=0xffffffff refin=true refout=true xorout=0xffffffff check=0xcbf43926
seed = 0xffffffff;
return crc32_upd(data, datalen);
}
/** CKSUM
* Alias CRC-32/POSIX
* @param data Pointer to Data
* @param datalen Length of Data
* @return CRC value
*/
#if CRC_BIGTABLES
#define CRC_TABLE_CKSUM crc_table_cksum_big
#else
#define CRC_TABLE_CKSUM crc_table_cksum
#endif
uint32_t FastCRC32::cksum_upd(const uint8_t *data, uint16_t len)
{
uint32_t crc = seed;
while (((uintptr_t)data & 3) && len) {
crc = (crc >> 8) ^ pgm_read_dword(&CRC_TABLE_CKSUM[(crc & 0xff) ^ *data++]);
len--;
}
while (len >= 16) {
len -= 16;
#if CRC_BIGTABLES
crc_n4d(crc, ((uint32_t *)data)[0], CRC_TABLE_CKSUM);
crc_n4d(crc, ((uint32_t *)data)[1], CRC_TABLE_CKSUM);
crc_n4d(crc, ((uint32_t *)data)[2], CRC_TABLE_CKSUM);
crc_n4d(crc, ((uint32_t *)data)[3], CRC_TABLE_CKSUM);
#else
crcsm_n4d(crc, ((uint32_t *)data)[0], CRC_TABLE_CKSUM);
crcsm_n4d(crc, ((uint32_t *)data)[1], CRC_TABLE_CKSUM);
crcsm_n4d(crc, ((uint32_t *)data)[2], CRC_TABLE_CKSUM);
crcsm_n4d(crc, ((uint32_t *)data)[3], CRC_TABLE_CKSUM);
#endif
data += 16;
}
while (len--) {
crc = (crc >> 8) ^ pgm_read_dword(&CRC_TABLE_CKSUM[(crc & 0xff) ^ *data++]);
}
seed = crc;
crc = ~REV32(crc);
return crc;
}
uint32_t FastCRC32::cksum(const uint8_t *data, const uint16_t datalen)
{
// width=32 poly=0x04c11db7 init=0x00000000 refin=false refout=false xorout=0xffffffff check=0x765e7680
seed = 0x00;
return cksum_upd(data, datalen);
}
#endif // #if !defined(KINETISK)

View File

@ -0,0 +1,21 @@
The MIT License (MIT)
Copyright (c) 2016 Frank
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.

56
speeduino/src/FastCRC/README.md Executable file
View File

@ -0,0 +1,56 @@
FastCRC
=======
Fast CRC Arduino library
Up to 30 times faster than crc16.h (_avr_libc)
- uses the on-chip hardware for Teensy 3.0 / 3.1 / 3.2 / 3.5 / 3.6
- uses fast table-algorithms for other chips
List of supported CRC calculations:
-
7 BIT:
CRC7
(poly=0x09 init=0x00 refin=false refout=false xorout=0x00 check=0x75)
MultiMediaCard interface
8 BIT:
SMBUS
(poly=0x07 init=0x00 refin=false refout=false xorout=0x00 check=0xf4)
MAXIM
(poly=0x31 init=0x00 refin=true refout=true xorout=0x00 check=0xa1)
16 BIT:
KERMIT (Alias CRC-16/CCITT, CRC-16/CCITT-TRUE, CRC-CCITT)
(poly=0x1021 init=0x0000 refin=true refout=true xorout=0x0000 check=0x2189
Attention: sometimes you'll find byteswapped presentation of result in other implementations)
CCITT-FALSE
(poly=0x1021 init=0xffff refin=false refout=false xorout=0x0000 check=0x29b1)
MCRF4XX
(poly=0x1021 init=0xffff refin=true refout=true xorout=0x0000 check=0x6f91)
MODBUS
(poly=0x8005 init=0xffff refin=true refout=true xorout=0x0000 check=0x4b37)
XMODEM (Alias ZMODEM, CRC-16/ACORN)
(poly=0x1021 init=0x0000 refin=false refout=false xorout=0x0000 check=0x31c3)
X25 (Alias CRC-16/IBM-SDLC, CRC-16/ISO-HDLC, CRC-B)
(poly=0x1021 init=0xffff refin=true refout=true xorout=0xffff check=0x906e)
32 BIT:
CRC32, CRC-32/ADCCP, PKZIP, ETHERNET, 802.3
(poly=0x04c11db7 init=0xffffffff refin=true refout=true xorout=0xffffffff check=0xcbf43926)
CKSUM, CRC-32/POSIX
(poly=0x04c11db7 init=0x00000000 refin=false refout=false xorout=0xffffffff check=0x765e7680)

View File

@ -0,0 +1,163 @@
/*
FastCRC
Benchmark
(c) Frank Boesing 2014-2016
Edit FastCRC.h for smaller Tables (#define CRC_BIGTABLES 1) - not needed for Teensy 3.x
*/
#include <util/crc16.h>
#include <FastCRC.h>
//#define LOFLASH // <- Uncomment this for devices with small flashmemory
//Determince the max. possible size for the data:
#if defined(__MK20DX256__) || defined(__MK64FX512__) || defined(__MK66FX1M0__)
#define BUFSIZE (56 * 1024) // 56KB for Teensy 3.x
#elif defined(__MK20DX128__)
#define BUFSIZE (12 * 1024) // 12KB for Teensy 3.0
#elif defined(__MKL26Z64__)
#define BUFSIZE (4 * 1024) // 4KB for Teensy LC
#else
#define BUFSIZE (1 * 1024) // 1KB for Teensy 2.0 / others...(use max. possible!)
#endif
uint8_t buf[BUFSIZE];
FastCRC8 CRC8;
FastCRC16 CRC16;
FastCRC32 CRC32;
// Supporting functions for Software CRC
inline uint16_t softcrc(uint16_t seed, uint8_t *data, uint16_t datalen) {
for (uint16_t i = 0; i < datalen; i++) {
seed = _crc16_update(seed, data[i]);
}
return seed;
}
inline uint16_t softcrcIbutton(uint16_t seed, uint8_t *data, uint16_t datalen) {
for (uint16_t i = 0; i < datalen; i++) {
seed = _crc_ibutton_update(seed, data[i]);
}
return seed;
}
inline uint16_t softcrcCCIT(uint16_t seed, uint8_t *data, uint16_t datalen) {
for (uint16_t i = 0; i < datalen; i++) {
seed = _crc_ccitt_update(seed, data[i]);
}
return seed;
}
inline uint16_t softcrcXMODEM(uint16_t seed, uint8_t *data, uint16_t datalen) {
for (uint16_t i = 0; i < datalen; i++) {
seed = _crc_xmodem_update(seed, data[i]);
}
return seed;
}
void printVals(const char * name, const uint32_t crc, const uint32_t time) {
Serial.print(name);
Serial.print("\tValue:0x");
Serial.print(crc, HEX);
Serial.print(", Time: ");
Serial.print(time);
Serial.print(" us (");
Serial.print((8.*BUFSIZE) / time);
Serial.println(" mbs)");
}
void setup() {
int time;
uint32_t crc;
delay(1500);
Serial.begin(115200);
Serial.println("CRC Benchmark");
Serial.print("F_CPU: ");
Serial.print((int) (F_CPU / 1E6));
Serial.print(" MHz, length: ");
Serial.print(BUFSIZE);
Serial.println(" Bytes.");
Serial.println();
//Fill array with testdata
for (uint16_t i = 0; i < BUFSIZE; i++) {
buf[i] = (i + 1) & 0xff;
}
/* 8 BIT */
time = micros();
crc = CRC8.maxim(buf, BUFSIZE);
time = micros() - time;
printVals("Maxim (iButton) FastCRC:", crc, time);
time = micros();
crc = softcrcIbutton(0, buf, BUFSIZE);
time = micros() - time;
printVals("Maxim (iButton) builtin:", crc, time);
#if !defined(LOFLASH)
time = micros();
crc = CRC16.modbus(buf, BUFSIZE);
time = micros() - time;
printVals("MODBUS FastCRC:", crc, time);
time = micros();
crc = softcrc(0xffff, buf, BUFSIZE);
time = micros() - time;
printVals("MODBUS builtin: ", crc, time);
time = micros();
crc = CRC16.xmodem(buf, BUFSIZE);
time = micros() - time;
printVals("XMODEM FastCRC:", crc, time);
time = micros();
crc = softcrcXMODEM(0, buf, BUFSIZE);
time = micros() - time;
printVals("XMODEM builtin: ", crc, time);
#endif
/* 16 BIT */
time = micros();
crc = CRC16.mcrf4xx(buf, BUFSIZE);
time = micros() - time;
printVals("MCRF4XX FastCRC:", crc, time);
time = micros();
crc = softcrcCCIT(0xffff, buf, BUFSIZE);
time = micros() - time;
printVals("MCRF4XX builtin:", crc, time);
#if !defined(LOFLASH)
time = micros();
crc = CRC16.kermit(buf, BUFSIZE);
time = micros() - time;
printVals("KERMIT FastCRC:", crc, time);
#endif
/* 32 BIT */
#if !defined(LOFLASH)
time = micros();
crc = CRC32.crc32(buf, BUFSIZE);
time = micros() - time;
printVals("Ethernet FastCRC:", crc, time);
#endif
}
void loop() {
}

View File

@ -0,0 +1,36 @@
/*
FastCRC-Example
(c) Frank Boesing 2014
*/
#include <FastCRC.h>
FastCRC16 CRC16;
uint8_t buf[9] = {'1', '2', '3', '4', '5', '6', '7', '8', '9'};
void setup() {
delay(1500);
Serial.begin(115200);
Serial.println("CRC Example");
Serial.println();
Serial.print("CCITT-CRC of \"");
for (unsigned int i = 0; i < sizeof(buf); i++) {
Serial.print((char) buf[i]);
}
Serial.print("\" is: 0x");
Serial.println( CRC16.ccitt(buf, sizeof(buf)), HEX );
}
void loop() {
}

View File

@ -0,0 +1,36 @@
/*
FastCRC-Example
(c) Frank Boesing 2014
*/
#include <FastCRC.h>
FastCRC32 CRC32;
uint8_t buf[9] = {'1', '2', '3', '4', '5', '6', '7', '8', '9'};
void setup() {
delay(1500);
Serial.begin(115200);
Serial.println("CRC Example");
Serial.println();
Serial.print("CRC32 of \"");
for (unsigned int i = 0; i < sizeof(buf); i++) {
Serial.print((char) buf[i]);
}
Serial.print("\" is: 0x");
Serial.println( CRC32.crc32(buf, sizeof(buf)), HEX );
}
void loop() {
}

View File

@ -0,0 +1,36 @@
/*
FastCRC-Example
(c) Frank Boesing 2014
*/
#include <FastCRC.h>
FastCRC8 CRC8;
uint8_t buf[9] = {'1', '2', '3', '4', '5', '6', '7', '8', '9'};
void setup() {
delay(1500);
Serial.begin(115200);
Serial.println("CRC Example");
Serial.println();
Serial.print("SMBUS-CRC of \"");
for (unsigned int i = 0; i < sizeof(buf); i++) {
Serial.print((char) buf[i]);
}
Serial.print("\" is: 0x");
Serial.println( CRC8.smbus(buf, sizeof(buf)), HEX );
}
void loop() {
}

View File

@ -0,0 +1,47 @@
/*
FastCRC-Example
(c) Frank Boesing 2014
This example shows how to use the update functions.
*/
#include <FastCRC.h>
FastCRC16 CRC16;
uint8_t buf[9] = {'1', '2', '3', '4', '5', '6', '7', '8', '9'};
void setup() {
uint16_t crc;
delay(1500);
Serial.begin(115200);
Serial.println("CRC Example");
Serial.println();
Serial.print("CCITT-CRC of \"");
for (unsigned int i = 0; i < sizeof(buf); i++) {
Serial.print((char) buf[i]);
}
Serial.print("\" is: 0x");
//Calculate first half of buffer:
crc = CRC16.ccitt(&buf[0], 4);
//Calculate seconde half of buffer:
crc = CRC16.ccitt_upd(&buf[4],5);
Serial.println(crc, HEX );
}
void loop() {
}

View File

@ -0,0 +1,71 @@
//FastCRC
//Validate computed CRCs
//
//(c) Frank Boesing 2014
#include <util/crc16.h>
#include <FastCRC.h>
FastCRC7 CRC7;
FastCRC8 CRC8;
FastCRC16 CRC16;
FastCRC32 CRC32;
uint8_t buf[9] = {'1','2','3','4','5','6','7','8','9'};
void printVals(const char * name, uint32_t check, uint32_t val){
Serial.print(name);
if (check == val)
Serial.print(" is ok");
else
Serial.print(" is NOT ok");
Serial.println();
}
void setup() {
uint32_t crc;
delay(1500);
Serial.begin(115200);
Serial.println("CRC Validation");
crc = CRC7.crc7(buf, sizeof(buf));
printVals("CRC7", 0x75, crc);
crc = CRC8.smbus(buf, sizeof(buf));
printVals("SMBUS", 0xf4, crc);
crc = CRC8.maxim(buf, sizeof(buf));
printVals("Maxim", 0xa1, crc);
crc = CRC16.ccitt(buf, sizeof(buf));
printVals("CCITT", 0x29b1, crc);
crc = CRC16.mcrf4xx(buf, sizeof(buf));
printVals("MCRF4XX", 0x6f91, crc);
crc = CRC16.modbus(buf, sizeof(buf));
printVals("MODBUS", 0x4b37, crc);
crc = CRC16.kermit(buf, sizeof(buf));
printVals("KERMIT", 0x2189, crc);
crc = CRC16.xmodem(buf, sizeof(buf));
printVals("XMODEM", 0x31c3, crc);
crc = CRC16.x25(buf, sizeof(buf));
printVals("X.25", 0x906e, crc);
crc = CRC32.crc32(buf, sizeof(buf));
printVals("CRC32", 0xcbf43926, crc);
crc = CRC32.cksum(buf, sizeof(buf));
printVals("CKSUM", 0x765e7680, crc);
}
void loop() {
}

View File

@ -0,0 +1,52 @@
#######################################
# Syntax Coloring Map For FastCRC
#######################################
#######################################
# Datatypes (KEYWORD1)
#######################################
FastCRC7 KEYWORD1
FastCRC8 KEYWORD1
FastCRC16 KEYWORD1
FastCRC32 KEYWORD1
CRC7 KEYWORD1
CRC8 KEYWORD1
CRC16 KEYWORD1
CRC32 KEYWORD1
#######################################
# Methods and Functions (KEYWORD2)
#######################################
crc7 KEYWORD2
crc7_upd KEYWORD2
ccitt KEYWORD2
ccitt_upd KEYWORD2
kermit KEYWORD2
kermit_upd KEYWORD2
mcrf4xx KEYWORD2
mcrf4xx_upd KEYWORD2
modbus KEYWORD2
modbus_upd KEYWORD2
xmodem KEYWORD2
xmodem_upd KEYWORD2
x25 KEYWORD2
x25_upd KEYWORD2
update KEYWORD2
update_upd KEYWORD2
generic KEYWORD2
crc32 KEYWORD2
crc32_upd KEYWORD2
cksum KEYWORD2
cksum_upd KEYWORD2
#######################################
# Constants (LITERAL1)
#######################################
CRC_FLAG_NOREFLECT LITERAL1
CRC_FLAG_REFLECT LITERAL1
CRC_FLAG_XOR LITERAL1
CRC_FLAG_NOREFLECT_8 LITERAL1
CRC_FLAG_REFLECT_SWAP LITERAL1

View File

@ -0,0 +1,9 @@
name=FastCRC
version=1.2
author=Frank Bösing
maintainer=Frank Boesing<f.boesing@gmx.de>
sentence=Fast CRC routines
paragraph=
category=Data Processing
url=https://github.com/FrankBoesing/FastCRC
architectures=*