diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2013-02-09 11:35:39 +1100 |
---|---|---|
committer | Dirk Hohndel <dirk@hohndel.org> | 2013-02-08 18:28:38 -0800 |
commit | b12b2f1c85a3c18a66b7bddffbae574212a33bc2 (patch) | |
tree | 7f6ef3267d9c76c548ea9348a23e6de9e1b02e5b /dive.c | |
parent | 926fcef2a1e83b58c37c948a3f1a904aa0be0d0e (diff) | |
download | subsurface-b12b2f1c85a3c18a66b7bddffbae574212a33bc2.tar.gz |
Walk over each divecomputer entry in fixup_dives()
The fixup_dives() code used to only look at the first divecomputer,
which meant that minimun temperatures etc for the dive would only ever
come from the primary divecomputer.
This splits up the code that walks over the divecomputer into a function
of its own, and iterates over all computers in fixup_dive() calling into
it.
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
Diffstat (limited to 'dive.c')
-rw-r--r-- | dive.c | 135 |
1 files changed, 75 insertions, 60 deletions
@@ -454,10 +454,53 @@ static void fixup_water_salinity(struct dive *dive) dive->salinity = (sum + nr/2)/nr; } -/* right now this only operates on the first divecomputer */ -struct dive *fixup_dive(struct dive *dive) +/* + * events are stored as a linked list, so the concept of + * "consecutive, identical events" is somewhat hard to + * implement correctly (especially given that on some dive + * computers events are asynchronous, so they can come in + * between what would be the non-constant sample rate). + * + * So what we do is that we throw away clearly redundant + * events that are fewer than 61 seconds apart (assuming there + * is no dive computer with a sample rate of more than 60 + * seconds... that would be pretty pointless to plot the + * profile with) + * + * We first only mark the events for deletion so that we + * still know when the previous event happened. + */ +static void fixup_dc_events(struct divecomputer *dc) { - int i,j; + struct event *event; + + event = dc->events; + while (event) { + struct event *prev; + if (is_potentially_redundant(event)) { + prev = find_previous_event(dc, event); + if (prev && prev->value == event->value && + prev->flags == event->flags && + event->time.seconds - prev->time.seconds < 61) + event->deleted = TRUE; + } + event = event->next; + } + event = dc->events; + while (event) { + if (event->next && event->next->deleted) { + struct event *nextnext = event->next->next; + free(event->next); + event->next = nextnext; + } else { + event = event->next; + } + } +} + +static void fixup_dive_dc(struct dive *dive, struct divecomputer *dc) +{ + int i, j; double depthtime = 0; int lasttime = 0; int lastindex = -1; @@ -466,20 +509,7 @@ struct dive *fixup_dive(struct dive *dive) int lastdepth = 0; int lasttemp = 0, lastpressure = 0; int pressure_delta[MAX_CYLINDERS] = {INT_MAX, }; - struct divecomputer *dc; - struct event *event; - - add_people(dive->buddy); - add_people(dive->divemaster); - add_location(dive->location); - add_suit(dive->suit); - sanitize_cylinder_info(dive); - dive->maxcns = dive->cns; - - fixup_water_salinity(dive); - fixup_surface_pressure(dive); - dc = &dive->dc; for (i = 0; i < dc->samples; i++) { struct sample *sample = dc->sample + i; int time = sample->time.seconds; @@ -574,9 +604,9 @@ struct dive *fixup_dive(struct dive *dive) } if (end < 0) { /* Assume an ascent/descent rate of 9 m/min */ - int depth = dive->dc.maxdepth.mm; + int depth = dc->maxdepth.mm; int asc_desc_time = depth*60/9000; - int duration = dive->dc.duration.seconds; + int duration = dc->duration.seconds; /* Some sanity checks against insane dives */ if (duration < 2) @@ -584,17 +614,38 @@ struct dive *fixup_dive(struct dive *dive) if (asc_desc_time * 2 >= duration) asc_desc_time = duration/2; - dive->dc.meandepth.mm = depth*(duration-asc_desc_time)/duration; - return dive; + dc->meandepth.mm = depth*(duration-asc_desc_time)/duration; + return; } - update_duration(&dive->dc.duration, end - start); + update_duration(&dc->duration, end - start); if (start != end) depthtime /= (end - start); - update_depth(&dive->dc.meandepth, depthtime); - update_temperature(&dive->dc.watertemp, mintemp); - update_depth(&dive->dc.maxdepth, maxdepth); + update_depth(&dc->meandepth, depthtime); + update_temperature(&dc->watertemp, mintemp); + update_depth(&dc->maxdepth, maxdepth); + + fixup_dc_events(dc); +} + +struct dive *fixup_dive(struct dive *dive) +{ + int i; + struct divecomputer *dc; + + add_people(dive->buddy); + add_people(dive->divemaster); + add_location(dive->location); + add_suit(dive->suit); + sanitize_cylinder_info(dive); + dive->maxcns = dive->cns; + + fixup_water_salinity(dive); + fixup_surface_pressure(dive); + + for_each_dc(dive, dc) + fixup_dive_dc(dive, dc); for (i = 0; i < MAX_CYLINDERS; i++) { cylinder_t *cyl = dive->cylinder + i; @@ -609,42 +660,6 @@ struct dive *fixup_dive(struct dive *dive) add_weightsystem_description(ws); } - /* events are stored as a linked list, so the concept of - * "consecutive, identical events" is somewhat hard to - * implement correctly (especially given that on some dive - * computers events are asynchronous, so they can come in - * between what would be the non-constant sample rate). - * - * So what we do is that we throw away clearly redundant - * events that are fewer than 61 seconds apart (assuming there - * is no dive computer with a sample rate of more than 60 - * seconds... that would be pretty pointless to plot the - * profile with) - * We first only mark the events for deletion so that we - * still know when the previous event happened. */ - event = dc->events; - while (event) { - struct event *prev; - if (is_potentially_redundant(event)) { - prev = find_previous_event(dc, event); - if (prev && prev->value == event->value && - prev->flags == event->flags && - event->time.seconds - prev->time.seconds < 61) - event->deleted = TRUE; - } - event = event->next; - } - event = dc->events; - while (event) { - if (event->next && event->next->deleted) { - struct event *nextnext = event->next->next; - free(event->next); - event->next = nextnext; - } else { - event = event->next; - } - } - return dive; } |