Created
October 3, 2016 14:18
-
-
Save zzeroo/95058de022476063ce6d6e7bae3e4bdd to your computer and use it in GitHub Desktop.
CRC-16 Funktion und Aufruf in C
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// gcc -o crc16 crc16.c && ./crc16 2 7 # ./crc16 0x2 0x7 # geht auch .oO | |
#include <stdio.h> | |
#include <stdint.h> | |
#include <stdlib.h> | |
// CRC-16 Funktion nach dem Vorbild von https://ctlsys.com/how_to_compute_the_modbus_rtu_message_crc/ | |
unsigned short crc16(unsigned char buf[], int len) { | |
// Start Definition nach Modbus Standard http://www.modbus.org/docs/Modbus_over_serial_line_V1_02.pdf | |
// Seite 39ff | |
unsigned short crc = 0xFFFF; | |
// Durchlaufe jedes Byte (char) | |
for (int pos = 0; pos < len; pos++) { | |
// XOR das erste Byte des Buffers mit dem low-order Byte des 16bit CRC | |
// Registers. Das Ergebnis wird ebenfalls im CRC Register gespeichert | |
crc ^= (unsigned short)buf[pos]; | |
// Loop über jedes Bit | |
for (int i = 8; i != 0; i--) { | |
// Shifte das CRC Register ein Bit nach rechts (Richtung LSB), | |
// und fülle das MSB mit einer Null auf (Step 3) | |
if ((crc & 0x001) != 0) { | |
// (Wenn LSB 1 ist) | |
crc >>= 1; | |
// XOR das CRC Register mit dem Polynominal Wert 0xA001 (Step 4) | |
crc ^= 0xA001; | |
} else { | |
// (Wenn LSB Null war) Shifte CRC Register ein bit nach rechts (Step 3) | |
crc >>= 1; | |
} | |
} | |
} | |
return crc; | |
} | |
int main(int argc, char* argv[]) { | |
// Wenn keine Parameter übergeben wurden Fehler ausgeben. | |
if (argc < 2) { | |
fprintf(stderr, "Usage: %s <NUMBERS>\n", argv[0]); | |
exit(EXIT_FAILURE); | |
} | |
// Message Buffer (Array in der Grösse der übergebenen Parameter, | |
// -1 da er erste Parameter der Name der Programm ist) | |
// Wird also ein Parameter übergeben, dann ist das Array 1Byte (char) groß | |
char message[argc - 1]; | |
// Jeder einzelne "String"-Parameter wird nun in ein Char gekastet | |
// sie dazu auch `man strtol` der letzte Parameter ist interessant >< | |
for (int i = 1; i < argc; i++) { | |
message[i - 1] = (char)strtol(argv[i], NULL, 0); | |
} | |
// HIER WIRD DIE CRC16 Funktion nun endlich aufgerufen. | |
// Parameter sind der message Buffer und dessen Größe | |
int result = crc16(message, sizeof(message)); | |
// Das Resultat wird nun noch in Hex und Dezimal ausgegeben | |
printf("crc16 ist: 0x%X (%d)\r\n", result, result); | |
return (0); | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment