Incomplete dives may have profile data but since we don't have an end-pointer, we have to use the next dive's pointer or ringbuffer head point in config to get close to the end of the dive. This often includes inter-dive events. We can eliminate those by parsing backwards. --- src/cochran_cmdr_parser.c | 14 ++++++++++++-- src/cochran_commander.c | 9 +++++++-- src/cochran_commander_parser.c | 26 +++++++++++++++++++++++++- src/cochran_commander_parser.h | 2 ++ src/cochran_emc_parser.c | 19 ++++++++++++++++--- 5 files changed, 62 insertions(+), 8 deletions(-)
diff --git a/src/cochran_cmdr_parser.c b/src/cochran_cmdr_parser.c index 73b344f..a7db1cd 100644 --- a/src/cochran_cmdr_parser.c +++ b/src/cochran_cmdr_parser.c @@ -130,10 +130,20 @@ cochran_cmdr_parser_samples_foreach (dc_parser_t *abstract, double depth; double ascent_rate; unsigned char corrupt_dive = 0; - - if (array_uint32_le(log + COCHRAN_CMDR_LOG_SIZE / 2) == 0xFFFFFFFF) + int cmdr_event_bytes[15][2] = { {0x00, 17}, {0x01, 21}, {0x02, 18}, + {0x03, 17}, {0x06, 19}, {0x07, 19}, + {0x08, 19}, {0x09, 19}, {0x0a, 19}, + {0x0b, 21}, {0x0c, 19}, {0x0d, 19}, + {0x0e, 19}, {0x10, 21}, + { -1, 1} }; + + if (array_uint32_le(log + COCHRAN_CMDR_LOG_SIZE / 2) == 0xFFFFFFFF) { corrupt_dive = 1;
+ // Eliminate inter-dive events + size = cochran_backparse(abstract, samples, size, &cmdr_event_bytes); + } + // Cochran samples depth every second and varies between ascent rate // and temp ever other second.
diff --git a/src/cochran_commander.c b/src/cochran_commander.c index a8b2f4a..ae2dc45 100644 --- a/src/cochran_commander.c +++ b/src/cochran_commander.c @@ -195,8 +195,13 @@ cochran_packet (cochran_device_t *device, dc_event_progress_t *progress, rc = serial_configure(device->port, layout->high_baud_rate, 8, SERIAL_PARITY_NONE, 2, SERIAL_FLOWCONTROL_NONE); if (rc == -1) { - ERROR (abstract->context, "Failed to set the high baud rate."); - return DC_STATUS_IO; + // Assume we are talking to a pty, a simulator + rc = serial_configure(device->port, 115200, 8, SERIAL_PARITY_NONE, + 2, SERIAL_FLOWCONTROL_NONE); + if (rc == -1) { + ERROR (abstract->context, "Failed to set the high baud rate."); + return DC_STATUS_IO; + } } }
diff --git a/src/cochran_commander_parser.c b/src/cochran_commander_parser.c index 955dba0..e2b854c 100644 --- a/src/cochran_commander_parser.c +++ b/src/cochran_commander_parser.c @@ -100,7 +100,7 @@ cochran_commander_parser_set_data (dc_parser_t *abstract, parser->layout = cochran_commander_get_layout(data);
return DC_STATUS_SUCCESS; -} +}
// There are two date formats used by Cochran @@ -236,3 +236,27 @@ cochran_commander_handle_event (dc_parser_t *abstract,
return event.data_bytes; } + +/* +* cochran_backparse +* +* Used to find the end of a dive that has an incomplete dive-end +* block. It parses backwards past inter-dive events. +*/ + +int cochran_backparse(dc_parser_t *abstract, const char *samples, int size, int (*event_bytes)[15][2]) { + int result = size, best_result = size; + + for (int x = 0; (*event_bytes)[x][0] != -1; x++) { + int ptr = size - (*event_bytes)[x][1]; + if (ptr > 0 && samples[ptr] == (*event_bytes)[x][0]) { + result = cochran_backparse(abstract, samples, ptr, event_bytes); + } + + if (result < best_result) { + best_result = result; + } + } + + return best_result; +} diff --git a/src/cochran_commander_parser.h b/src/cochran_commander_parser.h index 4e9fc01..730edf7 100644 --- a/src/cochran_commander_parser.h +++ b/src/cochran_commander_parser.h @@ -102,6 +102,8 @@ void cochran_commander_get_event_info(const unsigned char code, int cochran_commander_handle_event (dc_parser_t *abstract, dc_sample_callback_t callback, void *userdata, unsigned char code, unsigned int offset, unsigned int time); +int cochran_backparse(dc_parser_t *abstract, const char *samples, int size, int (*event_bytes)[15][2]); +
// EMC FAMILY dc_status_t cochran_emc_parser_get_field (dc_parser_t *abstract, diff --git a/src/cochran_emc_parser.c b/src/cochran_emc_parser.c index 884f8aa..322f3d4 100644 --- a/src/cochran_emc_parser.c +++ b/src/cochran_emc_parser.c @@ -43,6 +43,12 @@ struct dive_stats { float max_temp; };
+// Size of inter-dive events +int emc_event_bytes[15][2] = { {0x00, 19}, {0x01, 23}, {0x02, 20}, + {0x03, 19}, {0x06, 21}, {0x07, 21}, + {0x0a, 21}, {0x0b, 21}, {0x0f, 19}, + {0x10, 21}, + { -1, 1} };
static void cochran_emc_parse_dive_stats (dc_parser_t *abstract, struct dive_stats *stats); @@ -158,10 +164,13 @@ cochran_emc_parser_samples_foreach (dc_parser_t *abstract, unsigned int deco_time; unsigned char corrupt_dive = 0;
- - if (array_uint32_le(log + COCHRAN_EMC_LOG_SIZE / 2) == 0xFFFFFFFF) + if (array_uint32_le(log + COCHRAN_EMC_LOG_SIZE / 2) == 0xFFFFFFFF) { corrupt_dive = 1;
+ // Eliminate inter-dive events + size = cochran_backparse(abstract, samples, size, &emc_event_bytes); + } + /* * Cochran samples depth every second and varies between ascent rate * and temp ever other second. @@ -330,9 +339,13 @@ void cochran_emc_parse_dive_stats (dc_parser_t *abstract, unsigned int time = 0; unsigned char corrupt_dive = 0;
- if (array_uint32_le(log + COCHRAN_EMC_LOG_SIZE / 2) == 0xFFFFFFFF) + if (array_uint32_le(log + COCHRAN_EMC_LOG_SIZE / 2) == 0xFFFFFFFF) { corrupt_dive = 1;
+ // Eliminate inter-dive events + size = cochran_backparse(abstract, samples, size, &emc_event_bytes); + } + // Prime with values from the dive log section depth = array_uint16_le (log + EMC_START_DEPTH) / 256;