| OLD | NEW | 
|---|
| 1 /* | 1 /* | 
| 2  *  Copyright (c) 2013 The WebRTC project authors. All Rights Reserved. | 2  *  Copyright (c) 2013 The WebRTC project authors. All Rights Reserved. | 
| 3  * | 3  * | 
| 4  *  Use of this source code is governed by a BSD-style license | 4  *  Use of this source code is governed by a BSD-style license | 
| 5  *  that can be found in the LICENSE file in the root of the source | 5  *  that can be found in the LICENSE file in the root of the source | 
| 6  *  tree. An additional intellectual property rights grant can be found | 6  *  tree. An additional intellectual property rights grant can be found | 
| 7  *  in the file PATENTS.  All contributing project authors may | 7  *  in the file PATENTS.  All contributing project authors may | 
| 8  *  be found in the AUTHORS file in the root of the source tree. | 8  *  be found in the AUTHORS file in the root of the source tree. | 
| 9  */ | 9  */ | 
| 10 | 10 | 
| 11 #include "webrtc/video/send_statistics_proxy.h" | 11 #include "webrtc/video/send_statistics_proxy.h" | 
| 12 | 12 | 
| 13 #include <map> | 13 #include <map> | 
| 14 #include <memory> | 14 #include <memory> | 
| 15 #include <string> | 15 #include <string> | 
| 16 #include <vector> | 16 #include <vector> | 
| 17 | 17 | 
| 18 #include "webrtc/system_wrappers/include/metrics.h" | 18 #include "webrtc/system_wrappers/include/metrics.h" | 
| 19 #include "webrtc/system_wrappers/include/metrics_default.h" | 19 #include "webrtc/system_wrappers/include/metrics_default.h" | 
| 20 #include "webrtc/test/gtest.h" | 20 #include "webrtc/test/gtest.h" | 
| 21 | 21 | 
| 22 namespace webrtc { | 22 namespace webrtc { | 
| 23 namespace { | 23 namespace { | 
| 24 const uint32_t kFirstSsrc = 17; | 24 const uint32_t kFirstSsrc = 17; | 
| 25 const uint32_t kSecondSsrc = 42; | 25 const uint32_t kSecondSsrc = 42; | 
| 26 const uint32_t kFirstRtxSsrc = 18; | 26 const uint32_t kFirstRtxSsrc = 18; | 
| 27 const uint32_t kSecondRtxSsrc = 43; | 27 const uint32_t kSecondRtxSsrc = 43; | 
| 28 | 28 | 
| 29 const int kMinRequiredSamples = 200; |  | 
| 30 const int kQpIdx0 = 21; | 29 const int kQpIdx0 = 21; | 
| 31 const int kQpIdx1 = 39; | 30 const int kQpIdx1 = 39; | 
| 32 }  // namespace | 31 }  // namespace | 
| 33 | 32 | 
| 34 class SendStatisticsProxyTest : public ::testing::Test { | 33 class SendStatisticsProxyTest : public ::testing::Test { | 
| 35  public: | 34  public: | 
| 36   SendStatisticsProxyTest() | 35   SendStatisticsProxyTest() | 
| 37       : fake_clock_(1234), config_(GetTestConfig()), avg_delay_ms_(0), | 36       : fake_clock_(1234), config_(GetTestConfig()), avg_delay_ms_(0), | 
| 38         max_delay_ms_(0) {} | 37         max_delay_ms_(0) {} | 
| 39   virtual ~SendStatisticsProxyTest() {} | 38   virtual ~SendStatisticsProxyTest() {} | 
| (...skipping 268 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 308   for (uint32_t i = 1; i <= 3; ++i) { | 307   for (uint32_t i = 1; i <= 3; ++i) { | 
| 309     statistics_proxy_->OnSendEncodedImage(encoded_image, &codec_info); | 308     statistics_proxy_->OnSendEncodedImage(encoded_image, &codec_info); | 
| 310     EXPECT_EQ(i, statistics_proxy_->GetStats().frames_encoded); | 309     EXPECT_EQ(i, statistics_proxy_->GetStats().frames_encoded); | 
| 311   } | 310   } | 
| 312 } | 311 } | 
| 313 | 312 | 
| 314 TEST_F(SendStatisticsProxyTest, SwitchContentTypeUpdatesHistograms) { | 313 TEST_F(SendStatisticsProxyTest, SwitchContentTypeUpdatesHistograms) { | 
| 315   const int kWidth = 640; | 314   const int kWidth = 640; | 
| 316   const int kHeight = 480; | 315   const int kHeight = 480; | 
| 317 | 316 | 
| 318   for (int i = 0; i < kMinRequiredSamples; ++i) | 317   for (int i = 0; i < SendStatisticsProxy::kMinRequiredMetricsSamples; ++i) | 
| 319     statistics_proxy_->OnIncomingFrame(kWidth, kHeight); | 318     statistics_proxy_->OnIncomingFrame(kWidth, kHeight); | 
| 320 | 319 | 
| 321   // No switch, stats should not be updated. | 320   // No switch, stats should not be updated. | 
| 322   VideoEncoderConfig config; | 321   VideoEncoderConfig config; | 
| 323   config.content_type = VideoEncoderConfig::ContentType::kRealtimeVideo; | 322   config.content_type = VideoEncoderConfig::ContentType::kRealtimeVideo; | 
| 324   statistics_proxy_->OnEncoderReconfigured(config, 50); | 323   statistics_proxy_->OnEncoderReconfigured(config, 50); | 
| 325   EXPECT_EQ(0, metrics::NumSamples("WebRTC.Video.InputWidthInPixels")); | 324   EXPECT_EQ(0, metrics::NumSamples("WebRTC.Video.InputWidthInPixels")); | 
| 326 | 325 | 
| 327   // Switch to screenshare, real-time stats should be updated. | 326   // Switch to screenshare, real-time stats should be updated. | 
| 328   config.content_type = VideoEncoderConfig::ContentType::kScreen; | 327   config.content_type = VideoEncoderConfig::ContentType::kScreen; | 
| 329   statistics_proxy_->OnEncoderReconfigured(config, 50); | 328   statistics_proxy_->OnEncoderReconfigured(config, 50); | 
| 330   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.InputWidthInPixels")); | 329   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.InputWidthInPixels")); | 
| 331 } | 330 } | 
| 332 | 331 | 
|  | 332 TEST_F(SendStatisticsProxyTest, CpuLimitedResolutionUpdated) { | 
|  | 333   const int kWidth = 640; | 
|  | 334   const int kHeight = 480; | 
|  | 335 | 
|  | 336   for (int i = 0; i < SendStatisticsProxy::kMinRequiredMetricsSamples; ++i) | 
|  | 337     statistics_proxy_->OnIncomingFrame(kWidth, kHeight); | 
|  | 338 | 
|  | 339   statistics_proxy_->OnCpuRestrictedResolutionChanged(true); | 
|  | 340 | 
|  | 341   for (int i = 0; i < SendStatisticsProxy::kMinRequiredMetricsSamples; ++i) | 
|  | 342     statistics_proxy_->OnIncomingFrame(kWidth, kHeight); | 
|  | 343 | 
|  | 344   statistics_proxy_.reset(); | 
|  | 345   EXPECT_EQ(1, | 
|  | 346             metrics::NumSamples("WebRTC.Video.CpuLimitedResolutionInPercent")); | 
|  | 347   EXPECT_EQ( | 
|  | 348       1, metrics::NumEvents("WebRTC.Video.CpuLimitedResolutionInPercent", 50)); | 
|  | 349 } | 
|  | 350 | 
| 333 TEST_F(SendStatisticsProxyTest, LifetimeHistogramIsUpdated) { | 351 TEST_F(SendStatisticsProxyTest, LifetimeHistogramIsUpdated) { | 
| 334   const int64_t kTimeSec = 3; | 352   const int64_t kTimeSec = 3; | 
| 335   fake_clock_.AdvanceTimeMilliseconds(kTimeSec * 1000); | 353   fake_clock_.AdvanceTimeMilliseconds(kTimeSec * 1000); | 
| 336   statistics_proxy_.reset(); | 354   statistics_proxy_.reset(); | 
| 337   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.SendStreamLifetimeInSeconds")); | 355   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.SendStreamLifetimeInSeconds")); | 
| 338   EXPECT_EQ(1, metrics::NumEvents("WebRTC.Video.SendStreamLifetimeInSeconds", | 356   EXPECT_EQ(1, metrics::NumEvents("WebRTC.Video.SendStreamLifetimeInSeconds", | 
| 339                                   kTimeSec)); | 357                                   kTimeSec)); | 
| 340 } | 358 } | 
| 341 | 359 | 
| 342 TEST_F(SendStatisticsProxyTest, CodecTypeHistogramIsUpdated) { | 360 TEST_F(SendStatisticsProxyTest, CodecTypeHistogramIsUpdated) { | 
| 343   fake_clock_.AdvanceTimeMilliseconds(metrics::kMinRunTimeInSeconds * 1000); | 361   fake_clock_.AdvanceTimeMilliseconds(metrics::kMinRunTimeInSeconds * 1000); | 
| 344   statistics_proxy_.reset(); | 362   statistics_proxy_.reset(); | 
| 345   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.Encoder.CodecType")); | 363   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.Encoder.CodecType")); | 
| 346 } | 364 } | 
| 347 | 365 | 
| 348 TEST_F(SendStatisticsProxyTest, VerifyQpHistogramStats_Vp8) { | 366 TEST_F(SendStatisticsProxyTest, VerifyQpHistogramStats_Vp8) { | 
| 349   EncodedImage encoded_image; | 367   EncodedImage encoded_image; | 
| 350   CodecSpecificInfo codec_info; | 368   CodecSpecificInfo codec_info; | 
| 351   codec_info.codecType = kVideoCodecVP8; | 369   codec_info.codecType = kVideoCodecVP8; | 
| 352 | 370 | 
| 353   for (int i = 0; i < kMinRequiredSamples; ++i) { | 371   for (int i = 0; i < SendStatisticsProxy::kMinRequiredMetricsSamples; ++i) { | 
| 354     codec_info.codecSpecific.VP8.simulcastIdx = 0; | 372     codec_info.codecSpecific.VP8.simulcastIdx = 0; | 
| 355     encoded_image.qp_ = kQpIdx0; | 373     encoded_image.qp_ = kQpIdx0; | 
| 356     statistics_proxy_->OnSendEncodedImage(encoded_image, &codec_info); | 374     statistics_proxy_->OnSendEncodedImage(encoded_image, &codec_info); | 
| 357     codec_info.codecSpecific.VP8.simulcastIdx = 1; | 375     codec_info.codecSpecific.VP8.simulcastIdx = 1; | 
| 358     encoded_image.qp_ = kQpIdx1; | 376     encoded_image.qp_ = kQpIdx1; | 
| 359     statistics_proxy_->OnSendEncodedImage(encoded_image, &codec_info); | 377     statistics_proxy_->OnSendEncodedImage(encoded_image, &codec_info); | 
| 360   } | 378   } | 
| 361   statistics_proxy_.reset(); | 379   statistics_proxy_.reset(); | 
| 362   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.Encoded.Qp.Vp8.S0")); | 380   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.Encoded.Qp.Vp8.S0")); | 
| 363   EXPECT_EQ(1, metrics::NumEvents("WebRTC.Video.Encoded.Qp.Vp8.S0", kQpIdx0)); | 381   EXPECT_EQ(1, metrics::NumEvents("WebRTC.Video.Encoded.Qp.Vp8.S0", kQpIdx0)); | 
| 364   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.Encoded.Qp.Vp8.S1")); | 382   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.Encoded.Qp.Vp8.S1")); | 
| 365   EXPECT_EQ(1, metrics::NumEvents("WebRTC.Video.Encoded.Qp.Vp8.S1", kQpIdx1)); | 383   EXPECT_EQ(1, metrics::NumEvents("WebRTC.Video.Encoded.Qp.Vp8.S1", kQpIdx1)); | 
| 366 } | 384 } | 
| 367 | 385 | 
| 368 TEST_F(SendStatisticsProxyTest, VerifyQpHistogramStats_Vp8OneSsrc) { | 386 TEST_F(SendStatisticsProxyTest, VerifyQpHistogramStats_Vp8OneSsrc) { | 
| 369   VideoSendStream::Config config(nullptr); | 387   VideoSendStream::Config config(nullptr); | 
| 370   config.rtp.ssrcs.push_back(kFirstSsrc); | 388   config.rtp.ssrcs.push_back(kFirstSsrc); | 
| 371   statistics_proxy_.reset(new SendStatisticsProxy( | 389   statistics_proxy_.reset(new SendStatisticsProxy( | 
| 372       &fake_clock_, config, VideoEncoderConfig::ContentType::kRealtimeVideo)); | 390       &fake_clock_, config, VideoEncoderConfig::ContentType::kRealtimeVideo)); | 
| 373 | 391 | 
| 374   EncodedImage encoded_image; | 392   EncodedImage encoded_image; | 
| 375   CodecSpecificInfo codec_info; | 393   CodecSpecificInfo codec_info; | 
| 376   codec_info.codecType = kVideoCodecVP8; | 394   codec_info.codecType = kVideoCodecVP8; | 
| 377 | 395 | 
| 378   for (int i = 0; i < kMinRequiredSamples; ++i) { | 396   for (int i = 0; i < SendStatisticsProxy::kMinRequiredMetricsSamples; ++i) { | 
| 379     codec_info.codecSpecific.VP8.simulcastIdx = 0; | 397     codec_info.codecSpecific.VP8.simulcastIdx = 0; | 
| 380     encoded_image.qp_ = kQpIdx0; | 398     encoded_image.qp_ = kQpIdx0; | 
| 381     statistics_proxy_->OnSendEncodedImage(encoded_image, &codec_info); | 399     statistics_proxy_->OnSendEncodedImage(encoded_image, &codec_info); | 
| 382   } | 400   } | 
| 383   statistics_proxy_.reset(); | 401   statistics_proxy_.reset(); | 
| 384   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.Encoded.Qp.Vp8")); | 402   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.Encoded.Qp.Vp8")); | 
| 385   EXPECT_EQ(1, metrics::NumEvents("WebRTC.Video.Encoded.Qp.Vp8", kQpIdx0)); | 403   EXPECT_EQ(1, metrics::NumEvents("WebRTC.Video.Encoded.Qp.Vp8", kQpIdx0)); | 
| 386 } | 404 } | 
| 387 | 405 | 
| 388 TEST_F(SendStatisticsProxyTest, VerifyQpHistogramStats_Vp9) { | 406 TEST_F(SendStatisticsProxyTest, VerifyQpHistogramStats_Vp9) { | 
| 389   EncodedImage encoded_image; | 407   EncodedImage encoded_image; | 
| 390   CodecSpecificInfo codec_info; | 408   CodecSpecificInfo codec_info; | 
| 391   codec_info.codecType = kVideoCodecVP9; | 409   codec_info.codecType = kVideoCodecVP9; | 
| 392   codec_info.codecSpecific.VP9.num_spatial_layers = 2; | 410   codec_info.codecSpecific.VP9.num_spatial_layers = 2; | 
| 393 | 411 | 
| 394   for (int i = 0; i < kMinRequiredSamples; ++i) { | 412   for (int i = 0; i < SendStatisticsProxy::kMinRequiredMetricsSamples; ++i) { | 
| 395     encoded_image.qp_ = kQpIdx0; | 413     encoded_image.qp_ = kQpIdx0; | 
| 396     codec_info.codecSpecific.VP9.spatial_idx = 0; | 414     codec_info.codecSpecific.VP9.spatial_idx = 0; | 
| 397     statistics_proxy_->OnSendEncodedImage(encoded_image, &codec_info); | 415     statistics_proxy_->OnSendEncodedImage(encoded_image, &codec_info); | 
| 398     encoded_image.qp_ = kQpIdx1; | 416     encoded_image.qp_ = kQpIdx1; | 
| 399     codec_info.codecSpecific.VP9.spatial_idx = 1; | 417     codec_info.codecSpecific.VP9.spatial_idx = 1; | 
| 400     statistics_proxy_->OnSendEncodedImage(encoded_image, &codec_info); | 418     statistics_proxy_->OnSendEncodedImage(encoded_image, &codec_info); | 
| 401   } | 419   } | 
| 402   statistics_proxy_.reset(); | 420   statistics_proxy_.reset(); | 
| 403   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.Encoded.Qp.Vp9.S0")); | 421   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.Encoded.Qp.Vp9.S0")); | 
| 404   EXPECT_EQ(1, metrics::NumEvents("WebRTC.Video.Encoded.Qp.Vp9.S0", kQpIdx0)); | 422   EXPECT_EQ(1, metrics::NumEvents("WebRTC.Video.Encoded.Qp.Vp9.S0", kQpIdx0)); | 
| 405   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.Encoded.Qp.Vp9.S1")); | 423   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.Encoded.Qp.Vp9.S1")); | 
| 406   EXPECT_EQ(1, metrics::NumEvents("WebRTC.Video.Encoded.Qp.Vp9.S1", kQpIdx1)); | 424   EXPECT_EQ(1, metrics::NumEvents("WebRTC.Video.Encoded.Qp.Vp9.S1", kQpIdx1)); | 
| 407 } | 425 } | 
| 408 | 426 | 
| 409 TEST_F(SendStatisticsProxyTest, VerifyQpHistogramStats_Vp9OneSpatialLayer) { | 427 TEST_F(SendStatisticsProxyTest, VerifyQpHistogramStats_Vp9OneSpatialLayer) { | 
| 410   VideoSendStream::Config config(nullptr); | 428   VideoSendStream::Config config(nullptr); | 
| 411   config.rtp.ssrcs.push_back(kFirstSsrc); | 429   config.rtp.ssrcs.push_back(kFirstSsrc); | 
| 412   statistics_proxy_.reset(new SendStatisticsProxy( | 430   statistics_proxy_.reset(new SendStatisticsProxy( | 
| 413       &fake_clock_, config, VideoEncoderConfig::ContentType::kRealtimeVideo)); | 431       &fake_clock_, config, VideoEncoderConfig::ContentType::kRealtimeVideo)); | 
| 414 | 432 | 
| 415   EncodedImage encoded_image; | 433   EncodedImage encoded_image; | 
| 416   CodecSpecificInfo codec_info; | 434   CodecSpecificInfo codec_info; | 
| 417   codec_info.codecType = kVideoCodecVP9; | 435   codec_info.codecType = kVideoCodecVP9; | 
| 418   codec_info.codecSpecific.VP9.num_spatial_layers = 1; | 436   codec_info.codecSpecific.VP9.num_spatial_layers = 1; | 
| 419 | 437 | 
| 420   for (int i = 0; i < kMinRequiredSamples; ++i) { | 438   for (int i = 0; i < SendStatisticsProxy::kMinRequiredMetricsSamples; ++i) { | 
| 421     encoded_image.qp_ = kQpIdx0; | 439     encoded_image.qp_ = kQpIdx0; | 
| 422     codec_info.codecSpecific.VP9.spatial_idx = 0; | 440     codec_info.codecSpecific.VP9.spatial_idx = 0; | 
| 423     statistics_proxy_->OnSendEncodedImage(encoded_image, &codec_info); | 441     statistics_proxy_->OnSendEncodedImage(encoded_image, &codec_info); | 
| 424   } | 442   } | 
| 425   statistics_proxy_.reset(); | 443   statistics_proxy_.reset(); | 
| 426   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.Encoded.Qp.Vp9")); | 444   EXPECT_EQ(1, metrics::NumSamples("WebRTC.Video.Encoded.Qp.Vp9")); | 
| 427   EXPECT_EQ(1, metrics::NumEvents("WebRTC.Video.Encoded.Qp.Vp9", kQpIdx0)); | 445   EXPECT_EQ(1, metrics::NumEvents("WebRTC.Video.Encoded.Qp.Vp9", kQpIdx0)); | 
| 428 } | 446 } | 
| 429 | 447 | 
| 430 TEST_F(SendStatisticsProxyTest, NoSubstreams) { | 448 TEST_F(SendStatisticsProxyTest, NoSubstreams) { | 
| (...skipping 336 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 767 | 785 | 
| 768   EXPECT_EQ( | 786   EXPECT_EQ( | 
| 769       1, metrics::NumSamples("WebRTC.Video.Screenshare.FecBitrateSentInKbps")); | 787       1, metrics::NumSamples("WebRTC.Video.Screenshare.FecBitrateSentInKbps")); | 
| 770   EXPECT_EQ(1, metrics::NumEvents( | 788   EXPECT_EQ(1, metrics::NumEvents( | 
| 771                    "WebRTC.Video.Screenshare.FecBitrateSentInKbps", | 789                    "WebRTC.Video.Screenshare.FecBitrateSentInKbps", | 
| 772                    static_cast<int>((rtx_counters.fec.TotalBytes() * 2 * 8) / | 790                    static_cast<int>((rtx_counters.fec.TotalBytes() * 2 * 8) / | 
| 773                                     metrics::kMinRunTimeInSeconds / 1000))); | 791                                     metrics::kMinRunTimeInSeconds / 1000))); | 
| 774 } | 792 } | 
| 775 | 793 | 
| 776 }  // namespace webrtc | 794 }  // namespace webrtc | 
| OLD | NEW | 
|---|