diff options
author | Robert C. Helling <helling@atdotde.de> | 2017-05-26 00:45:53 +0200 |
---|---|---|
committer | Dirk Hohndel <dirk@hohndel.org> | 2017-05-26 15:44:36 -0700 |
commit | 7b18be2a50e3c94fa1e9ae30c92bbb3eee3593d6 (patch) | |
tree | af16a82b1302591c3448812280f261b1cc5296e4 | |
parent | 57ee5a5477c92ff4dd7b8975b1866c988556d14e (diff) | |
download | subsurface-7b18be2a50e3c94fa1e9ae30c92bbb3eee3593d6.tar.gz |
Adopt planner state caching to new struct
Signed-off-by: Robert C. Helling <helling@atdotde.de>
-rw-r--r-- | core/deco.c | 34 | ||||
-rw-r--r-- | core/dive.h | 6 | ||||
-rw-r--r-- | core/planner.c | 21 | ||||
-rw-r--r-- | core/profile.c | 8 | ||||
-rw-r--r-- | qt-models/diveplannermodel.cpp | 4 | ||||
-rw-r--r-- | tests/testplan.cpp | 24 |
6 files changed, 49 insertions, 48 deletions
diff --git a/core/deco.c b/core/deco.c index 37c34a024..33a049f7c 100644 --- a/core/deco.c +++ b/core/deco.c @@ -569,32 +569,30 @@ void clear_deco(double surface_pressure) deco_state->max_ambient_pressure = 0.0; } -void cache_deco_state(char **cached_datap) +void cache_deco_state(struct deco_state **cached_datap) { - char *data = *cached_datap; + struct deco_state *data = *cached_datap; if (!data) { - data = malloc(2 * TISSUE_ARRAY_SZ + sizeof(double) + sizeof(int)); + data = malloc(sizeof(struct deco_state)); *cached_datap = data; } - memcpy(data, deco_state->tissue_n2_sat, TISSUE_ARRAY_SZ); - data += TISSUE_ARRAY_SZ; - memcpy(data, deco_state->tissue_he_sat, TISSUE_ARRAY_SZ); - data += TISSUE_ARRAY_SZ; - memcpy(data, &deco_state->gf_low_pressure_this_dive, sizeof(double)); - data += sizeof(double); - memcpy(data, &deco_state->ci_pointing_to_guiding_tissue, sizeof(int)); + *data = *deco_state; } -void restore_deco_state(char *data) +void restore_deco_state(struct deco_state *data, bool keep_vpmb_state) { - memcpy(deco_state->tissue_n2_sat, data, TISSUE_ARRAY_SZ); - data += TISSUE_ARRAY_SZ; - memcpy(deco_state->tissue_he_sat, data, TISSUE_ARRAY_SZ); - data += TISSUE_ARRAY_SZ; - memcpy(&deco_state->gf_low_pressure_this_dive, data, sizeof(double)); - data += sizeof(double); - memcpy(&deco_state->ci_pointing_to_guiding_tissue, data, sizeof(int)); + if (keep_vpmb_state) { + int ci; + for (ci = 0; ci < 16; ci++) { + data->bottom_n2_gradient[ci] = deco_state->bottom_n2_gradient[ci]; + data->bottom_he_gradient[ci] = deco_state->bottom_he_gradient[ci]; + data->initial_n2_gradient[ci] = deco_state->initial_n2_gradient[ci]; + data->initial_he_gradient[ci] = deco_state->initial_he_gradient[ci]; + } + } + *deco_state = *data; + } int deco_allowed_depth(double tissues_tolerance, double surface_pressure, struct dive *dive, bool smooth) diff --git a/core/dive.h b/core/dive.h index a39759763..fa89edc44 100644 --- a/core/dive.h +++ b/core/dive.h @@ -863,8 +863,8 @@ extern void clear_deco(double surface_pressure); extern void dump_tissues(void); extern void set_gf(short gflow, short gfhigh, bool gf_low_at_maxdepth); extern void set_vpmb_conservatism(short conservatism); -extern void cache_deco_state(char **datap); -extern void restore_deco_state(char *data); +extern void cache_deco_state(struct deco_state **datap); +extern void restore_deco_state(struct deco_state *data, bool keep_vpmb_state); extern void nuclear_regeneration(double time); extern void vpmb_start_gradient(); extern void vpmb_next_gradient(double deco_time, double surface_pressure); @@ -900,7 +900,7 @@ struct divedatapoint *create_dp(int time_incr, int depth, int cylinderid, int po #if DEBUG_PLAN void dump_plan(struct diveplan *diveplan); #endif -bool plan(struct diveplan *diveplan, char **cached_datap, bool is_planner, bool show_disclaimer); +bool plan(struct diveplan *diveplan, struct deco_state **cached_datap, bool is_planner, bool show_disclaimer); void calc_crushing_pressure(double pressure); void vpmb_start_gradient(); void clear_vpmb_state(); diff --git a/core/planner.c b/core/planner.c index 30552a954..22f62a2c1 100644 --- a/core/planner.c +++ b/core/planner.c @@ -130,7 +130,7 @@ void interpolate_transition(struct dive *dive, duration_t t0, duration_t t1, dep } /* returns the tissue tolerance at the end of this (partial) dive */ -unsigned int tissue_at_end(struct dive *dive, char **cached_datap) +unsigned int tissue_at_end(struct dive *dive, struct deco_state **cached_datap) { struct divecomputer *dc; struct sample *sample, *psample; @@ -143,7 +143,7 @@ unsigned int tissue_at_end(struct dive *dive, char **cached_datap) if (!dive) return 0; if (*cached_datap) { - restore_deco_state(*cached_datap); + restore_deco_state(*cached_datap, true); } else { surface_interval = init_decompression(dive); cache_deco_state(cached_datap); @@ -563,17 +563,20 @@ bool trial_ascent(int trial_depth, int stoplevel, int avg_depth, int bottom_time { bool clear_to_ascend = true; - char *trial_cache = NULL; + struct deco_state *trial_cache = NULL; // For consistency with other VPM-B implementations, we should not start the ascent while the ceiling is // deeper than the next stop (thus the offgasing during the ascent is ignored). // However, we still need to make sure we don't break the ceiling due to on-gassing during ascent. + cache_deco_state(&trial_cache); if (decoMode() == VPMB && (deco_allowed_depth(tissue_tolerance_calc(&displayed_dive, depth_to_bar(stoplevel, &displayed_dive)), - surface_pressure, &displayed_dive, 1) > stoplevel)) + surface_pressure, &displayed_dive, 1) > stoplevel)) { + restore_deco_state(trial_cache, false); + free(trial_cache); return false; + } - cache_deco_state(&trial_cache); while (trial_depth > stoplevel) { int deltad = ascent_velocity(trial_depth, avg_depth, bottom_time) * TIMESTEP; if (deltad > trial_depth) /* don't test against depth above surface */ @@ -589,7 +592,7 @@ bool trial_ascent(int trial_depth, int stoplevel, int avg_depth, int bottom_time } trial_depth -= deltad; } - restore_deco_state(trial_cache); + restore_deco_state(trial_cache, false); free(trial_cache); return clear_to_ascend; } @@ -613,7 +616,7 @@ bool enough_gas(int current_cylinder) // Work out the stops. Return value is if there were any mandatory stops. -bool plan(struct diveplan *diveplan, char **cached_datap, bool is_planner, bool show_disclaimer) +bool plan(struct diveplan *diveplan, struct deco_state **cached_datap, bool is_planner, bool show_disclaimer) { int bottom_depth; int bottom_gi; @@ -621,7 +624,7 @@ bool plan(struct diveplan *diveplan, char **cached_datap, bool is_planner, bool bool is_final_plan = true; int deco_time; int previous_deco_time; - char *bottom_cache = NULL; + struct deco_state *bottom_cache = NULL; struct sample *sample; int po2; int transitiontime, gi; @@ -807,7 +810,7 @@ bool plan(struct diveplan *diveplan, char **cached_datap, bool is_planner, bool vpmb_next_gradient(deco_time, diveplan->surface_pressure / 1000.0); previous_deco_time = deco_time; - restore_deco_state(bottom_cache); + restore_deco_state(bottom_cache, true); depth = bottom_depth; gi = bottom_gi; diff --git a/core/profile.c b/core/profile.c index efe97d4f3..86bc974b8 100644 --- a/core/profile.c +++ b/core/profile.c @@ -950,7 +950,7 @@ void calculate_deco_information(struct dive *dive, struct divecomputer *dc, stru double surface_pressure = (dc->surface_pressure.mbar ? dc->surface_pressure.mbar : get_surface_pressure_in_mbar(dive, true)) / 1000.0; bool first_iteration = true; int deco_time = 0, prev_deco_time = 10000000; - char *cache_data_initial = NULL; + struct deco_state *cache_data_initial = NULL; /* For VPM-B outside the planner, cache the initial deco state for CVA iterations */ if (decoMode() == VPMB && !in_planner()) cache_deco_state(&cache_data_initial); @@ -1043,13 +1043,13 @@ void calculate_deco_information(struct dive *dive, struct divecomputer *dc, stru last_ndl_tts_calc_time = entry->sec; /* We are going to mess up deco state, so store it for later restore */ - char *cache_data = NULL; + struct deco_state *cache_data = NULL; cache_deco_state(&cache_data); calculate_ndl_tts(entry, dive, surface_pressure); if (decoMode() == VPMB && !in_planner() && i == pi->nr - 1) final_tts = entry->tts_calc; /* Restore "real" deco state for next real time step */ - restore_deco_state(cache_data); + restore_deco_state(cache_data, false); free(cache_data); } } @@ -1066,7 +1066,7 @@ void calculate_deco_information(struct dive *dive, struct divecomputer *dc, stru first_ceiling = 0; first_iteration = false; count_iteration ++; - restore_deco_state(cache_data_initial); + restore_deco_state(cache_data_initial, false); } else { // With Buhlmann, or not in planner, iterating isn't needed. This makes the while condition false. prev_deco_time = deco_time = 0; diff --git a/qt-models/diveplannermodel.cpp b/qt-models/diveplannermodel.cpp index 643a70234..54a5ce7b6 100644 --- a/qt-models/diveplannermodel.cpp +++ b/qt-models/diveplannermodel.cpp @@ -823,7 +823,7 @@ void DivePlannerPointsModel::createTemporaryPlan() } // what does the cache do??? - char *cache = NULL; + struct deco_state *cache = NULL; struct divedatapoint *dp = NULL; for (int i = 0; i < MAX_CYLINDERS; i++) { cylinder_t *cyl = &displayed_dive.cylinder[i]; @@ -871,7 +871,7 @@ void DivePlannerPointsModel::saveDuplicatePlan() void DivePlannerPointsModel::createPlan(bool replanCopy) { // Ok, so, here the diveplan creates a dive - char *cache = NULL; + struct deco_state *cache = NULL; bool oldRecalc = setRecalc(false); removeDeco(); createTemporaryPlan(); diff --git a/tests/testplan.cpp b/tests/testplan.cpp index bc8d6e7cf..7b4671cfd 100644 --- a/tests/testplan.cpp +++ b/tests/testplan.cpp @@ -10,7 +10,7 @@ #define DEBUG 1 // testing the dive plan algorithm -extern bool plan(struct diveplan *diveplan, char **cached_datap, bool is_planner, bool show_disclaimer); +extern bool plan(struct diveplan *diveplan, struct deco_state **cached_datap, bool is_planner, bool show_disclaimer); extern pressure_t first_ceiling_pressure; @@ -354,7 +354,7 @@ bool compareDecoTime(int actualRunTimeSeconds, int benchmarkRunTimeSeconds, int void TestPlan::testMetric() { - char *cache = NULL; + struct deco_state *cache = NULL; setupPrefs(); prefs.unit_system = METRIC; @@ -394,7 +394,7 @@ void TestPlan::testMetric() void TestPlan::testImperial() { - char *cache = NULL; + struct deco_state *cache = NULL; setupPrefs(); prefs.unit_system = IMPERIAL; @@ -434,7 +434,7 @@ void TestPlan::testImperial() void TestPlan::testVpmbMetric45m30minTx() { - char *cache = NULL; + struct deco_state *cache = NULL; setupPrefsVpmb(); prefs.unit_system = METRIC; @@ -464,7 +464,7 @@ void TestPlan::testVpmbMetric45m30minTx() void TestPlan::testVpmbMetric60m10minTx() { - char *cache = NULL; + struct deco_state *cache = NULL; setupPrefsVpmb(); prefs.unit_system = METRIC; @@ -494,7 +494,7 @@ void TestPlan::testVpmbMetric60m10minTx() void TestPlan::testVpmbMetric60m30minAir() { - char *cache = NULL; + struct deco_state *cache = NULL; setupPrefsVpmb(); prefs.unit_system = METRIC; @@ -524,7 +524,7 @@ void TestPlan::testVpmbMetric60m30minAir() void TestPlan::testVpmbMetric60m30minEan50() { - char *cache = NULL; + struct deco_state *cache = NULL; setupPrefsVpmb(); prefs.unit_system = METRIC; @@ -560,7 +560,7 @@ void TestPlan::testVpmbMetric60m30minEan50() void TestPlan::testVpmbMetric60m30minTx() { - char *cache = NULL; + struct deco_state *cache = NULL; setupPrefsVpmb(); prefs.unit_system = METRIC; @@ -596,7 +596,7 @@ void TestPlan::testVpmbMetric60m30minTx() void TestPlan::testVpmbMetric100m60min() { - char *cache = NULL; + struct deco_state *cache = NULL; setupPrefsVpmb(); prefs.unit_system = METRIC; @@ -638,7 +638,7 @@ void TestPlan::testVpmbMetric100m60min() void TestPlan::testVpmbMetricMultiLevelAir() { - char *cache = NULL; + struct deco_state *cache = NULL; setupPrefsVpmb(); prefs.unit_system = METRIC; @@ -668,7 +668,7 @@ void TestPlan::testVpmbMetricMultiLevelAir() void TestPlan::testVpmbMetric100m10min() { - char *cache = NULL; + struct deco_state *cache = NULL; setupPrefsVpmb(); prefs.unit_system = METRIC; @@ -714,7 +714,7 @@ void TestPlan::testVpmbMetric100m10min() */ void TestPlan::testVpmbMetricRepeat() { - char *cache = NULL; + struct deco_state *cache = NULL; setupPrefsVpmb(); prefs.unit_system = METRIC; |