Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(706)

Side by Side Diff: webrtc/media/base/videoadapter.cc

Issue 1695263002: Move direct use of VideoCapturer::VideoAdapter to VideoSinkWants. (Closed) Base URL: https://chromium.googlesource.com/external/webrtc.git@master
Patch Set: Tried to address pthatchers comments. Created 4 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 /* 1 /*
2 * Copyright (c) 2010 The WebRTC project authors. All Rights Reserved. 2 * Copyright (c) 2010 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/media/base/videoadapter.h" 11 #include "webrtc/media/base/videoadapter.h"
12 12
13 #include <limits.h> // For INT_MAX 13 #include <limits.h> // For INT_MAX
14 #include <algorithm> 14 #include <algorithm>
15 15
16 #include "webrtc/base/logging.h" 16 #include "webrtc/base/logging.h"
17 #include "webrtc/base/timeutils.h" 17 #include "webrtc/base/timeutils.h"
18 #include "webrtc/media/base/constants.h" 18 #include "webrtc/media/base/constants.h"
19 #include "webrtc/media/base/videocommon.h" 19 #include "webrtc/media/base/videocommon.h"
20 #include "webrtc/media/base/videoframe.h" 20 #include "webrtc/media/base/videoframe.h"
21 21
22 namespace cricket { 22 namespace cricket {
23 23
24 // TODO(fbarchard): Make downgrades settable
25 static const int kMaxCpuDowngrades = 2; // Downgrade at most 2 times for CPU.
26 // The number of cpu samples to require before adapting. This value depends on
27 // the cpu monitor sampling frequency being 2000ms.
28 static const int kCpuLoadMinSamples = 3;
29 // The amount of weight to give to each new cpu load sample. The lower the
30 // value, the slower we'll adapt to changing cpu conditions.
31 static const float kCpuLoadWeightCoefficient = 0.4f;
32 // The seed value for the cpu load moving average.
33 static const float kCpuLoadInitialAverage = 0.5f;
34
35 // Desktop needs 1/8 scale for HD (1280 x 720) to QQVGA (160 x 90) 24 // Desktop needs 1/8 scale for HD (1280 x 720) to QQVGA (160 x 90)
36 static const float kScaleFactors[] = { 25 static const float kScaleFactors[] = {
37 1.f / 1.f, // Full size. 26 1.f / 1.f, // Full size.
38 3.f / 4.f, // 3/4 scale. 27 3.f / 4.f, // 3/4 scale.
39 1.f / 2.f, // 1/2 scale. 28 1.f / 2.f, // 1/2 scale.
40 3.f / 8.f, // 3/8 scale. 29 3.f / 8.f, // 3/8 scale.
41 1.f / 4.f, // 1/4 scale. 30 1.f / 4.f, // 1/4 scale.
42 3.f / 16.f, // 3/16 scale. 31 3.f / 16.f, // 3/16 scale.
43 1.f / 8.f, // 1/8 scale. 32 1.f / 8.f, // 1/8 scale.
44 0.f // End of table. 33 0.f // End of table.
(...skipping 146 matching lines...) Expand 10 before | Expand all | Expand 10 after
191 LOG(LS_INFO) << "VAdapt Input Resolution Change: " 180 LOG(LS_INFO) << "VAdapt Input Resolution Change: "
192 << "Previous input resolution: " 181 << "Previous input resolution: "
193 << previous_width << "x" << previous_height 182 << previous_width << "x" << previous_height
194 << " New input resolution: " 183 << " New input resolution: "
195 << format.width << "x" << format.height 184 << format.width << "x" << format.height
196 << " New output resolution: " 185 << " New output resolution: "
197 << width << "x" << height; 186 << width << "x" << height;
198 } 187 }
199 } 188 }
200 189
201 void CoordinatedVideoAdapter::set_cpu_smoothing(bool enable) {
202 LOG(LS_INFO) << "CPU smoothing is now "
203 << (enable ? "enabled" : "disabled");
204 cpu_smoothing_ = enable;
205 }
206
207 void VideoAdapter::SetOutputFormat(const VideoFormat& format) { 190 void VideoAdapter::SetOutputFormat(const VideoFormat& format) {
208 rtc::CritScope cs(&critical_section_); 191 rtc::CritScope cs(&critical_section_);
209 int64_t old_output_interval = output_format_.interval; 192 int64_t old_output_interval = output_format_.interval;
210 output_format_ = format; 193 output_format_ = format;
211 output_num_pixels_ = output_format_.width * output_format_.height; 194 output_num_pixels_ = output_format_.width * output_format_.height;
212 output_format_.interval = 195 output_format_.interval =
213 std::max(output_format_.interval, input_format_.interval); 196 std::max(output_format_.interval, input_format_.interval);
214 if (old_output_interval != output_format_.interval) { 197 if (old_output_interval != output_format_.interval) {
215 LOG(LS_INFO) << "VAdapt output interval changed from " 198 LOG(LS_INFO) << "VAdapt output interval changed from "
216 << old_output_interval << " to " << output_format_.interval; 199 << old_output_interval << " to " << output_format_.interval;
(...skipping 122 matching lines...) Expand 10 before | Expand all | Expand 10 after
339 } 322 }
340 323
341 /////////////////////////////////////////////////////////////////////// 324 ///////////////////////////////////////////////////////////////////////
342 // Implementation of CoordinatedVideoAdapter 325 // Implementation of CoordinatedVideoAdapter
343 CoordinatedVideoAdapter::CoordinatedVideoAdapter() 326 CoordinatedVideoAdapter::CoordinatedVideoAdapter()
344 : cpu_adaptation_(true), 327 : cpu_adaptation_(true),
345 cpu_smoothing_(false), 328 cpu_smoothing_(false),
346 gd_adaptation_(true), 329 gd_adaptation_(true),
347 view_adaptation_(true), 330 view_adaptation_(true),
348 view_switch_(false), 331 view_switch_(false),
349 cpu_downgrade_count_(0),
350 cpu_load_min_samples_(kCpuLoadMinSamples),
351 cpu_load_num_samples_(0),
352 high_system_threshold_(kHighSystemCpuThreshold),
353 low_system_threshold_(kLowSystemCpuThreshold),
354 process_threshold_(kProcessCpuThreshold),
355 view_desired_num_pixels_(INT_MAX), 332 view_desired_num_pixels_(INT_MAX),
356 view_desired_interval_(0), 333 view_desired_interval_(0),
357 encoder_desired_num_pixels_(INT_MAX), 334 encoder_desired_num_pixels_(INT_MAX),
358 cpu_desired_num_pixels_(INT_MAX), 335 cpu_desired_num_pixels_(INT_MAX),
359 adapt_reason_(ADAPTREASON_NONE), 336 adapt_reason_(ADAPTREASON_NONE) {}
360 system_load_average_(kCpuLoadInitialAverage) {
361 }
362 337
363 // Helper function to UPGRADE or DOWNGRADE a number of pixels 338 // Helper function to UPGRADE or DOWNGRADE a number of pixels
364 void CoordinatedVideoAdapter::StepPixelCount( 339 void CoordinatedVideoAdapter::StepPixelCount(
365 CoordinatedVideoAdapter::AdaptRequest request, 340 CoordinatedVideoAdapter::AdaptRequest request,
366 int* num_pixels) { 341 int* num_pixels) {
367 switch (request) { 342 switch (request) {
368 case CoordinatedVideoAdapter::DOWNGRADE: 343 case CoordinatedVideoAdapter::DOWNGRADE:
369 *num_pixels /= 2; 344 *num_pixels /= 2;
370 break; 345 break;
371 346
372 case CoordinatedVideoAdapter::UPGRADE: 347 case CoordinatedVideoAdapter::UPGRADE:
373 *num_pixels *= 2; 348 *num_pixels *= 2;
374 break; 349 break;
375 350
376 default: // No change in pixel count 351 default: // No change in pixel count
377 break; 352 break;
378 } 353 }
379 return; 354 return;
380 } 355 }
381 356
382 // Find the adaptation request of the cpu based on the load. Return UPGRADE if
383 // the load is low, DOWNGRADE if the load is high, and KEEP otherwise.
384 CoordinatedVideoAdapter::AdaptRequest CoordinatedVideoAdapter::FindCpuRequest(
385 int current_cpus, int max_cpus,
386 float process_load, float system_load) {
387 // Downgrade if system is high and plugin is at least more than midrange.
388 if (system_load >= high_system_threshold_ * max_cpus &&
389 process_load >= process_threshold_ * current_cpus) {
390 return CoordinatedVideoAdapter::DOWNGRADE;
391 // Upgrade if system is low.
392 } else if (system_load < low_system_threshold_ * max_cpus) {
393 return CoordinatedVideoAdapter::UPGRADE;
394 }
395 return CoordinatedVideoAdapter::KEEP;
396 }
397 357
398 // A remote view request for a new resolution. 358 // A remote view request for a new resolution.
399 void CoordinatedVideoAdapter::OnOutputFormatRequest(const VideoFormat& format) { 359 void CoordinatedVideoAdapter::OnOutputFormatRequest(const VideoFormat& format) {
400 rtc::CritScope cs(&request_critical_section_); 360 rtc::CritScope cs(&request_critical_section_);
401 if (!view_adaptation_) { 361 if (!view_adaptation_) {
402 return; 362 return;
403 } 363 }
404 // Set output for initial aspect ratio in mediachannel unittests. 364 // Set output for initial aspect ratio in mediachannel unittests.
405 int old_num_pixels = GetOutputNumPixels(); 365 int old_num_pixels = GetOutputNumPixels();
406 SetOutputFormat(format); 366 SetOutputFormat(format);
407 SetOutputNumPixels(old_num_pixels); 367 SetOutputNumPixels(old_num_pixels);
408 view_desired_num_pixels_ = format.width * format.height; 368 view_desired_num_pixels_ = format.width * format.height;
409 view_desired_interval_ = format.interval; 369 view_desired_interval_ = format.interval;
410 int new_width, new_height; 370 int new_width, new_height;
411 bool changed = AdaptToMinimumFormat(&new_width, &new_height); 371 bool changed = AdaptToMinimumFormat(&new_width, &new_height);
412 LOG(LS_INFO) << "VAdapt View Request: " 372 LOG(LS_INFO) << "VAdapt View Request: "
413 << format.width << "x" << format.height 373 << format.width << "x" << format.height
414 << " Pixels: " << view_desired_num_pixels_ 374 << " Pixels: " << view_desired_num_pixels_
415 << " Changed: " << (changed ? "true" : "false") 375 << " Changed: " << (changed ? "true" : "false")
416 << " To: " << new_width << "x" << new_height; 376 << " To: " << new_width << "x" << new_height;
417 } 377 }
418 378
419 void CoordinatedVideoAdapter::set_cpu_load_min_samples(
420 int cpu_load_min_samples) {
421 if (cpu_load_min_samples_ != cpu_load_min_samples) {
422 LOG(LS_INFO) << "VAdapt Change Cpu Adapt Min Samples from: "
423 << cpu_load_min_samples_ << " to "
424 << cpu_load_min_samples;
425 cpu_load_min_samples_ = cpu_load_min_samples;
426 }
427 }
428
429 void CoordinatedVideoAdapter::set_high_system_threshold(
430 float high_system_threshold) {
431 ASSERT(high_system_threshold <= 1.0f);
432 ASSERT(high_system_threshold >= 0.0f);
433 if (high_system_threshold_ != high_system_threshold) {
434 LOG(LS_INFO) << "VAdapt Change High System Threshold from: "
435 << high_system_threshold_ << " to " << high_system_threshold;
436 high_system_threshold_ = high_system_threshold;
437 }
438 }
439
440 void CoordinatedVideoAdapter::set_low_system_threshold(
441 float low_system_threshold) {
442 ASSERT(low_system_threshold <= 1.0f);
443 ASSERT(low_system_threshold >= 0.0f);
444 if (low_system_threshold_ != low_system_threshold) {
445 LOG(LS_INFO) << "VAdapt Change Low System Threshold from: "
446 << low_system_threshold_ << " to " << low_system_threshold;
447 low_system_threshold_ = low_system_threshold;
448 }
449 }
450
451 void CoordinatedVideoAdapter::set_process_threshold(float process_threshold) {
452 ASSERT(process_threshold <= 1.0f);
453 ASSERT(process_threshold >= 0.0f);
454 if (process_threshold_ != process_threshold) {
455 LOG(LS_INFO) << "VAdapt Change High Process Threshold from: "
456 << process_threshold_ << " to " << process_threshold;
457 process_threshold_ = process_threshold;
458 }
459 }
460
461 // A Bandwidth GD request for new resolution 379 // A Bandwidth GD request for new resolution
462 void CoordinatedVideoAdapter::OnEncoderResolutionRequest( 380 void CoordinatedVideoAdapter::OnEncoderResolutionRequest(
463 int width, int height, AdaptRequest request) { 381 int width, int height, AdaptRequest request) {
464 rtc::CritScope cs(&request_critical_section_); 382 rtc::CritScope cs(&request_critical_section_);
465 if (!gd_adaptation_) { 383 if (!gd_adaptation_) {
466 return; 384 return;
467 } 385 }
468 int old_encoder_desired_num_pixels = encoder_desired_num_pixels_; 386 int old_encoder_desired_num_pixels = encoder_desired_num_pixels_;
469 if (KEEP != request) { 387 if (KEEP != request) {
470 int new_encoder_desired_num_pixels = width * height; 388 int new_encoder_desired_num_pixels = width * height;
(...skipping 17 matching lines...) Expand all
488 406
489 LOG(LS_INFO) << "VAdapt GD Request: " 407 LOG(LS_INFO) << "VAdapt GD Request: "
490 << (DOWNGRADE == request ? "down" : 408 << (DOWNGRADE == request ? "down" :
491 (UPGRADE == request ? "up" : "keep")) 409 (UPGRADE == request ? "up" : "keep"))
492 << " From: " << width << "x" << height 410 << " From: " << width << "x" << height
493 << " Pixels: " << encoder_desired_num_pixels_ 411 << " Pixels: " << encoder_desired_num_pixels_
494 << " Changed: " << (changed ? "true" : "false") 412 << " Changed: " << (changed ? "true" : "false")
495 << " To: " << new_width << "x" << new_height; 413 << " To: " << new_width << "x" << new_height;
496 } 414 }
497 415
498 // A Bandwidth GD request for new resolution 416 void CoordinatedVideoAdapter::OnLimitResolution(int max_number_of_pixels) {
499 void CoordinatedVideoAdapter::OnCpuResolutionRequest(AdaptRequest request) {
500 rtc::CritScope cs(&request_critical_section_); 417 rtc::CritScope cs(&request_critical_section_);
501 if (!cpu_adaptation_) { 418 if (!cpu_adaptation_) {
502 return; 419 return;
503 } 420 }
504 // Update how many times we have downgraded due to the cpu load. 421
505 switch (request) { 422 const VideoFormat& input = input_format();
506 case DOWNGRADE: 423 if (input.IsSize0x0()) {
507 // Ignore downgrades if we have downgraded the maximum times. 424 // TODO NOW.... Make sure AdaptToMinimumFormat can be called before first
508 if (cpu_downgrade_count_ < kMaxCpuDowngrades) { 425 // frame....
509 ++cpu_downgrade_count_; 426 return;
510 } else {
511 LOG(LS_VERBOSE) << "VAdapt CPU load high but do not downgrade "
512 "because maximum downgrades reached";
513 SignalCpuAdaptationUnable();
514 }
515 break;
516 case UPGRADE:
517 if (cpu_downgrade_count_ > 0) {
518 bool is_min = IsMinimumFormat(cpu_desired_num_pixels_);
519 if (is_min) {
520 --cpu_downgrade_count_;
521 } else {
522 LOG(LS_VERBOSE) << "VAdapt CPU load low but do not upgrade "
523 "because cpu is not limiting resolution";
524 }
525 } else {
526 LOG(LS_VERBOSE) << "VAdapt CPU load low but do not upgrade "
527 "because minimum downgrades reached";
528 }
529 break;
530 case KEEP:
531 default:
532 break;
533 } 427 }
534 if (KEEP != request) { 428 cpu_desired_num_pixels_ =
535 // TODO(fbarchard): compute stepping up/down from OutputNumPixels but 429 std::min(input.width * input.height, max_number_of_pixels);
536 // clamp to inputpixels / 4 (2 steps) 430
537 cpu_desired_num_pixels_ = cpu_downgrade_count_ == 0 ? INT_MAX :
538 static_cast<int>(input_format().width * input_format().height >>
539 cpu_downgrade_count_);
540 }
541 int new_width, new_height; 431 int new_width, new_height;
542 bool changed = AdaptToMinimumFormat(&new_width, &new_height); 432 bool changed = AdaptToMinimumFormat(&new_width, &new_height);
543 LOG(LS_INFO) << "VAdapt CPU Request: " 433 LOG(LS_INFO) << "VAdapt OnLimitResolution: "
544 << (DOWNGRADE == request ? "down" :
545 (UPGRADE == request ? "up" : "keep"))
546 << " Steps: " << cpu_downgrade_count_
547 << " Changed: " << (changed ? "true" : "false") 434 << " Changed: " << (changed ? "true" : "false")
548 << " To: " << new_width << "x" << new_height; 435 << " To: " << new_width << "x" << new_height;
549 } 436 }
550 437
551 // A CPU request for new resolution
552 // TODO(fbarchard): Move outside adapter.
553 void CoordinatedVideoAdapter::OnCpuLoadUpdated(
554 int current_cpus, int max_cpus, float process_load, float system_load) {
555 rtc::CritScope cs(&request_critical_section_);
556 if (!cpu_adaptation_) {
557 return;
558 }
559 // Update the moving average of system load. Even if we aren't smoothing,
560 // we'll still calculate this information, in case smoothing is later enabled.
561 system_load_average_ = kCpuLoadWeightCoefficient * system_load +
562 (1.0f - kCpuLoadWeightCoefficient) * system_load_average_;
563 ++cpu_load_num_samples_;
564 if (cpu_smoothing_) {
565 system_load = system_load_average_;
566 }
567 AdaptRequest request = FindCpuRequest(current_cpus, max_cpus,
568 process_load, system_load);
569 // Make sure we're not adapting too quickly.
570 if (request != KEEP) {
571 if (cpu_load_num_samples_ < cpu_load_min_samples_) {
572 LOG(LS_VERBOSE) << "VAdapt CPU load high/low but do not adapt until "
573 << (cpu_load_min_samples_ - cpu_load_num_samples_)
574 << " more samples";
575 request = KEEP;
576 }
577 }
578
579 OnCpuResolutionRequest(request);
580 }
581
582 // Called by cpu adapter on up requests. 438 // Called by cpu adapter on up requests.
583 bool CoordinatedVideoAdapter::IsMinimumFormat(int pixels) { 439 bool CoordinatedVideoAdapter::IsMinimumFormat(int pixels) {
584 // Find closest scale factor that matches input resolution to min_num_pixels 440 // Find closest scale factor that matches input resolution to min_num_pixels
585 // and set that for output resolution. This is not needed for VideoAdapter, 441 // and set that for output resolution. This is not needed for VideoAdapter,
586 // but provides feedback to unittests and users on expected resolution. 442 // but provides feedback to unittests and users on expected resolution.
587 // Actual resolution is based on input frame. 443 // Actual resolution is based on input frame.
588 VideoFormat new_output = output_format(); 444 VideoFormat new_output = output_format();
589 VideoFormat input = input_format(); 445 VideoFormat input = input_format();
590 if (input_format().IsSize0x0()) { 446 if (input_format().IsSize0x0()) {
591 input = new_output; 447 input = new_output;
(...skipping 90 matching lines...) Expand 10 before | Expand all | Expand 10 after
682 << " CPU: " << cpu_desired_num_pixels_ 538 << " CPU: " << cpu_desired_num_pixels_
683 << " Pixels: " << min_num_pixels 539 << " Pixels: " << min_num_pixels
684 << " Input: " << input.width 540 << " Input: " << input.width
685 << "x" << input.height 541 << "x" << input.height
686 << " Scale: " << scale 542 << " Scale: " << scale
687 << " Resolution: " << new_output.width 543 << " Resolution: " << new_output.width
688 << "x" << new_output.height 544 << "x" << new_output.height
689 << " Changed: " << (changed ? "true" : "false") 545 << " Changed: " << (changed ? "true" : "false")
690 << " Reason: " << kReasons[adapt_reason_]; 546 << " Reason: " << kReasons[adapt_reason_];
691 547
692 if (changed) {
693 // When any adaptation occurs, historic CPU load levels are no longer
694 // accurate. Clear out our state so we can re-learn at the new normal.
695 cpu_load_num_samples_ = 0;
696 system_load_average_ = kCpuLoadInitialAverage;
697 }
698
699 return changed; 548 return changed;
700 } 549 }
701 550
702 } // namespace cricket 551 } // namespace cricket
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698