OLD | NEW |
1 /* | 1 /* |
2 * Copyright (c) 2014 The WebRTC project authors. All Rights Reserved. | 2 * Copyright (c) 2014 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/engine/webrtcvideoengine2.h" | 11 #include "webrtc/media/engine/webrtcvideoengine2.h" |
12 | 12 |
13 #include <stdio.h> | 13 #include <stdio.h> |
14 #include <algorithm> | 14 #include <algorithm> |
15 #include <set> | 15 #include <set> |
16 #include <string> | 16 #include <string> |
17 #include <utility> | 17 #include <utility> |
18 | 18 |
19 #include "webrtc/base/copyonwritebuffer.h" | 19 #include "webrtc/base/copyonwritebuffer.h" |
20 #include "webrtc/base/logging.h" | 20 #include "webrtc/base/logging.h" |
21 #include "webrtc/base/stringutils.h" | 21 #include "webrtc/base/stringutils.h" |
22 #include "webrtc/base/timeutils.h" | 22 #include "webrtc/base/timeutils.h" |
23 #include "webrtc/base/trace_event.h" | 23 #include "webrtc/base/trace_event.h" |
24 #include "webrtc/call.h" | 24 #include "webrtc/call.h" |
25 #include "webrtc/common_video/h264/profile_level_id.h" | 25 #include "webrtc/common_video/h264/profile_level_id.h" |
26 #include "webrtc/media/engine/constants.h" | 26 #include "webrtc/media/engine/constants.h" |
| 27 #include "webrtc/media/engine/internalencoderfactory.h" |
27 #include "webrtc/media/engine/simulcast.h" | 28 #include "webrtc/media/engine/simulcast.h" |
28 #include "webrtc/media/engine/videoencodersoftwarefallbackwrapper.h" | 29 #include "webrtc/media/engine/videoencodersoftwarefallbackwrapper.h" |
29 #include "webrtc/media/engine/webrtcmediaengine.h" | 30 #include "webrtc/media/engine/webrtcmediaengine.h" |
30 #include "webrtc/media/engine/webrtcvideoencoderfactory.h" | 31 #include "webrtc/media/engine/webrtcvideoencoderfactory.h" |
31 #include "webrtc/media/engine/webrtcvoiceengine.h" | 32 #include "webrtc/media/engine/webrtcvoiceengine.h" |
32 #include "webrtc/modules/video_coding/codecs/h264/include/h264.h" | |
33 #include "webrtc/modules/video_coding/codecs/vp8/simulcast_encoder_adapter.h" | 33 #include "webrtc/modules/video_coding/codecs/vp8/simulcast_encoder_adapter.h" |
34 #include "webrtc/modules/video_coding/codecs/vp9/include/vp9.h" | |
35 #include "webrtc/system_wrappers/include/field_trial.h" | 34 #include "webrtc/system_wrappers/include/field_trial.h" |
36 #include "webrtc/video_decoder.h" | 35 #include "webrtc/video_decoder.h" |
37 #include "webrtc/video_encoder.h" | 36 #include "webrtc/video_encoder.h" |
38 | 37 |
39 namespace cricket { | 38 namespace cricket { |
40 namespace { | 39 namespace { |
41 | 40 |
42 // Wrap cricket::WebRtcVideoEncoderFactory as a webrtc::VideoEncoderFactory. | 41 // Wrap cricket::WebRtcVideoEncoderFactory as a webrtc::VideoEncoderFactory. |
43 class EncoderFactoryAdapter : public webrtc::VideoEncoderFactory { | 42 class EncoderFactoryAdapter : public webrtc::VideoEncoderFactory { |
44 public: | 43 public: |
(...skipping 118 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
163 | 162 |
164 void AddDefaultFeedbackParams(VideoCodec* codec) { | 163 void AddDefaultFeedbackParams(VideoCodec* codec) { |
165 codec->AddFeedbackParam(FeedbackParam(kRtcpFbParamCcm, kRtcpFbCcmParamFir)); | 164 codec->AddFeedbackParam(FeedbackParam(kRtcpFbParamCcm, kRtcpFbCcmParamFir)); |
166 codec->AddFeedbackParam(FeedbackParam(kRtcpFbParamNack, kParamValueEmpty)); | 165 codec->AddFeedbackParam(FeedbackParam(kRtcpFbParamNack, kParamValueEmpty)); |
167 codec->AddFeedbackParam(FeedbackParam(kRtcpFbParamNack, kRtcpFbNackParamPli)); | 166 codec->AddFeedbackParam(FeedbackParam(kRtcpFbParamNack, kRtcpFbNackParamPli)); |
168 codec->AddFeedbackParam(FeedbackParam(kRtcpFbParamRemb, kParamValueEmpty)); | 167 codec->AddFeedbackParam(FeedbackParam(kRtcpFbParamRemb, kParamValueEmpty)); |
169 codec->AddFeedbackParam( | 168 codec->AddFeedbackParam( |
170 FeedbackParam(kRtcpFbParamTransportCc, kParamValueEmpty)); | 169 FeedbackParam(kRtcpFbParamTransportCc, kParamValueEmpty)); |
171 } | 170 } |
172 | 171 |
173 static VideoCodec MakeVideoCodecWithDefaultFeedbackParams(int payload_type, | |
174 const char* name) { | |
175 VideoCodec codec(payload_type, name); | |
176 AddDefaultFeedbackParams(&codec); | |
177 return codec; | |
178 } | |
179 | |
180 static std::string CodecVectorToString(const std::vector<VideoCodec>& codecs) { | 172 static std::string CodecVectorToString(const std::vector<VideoCodec>& codecs) { |
181 std::stringstream out; | 173 std::stringstream out; |
182 out << '{'; | 174 out << '{'; |
183 for (size_t i = 0; i < codecs.size(); ++i) { | 175 for (size_t i = 0; i < codecs.size(); ++i) { |
184 out << codecs[i].ToString(); | 176 out << codecs[i].ToString(); |
185 if (i != codecs.size() - 1) { | 177 if (i != codecs.size() - 1) { |
186 out << ", "; | 178 out << ", "; |
187 } | 179 } |
188 } | 180 } |
189 out << '}'; | 181 out << '}'; |
(...skipping 195 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
385 // duration hasn't been implemented. | 377 // duration hasn't been implemented. |
386 static const int kNackHistoryMs = 1000; | 378 static const int kNackHistoryMs = 1000; |
387 | 379 |
388 static const int kDefaultQpMax = 56; | 380 static const int kDefaultQpMax = 56; |
389 | 381 |
390 static const int kDefaultRtcpReceiverReportSsrc = 1; | 382 static const int kDefaultRtcpReceiverReportSsrc = 1; |
391 | 383 |
392 // Minimum time interval for logging stats. | 384 // Minimum time interval for logging stats. |
393 static const int64_t kStatsLogIntervalMs = 10000; | 385 static const int64_t kStatsLogIntervalMs = 10000; |
394 | 386 |
395 // Adds |codec| to |list|, and also adds an RTX codec if |codec|'s name is | |
396 // recognized. | |
397 // TODO(deadbeef): Should we add RTX codecs for external codecs whose names we | |
398 // don't recognize? | |
399 void AddCodecAndMaybeRtxCodec(const VideoCodec& codec, | |
400 std::vector<VideoCodec>* codecs) { | |
401 codecs->push_back(codec); | |
402 int rtx_payload_type = 0; | |
403 if (CodecNamesEq(codec.name, kVp8CodecName)) { | |
404 rtx_payload_type = kDefaultRtxVp8PlType; | |
405 } else if (CodecNamesEq(codec.name, kVp9CodecName)) { | |
406 rtx_payload_type = kDefaultRtxVp9PlType; | |
407 } else if (CodecNamesEq(codec.name, kH264CodecName)) { | |
408 // Parse H264 profile. | |
409 const rtc::Optional<webrtc::H264::ProfileLevelId> profile_level_id = | |
410 webrtc::H264::ParseSdpProfileLevelId(codec.params); | |
411 if (!profile_level_id) | |
412 return; | |
413 const webrtc::H264::Profile profile = profile_level_id->profile; | |
414 // In H.264, we only support rtx for constrained baseline and constrained | |
415 // high profile. | |
416 if (profile == webrtc::H264::kProfileConstrainedBaseline) { | |
417 rtx_payload_type = kDefaultRtxH264ConstrainedBaselinePlType; | |
418 } else if (profile == webrtc::H264::kProfileConstrainedHigh) { | |
419 rtx_payload_type = kDefaultRtxH264ConstrainedHighPlType; | |
420 } else { | |
421 return; | |
422 } | |
423 } else if (CodecNamesEq(codec.name, kRedCodecName)) { | |
424 rtx_payload_type = kDefaultRtxRedPlType; | |
425 } else { | |
426 return; | |
427 } | |
428 codecs->push_back(VideoCodec::CreateRtxCodec(rtx_payload_type, codec.id)); | |
429 } | |
430 | |
431 std::vector<VideoCodec> DefaultVideoCodecList() { | |
432 std::vector<VideoCodec> codecs; | |
433 AddCodecAndMaybeRtxCodec( | |
434 MakeVideoCodecWithDefaultFeedbackParams(kDefaultVp8PlType, kVp8CodecName), | |
435 &codecs); | |
436 if (webrtc::VP9Encoder::IsSupported() && webrtc::VP9Decoder::IsSupported()) { | |
437 AddCodecAndMaybeRtxCodec(MakeVideoCodecWithDefaultFeedbackParams( | |
438 kDefaultVp9PlType, kVp9CodecName), | |
439 &codecs); | |
440 } | |
441 if (webrtc::H264Encoder::IsSupported() && | |
442 webrtc::H264Decoder::IsSupported()) { | |
443 VideoCodec codec = MakeVideoCodecWithDefaultFeedbackParams( | |
444 kDefaultH264PlType, kH264CodecName); | |
445 // TODO(hta): Move all parameter generation for SDP into the codec | |
446 // implementation, for all codecs and parameters. | |
447 // TODO(hta): Move selection of profile-level-id to H.264 codec | |
448 // implementation. | |
449 // TODO(hta): Set FMTP parameters for all codecs of type H264. | |
450 codec.SetParam(kH264FmtpProfileLevelId, | |
451 kH264ProfileLevelConstrainedBaseline); | |
452 codec.SetParam(kH264FmtpLevelAsymmetryAllowed, "1"); | |
453 codec.SetParam(kH264FmtpPacketizationMode, "1"); | |
454 AddCodecAndMaybeRtxCodec(codec, &codecs); | |
455 } | |
456 AddCodecAndMaybeRtxCodec(VideoCodec(kDefaultRedPlType, kRedCodecName), | |
457 &codecs); | |
458 codecs.push_back(VideoCodec(kDefaultUlpfecType, kUlpfecCodecName)); | |
459 return codecs; | |
460 } | |
461 | |
462 static std::vector<VideoCodec> GetSupportedCodecs( | 387 static std::vector<VideoCodec> GetSupportedCodecs( |
463 const WebRtcVideoEncoderFactory* external_encoder_factory); | 388 const WebRtcVideoEncoderFactory* external_encoder_factory); |
464 | 389 |
465 rtc::scoped_refptr<webrtc::VideoEncoderConfig::EncoderSpecificSettings> | 390 rtc::scoped_refptr<webrtc::VideoEncoderConfig::EncoderSpecificSettings> |
466 WebRtcVideoChannel2::WebRtcVideoSendStream::ConfigureVideoEncoderSettings( | 391 WebRtcVideoChannel2::WebRtcVideoSendStream::ConfigureVideoEncoderSettings( |
467 const VideoCodec& codec) { | 392 const VideoCodec& codec) { |
468 RTC_DCHECK_RUN_ON(&thread_checker_); | 393 RTC_DCHECK_RUN_ON(&thread_checker_); |
469 bool is_screencast = parameters_.options.is_screencast.value_or(false); | 394 bool is_screencast = parameters_.options.is_screencast.value_or(false); |
470 // No automatic resizing when using simulcast or screencast. | 395 // No automatic resizing when using simulcast or screencast. |
471 bool automatic_resize = | 396 bool automatic_resize = |
(...skipping 155 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
627 encoder_factory->supported_codecs())) { | 552 encoder_factory->supported_codecs())) { |
628 simulcast_encoder_factory_.reset( | 553 simulcast_encoder_factory_.reset( |
629 new WebRtcSimulcastEncoderFactory(encoder_factory)); | 554 new WebRtcSimulcastEncoderFactory(encoder_factory)); |
630 encoder_factory = simulcast_encoder_factory_.get(); | 555 encoder_factory = simulcast_encoder_factory_.get(); |
631 } | 556 } |
632 external_encoder_factory_ = encoder_factory; | 557 external_encoder_factory_ = encoder_factory; |
633 | 558 |
634 video_codecs_ = GetSupportedCodecs(encoder_factory); | 559 video_codecs_ = GetSupportedCodecs(encoder_factory); |
635 } | 560 } |
636 | 561 |
| 562 // This is a helper function for AppendVideoCodecs below. It will return the |
| 563 // first unused dynamic payload type (in the range [96, 127]), or nothing if no |
| 564 // payload type is unused. |
| 565 static rtc::Optional<int> NextFreePayloadType( |
| 566 const std::vector<VideoCodec>& codecs) { |
| 567 static const int kFirstDynamicPayloadType = 96; |
| 568 static const int kLastDynamicPayloadType = 127; |
| 569 bool is_payload_used[1 + kLastDynamicPayloadType - kFirstDynamicPayloadType] = |
| 570 {false}; |
| 571 for (const VideoCodec& codec : codecs) { |
| 572 if (kFirstDynamicPayloadType <= codec.id && |
| 573 codec.id <= kLastDynamicPayloadType) { |
| 574 is_payload_used[codec.id - kFirstDynamicPayloadType] = true; |
| 575 } |
| 576 } |
| 577 for (int i = kFirstDynamicPayloadType; i <= kLastDynamicPayloadType; ++i) { |
| 578 if (!is_payload_used[i - kFirstDynamicPayloadType]) |
| 579 return rtc::Optional<int>(i); |
| 580 } |
| 581 // No free payload type. |
| 582 return rtc::Optional<int>(); |
| 583 } |
| 584 |
| 585 // This is a helper function for GetSupportedCodecs below. It will append new |
| 586 // unique codecs from |input_codecs| to |unified_codecs|. It will add default |
| 587 // feedback params to the codecs and will also add an associated RTX codec for |
| 588 // recognized codecs (VP8, VP9, H264, and Red). |
| 589 static void AppendVideoCodecs(const std::vector<VideoCodec>& input_codecs, |
| 590 std::vector<VideoCodec>* unified_codecs) { |
| 591 for (VideoCodec codec : input_codecs) { |
| 592 const rtc::Optional<int> payload_type = |
| 593 NextFreePayloadType(*unified_codecs); |
| 594 if (!payload_type) |
| 595 return; |
| 596 codec.id = *payload_type; |
| 597 // TODO(magjed): Move the responsibility of setting these parameters to the |
| 598 // encoder factories instead. |
| 599 if (codec.name != kRedCodecName && codec.name != kUlpfecCodecName) |
| 600 AddDefaultFeedbackParams(&codec); |
| 601 // Don't add same codec twice. |
| 602 if (FindMatchingCodec(*unified_codecs, codec)) |
| 603 continue; |
| 604 |
| 605 unified_codecs->push_back(codec); |
| 606 |
| 607 // Add associated RTX codec for recognized codecs. |
| 608 // TODO(deadbeef): Should we add RTX codecs for external codecs whose names |
| 609 // we don't recognize? |
| 610 if (CodecNamesEq(codec.name, kVp8CodecName) || |
| 611 CodecNamesEq(codec.name, kVp9CodecName) || |
| 612 CodecNamesEq(codec.name, kH264CodecName) || |
| 613 CodecNamesEq(codec.name, kRedCodecName)) { |
| 614 const rtc::Optional<int> rtx_payload_type = |
| 615 NextFreePayloadType(*unified_codecs); |
| 616 if (!rtx_payload_type) |
| 617 return; |
| 618 unified_codecs->push_back( |
| 619 VideoCodec::CreateRtxCodec(*rtx_payload_type, codec.id)); |
| 620 } |
| 621 } |
| 622 } |
| 623 |
637 static std::vector<VideoCodec> GetSupportedCodecs( | 624 static std::vector<VideoCodec> GetSupportedCodecs( |
638 const WebRtcVideoEncoderFactory* external_encoder_factory) { | 625 const WebRtcVideoEncoderFactory* external_encoder_factory) { |
639 std::vector<VideoCodec> supported_codecs = DefaultVideoCodecList(); | 626 const std::vector<VideoCodec> internal_codecs = |
| 627 InternalEncoderFactory().supported_codecs(); |
| 628 LOG(LS_INFO) << "Internally supported codecs: " |
| 629 << CodecVectorToString(internal_codecs); |
640 | 630 |
641 if (external_encoder_factory == nullptr) { | 631 std::vector<VideoCodec> unified_codecs; |
642 LOG(LS_INFO) << "Supported codecs: " | 632 AppendVideoCodecs(internal_codecs, &unified_codecs); |
643 << CodecVectorToString(supported_codecs); | 633 |
644 return supported_codecs; | 634 if (external_encoder_factory != nullptr) { |
| 635 const std::vector<VideoCodec>& external_codecs = |
| 636 external_encoder_factory->supported_codecs(); |
| 637 AppendVideoCodecs(external_codecs, &unified_codecs); |
| 638 LOG(LS_INFO) << "Codecs supported by the external encoder factory: " |
| 639 << CodecVectorToString(external_codecs); |
645 } | 640 } |
646 | 641 |
647 std::stringstream out; | 642 return unified_codecs; |
648 const std::vector<VideoCodec>& codecs = | |
649 external_encoder_factory->supported_codecs(); | |
650 for (size_t i = 0; i < codecs.size(); ++i) { | |
651 VideoCodec codec = codecs[i]; | |
652 out << codec.name; | |
653 if (i != codecs.size() - 1) { | |
654 out << ", "; | |
655 } | |
656 // Don't add internally-supported codecs twice. | |
657 if (FindMatchingCodec(supported_codecs, codec)) | |
658 continue; | |
659 | |
660 // External video encoders are given payloads 120-127. This also means that | |
661 // we only support up to 8 external payload types. | |
662 // TODO(deadbeef): mediasession.cc already has code to dynamically | |
663 // determine a payload type. We should be able to just leave the payload | |
664 // type empty and let mediasession determine it. However, currently RTX | |
665 // codecs are associated to codecs by payload type, meaning we DO need | |
666 // to allocate unique payload types here. So to make this change we would | |
667 // need to make RTX codecs associated by name instead. | |
668 const int kExternalVideoPayloadTypeBase = 120; | |
669 size_t payload_type = kExternalVideoPayloadTypeBase + i; | |
670 RTC_DCHECK(payload_type < 128); | |
671 codec.id = payload_type; | |
672 | |
673 AddDefaultFeedbackParams(&codec); | |
674 AddCodecAndMaybeRtxCodec(codec, &supported_codecs); | |
675 } | |
676 LOG(LS_INFO) << "Supported codecs (incl. external codecs): " | |
677 << CodecVectorToString(supported_codecs); | |
678 LOG(LS_INFO) << "Codecs supported by the external encoder factory: " | |
679 << out.str(); | |
680 return supported_codecs; | |
681 } | 643 } |
682 | 644 |
683 WebRtcVideoChannel2::WebRtcVideoChannel2( | 645 WebRtcVideoChannel2::WebRtcVideoChannel2( |
684 webrtc::Call* call, | 646 webrtc::Call* call, |
685 const MediaConfig& config, | 647 const MediaConfig& config, |
686 const VideoOptions& options, | 648 const VideoOptions& options, |
687 WebRtcVideoEncoderFactory* external_encoder_factory, | 649 WebRtcVideoEncoderFactory* external_encoder_factory, |
688 WebRtcVideoDecoderFactory* external_decoder_factory) | 650 WebRtcVideoDecoderFactory* external_decoder_factory) |
689 : VideoMediaChannel(config), | 651 : VideoMediaChannel(config), |
690 call_(call), | 652 call_(call), |
(...skipping 857 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1548 int max_bitrate_bps, | 1510 int max_bitrate_bps, |
1549 const rtc::Optional<VideoCodecSettings>& codec_settings) | 1511 const rtc::Optional<VideoCodecSettings>& codec_settings) |
1550 : config(std::move(config)), | 1512 : config(std::move(config)), |
1551 options(options), | 1513 options(options), |
1552 max_bitrate_bps(max_bitrate_bps), | 1514 max_bitrate_bps(max_bitrate_bps), |
1553 conference_mode(false), | 1515 conference_mode(false), |
1554 codec_settings(codec_settings) {} | 1516 codec_settings(codec_settings) {} |
1555 | 1517 |
1556 WebRtcVideoChannel2::WebRtcVideoSendStream::AllocatedEncoder::AllocatedEncoder( | 1518 WebRtcVideoChannel2::WebRtcVideoSendStream::AllocatedEncoder::AllocatedEncoder( |
1557 webrtc::VideoEncoder* encoder, | 1519 webrtc::VideoEncoder* encoder, |
1558 webrtc::VideoCodecType type, | 1520 const cricket::VideoCodec& codec, |
1559 bool external) | 1521 bool external) |
1560 : encoder(encoder), | 1522 : encoder(encoder), |
1561 external_encoder(nullptr), | 1523 external_encoder(nullptr), |
1562 type(type), | 1524 codec(codec), |
1563 external(external) { | 1525 external(external) { |
1564 if (external) { | 1526 if (external) { |
1565 external_encoder = encoder; | 1527 external_encoder = encoder; |
1566 this->encoder = | 1528 this->encoder = |
1567 new webrtc::VideoEncoderSoftwareFallbackWrapper(type, encoder); | 1529 new webrtc::VideoEncoderSoftwareFallbackWrapper(codec, encoder); |
1568 } | 1530 } |
1569 } | 1531 } |
1570 | 1532 |
1571 WebRtcVideoChannel2::WebRtcVideoSendStream::WebRtcVideoSendStream( | 1533 WebRtcVideoChannel2::WebRtcVideoSendStream::WebRtcVideoSendStream( |
1572 webrtc::Call* call, | 1534 webrtc::Call* call, |
1573 const StreamParams& sp, | 1535 const StreamParams& sp, |
1574 webrtc::VideoSendStream::Config config, | 1536 webrtc::VideoSendStream::Config config, |
1575 const VideoOptions& options, | 1537 const VideoOptions& options, |
1576 WebRtcVideoEncoderFactory* external_encoder_factory, | 1538 WebRtcVideoEncoderFactory* external_encoder_factory, |
1577 bool enable_cpu_overuse_detection, | 1539 bool enable_cpu_overuse_detection, |
1578 int max_bitrate_bps, | 1540 int max_bitrate_bps, |
1579 const rtc::Optional<VideoCodecSettings>& codec_settings, | 1541 const rtc::Optional<VideoCodecSettings>& codec_settings, |
1580 const rtc::Optional<std::vector<webrtc::RtpExtension>>& rtp_extensions, | 1542 const rtc::Optional<std::vector<webrtc::RtpExtension>>& rtp_extensions, |
1581 // TODO(deadbeef): Don't duplicate information between send_params, | 1543 // TODO(deadbeef): Don't duplicate information between send_params, |
1582 // rtp_extensions, options, etc. | 1544 // rtp_extensions, options, etc. |
1583 const VideoSendParameters& send_params) | 1545 const VideoSendParameters& send_params) |
1584 : worker_thread_(rtc::Thread::Current()), | 1546 : worker_thread_(rtc::Thread::Current()), |
1585 ssrcs_(sp.ssrcs), | 1547 ssrcs_(sp.ssrcs), |
1586 ssrc_groups_(sp.ssrc_groups), | 1548 ssrc_groups_(sp.ssrc_groups), |
1587 call_(call), | 1549 call_(call), |
1588 enable_cpu_overuse_detection_(enable_cpu_overuse_detection), | 1550 enable_cpu_overuse_detection_(enable_cpu_overuse_detection), |
1589 source_(nullptr), | 1551 source_(nullptr), |
1590 external_encoder_factory_(external_encoder_factory), | 1552 external_encoder_factory_(external_encoder_factory), |
1591 stream_(nullptr), | 1553 stream_(nullptr), |
1592 encoder_sink_(nullptr), | 1554 encoder_sink_(nullptr), |
1593 parameters_(std::move(config), options, max_bitrate_bps, codec_settings), | 1555 parameters_(std::move(config), options, max_bitrate_bps, codec_settings), |
1594 rtp_parameters_(CreateRtpParametersWithOneEncoding()), | 1556 rtp_parameters_(CreateRtpParametersWithOneEncoding()), |
1595 allocated_encoder_(nullptr, webrtc::kVideoCodecUnknown, false), | 1557 allocated_encoder_(nullptr, cricket::VideoCodec(), false), |
1596 sending_(false), | 1558 sending_(false), |
1597 last_frame_timestamp_us_(0) { | 1559 last_frame_timestamp_us_(0) { |
1598 parameters_.config.rtp.max_packet_size = kVideoMtu; | 1560 parameters_.config.rtp.max_packet_size = kVideoMtu; |
1599 parameters_.conference_mode = send_params.conference_mode; | 1561 parameters_.conference_mode = send_params.conference_mode; |
1600 | 1562 |
1601 sp.GetPrimarySsrcs(¶meters_.config.rtp.ssrcs); | 1563 sp.GetPrimarySsrcs(¶meters_.config.rtp.ssrcs); |
1602 sp.GetFidSsrcs(parameters_.config.rtp.ssrcs, | 1564 sp.GetFidSsrcs(parameters_.config.rtp.ssrcs, |
1603 ¶meters_.config.rtp.rtx.ssrcs); | 1565 ¶meters_.config.rtp.rtx.ssrcs); |
1604 parameters_.config.rtp.c_name = sp.cname; | 1566 parameters_.config.rtp.c_name = sp.cname; |
1605 if (rtp_extensions) { | 1567 if (rtp_extensions) { |
(...skipping 114 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1720 | 1682 |
1721 const std::vector<uint32_t>& | 1683 const std::vector<uint32_t>& |
1722 WebRtcVideoChannel2::WebRtcVideoSendStream::GetSsrcs() const { | 1684 WebRtcVideoChannel2::WebRtcVideoSendStream::GetSsrcs() const { |
1723 return ssrcs_; | 1685 return ssrcs_; |
1724 } | 1686 } |
1725 | 1687 |
1726 WebRtcVideoChannel2::WebRtcVideoSendStream::AllocatedEncoder | 1688 WebRtcVideoChannel2::WebRtcVideoSendStream::AllocatedEncoder |
1727 WebRtcVideoChannel2::WebRtcVideoSendStream::CreateVideoEncoder( | 1689 WebRtcVideoChannel2::WebRtcVideoSendStream::CreateVideoEncoder( |
1728 const VideoCodec& codec) { | 1690 const VideoCodec& codec) { |
1729 RTC_DCHECK_RUN_ON(&thread_checker_); | 1691 RTC_DCHECK_RUN_ON(&thread_checker_); |
1730 webrtc::VideoCodecType type = CodecTypeFromName(codec.name); | |
1731 | |
1732 // Do not re-create encoders of the same type. | 1692 // Do not re-create encoders of the same type. |
1733 if (type == allocated_encoder_.type && allocated_encoder_.encoder != NULL) { | 1693 if (codec == allocated_encoder_.codec && |
| 1694 allocated_encoder_.encoder != nullptr) { |
1734 return allocated_encoder_; | 1695 return allocated_encoder_; |
1735 } | 1696 } |
1736 | 1697 |
1737 if (external_encoder_factory_ != NULL) { | 1698 // Try creating external encoder. |
| 1699 if (external_encoder_factory_ != nullptr && |
| 1700 FindMatchingCodec(external_encoder_factory_->supported_codecs(), codec)) { |
1738 webrtc::VideoEncoder* encoder = | 1701 webrtc::VideoEncoder* encoder = |
1739 external_encoder_factory_->CreateVideoEncoder(codec); | 1702 external_encoder_factory_->CreateVideoEncoder(codec); |
1740 if (encoder != NULL) { | 1703 if (encoder != nullptr) |
1741 return AllocatedEncoder(encoder, type, true); | 1704 return AllocatedEncoder(encoder, codec, true /* is_external */); |
1742 } | |
1743 } | 1705 } |
1744 | 1706 |
1745 if (type == webrtc::kVideoCodecVP8) { | 1707 // Try creating internal encoder. |
1746 return AllocatedEncoder( | 1708 InternalEncoderFactory internal_encoder_factory; |
1747 webrtc::VideoEncoder::Create(webrtc::VideoEncoder::kVp8), type, false); | 1709 if (FindMatchingCodec(internal_encoder_factory.supported_codecs(), codec)) { |
1748 } else if (type == webrtc::kVideoCodecVP9) { | 1710 return AllocatedEncoder(internal_encoder_factory.CreateVideoEncoder(codec), |
1749 return AllocatedEncoder( | 1711 codec, false /* is_external */); |
1750 webrtc::VideoEncoder::Create(webrtc::VideoEncoder::kVp9), type, false); | |
1751 } else if (type == webrtc::kVideoCodecH264) { | |
1752 return AllocatedEncoder( | |
1753 webrtc::VideoEncoder::Create(webrtc::VideoEncoder::kH264), type, false); | |
1754 } | 1712 } |
1755 | 1713 |
1756 // This shouldn't happen, we should not be trying to create something we don't | 1714 // This shouldn't happen, we should not be trying to create something we don't |
1757 // support. | 1715 // support. |
1758 RTC_DCHECK(false); | 1716 RTC_DCHECK(false); |
1759 return AllocatedEncoder(NULL, webrtc::kVideoCodecUnknown, false); | 1717 return AllocatedEncoder(NULL, cricket::VideoCodec(), false); |
1760 } | 1718 } |
1761 | 1719 |
1762 void WebRtcVideoChannel2::WebRtcVideoSendStream::DestroyVideoEncoder( | 1720 void WebRtcVideoChannel2::WebRtcVideoSendStream::DestroyVideoEncoder( |
1763 AllocatedEncoder* encoder) { | 1721 AllocatedEncoder* encoder) { |
1764 RTC_DCHECK_RUN_ON(&thread_checker_); | 1722 RTC_DCHECK_RUN_ON(&thread_checker_); |
1765 if (encoder->external) { | 1723 if (encoder->external) { |
1766 external_encoder_factory_->DestroyVideoEncoder(encoder->external_encoder); | 1724 external_encoder_factory_->DestroyVideoEncoder(encoder->external_encoder); |
1767 } | 1725 } |
1768 delete encoder->encoder; | 1726 delete encoder->encoder; |
1769 } | 1727 } |
(...skipping 820 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2590 rtx_mapping[video_codecs[i].codec.id] != | 2548 rtx_mapping[video_codecs[i].codec.id] != |
2591 ulpfec_config.red_payload_type) { | 2549 ulpfec_config.red_payload_type) { |
2592 video_codecs[i].rtx_payload_type = rtx_mapping[video_codecs[i].codec.id]; | 2550 video_codecs[i].rtx_payload_type = rtx_mapping[video_codecs[i].codec.id]; |
2593 } | 2551 } |
2594 } | 2552 } |
2595 | 2553 |
2596 return video_codecs; | 2554 return video_codecs; |
2597 } | 2555 } |
2598 | 2556 |
2599 } // namespace cricket | 2557 } // namespace cricket |
OLD | NEW |