From 147d3df63502b7393cf00bf85e085e60e475ea04 Mon Sep 17 00:00:00 2001 From: Linus Torvalds Date: Thu, 13 Jul 2023 13:58:44 -0700 Subject: [PATCH] garmin_parser: add support for compressed records and more debug output This turns out to have been another false turn: mis-parsing the FIT file caused us to think it had compressed records. So I spent much too much time trying to figure out how those compressed records actually work. This is the result. It looks like the only difference between a compressed record and a regular one is that the compressed record has a single-byte "this is the record type and the time offset" field at the start. That basically avoids the need of then having a full 4-byte absolute time for such a record. Signed-off-by: Linus Torvalds --- src/garmin_parser.c | 17 ++++++++--------- 1 file changed, 8 insertions(+), 9 deletions(-) diff --git a/src/garmin_parser.c b/src/garmin_parser.c index 81d8fac..0666a5d 100644 --- a/src/garmin_parser.c +++ b/src/garmin_parser.c @@ -1144,14 +1144,6 @@ static const struct msg_desc *lookup_msg_desc(unsigned short msg, int local, con return desc; } -static int traverse_compressed(struct garmin_parser_t *garmin, - const unsigned char *data, unsigned int size, - unsigned char type, unsigned int time) -{ - fprintf(stderr, "Compressed record for local type %d:\n", type); - return -1; -} - static int all_data_inval(const unsigned char *data, int base_type, int len) { int base_size = base_type_info[base_type].type_size; @@ -1413,10 +1405,17 @@ traverse_data(struct garmin_parser_t *garmin) newtime += 0x20; time = newtime; - len = traverse_compressed(garmin, data, datasize, type, time); + // Compressed records are like normal records + // with that added relative timestamp + DEBUG(garmin->base.context, "Compressed record for type %d", type); + HEXDUMP(garmin->base.context, DC_LOGLEVEL_DEBUG, "data", data, 40); + parse_ANY_timestamp(garmin, time); + len = traverse_regular(garmin, data, datasize, type, &time); } else if (record & 0x40) { // Definition record? len = traverse_definition(garmin, data, datasize, record); } else { // Normal data record + DEBUG(garmin->base.context, "Regular record for type %d", record); + HEXDUMP(garmin->base.context, DC_LOGLEVEL_DEBUG, "data", data, 40); len = traverse_regular(garmin, data, datasize, record, &time); } if (len <= 0 || len > datasize)