diff --git a/adaptive.c b/adaptive.c index fa1df6a..51c8d7e 100644 --- a/adaptive.c +++ b/adaptive.c @@ -399,6 +399,7 @@ static void adaptive_end_of_block() adaptive_burst_control_update(); adaptive_range_control_update(); + Modes.stats_current.adaptive_valid = true; unsigned current = Modes.stats_current.adaptive_gain = sdrGetGain(); ++Modes.stats_current.adaptive_gain_seconds[current < STATS_GAIN_COUNT ? current : STATS_GAIN_COUNT-1]; if (adaptive_burst_suppressing) diff --git a/net_io.c b/net_io.c index 438a34b..6ba9f16 100644 --- a/net_io.c +++ b/net_io.c @@ -1859,29 +1859,32 @@ static char * appendStatsJson(char *p, } p = safe_snprintf(p, end, "]"); - p = safe_snprintf(p, end, - ",\"adaptive\":" - "{\"gain_db\":%.1f" - ",\"gain_reduced_seconds\":%u" - ",\"loud_undecoded\":%u" - ",\"loud_decoded\":%u" - ",\"noise_dbfs\":%.1f" - ",\"gain_seconds\":[", - sdrGetGainDb(st->adaptive_gain), - st->adaptive_gain_reduced_seconds, - st->adaptive_loud_undecoded, - st->adaptive_loud_decoded, - st->adaptive_noise_dbfs); - bool first = true; - for (unsigned i = 0; i < STATS_GAIN_COUNT; ++i) { - if (st->adaptive_gain_seconds[i] > 0) { - p = safe_snprintf(p, end, "%s[%.1f,%u]", - first ? "" : ",", - sdrGetGainDb(i), st->adaptive_gain_seconds[i]); - first = false; + if (st->adaptive_valid) { + p = safe_snprintf(p, end, + ",\"adaptive\":" + "{\"gain_db\":%.1f" + ",\"gain_reduced_seconds\":%u" + ",\"loud_undecoded\":%u" + ",\"loud_decoded\":%u" + ",\"noise_dbfs\":%.1f" + ",\"gain_seconds\":[", + sdrGetGainDb(st->adaptive_gain), + st->adaptive_gain_reduced_seconds, + st->adaptive_loud_undecoded, + st->adaptive_loud_decoded, + st->adaptive_noise_dbfs); + bool first = true; + for (unsigned i = 0; i < STATS_GAIN_COUNT; ++i) { + if (st->adaptive_gain_seconds[i] > 0) { + p = safe_snprintf(p, end, "%s[%.1f,%u]", + first ? "" : ",", + sdrGetGainDb(i), st->adaptive_gain_seconds[i]); + first = false; + } } + p = safe_snprintf(p, end, "]}"); } - p = safe_snprintf(p, end, "]}}"); + p = safe_snprintf(p, end, "}"); return p; } diff --git a/stats.c b/stats.c index 0ebd64d..01e7e89 100644 --- a/stats.c +++ b/stats.c @@ -115,7 +115,7 @@ void display_stats(struct stats *st) { st->strong_signal_count); } - if (Modes.adaptive_burst_control || Modes.adaptive_range_control) { + if (st->adaptive_valid) { printf("Adaptive gain:\n" " %5u loud undecoded bursts\n" " %5u loud decoded messages\n" @@ -315,7 +315,7 @@ void add_stats(const struct stats *st1, const struct stats *st2, struct stats *t target->start = st2->start; const struct stats *newer; - if (st1->end > st2->end) { + if (st1->end > st2->end || (st1->end == st2->end && st1->start > st2->start)) { newer = st1; } else { newer = st2; @@ -395,11 +395,21 @@ void add_stats(const struct stats *st1, const struct stats *st2, struct stats *t target->range_histogram[i] = st1->range_histogram[i] + st2->range_histogram[i]; // adaptive gain measurements - target->adaptive_gain = newer->adaptive_gain; + + const struct stats *adaptive_best; + if (st1->adaptive_valid && st2->adaptive_valid) + adaptive_best = newer; + else if (st1->adaptive_valid) + adaptive_best = st1; + else + adaptive_best = st2; + + target->adaptive_valid = adaptive_best->adaptive_valid; + target->adaptive_gain = adaptive_best->adaptive_gain; for (unsigned i = 0; i < STATS_GAIN_COUNT; ++i) target->adaptive_gain_seconds[i] = st1->adaptive_gain_seconds[i] + st2->adaptive_gain_seconds[i]; target->adaptive_gain_reduced_seconds = st1->adaptive_gain_reduced_seconds + st2->adaptive_gain_reduced_seconds; target->adaptive_loud_undecoded = st1->adaptive_loud_undecoded + st2->adaptive_loud_undecoded; target->adaptive_loud_decoded = st1->adaptive_loud_decoded + st2->adaptive_loud_decoded; - target->adaptive_noise_dbfs = newer->adaptive_noise_dbfs; + target->adaptive_noise_dbfs = adaptive_best->adaptive_noise_dbfs; } diff --git a/stats.h b/stats.h index 387cb17..e1ca139 100644 --- a/stats.h +++ b/stats.h @@ -132,7 +132,8 @@ struct stats { // adaptive gain measurements #define STATS_GAIN_COUNT 64 - unsigned adaptive_gain; // Current gain step in use + bool adaptive_valid; // is the following data valid? + int adaptive_gain; // Current gain step in use uint32_t adaptive_gain_seconds[STATS_GAIN_COUNT]; // Seconds spent at each gain step uint32_t adaptive_gain_reduced_seconds; // Seconds spent at a reduced gain due to burst detection uint32_t adaptive_loud_undecoded; // Total number of loud, undecoded bursts