tags:

views:

262

answers:

2

I wish to use common CRC logic in a VB.NET or C# application as well as on a C/Linux application. I have one C/Linux application that interacts with a webservice (written in C#) and also a web application (written in VB.NET). For some data, I want to add a CRC to the data itself (say a file) from the .NET side and check for the integrity of the data (checking the CRC) on the client - and also vice-versa.

Can somebody please guide me?

+5  A: 

Since CRC implementation is a one-liner, I don't think you've have any problem with that. wikipedia has links to CRC source code in several different languages. The only thing you need to care about for portability is the endian-ness when you actually store the CRC in the file.

EDIT: Really, with a one-liner duplicating code is not going to be a problem.

C or C++ version

const uint16_t table[256] = {
 0x0000, 0x1189, 0x2312, 0x329B, 0x4624, 0x57AD, 0x6536, 0x74BF,
 0x8C48, 0x9DC1, 0xAF5A, 0xBED3, 0xCA6C, 0xDBE5, 0xE97E, 0xF8F7,
 0x1081, 0x0108, 0x3393, 0x221A, 0x56A5, 0x472C, 0x75B7, 0x643E,
 0x9CC9, 0x8D40, 0xBFDB, 0xAE52, 0xDAED, 0xCB64, 0xF9FF, 0xE876,
 0x2102, 0x308B, 0x0210, 0x1399, 0x6726, 0x76AF, 0x4434, 0x55BD,
 0xAD4A, 0xBCC3, 0x8E58, 0x9FD1, 0xEB6E, 0xFAE7, 0xC87C, 0xD9F5,
 0x3183, 0x200A, 0x1291, 0x0318, 0x77A7, 0x662E, 0x54B5, 0x453C,
 0xBDCB, 0xAC42, 0x9ED9, 0x8F50, 0xFBEF, 0xEA66, 0xD8FD, 0xC974,
 0x4204, 0x538D, 0x6116, 0x709F, 0x0420, 0x15A9, 0x2732, 0x36BB,
 0xCE4C, 0xDFC5, 0xED5E, 0xFCD7, 0x8868, 0x99E1, 0xAB7A, 0xBAF3,
 0x5285, 0x430C, 0x7197, 0x601E, 0x14A1, 0x0528, 0x37B3, 0x263A,
 0xDECD, 0xCF44, 0xFDDF, 0xEC56, 0x98E9, 0x8960, 0xBBFB, 0xAA72,
 0x6306, 0x728F, 0x4014, 0x519D, 0x2522, 0x34AB, 0x0630, 0x17B9,
 0xEF4E, 0xFEC7, 0xCC5C, 0xDDD5, 0xA96A, 0xB8E3, 0x8A78, 0x9BF1,
 0x7387, 0x620E, 0x5095, 0x411C, 0x35A3, 0x242A, 0x16B1, 0x0738,
 0xFFCF, 0xEE46, 0xDCDD, 0xCD54, 0xB9EB, 0xA862, 0x9AF9, 0x8B70,
 0x8408, 0x9581, 0xA71A, 0xB693, 0xC22C, 0xD3A5, 0xE13E, 0xF0B7,
 0x0840, 0x19C9, 0x2B52, 0x3ADB, 0x4E64, 0x5FED, 0x6D76, 0x7CFF,
 0x9489, 0x8500, 0xB79B, 0xA612, 0xD2AD, 0xC324, 0xF1BF, 0xE036,
 0x18C1, 0x0948, 0x3BD3, 0x2A5A, 0x5EE5, 0x4F6C, 0x7DF7, 0x6C7E,
 0xA50A, 0xB483, 0x8618, 0x9791, 0xE32E, 0xF2A7, 0xC03C, 0xD1B5,
 0x2942, 0x38CB, 0x0A50, 0x1BD9, 0x6F66, 0x7EEF, 0x4C74, 0x5DFD,
 0xB58B, 0xA402, 0x9699, 0x8710, 0xF3AF, 0xE226, 0xD0BD, 0xC134,
 0x39C3, 0x284A, 0x1AD1, 0x0B58, 0x7FE7, 0x6E6E, 0x5CF5, 0x4D7C,
 0xC60C, 0xD785, 0xE51E, 0xF497, 0x8028, 0x91A1, 0xA33A, 0xB2B3,
 0x4A44, 0x5BCD, 0x6956, 0x78DF, 0x0C60, 0x1DE9, 0x2F72, 0x3EFB,
 0xD68D, 0xC704, 0xF59F, 0xE416, 0x90A9, 0x8120, 0xB3BB, 0xA232,
 0x5AC5, 0x4B4C, 0x79D7, 0x685E, 0x1CE1, 0x0D68, 0x3FF3, 0x2E7A,
 0xE70E, 0xF687, 0xC41C, 0xD595, 0xA12A, 0xB0A3, 0x8238, 0x93B1,
 0x6B46, 0x7ACF, 0x4854, 0x59DD, 0x2D62, 0x3CEB, 0x0E70, 0x1FF9,
 0xF78F, 0xE606, 0xD49D, 0xC514, 0xB1AB, 0xA022, 0x92B9, 0x8330,
 0x7BC7, 0x6A4E, 0x58D5, 0x495C, 0x3DE3, 0x2C6A, 0x1EF1, 0x0F78
};

void crc_update(uint8_t by, uint16_t& crc)
{
    crc = table[by ^ (uint8_t)(crc >> (16 - 8))] ^ (crc << 8);
}

C# version

readonly UInt16[] table = new UInt16[256] { 0x0000, 0x1189, ... };
void crc_update(Byte by, ref UInt16 crc)
{
    crc = (UInt16)(table[by ^ (crc >> (16 - 8))] ^ (crc << 8));
}

VB.NET version

ReadOnly table As UInt16() = { &H0000, &H1189, ... }
Sub crc_update(ByVal by As System.Byte, ByRef crc As UInt16)
    crc = table(by Xor (crc >> (16 - 8))) Xor (crc << 8)
End Sub

To use a 16-bit CRC other than the CCITT, replace the lookup table. For a 32-bit CRC, replace all occurances of 16 with 32 and replace the lookup table.

Ben Voigt
Yes, looks like you should have no problems at all implementing what you need.
SoMoS
Actually I was looking for directions to any specific implementation that will give me the portability that I am looking for.
Kangkan
nice answer, +1
Alastair Pitts
Thanks a lot for the nice answer.
Kangkan
+1  A: 

There are a variety of CRC algorithms around, and the main thing is using the same one on both sides.

You could keep it simple and use a very common CRC algorithm. CRC-32 is about as standard as you can get, and there's bound to be source code for this for all platforms.

If you want to pick something less common... On the C side, you can use a tool such as pycrc to generate C code for pretty much any CRC algorithm you care to use (well, pick a size of 16 or 32 for sanity).

Craig McQueen
Thats so nice of you. I am actually a bit confused looking at so many different sources and wanted to zero on to a particular one. Shall be happy if anyone can guide me to any specific implementation.
Kangkan