@@ -90,23 +90,31 @@ uint8_t sd_crc7(const void *message, size_t width)
return shift_reg;
}
-uint16_t sd_crc16(const void *message, size_t width)
+/* 16 bit XMODEM CRC (polynomial 0x1021) */
+uint16_t sd_crc16(const void *data, size_t data_len)
{
- int i, bit;
- uint16_t shift_reg = 0x0000;
- const uint16_t *msg = (const uint16_t *)message;
- width <<= 1;
-
- for (i = 0; i < width; i++, msg++) {
- for (bit = 15; bit >= 0; bit--) {
- shift_reg <<= 1;
- if ((shift_reg >> 15) ^ ((*msg >> bit) & 1)) {
- shift_reg ^= 0x1011;
+ const unsigned char *d = (const unsigned char *)data;
+ uint16_t crc = 0x0000;
+ unsigned char c;
+ unsigned int i;
+ bool bit;
+
+ while (data_len--) {
+ c = *d++;
+ for (i = 0x80; i > 0; i >>= 1) {
+ bit = crc & 0x8000;
+ if (c & i) {
+ bit = !bit;
+ }
+ crc <<= 1;
+ if (bit) {
+ crc ^= 0x1021;
}
}
+ crc &= 0xffff;
}
- return shift_reg;
+ return crc;
}
static uint8_t sd_calc_frame48_crc7(uint8_t cmd, uint32_t arg, bool is_response)
The current sd_crc16() function does not pass the Spec test, change it by a working one. Code generated with pycrc v0.9.1 (https://pycrc.org) using the configuration: - Width = 16 - Poly = 0x1021 - XorIn = 0x0000 - ReflectIn = False - XorOut = 0x0000 - ReflectOut = False - Algorithm = bit-by-bit-fast Copyright of the generated source code ====================================== The code generated by pycrc is not considered a substantial portion of the software, therefore the licence does not cover the generated code, and the author of pycrc will not claim any copyright on the generated code. Signed-off-by: Philippe Mathieu-Daudé <f4bug@amsat.org> --- hw/sd/sdmmc-internal.c | 32 ++++++++++++++++++++------------ 1 file changed, 20 insertions(+), 12 deletions(-)