用C#实现的几种常用数据校验方法整理(CRC校验;LRC校验;BCC校验;累加和校验)
2021-02-04 06:14
标签:通信 CRC-16 异或 求和 convert 校验码 *** 协议 rc5
CRC即循环冗余校验码(Cyclic Redundancy Check):是数据通信领域中最常用的一种查错校验码,其特征是信息字段和校验字段的长度可以任意选定。循环冗余检查(CRC)是一种数据传输检错功能,对数据进行多项式计算,并将得到的结果附在帧的后面,接收设备也执行类似的算法,以保证数据传输的正确性和完整性。
/// CRC算法参数模型解释:
/// NAME:参数模型名称。
///WIDTH:宽度,即CRC比特数。
/// POLY:生成项的简写,以16进制表示。例如:CRC-32即是0x04C11DB7,忽略了最高位的"1",即完整的生成项是0x104C11DB7。
///INIT:这是算法开始时寄存器(crc)的初始化预置值,十六进制表示。
///REFIN:待测数据的每个字节是否按位反转,True或False。
/// REFOUT:在计算后之后,异或输出之前,整个数据是否按位反转,True或False。
/// XOROUT:计算结果与此参数异或后得到最终的CRC值。
1 /// ********************************************************************** 2 /// Name: CRC-4/ITU x4+x+1 3 /// Poly: 0x03 4 /// Init: 0x00 5 /// Refin: true 6 /// Refout: true 7 /// Xorout: 0x00 8 ///************************************************************************* 9 public static byte[] Crc1(byte[] buffer, int start = 0, int len = 0) 10 { 11 if (buffer == null || buffer.Length == 0) return null; 12 if (start 0) return null; 13 if (len == 0) len = buffer.Length - start; 14 int length = start + len; 15 if (length > buffer.Length) return null; 16 byte crc = 0;// Initial value 17 for (int i = start; i ) 18 { 19 crc ^= buffer[i]; 20 for (int j = 0; j 8; j++) 21 { 22 if ((crc & 1) > 0) 23 crc = (byte)((crc >> 1) ^ 0x0C);//0x0C = (reverse 0x03)>>(8-4) 24 else 25 crc = (byte)(crc >> 1); 26 } 27 } 28 return new byte[] { crc }; 29 } 30 /// ********************************************************************** 31 /// Name: CRC-5/EPC x5+x3+1 32 /// Poly: 0x09 33 /// Init: 0x09 34 /// Refin: false 35 /// Refout: false 36 /// Xorout: 0x00 37 ///************************************************************************* 38 public static byte[] Crc2(byte[] buffer, int start = 0, int len = 0) 39 { 40 if (buffer == null || buffer.Length == 0) return null; 41 if (start 0) return null; 42 if (len == 0) len = buffer.Length - start; 43 int length = start + len; 44 if (length > buffer.Length) return null; 45 byte crc = 0x48;// Initial value: 0x48 = 0x09 46 for (int i = start; i ) 47 { 48 crc ^= buffer[i]; 49 for (int j = 0; j 8; j++) 50 { 51 if ((crc & 0x80) > 0) 52 crc = (byte)((crc 1) ^ 0x48);// 0x48 = 0x09 53 else 54 crc = (byte)(crc 1); 55 } 56 } 57 return new byte[] { (byte)(crc >> 3) }; 58 } 59 /// ********************************************************************** 60 /// Name: CRC-5/ITU x5+x4+x2+1 61 /// Poly: 0x15 62 /// Init: 0x00 63 /// Refin: true 64 /// Refout: true 65 /// Xorout: 0x00 66 ///************************************************************************* 67 public static byte[] Crc3(byte[] buffer, int start = 0, int len = 0) 68 { 69 if (buffer == null || buffer.Length == 0) return null; 70 if (start 0) return null; 71 if (len == 0) len = buffer.Length - start; 72 int length = start + len; 73 if (length > buffer.Length) return null; 74 byte crc = 0;// Initial value 75 for (int i = start; i ) 76 { 77 crc ^= buffer[i]; 78 for (int j = 0; j 8; j++) 79 { 80 if ((crc & 1) > 0) 81 crc = (byte)((crc >> 1) ^ 0x15);// 0x15 = (reverse 0x15)>>(8-5) 82 else 83 crc = (byte)(crc >> 1); 84 } 85 } 86 return new byte[] { crc }; 87 } 88 /// ********************************************************************** 89 /// Name: CRC-5/USB x5+x2+1 90 /// Poly: 0x05 91 /// Init: 0x1F 92 /// Refin: true 93 /// Refout: true 94 /// Xorout: 0x1F 95 ///************************************************************************* 96 public static byte[] Crc4(byte[] buffer, int start = 0, int len = 0) 97 { 98 if (buffer == null || buffer.Length == 0) return null; 99 if (start 0) return null; 100 if (len == 0) len = buffer.Length - start; 101 int length = start + len; 102 if (length > buffer.Length) return null; 103 byte crc = 0x1F;// Initial value 104 for (int i = start; i ) 105 { 106 crc ^= buffer[i]; 107 for (int j = 0; j 8; j++) 108 { 109 if ((crc & 1) > 0) 110 crc = (byte)((crc >> 1) ^ 0x14);// 0x14 = (reverse 0x05)>>(8-5) 111 else 112 crc = (byte)(crc >> 1); 113 } 114 } 115 return new byte[] {(byte)( crc ^ 0x1F) }; 116 } 117 /// ********************************************************************** 118 /// Name: CRC-6/ITU x6+x+1 119 /// Poly: 0x03 120 /// Init: 0x00 121 /// Refin: true 122 /// Refout: true 123 /// Xorout: 0x00 124 ///************************************************************************* 125 public static byte[] Crc5(byte[] buffer, int start = 0, int len = 0) 126 { 127 if (buffer == null || buffer.Length == 0) return null; 128 if (start 0) return null; 129 if (len == 0) len = buffer.Length - start; 130 int length = start + len; 131 if (length > buffer.Length) return null; 132 byte crc = 0;// Initial value 133 for (int i = start; i ) 134 { 135 crc ^= buffer[i]; 136 for (int j = 0; j 8; j++) 137 { 138 if ((crc & 1) > 0) 139 crc = (byte)((crc >> 1) ^ 0x30);// 0x30 = (reverse 0x03)>>(8-6) 140 else 141 crc = (byte)(crc >> 1); 142 } 143 } 144 return new byte[] { crc }; 145 } 146 /// ********************************************************************** 147 /// Name: CRC-7/MMC x7+x3+1 148 /// Poly: 0x09 149 /// Init: 0x00 150 /// Refin: false 151 /// Refout: false 152 /// Xorout: 0x00 153 ///************************************************************************* 154 public static byte[] Crc6(byte[] buffer, int start = 0, int len = 0) 155 { 156 if (buffer == null || buffer.Length == 0) return null; 157 if (start 0) return null; 158 if (len == 0) len = buffer.Length - start; 159 int length = start + len; 160 if (length > buffer.Length) return null; 161 byte crc = 0;// Initial value 162 for (int i = start; i ) 163 { 164 crc ^= buffer[i]; 165 for (int j = 0; j 8; j++) 166 { 167 if ((crc & 0x80) > 0) 168 crc = (byte)((crc 1) ^ 0x12);// 0x12 = 0x09 169 else 170 crc = (byte)(crc 1); 171 } 172 } 173 return new byte[] { (byte)(crc >> 1) }; 174 } 175 /// ********************************************************************** 176 /// Name: CRC8 x8+x2+x+1 177 /// Poly: 0x07 178 /// Init: 0x00 179 /// Refin: false 180 /// Refout: false 181 /// Xorout: 0x00 182 ///************************************************************************* 183 public static byte[] Crc7(byte[] buffer, int start = 0, int len = 0) 184 { 185 if (buffer == null || buffer.Length == 0) return null; 186 if (start 0) return null; 187 if (len == 0) len = buffer.Length - start; 188 int length = start + len; 189 if (length > buffer.Length) return null; 190 byte crc = 0;// Initial value 191 for (int i = start; i ) 192 { 193 crc ^= buffer[i]; 194 for (int j = 0; j 8; j++) 195 { 196 if ((crc & 0x80) > 0) 197 crc = (byte)((crc 1) ^ 0x07); 198 else 199 crc = (byte)(crc 1); 200 } 201 } 202 return new byte[] { crc }; 203 } 204 /// ********************************************************************** 205 /// Name: CRC-8/ITU x8+x2+x+1 206 /// Poly: 0x07 207 /// Init: 0x00 208 /// Refin: false 209 /// Refout: false 210 /// Xorout: 0x55 211 ///************************************************************************* 212 public static byte[] Crc8(byte[] buffer, int start = 0, int len = 0) 213 { 214 if (buffer == null || buffer.Length == 0) return null; 215 if (start 0) return null; 216 if (len == 0) len = buffer.Length - start; 217 int length = start + len; 218 if (length > buffer.Length) return null; 219 byte crc = 0;// Initial value 220 for (int i = start; i ) 221 { 222 crc ^= buffer[i]; 223 for (int j = 0; j 8; j++) 224 { 225 if ((crc & 0x80) > 0) 226 crc = (byte)((crc 1) ^ 0x07); 227 else 228 crc = (byte)(crc 1); 229 } 230 } 231 return new byte[] { (byte)(crc ^ 0x55) }; 232 } 233 /// ********************************************************************** 234 /// Name: CRC-8/MAXIM x8+x5+x4+1 235 /// Poly: 0x31 236 /// Init: 0x00 237 /// Refin: true 238 /// Refout: true 239 /// Xorout: 0x00 240 ///************************************************************************* 241 public static byte[] Crc9(byte[] buffer, int start = 0, int len = 0) 242 { 243 if (buffer == null || buffer.Length == 0) return null; 244 if (start 0) return null; 245 if (len == 0) len = buffer.Length - start; 246 int length = start + len; 247 if (length > buffer.Length) return null; 248 byte crc = 0;// Initial value 249 for (int i = start; i ) 250 { 251 crc ^= buffer[i]; 252 for (int j = 0; j 8; j++) 253 { 254 if ((crc & 1) > 0) 255 crc = (byte)((crc >> 1) ^ 0x8C);// 0x8C = reverse 0x31 256 else 257 crc = (byte)(crc >> 1); 258 } 259 } 260 return new byte[] { crc }; 261 } 262 /// ********************************************************************** 263 /// Name: CRC-8/ROHC x8+x2+x+1 264 /// Poly: 0x07 265 /// Init: 0xFF 266 /// Refin: true 267 /// Refout: true 268 /// Xorout: 0x00 269 ///************************************************************************* 270 public static byte[] Crc10(byte[] buffer, int start = 0, int len = 0) 271 { 272 if (buffer == null || buffer.Length == 0) return null; 273 if (start 0) return null; 274 if (len == 0) len = buffer.Length - start; 275 int length = start + len; 276 if (length > buffer.Length) return null; 277 byte crc = 0xFF;// Initial value 278 for (int i = start; i ) 279 { 280 crc ^= buffer[i]; 281 for (int j = 0; j 8; j++) 282 { 283 if ((crc & 1) > 0) 284 crc = (byte)((crc >> 1) ^ 0xE0);// 0xE0 = reverse 0x07 285 else 286 crc = (byte)(crc >> 1); 287 } 288 } 289 return new byte[] { crc }; 290 } 291 /// Z1协议校验码计算 292 static byte[] table = { 0x00, 0x1C, 0x38, 0x24, 0x70, 0x6C, 0x48, 0x54, 0xE0, 0xFC, 293 0xD8, 0xC4, 0x90, 0x8C, 0xA8, 0xB4, 0xDC, 0xC0, 0xE4, 0xF8, 294 0xAC, 0xB0, 0x94, 0x88, 0x3C, 0x20, 0x04, 0x18, 0x4C, 0x50, 295 0x74, 0x68, 0xA4, 0xB8, 0x9C, 0x80, 0xD4, 0xC8, 0xEC, 0xF0, 296 0x44, 0x58, 0x7C, 0x60, 0x34, 0x28, 0x0C, 0x10, 0x78, 0x64, 297 0x40, 0x5C, 0x08, 0x14, 0x30, 0x2C, 0x98, 0x84, 0xA0, 0xBC, 298 0xE8, 0xF4, 0xD0, 0xCC, 0x54, 0x48, 0x6C, 0x70, 0x24, 0x38, 299 0x1C, 0x00, 0xB4, 0xA8, 0x8C, 0x90, 0xC4, 0xD8, 0xFC, 0xE0, 300 0x88, 0x94, 0xB0, 0xAC, 0xF8, 0xE4, 0xC0, 0xDC, 0x68, 0x74, 301 0x50, 0x4C, 0x18, 0x04, 0x20, 0x3C, 0xF0, 0xEC, 0xC8, 0xD4, 302 0x80, 0x9C, 0xB8, 0xA4, 0x10, 0x0C, 0x28, 0x34, 0x60, 0x7C, 303 0x58, 0x44, 0x2C, 0x30, 0x14, 0x08, 0x5C, 0x40, 0x64, 0x78, 304 0xCC, 0xD0, 0xF4, 0xE8, 0xBC, 0xA0, 0x84, 0x98, 0xA8, 0xB4, 305 0x90, 0x8C, 0xD8, 0xC4, 0xE0, 0xFC, 0x48, 0x54, 0x70, 0x6C, 306 0x38, 0x24, 0x00, 0x1C, 0x74, 0x68, 0x4C, 0x50, 0x04, 0x18, 307 0x3C, 0x20, 0x94, 0x88, 0xAC, 0xB0, 0xE4, 0xF8, 0xDC, 0xC0, 308 0x0C, 0x10, 0x34, 0x28, 0x7C, 0x60, 0x44, 0x58, 0xEC, 0xF0, 309 0xD4, 0xC8, 0x9C, 0x80, 0xA4, 0xB8, 0xD0, 0xCC, 0xE8, 0xF4, 310 0xA0, 0xBC, 0x98, 0x84, 0x30, 0x2C, 0x08, 0x14, 0x40, 0x5C, 311 0x78, 0x64, 0xFC, 0xE0, 0xC4, 0xD8, 0x8C, 0x90, 0xB4, 0xA8, 312 0x1C, 0x00, 0x24, 0x38, 0x6C, 0x70, 0x54, 0x48, 0x20, 0x3C, 313 0x18, 0x04, 0x50, 0x4C, 0x68, 0x74, 0xC0, 0xDC, 0xF8, 0xE4, 314 0xB0, 0xAC, 0x88, 0x94, 0x58, 0x44, 0x60, 0x7C, 0x28, 0x34, 315 0x10, 0x0C, 0xB8, 0xA4, 0x80, 0x9C, 0xC8, 0xD4, 0xF0, 0xEC, 316 0x84, 0x98, 0xBC, 0xA0, 0xF4, 0xE8, 0xCC, 0xD0, 0x64, 0x78, 317 0x5C, 0x40, 0x14, 0x08, 0x2C, 0x30 318 }; 319 public static byte[] Crc11(byte[] buffer, int start = 0, int len = 0) 320 { 321 if (buffer == null || buffer.Length == 0) return null; 322 if (start 0) return null; 323 if (len == 0) len = buffer.Length - start; 324 int length = start + len; 325 if (length > buffer.Length) return null; 326 int i; 327 byte crc = 0x00; 328 int tableIndex; 329 for (i = start; i ) 330 { 331 tableIndex = crc ^ (buffer[i] & 0xFF); 332 crc = table[tableIndex]; 333 } 334 return new byte[] { crc }; 335 } 336 /// ********************************************************************** 337 /// Name: CRC-12 x16+x12+x5+1 338 /// Poly: 0x80 339 /// Init: 0x0000 340 /// Refin: true 341 /// Refout: true 342 /// Xorout: 0x0000 343 ///************************************************************************* 344 public static byte[] Crc12(byte[] buffer, int start = 0, int len = 0) 345 { 346 if (buffer == null || buffer.Length == 0) return null; 347 if (start 0) return null; 348 if (len == 0) len = buffer.Length - start; 349 int length = start + len; 350 if (length > buffer.Length) return null; 351 ushort crc = 0;// Initial value 352 short iQ = 0, iR = 0; 353 for (int i = start; i ) 354 { 355 // 多项式除法 356 // 如果该位为1 357 if ((buffer[i] & (0x80 >> iR)) > 0) 358 { 359 // 则在余数尾部添1否则添0 360 crc |= 0x01; 361 } 362 // 如果12位除数中的最高位为1,则够除 363 if (crc >= 0x1000) 364 { 365 crc ^= 0x180D; 366 } 367 crc 1; 368 iR++; 369 if (8 == iR) 370 { 371 iR = 0; 372 iQ++; 373 } 374 } 375 // 对后面添加的12个0做处理 376 for (int i = 0; i 12; i++) 377 { 378 if (crc >= 0x1000) 379 { 380 crc ^= 0x180D; 381 } 382 crc 1; 383 } 384 crc >>= 1; 385 byte[] ret = BitConverter.GetBytes(crc); 386 Array.Reverse(ret); 387 return ret; 388 } 389 /// ********************************************************************** 390 /// Name: CRC-16/CCITT x16+x12+x5+1 391 /// Poly: 0x1021 392 /// Init: 0x0000 393 /// Refin: true 394 /// Refout: true 395 /// Xorout: 0x0000 396 ///************************************************************************* 397 public static byte[] Crc13(byte[] buffer, int start = 0, int len = 0) 398 { 399 if (buffer == null || buffer.Length == 0) return null; 400 if (start 0) return null; 401 if (len == 0) len = buffer.Length - start; 402 int length = start + len; 403 if (length > buffer.Length) return null; 404 ushort crc = 0;// Initial value 405 for (int i = start; i ) 406 { 407 crc ^= buffer[i]; 408 for (int j = 0; j 8; j++) 409 { 410 if ((crc & 1) > 0) 411 crc = (ushort)((crc >> 1) ^ 0x8408);// 0x8408 = reverse 0x1021 412 else 413 crc = (ushort)(crc >> 1); 414 } 415 } 416 byte[] ret = BitConverter.GetBytes(crc); 417 Array.Reverse(ret); 418 return ret; 419 } 420 /// ********************************************************************** 421 /// Name: CRC-16/CCITT FALSE x16+x12+x5+1 422 /// Poly: 0x1021 423 /// Init: 0xFFFF 424 /// Refin: false 425 /// Refout: false 426 /// Xorout: 0x0000 427 ///************************************************************************* 428 public static byte[] Crc14(byte[] buffer, int start = 0, int
文章标题:用C#实现的几种常用数据校验方法整理(CRC校验;LRC校验;BCC校验;累加和校验)
文章链接:http://soscw.com/essay/50766.html