Hallo,
in existierendem Code finde ich zwei Varianten zur Prüfsummenberechnung
nach CCITT und frage mich, ob beide tatsächlich einen gültigen CRC-Wert
berechnen.
Startwert ist 0x0, verwendetes Polynom ist 0x1021:
Variante A:
1
voidcrcAlgA(char*buf,unsignedshort*crc){
2
unsignedshorti;
3
4
for(i=0;i<strlen(buf);i++){
5
*crc=((*crc)<<8)^crctab[((*crc)>>8)^buf[i]];
6
}
7
}
Variante B:
1
voidcrcAlgB(char*buf,unsignedshort*crc){
2
unsignedshorti;
3
4
for(i=0;i<strlen(buf);i++){
5
*crc=((*crc)<<8)^crctab[((*crc)>>8)]^buf[i];
6
}
7
}
Beide Variante verwenden die gleiche Lookup-Tabelle:
Algorithmus A erzeugt einen Wert gemäß CRC-16/XMODEM, soweit OK. Was
aber Algorithmus B erzeugt, kann ich einfach nicht sinnvoll beurteilen.
Hängt man jedoch zwei Nullbytes an die Nachricht an, entspricht das
Ergebnis von B dem von A.
Ist Variante B überhaupt ein CRC-Algorithmus? Falls ja: welcher
Algorithmus ist das? Ich muss die Prüfsummenberechnung für extern
spezifizieren und kann dabei nicht auf Quelltext ausweichen, sondern
muss allgemein formulieren.
Beim Versuch der Identifikation, um welchen Algorithmus es sich handeln
könnte, habe ich diese Seiten sehr hilfreich gefunden:
https://crccalc.com/?crc=AB01&method=crc16&datatype=asciihttp://www.sunshine2k.de/coding/javascript/crc/crc_js.html
Vielen Dank schon mal und viele Grüße,
D.
Hallo,
Ich würde sagen, B ist fehlerhaft. Das XOR mit buf[i] wirkt auf das
Ergebnis des Zugriffes auf die Tabelle. Während in A der Platz im Array
über das XOR buf[1] ermittelt wird.
Gruß
Frank
Hallo,
richtig ist Version A,
aber die Version ist ebenfals grenzwertig
da in deinem Array buf wegen dem strlen(buf)
kein Zeichen 0x00 vorkommen darf!
Gruss
Hallo,
vielleicht noch eine Anmerkung zu
Daniel M. schrieb:> Ist Variante B überhaupt ein CRC-Algorithmus? Falls ja: welcher> Algorithmus ist das?
eine Prüfsumme (sprich CRC) kann jeder berechnen wie er lustig ist. Sie
muss nur eindeutig reproduzierbar sein.
Nur der internationalen Gepflogenheit der fortgesetzten Polynomdivision
mit genormten Polynom entspricht Version B nicht!
Gruss
Es ist aber schon klar, dass man strlen() nicht in einem loop verwenden
sollte ? Falls der Compiler doof genung ist rechnet er das jedes mal
neu, heisst er zaehlt die character.
Hallo,
Megatroll schrieb:> Falls der Compiler doof genung ist rechnet er das jedes mal> neu, heisst er zaehlt die character.
strlen() ermittelt immer die Länge eines Strings bzw. zählt die Anzahl
seiner Zeichen bis zu 0x00
@Megatroll: ich nehme an, das bezieht sich auf meine zwei vorgestellten
Varianten? Mir persönlich war das tatsächlich nicht klar, da ich C-Code
gerade so gut verstehe, um ihn halbwegs lesen zu können -- ich komme
eher aus der Python-Ecke ;) In jedem Fall Danke für den Hinweis!
Letztlich geht es mir bei der Frage aber gar nicht um Effizienz, sondern
darum ob Variante B überhaupt eine gültige Implementierung darstellt.
Variante A kann ich einfach spezifizieren: Startwert 0x0, Poly 0x1021,
kein Bit-Reversal für Input/Result, Result XOR 0x0. Variante B ist hier
deutlich unorthodoxer. Ich finde keine solche Entsprechung auf
einschlägigen Seiten:
http://www.sunshine2k.de/coding/javascript/crc/crc_js.htmlhttp://www.zorc.breitbandkatze.de/crc.html
Georg G. schrieb:> DPA schrieb:>> Ich würd das so anpassen:>> und sobald im Datensatz eine Null ist, knallt es.> Die Länge sollte explizit übergeben werden.
char* (in der Schnittstelle) und c!=0 (implizit in der Loop) spricht
dafür, daß C-Strings behandelt werden sollen. Was soll da knallen?