2 * This file is part of Cleanflight and Betaflight.
4 * Cleanflight and Betaflight are free software. You can redistribute
5 * this software and/or modify this software under the terms of the
6 * GNU General Public License as published by the Free Software
7 * Foundation, either version 3 of the License, or (at your option)
10 * Cleanflight and Betaflight are distributed in the hope that they
11 * will be useful, but WITHOUT ANY WARRANTY; without even the implied
12 * warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
13 * See the GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with this software.
18 * If not, see <http://www.gnu.org/licenses/>.
23 #include "common/crc.h"
27 #include "streambuf.h"
29 uint16_t crc16_ccitt(uint16_t crc
, unsigned char a
)
31 crc
^= (uint16_t)a
<< 8;
32 for (int ii
= 0; ii
< 8; ++ii
) {
34 crc
= (crc
<< 1) ^ 0x1021;
42 uint16_t crc16_ccitt_update(uint16_t crc
, const void *data
, uint32_t length
)
44 const uint8_t *p
= (const uint8_t *)data
;
45 const uint8_t *pend
= p
+ length
;
47 for (; p
!= pend
; p
++) {
48 crc
= crc16_ccitt(crc
, *p
);
53 void crc16_ccitt_sbuf_append(sbuf_t
*dst
, uint8_t *start
)
56 const uint8_t * const end
= sbufPtr(dst
);
57 for (const uint8_t *ptr
= start
; ptr
< end
; ++ptr
) {
58 crc
= crc16_ccitt(crc
, *ptr
);
60 sbufWriteU16(dst
, crc
);
63 uint8_t crc8_calc(uint8_t crc
, unsigned char a
, uint8_t poly
)
66 for (int ii
= 0; ii
< 8; ++ii
) {
68 crc
= (crc
<< 1) ^ poly
;
76 uint8_t crc8_update(uint8_t crc
, const void *data
, uint32_t length
, uint8_t poly
)
78 const uint8_t *p
= (const uint8_t *)data
;
79 const uint8_t *pend
= p
+ length
;
81 for (; p
!= pend
; p
++) {
82 crc
= crc8_calc(crc
, *p
, poly
);
87 void crc8_sbuf_append(sbuf_t
*dst
, uint8_t *start
, uint8_t poly
)
90 const uint8_t * const end
= dst
->ptr
;
91 for (const uint8_t *ptr
= start
; ptr
< end
; ++ptr
) {
92 crc
= crc8_calc(crc
, *ptr
, poly
);
94 sbufWriteU8(dst
, crc
);
97 uint8_t crc8_xor_update(uint8_t crc
, const void *data
, uint32_t length
)
99 const uint8_t *p
= (const uint8_t *)data
;
100 const uint8_t *pend
= p
+ length
;
102 for (; p
!= pend
; p
++) {
108 void crc8_xor_sbuf_append(sbuf_t
*dst
, uint8_t *start
)
111 const uint8_t *end
= dst
->ptr
;
112 for (uint8_t *ptr
= start
; ptr
< end
; ++ptr
) {
115 sbufWriteU8(dst
, crc
);
118 // Fowler–Noll–Vo hash function; see https://en.wikipedia.org/wiki/Fowler–Noll–Vo_hash_function
119 uint32_t fnv_update(uint32_t hash
, const void *data
, uint32_t length
)
121 const uint8_t *p
= (const uint8_t *)data
;
122 const uint8_t *pend
= p
+ length
;
124 for (; p
!= pend
; p
++) {