Adding NetEq lifetime stats to event log visualizer.
Bug: webrtc:9147 Change-Id: I798f8ac41192182d50df6fe98fbe56c8cb7f294c Reviewed-on: https://webrtc-review.googlesource.com/85340 Commit-Queue: Minyue Li <minyue@webrtc.org> Reviewed-by: Björn Terelius <terelius@webrtc.org> Reviewed-by: Ivo Creusen <ivoc@webrtc.org> Cr-Commit-Position: refs/heads/master@{#23738}
This commit is contained in:
@ -46,15 +46,17 @@ void NetEqStatsGetter::AfterGetAudio(int64_t time_now_ms,
|
||||
NetEq* neteq) {
|
||||
// TODO(minyue): Get stats should better not be called as a call back after
|
||||
// get audio. It is called independently from get audio in practice.
|
||||
const auto lifetime_stat = neteq->GetLifetimeStatistics();
|
||||
if (last_stats_query_time_ms_ == 0 ||
|
||||
rtc::TimeDiff(time_now_ms, last_stats_query_time_ms_) >=
|
||||
stats_query_interval_ms_) {
|
||||
NetEqNetworkStatistics stats;
|
||||
RTC_CHECK_EQ(neteq->NetworkStatistics(&stats), 0);
|
||||
stats_.push_back(std::make_pair(time_now_ms, stats));
|
||||
lifetime_stats_.push_back(std::make_pair(time_now_ms, lifetime_stat));
|
||||
last_stats_query_time_ms_ = time_now_ms;
|
||||
}
|
||||
const auto lifetime_stat = neteq->GetLifetimeStatistics();
|
||||
|
||||
if (current_concealment_event_ != lifetime_stat.concealment_events &&
|
||||
voice_concealed_samples_until_last_event_ <
|
||||
lifetime_stat.voice_concealed_samples) {
|
||||
|
@ -77,8 +77,13 @@ class NetEqStatsGetter : public NetEqGetAudioCallback {
|
||||
return concealment_events_;
|
||||
}
|
||||
|
||||
const std::vector<std::pair<int64_t, NetEqNetworkStatistics>>& stats() const {
|
||||
return stats_;
|
||||
const std::vector<std::pair<int64_t, NetEqNetworkStatistics>>* stats() const {
|
||||
return &stats_;
|
||||
}
|
||||
|
||||
const std::vector<std::pair<int64_t, NetEqLifetimeStatistics>>*
|
||||
lifetime_stats() const {
|
||||
return &lifetime_stats_;
|
||||
}
|
||||
|
||||
Stats AverageStats() const;
|
||||
@ -88,6 +93,7 @@ class NetEqStatsGetter : public NetEqGetAudioCallback {
|
||||
int64_t stats_query_interval_ms_ = 1000;
|
||||
int64_t last_stats_query_time_ms_ = 0;
|
||||
std::vector<std::pair<int64_t, NetEqNetworkStatistics>> stats_;
|
||||
std::vector<std::pair<int64_t, NetEqLifetimeStatistics>> lifetime_stats_;
|
||||
size_t current_concealment_event_ = 1;
|
||||
uint64_t voice_concealed_samples_until_last_event_ = 0;
|
||||
std::vector<ConcealmentEvent> concealment_events_;
|
||||
|
@ -1844,20 +1844,23 @@ void EventLogAnalyzer::CreateAudioJitterBufferGraph(
|
||||
plot->SetTitle("NetEq timing for " + GetStreamName(kIncomingPacket, ssrc));
|
||||
}
|
||||
|
||||
void EventLogAnalyzer::CreateNetEqStatsGraph(
|
||||
template <typename NetEqStatsType>
|
||||
void EventLogAnalyzer::CreateNetEqStatsGraphInternal(
|
||||
const NetEqStatsGetterMap& neteq_stats,
|
||||
rtc::FunctionView<float(const NetEqNetworkStatistics&)> stats_extractor,
|
||||
rtc::FunctionView<const std::vector<std::pair<int64_t, NetEqStatsType>>*(
|
||||
const test::NetEqStatsGetter*)> data_extractor,
|
||||
rtc::FunctionView<float(const NetEqStatsType&)> stats_extractor,
|
||||
const std::string& plot_name,
|
||||
Plot* plot) const {
|
||||
std::map<uint32_t, TimeSeries> time_series;
|
||||
|
||||
for (const auto& st : neteq_stats) {
|
||||
const uint32_t ssrc = st.first;
|
||||
const auto& stats = st.second->stats();
|
||||
|
||||
for (size_t i = 0; i < stats.size(); ++i) {
|
||||
const float time = ToCallTimeSec(stats[i].first * 1000); // ms to us.
|
||||
const float value = stats_extractor(stats[i].second);
|
||||
const std::vector<std::pair<int64_t, NetEqStatsType>>* data_vector =
|
||||
data_extractor(st.second.get());
|
||||
for (const auto& data : *data_vector) {
|
||||
const float time = ToCallTimeSec(data.first * 1000); // ms to us.
|
||||
const float value = stats_extractor(data.second);
|
||||
time_series[ssrc].points.emplace_back(TimeSeriesPoint(time, value));
|
||||
}
|
||||
}
|
||||
@ -1874,6 +1877,32 @@ void EventLogAnalyzer::CreateNetEqStatsGraph(
|
||||
plot->SetTitle(plot_name);
|
||||
}
|
||||
|
||||
void EventLogAnalyzer::CreateNetEqNetworkStatsGraph(
|
||||
const NetEqStatsGetterMap& neteq_stats,
|
||||
rtc::FunctionView<float(const NetEqNetworkStatistics&)> stats_extractor,
|
||||
const std::string& plot_name,
|
||||
Plot* plot) const {
|
||||
CreateNetEqStatsGraphInternal<NetEqNetworkStatistics>(
|
||||
neteq_stats,
|
||||
[](const test::NetEqStatsGetter* stats_getter) {
|
||||
return stats_getter->stats();
|
||||
},
|
||||
stats_extractor, plot_name, plot);
|
||||
}
|
||||
|
||||
void EventLogAnalyzer::CreateNetEqLifetimeStatsGraph(
|
||||
const NetEqStatsGetterMap& neteq_stats,
|
||||
rtc::FunctionView<float(const NetEqLifetimeStatistics&)> stats_extractor,
|
||||
const std::string& plot_name,
|
||||
Plot* plot) const {
|
||||
CreateNetEqStatsGraphInternal<NetEqLifetimeStatistics>(
|
||||
neteq_stats,
|
||||
[](const test::NetEqStatsGetter* stats_getter) {
|
||||
return stats_getter->lifetime_stats();
|
||||
},
|
||||
stats_extractor, plot_name, plot);
|
||||
}
|
||||
|
||||
void EventLogAnalyzer::CreateIceCandidatePairConfigGraph(Plot* plot) {
|
||||
std::map<uint32_t, TimeSeries> configs_by_cp_id;
|
||||
for (const auto& config : parsed_log_.ice_candidate_pair_configs()) {
|
||||
|
@ -76,14 +76,20 @@ class EventLogAnalyzer {
|
||||
std::map<uint32_t, std::unique_ptr<test::NetEqStatsGetter>>;
|
||||
NetEqStatsGetterMap SimulateNetEq(const std::string& replacement_file_name,
|
||||
int file_sample_rate_hz) const;
|
||||
|
||||
void CreateAudioJitterBufferGraph(uint32_t ssrc,
|
||||
const test::NetEqStatsGetter* stats_getter,
|
||||
Plot* plot) const;
|
||||
void CreateNetEqStatsGraph(
|
||||
void CreateNetEqNetworkStatsGraph(
|
||||
const NetEqStatsGetterMap& neteq_stats_getters,
|
||||
rtc::FunctionView<float(const NetEqNetworkStatistics&)> stats_extractor,
|
||||
const std::string& plot_name,
|
||||
Plot* plot) const;
|
||||
void CreateNetEqLifetimeStatsGraph(
|
||||
const NetEqStatsGetterMap& neteq_stats_getters,
|
||||
rtc::FunctionView<float(const NetEqLifetimeStatistics&)> stats_extractor,
|
||||
const std::string& plot_name,
|
||||
Plot* plot) const;
|
||||
|
||||
void CreateIceCandidatePairConfigGraph(Plot* plot);
|
||||
void CreateIceConnectivityCheckGraph(Plot* plot);
|
||||
@ -122,6 +128,15 @@ class EventLogAnalyzer {
|
||||
}
|
||||
}
|
||||
|
||||
template <typename NetEqStatsType>
|
||||
void CreateNetEqStatsGraphInternal(
|
||||
const NetEqStatsGetterMap& neteq_stats,
|
||||
rtc::FunctionView<const std::vector<std::pair<int64_t, NetEqStatsType>>*(
|
||||
const test::NetEqStatsGetter*)> data_extractor,
|
||||
rtc::FunctionView<float(const NetEqStatsType&)> stats_extractor,
|
||||
const std::string& plot_name,
|
||||
Plot* plot) const;
|
||||
|
||||
template <typename IterableType>
|
||||
void CreateAccumulatedPacketsTimeSeries(Plot* plot,
|
||||
const IterableType& packets,
|
||||
|
@ -341,30 +341,36 @@ int main(int argc, char* argv[]) {
|
||||
analyzer.CreateAudioJitterBufferGraph(it->first, it->second.get(),
|
||||
collection->AppendNewPlot());
|
||||
}
|
||||
analyzer.CreateNetEqStatsGraph(
|
||||
analyzer.CreateNetEqNetworkStatsGraph(
|
||||
neteq_stats,
|
||||
[](const webrtc::NetEqNetworkStatistics& stats) {
|
||||
return stats.expand_rate / 16384.f;
|
||||
},
|
||||
"Expand rate", collection->AppendNewPlot());
|
||||
analyzer.CreateNetEqStatsGraph(
|
||||
analyzer.CreateNetEqNetworkStatsGraph(
|
||||
neteq_stats,
|
||||
[](const webrtc::NetEqNetworkStatistics& stats) {
|
||||
return stats.speech_expand_rate / 16384.f;
|
||||
},
|
||||
"Speech expand rate", collection->AppendNewPlot());
|
||||
analyzer.CreateNetEqStatsGraph(
|
||||
analyzer.CreateNetEqNetworkStatsGraph(
|
||||
neteq_stats,
|
||||
[](const webrtc::NetEqNetworkStatistics& stats) {
|
||||
return stats.accelerate_rate / 16384.f;
|
||||
},
|
||||
"Accelerate rate", collection->AppendNewPlot());
|
||||
analyzer.CreateNetEqStatsGraph(
|
||||
analyzer.CreateNetEqNetworkStatsGraph(
|
||||
neteq_stats,
|
||||
[](const webrtc::NetEqNetworkStatistics& stats) {
|
||||
return stats.packet_loss_rate / 16384.f;
|
||||
},
|
||||
"Packet loss rate", collection->AppendNewPlot());
|
||||
analyzer.CreateNetEqLifetimeStatsGraph(
|
||||
neteq_stats,
|
||||
[](const webrtc::NetEqLifetimeStatistics& stats) {
|
||||
return static_cast<float>(stats.concealment_events);
|
||||
},
|
||||
"Concealment events", collection->AppendNewPlot());
|
||||
}
|
||||
|
||||
if (FLAG_plot_ice_candidate_pair_config) {
|
||||
|
Reference in New Issue
Block a user