| Index: webrtc/video/send_statistics_proxy.cc
|
| diff --git a/webrtc/video/send_statistics_proxy.cc b/webrtc/video/send_statistics_proxy.cc
|
| index 98b2b1d45de80e7dc5aa2edb15be54722ab31df1..0d0d3f348cfc23231c00d0e815dea403da131d2a 100644
|
| --- a/webrtc/video/send_statistics_proxy.cc
|
| +++ b/webrtc/video/send_statistics_proxy.cc
|
| @@ -108,22 +108,37 @@ SendStatisticsProxy::UmaSamplesContainer::UmaSamplesContainer(
|
| input_frame_rate_tracker_(100, 10u),
|
| input_fps_counter_(clock, nullptr, true),
|
| sent_fps_counter_(clock, nullptr, true),
|
| + total_byte_counter_(clock, nullptr, true),
|
| + media_byte_counter_(clock, nullptr, true),
|
| + rtx_byte_counter_(clock, nullptr, true),
|
| + padding_byte_counter_(clock, nullptr, true),
|
| + retransmit_byte_counter_(clock, nullptr, true),
|
| + fec_byte_counter_(clock, nullptr, true),
|
| first_rtcp_stats_time_ms_(-1),
|
| first_rtp_stats_time_ms_(-1),
|
| - start_stats_(stats) {}
|
| + start_stats_(stats) {
|
| + InitializeBitrateCounters(stats);
|
| +}
|
|
|
| SendStatisticsProxy::UmaSamplesContainer::~UmaSamplesContainer() {}
|
|
|
| -void AccumulateRtxStats(const VideoSendStream::Stats& stats,
|
| - const std::vector<uint32_t>& rtx_ssrcs,
|
| - StreamDataCounters* total_rtp_stats,
|
| - StreamDataCounters* rtx_stats) {
|
| - for (auto it : stats.substreams) {
|
| - if (std::find(rtx_ssrcs.begin(), rtx_ssrcs.end(), it.first) !=
|
| - rtx_ssrcs.end()) {
|
| - rtx_stats->Add(it.second.rtp_stats);
|
| +void SendStatisticsProxy::UmaSamplesContainer::InitializeBitrateCounters(
|
| + const VideoSendStream::Stats& stats) {
|
| + for (const auto& it : stats.substreams) {
|
| + uint32_t ssrc = it.first;
|
| + total_byte_counter_.SetLast(it.second.rtp_stats.transmitted.TotalBytes(),
|
| + ssrc);
|
| + padding_byte_counter_.SetLast(it.second.rtp_stats.transmitted.padding_bytes,
|
| + ssrc);
|
| + retransmit_byte_counter_.SetLast(
|
| + it.second.rtp_stats.retransmitted.TotalBytes(), ssrc);
|
| + fec_byte_counter_.SetLast(it.second.rtp_stats.fec.TotalBytes(), ssrc);
|
| + if (it.second.is_rtx) {
|
| + rtx_byte_counter_.SetLast(it.second.rtp_stats.transmitted.TotalBytes(),
|
| + ssrc);
|
| } else {
|
| - total_rtp_stats->Add(it.second.rtp_stats);
|
| + media_byte_counter_.SetLast(it.second.rtp_stats.MediaPayloadBytes(),
|
| + ssrc);
|
| }
|
| }
|
| }
|
| @@ -331,47 +346,63 @@ void SendStatisticsProxy::UmaSamplesContainer::UpdateHistograms(
|
| RTC_HISTOGRAMS_PERCENTAGE(kIndex, uma_prefix_ + "PausedTimeInPercent",
|
| paused_time_percent);
|
| }
|
| + }
|
| + }
|
|
|
| - StreamDataCounters rtp;
|
| - StreamDataCounters rtx;
|
| - AccumulateRtxStats(current_stats, rtp_config.rtx.ssrcs, &rtp, &rtx);
|
| - StreamDataCounters start_rtp;
|
| - StreamDataCounters start_rtx;
|
| - AccumulateRtxStats(start_stats_, rtp_config.rtx.ssrcs, &start_rtp,
|
| - &start_rtx);
|
| - rtp.Subtract(start_rtp);
|
| - rtx.Subtract(start_rtx);
|
| - StreamDataCounters rtp_rtx = rtp;
|
| - rtp_rtx.Add(rtx);
|
| -
|
| - RTC_HISTOGRAMS_COUNTS_10000(
|
| - kIndex, uma_prefix_ + "BitrateSentInKbps",
|
| - static_cast<int>(rtp_rtx.transmitted.TotalBytes() * 8 / elapsed_sec /
|
| - 1000));
|
| - RTC_HISTOGRAMS_COUNTS_10000(
|
| - kIndex, uma_prefix_ + "MediaBitrateSentInKbps",
|
| - static_cast<int>(rtp.MediaPayloadBytes() * 8 / elapsed_sec / 1000));
|
| - RTC_HISTOGRAMS_COUNTS_10000(
|
| - kIndex, uma_prefix_ + "PaddingBitrateSentInKbps",
|
| - static_cast<int>(rtp_rtx.transmitted.padding_bytes * 8 / elapsed_sec /
|
| - 1000));
|
| - RTC_HISTOGRAMS_COUNTS_10000(
|
| - kIndex, uma_prefix_ + "RetransmittedBitrateSentInKbps",
|
| - static_cast<int>(rtp_rtx.retransmitted.TotalBytes() * 8 /
|
| - elapsed_sec / 1000));
|
| - if (!rtp_config.rtx.ssrcs.empty()) {
|
| - RTC_HISTOGRAMS_COUNTS_10000(
|
| - kIndex, uma_prefix_ + "RtxBitrateSentInKbps",
|
| - static_cast<int>(rtx.transmitted.TotalBytes() * 8 / elapsed_sec /
|
| - 1000));
|
| - }
|
| - if (rtp_config.flexfec.payload_type != -1 ||
|
| - rtp_config.ulpfec.red_payload_type != -1) {
|
| - RTC_HISTOGRAMS_COUNTS_10000(kIndex,
|
| - uma_prefix_ + "FecBitrateSentInKbps",
|
| - static_cast<int>(rtp_rtx.fec.TotalBytes() *
|
| - 8 / elapsed_sec / 1000));
|
| - }
|
| + AggregatedStats total_bytes_per_sec = total_byte_counter_.GetStats();
|
| + if (total_bytes_per_sec.num_samples > kMinRequiredPeriodicSamples) {
|
| + RTC_HISTOGRAMS_COUNTS_10000(kIndex, uma_prefix_ + "BitrateSentInKbps",
|
| + total_bytes_per_sec.average * 8 / 1000);
|
| + LOG(LS_INFO) << uma_prefix_ << "BitrateSentInBps, "
|
| + << total_bytes_per_sec.ToStringWithMultiplier(8);
|
| + }
|
| + AggregatedStats media_bytes_per_sec = media_byte_counter_.GetStats();
|
| + if (media_bytes_per_sec.num_samples > kMinRequiredPeriodicSamples) {
|
| + RTC_HISTOGRAMS_COUNTS_10000(kIndex, uma_prefix_ + "MediaBitrateSentInKbps",
|
| + media_bytes_per_sec.average * 8 / 1000);
|
| + LOG(LS_INFO) << uma_prefix_ << "MediaBitrateSentInBps, "
|
| + << media_bytes_per_sec.ToStringWithMultiplier(8);
|
| + }
|
| + AggregatedStats padding_bytes_per_sec = padding_byte_counter_.GetStats();
|
| + if (padding_bytes_per_sec.num_samples > kMinRequiredPeriodicSamples) {
|
| + RTC_HISTOGRAMS_COUNTS_10000(kIndex,
|
| + uma_prefix_ + "PaddingBitrateSentInKbps",
|
| + padding_bytes_per_sec.average * 8 / 1000);
|
| + LOG(LS_INFO) << uma_prefix_ << "PaddingBitrateSentInBps, "
|
| + << padding_bytes_per_sec.ToStringWithMultiplier(8);
|
| + }
|
| + AggregatedStats retransmit_bytes_per_sec =
|
| + retransmit_byte_counter_.GetStats();
|
| + if (retransmit_bytes_per_sec.num_samples > kMinRequiredPeriodicSamples) {
|
| + RTC_HISTOGRAMS_COUNTS_10000(kIndex,
|
| + uma_prefix_ + "RetransmittedBitrateSentInKbps",
|
| + retransmit_bytes_per_sec.average * 8 / 1000);
|
| + LOG(LS_INFO) << uma_prefix_ << "RetransmittedBitrateSentInBps, "
|
| + << retransmit_bytes_per_sec.ToStringWithMultiplier(8);
|
| + }
|
| + if (!rtp_config.rtx.ssrcs.empty()) {
|
| + AggregatedStats rtx_bytes_per_sec = rtx_byte_counter_.GetStats();
|
| + int rtx_bytes_per_sec_avg = -1;
|
| + if (rtx_bytes_per_sec.num_samples > kMinRequiredPeriodicSamples) {
|
| + rtx_bytes_per_sec_avg = rtx_bytes_per_sec.average;
|
| + LOG(LS_INFO) << uma_prefix_ << "RtxBitrateSentInBps, "
|
| + << rtx_bytes_per_sec.ToStringWithMultiplier(8);
|
| + } else if (total_bytes_per_sec.num_samples > kMinRequiredPeriodicSamples) {
|
| + rtx_bytes_per_sec_avg = 0; // RTX enabled but no RTX data sent, record 0.
|
| + }
|
| + if (rtx_bytes_per_sec_avg != -1) {
|
| + RTC_HISTOGRAMS_COUNTS_10000(kIndex, uma_prefix_ + "RtxBitrateSentInKbps",
|
| + rtx_bytes_per_sec_avg * 8 / 1000);
|
| + }
|
| + }
|
| + if (rtp_config.flexfec.payload_type != -1 ||
|
| + rtp_config.ulpfec.red_payload_type != -1) {
|
| + AggregatedStats fec_bytes_per_sec = fec_byte_counter_.GetStats();
|
| + if (fec_bytes_per_sec.num_samples > kMinRequiredPeriodicSamples) {
|
| + RTC_HISTOGRAMS_COUNTS_10000(kIndex, uma_prefix_ + "FecBitrateSentInKbps",
|
| + fec_bytes_per_sec.average * 8 / 1000);
|
| + LOG(LS_INFO) << uma_prefix_ << "FecBitrateSentInBps, "
|
| + << fec_bytes_per_sec.ToStringWithMultiplier(8);
|
| }
|
| }
|
| }
|
| @@ -410,10 +441,26 @@ void SendStatisticsProxy::OnEncodedFrameTimeMeasured(
|
| void SendStatisticsProxy::OnSuspendChange(bool is_suspended) {
|
| rtc::CritScope lock(&crit_);
|
| stats_.suspended = is_suspended;
|
| - // Pause framerate stats.
|
| if (is_suspended) {
|
| - uma_container_->input_fps_counter_.ProcessAndPause();
|
| - uma_container_->sent_fps_counter_.ProcessAndPause();
|
| + // Pause framerate (add min pause time since there may be frames/packets
|
| + // that are not yet sent).
|
| + const int64_t kMinMs = 500;
|
| + uma_container_->input_fps_counter_.ProcessAndPauseForDuration(kMinMs);
|
| + uma_container_->sent_fps_counter_.ProcessAndPauseForDuration(kMinMs);
|
| + // Pause bitrate stats.
|
| + uma_container_->total_byte_counter_.ProcessAndPauseForDuration(kMinMs);
|
| + uma_container_->media_byte_counter_.ProcessAndPauseForDuration(kMinMs);
|
| + uma_container_->rtx_byte_counter_.ProcessAndPauseForDuration(kMinMs);
|
| + uma_container_->padding_byte_counter_.ProcessAndPauseForDuration(kMinMs);
|
| + uma_container_->retransmit_byte_counter_.ProcessAndPauseForDuration(kMinMs);
|
| + uma_container_->fec_byte_counter_.ProcessAndPauseForDuration(kMinMs);
|
| + } else {
|
| + // Stop pause explicitly for stats that may be zero/not updated for some
|
| + // time.
|
| + uma_container_->rtx_byte_counter_.ProcessAndStopPause();
|
| + uma_container_->padding_byte_counter_.ProcessAndStopPause();
|
| + uma_container_->retransmit_byte_counter_.ProcessAndStopPause();
|
| + uma_container_->fec_byte_counter_.ProcessAndStopPause();
|
| }
|
| }
|
|
|
| @@ -673,8 +720,7 @@ void SendStatisticsProxy::DataCountersUpdated(
|
| uint32_t ssrc) {
|
| rtc::CritScope lock(&crit_);
|
| VideoSendStream::StreamStats* stats = GetStatsEntry(ssrc);
|
| - RTC_DCHECK(stats) << "DataCountersUpdated reported for unknown ssrc: "
|
| - << ssrc;
|
| + RTC_DCHECK(stats) << "DataCountersUpdated reported for unknown ssrc " << ssrc;
|
|
|
| if (stats->is_flexfec) {
|
| // The same counters are reported for both the media ssrc and flexfec ssrc.
|
| @@ -685,6 +731,20 @@ void SendStatisticsProxy::DataCountersUpdated(
|
| stats->rtp_stats = counters;
|
| if (uma_container_->first_rtp_stats_time_ms_ == -1)
|
| uma_container_->first_rtp_stats_time_ms_ = clock_->TimeInMilliseconds();
|
| +
|
| + uma_container_->total_byte_counter_.Set(counters.transmitted.TotalBytes(),
|
| + ssrc);
|
| + uma_container_->padding_byte_counter_.Set(counters.transmitted.padding_bytes,
|
| + ssrc);
|
| + uma_container_->retransmit_byte_counter_.Set(
|
| + counters.retransmitted.TotalBytes(), ssrc);
|
| + uma_container_->fec_byte_counter_.Set(counters.fec.TotalBytes(), ssrc);
|
| + if (stats->is_rtx) {
|
| + uma_container_->rtx_byte_counter_.Set(counters.transmitted.TotalBytes(),
|
| + ssrc);
|
| + } else {
|
| + uma_container_->media_byte_counter_.Set(counters.MediaPayloadBytes(), ssrc);
|
| + }
|
| }
|
|
|
| void SendStatisticsProxy::Notify(uint32_t total_bitrate_bps,
|
|
|