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

Side by Side Diff: media/engine/webrtcvideoengine.cc

Issue 2951033003: [EXPERIMENTAL] Generic stereo codec with index header sending single frames
Patch Set: Rebase and add external codec support. Created 3 years, 2 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
« no previous file with comments | « media/engine/webrtcvideoengine.h ('k') | modules/include/module_common_types.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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 "media/engine/webrtcvideoengine.h" 11 #include "media/engine/webrtcvideoengine.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 "api/video/i420_buffer.h" 19 #include "api/video/i420_buffer.h"
20 #include "api/video_codecs/sdp_video_format.h" 20 #include "api/video_codecs/sdp_video_format.h"
21 #include "api/video_codecs/video_decoder.h" 21 #include "api/video_codecs/video_decoder.h"
22 #include "api/video_codecs/video_decoder_factory.h" 22 #include "api/video_codecs/video_decoder_factory.h"
23 #include "api/video_codecs/video_encoder.h" 23 #include "api/video_codecs/video_encoder.h"
24 #include "api/video_codecs/video_encoder_factory.h" 24 #include "api/video_codecs/video_encoder_factory.h"
25 #include "call/call.h" 25 #include "call/call.h"
26 #include "common_video/h264/profile_level_id.h" 26 #include "common_video/h264/profile_level_id.h"
27 #include "media/base/codec.h"
27 #include "media/engine/constants.h" 28 #include "media/engine/constants.h"
28 #include "media/engine/internaldecoderfactory.h" 29 #include "media/engine/internaldecoderfactory.h"
29 #include "media/engine/internalencoderfactory.h" 30 #include "media/engine/internalencoderfactory.h"
30 #include "media/engine/scopedvideodecoder.h" 31 #include "media/engine/scopedvideodecoder.h"
31 #include "media/engine/scopedvideoencoder.h" 32 #include "media/engine/scopedvideoencoder.h"
32 #include "media/engine/simulcast.h" 33 #include "media/engine/simulcast.h"
33 #include "media/engine/simulcast_encoder_adapter.h" 34 #include "media/engine/simulcast_encoder_adapter.h"
34 #include "media/engine/videodecodersoftwarefallbackwrapper.h" 35 #include "media/engine/videodecodersoftwarefallbackwrapper.h"
35 #include "media/engine/videoencodersoftwarefallbackwrapper.h" 36 #include "media/engine/videoencodersoftwarefallbackwrapper.h"
36 #include "media/engine/webrtcmediaengine.h" 37 #include "media/engine/webrtcmediaengine.h"
37 #include "media/engine/webrtcvideoencoderfactory.h" 38 #include "media/engine/webrtcvideoencoderfactory.h"
38 #include "media/engine/webrtcvoiceengine.h" 39 #include "media/engine/webrtcvoiceengine.h"
40 #include "modules/video_coding/codecs/stereo/include/stereo_decoder_adapter.h"
41 #include "modules/video_coding/codecs/stereo/include/stereo_encoder_adapter.h"
39 #include "rtc_base/copyonwritebuffer.h" 42 #include "rtc_base/copyonwritebuffer.h"
40 #include "rtc_base/logging.h" 43 #include "rtc_base/logging.h"
41 #include "rtc_base/stringutils.h" 44 #include "rtc_base/stringutils.h"
42 #include "rtc_base/timeutils.h" 45 #include "rtc_base/timeutils.h"
43 #include "rtc_base/trace_event.h" 46 #include "rtc_base/trace_event.h"
44 #include "system_wrappers/include/field_trial.h" 47 #include "system_wrappers/include/field_trial.h"
45 48
46 using DegradationPreference = webrtc::VideoSendStream::DegradationPreference; 49 using DegradationPreference = webrtc::VideoSendStream::DegradationPreference;
47 50
48 namespace cricket { 51 namespace cricket {
(...skipping 12 matching lines...) Expand all
61 64
62 std::unique_ptr<webrtc::VideoEncoder> encoder; 65 std::unique_ptr<webrtc::VideoEncoder> encoder;
63 bool is_hardware_accelerated; 66 bool is_hardware_accelerated;
64 bool has_internal_source; 67 bool has_internal_source;
65 }; 68 };
66 69
67 virtual ~EncoderFactoryAdapter() {} 70 virtual ~EncoderFactoryAdapter() {}
68 71
69 virtual AllocatedEncoder CreateVideoEncoder( 72 virtual AllocatedEncoder CreateVideoEncoder(
70 const VideoCodec& codec, 73 const VideoCodec& codec,
71 bool is_conference_mode_screenshare) const = 0; 74 bool is_conference_mode_screenshare,
75 bool is_stereo_codec) const = 0;
72 76
73 virtual std::vector<VideoCodec> GetSupportedCodecs() const = 0; 77 virtual std::vector<VideoCodec> GetSupportedCodecs() const = 0;
74 }; 78 };
75 79
76 class DecoderFactoryAdapter { 80 class DecoderFactoryAdapter {
77 public: 81 public:
78 virtual ~DecoderFactoryAdapter() {} 82 virtual ~DecoderFactoryAdapter() {}
79 83
80 virtual std::unique_ptr<webrtc::VideoDecoder> CreateVideoDecoder( 84 virtual std::unique_ptr<webrtc::VideoDecoder> CreateVideoDecoder(
81 const VideoCodec& codec, 85 const VideoCodec& codec,
82 const VideoDecoderParams& decoder_params) const = 0; 86 const VideoDecoderParams& decoder_params,
87 bool is_stereo_codec) const = 0;
83 }; 88 };
84 89
85 namespace { 90 namespace {
86 91
87 std::vector<VideoCodec> AssignPayloadTypesAndAddAssociatedRtxCodecs( 92 std::vector<VideoCodec> AssignPayloadTypesAndAddAssociatedRtxCodecs(
88 const std::vector<VideoCodec>& input_codecs); 93 const std::vector<VideoCodec>& input_codecs);
89 94
90 // Wraps cricket::WebRtcVideoEncoderFactory* into common EncoderFactoryAdapter 95 // Wraps cricket::WebRtcVideoEncoderFactory* into common EncoderFactoryAdapter
91 // interface. 96 // interface.
92 // TODO(magjed): Remove once WebRtcVideoEncoderFactory* is deprecated and 97 // TODO(magjed): Remove once WebRtcVideoEncoderFactory* is deprecated and
93 // webrtc:7925 is fixed. 98 // webrtc:7925 is fixed.
94 class CricketEncoderFactoryAdapter : public EncoderFactoryAdapter { 99 class CricketEncoderFactoryAdapter : public EncoderFactoryAdapter {
95 public: 100 public:
96 explicit CricketEncoderFactoryAdapter( 101 explicit CricketEncoderFactoryAdapter(
97 WebRtcVideoEncoderFactory* external_encoder_factory) 102 WebRtcVideoEncoderFactory* external_encoder_factory)
98 : internal_encoder_factory_(new InternalEncoderFactory()), 103 : internal_encoder_factory_(new InternalEncoderFactory()),
99 external_encoder_factory_(external_encoder_factory) {} 104 external_encoder_factory_(external_encoder_factory) {}
100 105
101 private: 106 private:
102 explicit CricketEncoderFactoryAdapter( 107 explicit CricketEncoderFactoryAdapter(
103 const CricketEncoderFactoryAdapter& other) 108 const CricketEncoderFactoryAdapter& other)
104 : CricketEncoderFactoryAdapter(other.external_encoder_factory_) {} 109 : CricketEncoderFactoryAdapter(other.external_encoder_factory_) {}
105 110
106 AllocatedEncoder CreateVideoEncoder( 111 AllocatedEncoder CreateVideoEncoder(
107 const VideoCodec& codec, 112 const VideoCodec& codec,
108 bool is_conference_mode_screenshare) const override; 113 bool is_conference_mode_screenshare,
114 bool is_stereo_codec) const override;
109 115
110 std::vector<VideoCodec> GetSupportedCodecs() const override; 116 std::vector<VideoCodec> GetSupportedCodecs() const override;
111 117
112 const std::unique_ptr<WebRtcVideoEncoderFactory> internal_encoder_factory_; 118 const std::unique_ptr<WebRtcVideoEncoderFactory> internal_encoder_factory_;
113 WebRtcVideoEncoderFactory* const external_encoder_factory_; 119 WebRtcVideoEncoderFactory* const external_encoder_factory_;
120 std::unique_ptr<WebRtcVideoEncoderFactory> stereo_encoder_factory_;
114 }; 121 };
115 122
116 class CricketDecoderFactoryAdapter : public DecoderFactoryAdapter { 123 class CricketDecoderFactoryAdapter : public DecoderFactoryAdapter {
117 public: 124 public:
118 explicit CricketDecoderFactoryAdapter( 125 explicit CricketDecoderFactoryAdapter(
119 WebRtcVideoDecoderFactory* external_decoder_factory) 126 WebRtcVideoDecoderFactory* external_decoder_factory)
120 : internal_decoder_factory_(new InternalDecoderFactory()), 127 : internal_decoder_factory_(new InternalDecoderFactory()),
121 external_decoder_factory_(external_decoder_factory) {} 128 external_decoder_factory_(external_decoder_factory) {}
122 129
123 private: 130 private:
124 explicit CricketDecoderFactoryAdapter( 131 explicit CricketDecoderFactoryAdapter(
125 const CricketDecoderFactoryAdapter& other) 132 const CricketDecoderFactoryAdapter& other)
126 : CricketDecoderFactoryAdapter(other.external_decoder_factory_) {} 133 : CricketDecoderFactoryAdapter(other.external_decoder_factory_) {}
127 134
128 std::unique_ptr<webrtc::VideoDecoder> CreateVideoDecoder( 135 std::unique_ptr<webrtc::VideoDecoder> CreateVideoDecoder(
129 const VideoCodec& codec, 136 const VideoCodec& codec,
130 const VideoDecoderParams& decoder_params) const override; 137 const VideoDecoderParams& decoder_params,
138 bool is_stereo_codec) const override;
131 139
132 const std::unique_ptr<WebRtcVideoDecoderFactory> internal_decoder_factory_; 140 const std::unique_ptr<WebRtcVideoDecoderFactory> internal_decoder_factory_;
133 WebRtcVideoDecoderFactory* const external_decoder_factory_; 141 WebRtcVideoDecoderFactory* const external_decoder_factory_;
142 std::unique_ptr<WebRtcVideoDecoderFactory> stereo_decoder_factory_;
134 }; 143 };
135 144
136 // Wraps webrtc::VideoEncoderFactory into common EncoderFactoryAdapter 145 // Wraps webrtc::VideoEncoderFactory into common EncoderFactoryAdapter
137 // interface. 146 // interface.
138 class WebRtcEncoderFactoryAdapter : public EncoderFactoryAdapter { 147 class WebRtcEncoderFactoryAdapter : public EncoderFactoryAdapter {
139 public: 148 public:
140 explicit WebRtcEncoderFactoryAdapter( 149 explicit WebRtcEncoderFactoryAdapter(
141 std::unique_ptr<webrtc::VideoEncoderFactory> encoder_factory) 150 std::unique_ptr<webrtc::VideoEncoderFactory> encoder_factory)
142 : encoder_factory_(std::move(encoder_factory)) {} 151 : encoder_factory_(std::move(encoder_factory)) {}
143 152
144 private: 153 private:
145 AllocatedEncoder CreateVideoEncoder( 154 AllocatedEncoder CreateVideoEncoder(
146 const VideoCodec& codec, 155 const VideoCodec& codec,
147 bool is_conference_mode_screenshare) const override { 156 bool is_conference_mode_screenshare,
157 bool is_stereo_codec) const override {
148 if (!encoder_factory_) 158 if (!encoder_factory_)
149 return AllocatedEncoder(); 159 return AllocatedEncoder();
150 const webrtc::SdpVideoFormat format(codec.name, codec.params); 160 const webrtc::SdpVideoFormat format(codec.name, codec.params);
151 const webrtc::VideoEncoderFactory::CodecInfo info = 161 const webrtc::VideoEncoderFactory::CodecInfo info =
152 encoder_factory_->QueryVideoEncoder(format); 162 encoder_factory_->QueryVideoEncoder(format);
153 return AllocatedEncoder(encoder_factory_->CreateVideoEncoder(format), 163 return AllocatedEncoder(encoder_factory_->CreateVideoEncoder(format),
154 info.is_hardware_accelerated, 164 info.is_hardware_accelerated,
155 info.has_internal_source); 165 info.has_internal_source);
156 } 166 }
157 167
(...skipping 18 matching lines...) Expand all
176 // interface. 186 // interface.
177 class WebRtcDecoderFactoryAdapter : public DecoderFactoryAdapter { 187 class WebRtcDecoderFactoryAdapter : public DecoderFactoryAdapter {
178 public: 188 public:
179 explicit WebRtcDecoderFactoryAdapter( 189 explicit WebRtcDecoderFactoryAdapter(
180 std::unique_ptr<webrtc::VideoDecoderFactory> decoder_factory) 190 std::unique_ptr<webrtc::VideoDecoderFactory> decoder_factory)
181 : decoder_factory_(std::move(decoder_factory)) {} 191 : decoder_factory_(std::move(decoder_factory)) {}
182 192
183 private: 193 private:
184 std::unique_ptr<webrtc::VideoDecoder> CreateVideoDecoder( 194 std::unique_ptr<webrtc::VideoDecoder> CreateVideoDecoder(
185 const VideoCodec& codec, 195 const VideoCodec& codec,
186 const VideoDecoderParams& decoder_params) const override { 196 const VideoDecoderParams& decoder_params,
197 bool is_stereo_codec) const override {
187 return decoder_factory_ 198 return decoder_factory_
188 ? decoder_factory_->CreateVideoDecoder( 199 ? decoder_factory_->CreateVideoDecoder(
189 webrtc::SdpVideoFormat(codec.name, codec.params)) 200 webrtc::SdpVideoFormat(codec.name, codec.params))
190 : nullptr; 201 : nullptr;
191 } 202 }
192 203
193 std::unique_ptr<webrtc::VideoDecoderFactory> decoder_factory_; 204 std::unique_ptr<webrtc::VideoDecoderFactory> decoder_factory_;
194 }; 205 };
195 206
196 // If this field trial is enabled, we will enable sending FlexFEC and disable 207 // If this field trial is enabled, we will enable sending FlexFEC and disable
(...skipping 352 matching lines...) Expand 10 before | Expand all | Expand 10 after
549 CodecNamesEq(codec.name, kH264CodecName) || 560 CodecNamesEq(codec.name, kH264CodecName) ||
550 CodecNamesEq(codec.name, kRedCodecName)) { 561 CodecNamesEq(codec.name, kRedCodecName)) {
551 output_codecs.push_back( 562 output_codecs.push_back(
552 VideoCodec::CreateRtxCodec(payload_type, codec.id)); 563 VideoCodec::CreateRtxCodec(payload_type, codec.id));
553 564
554 // Increment payload type. 565 // Increment payload type.
555 ++payload_type; 566 ++payload_type;
556 if (payload_type > kLastDynamicPayloadType) 567 if (payload_type > kLastDynamicPayloadType)
557 break; 568 break;
558 } 569 }
570
571 if (CodecNamesEq(codec.name, kVp9CodecName)) {
572 output_codecs.push_back(
573 VideoCodec::CreateStereoCodec(payload_type, codec));
574 ++payload_type;
575 if (payload_type > kLastDynamicPayloadType)
576 break;
577 }
559 } 578 }
560 return output_codecs; 579 return output_codecs;
561 } 580 }
562 } // namespace 581 } // namespace
563 582
564 std::vector<VideoCodec> CricketEncoderFactoryAdapter::GetSupportedCodecs() 583 std::vector<VideoCodec> CricketEncoderFactoryAdapter::GetSupportedCodecs()
565 const { 584 const {
566 std::vector<VideoCodec> codecs = InternalEncoderFactory().supported_codecs(); 585 std::vector<VideoCodec> codecs = InternalEncoderFactory().supported_codecs();
567 LOG(LS_INFO) << "Internally supported codecs: " 586 LOG(LS_INFO) << "Internally supported codecs: "
568 << CodecVectorToString(codecs); 587 << CodecVectorToString(codecs);
569 588
570 // Add external codecs. 589 // Add external codecs.
571 if (external_encoder_factory_ != nullptr) { 590 if (external_encoder_factory_ != nullptr) {
572 const std::vector<VideoCodec>& external_codecs = 591 const std::vector<VideoCodec>& external_codecs =
573 external_encoder_factory_->supported_codecs(); 592 external_encoder_factory_->supported_codecs();
574 for (const VideoCodec& codec : external_codecs) { 593 for (const VideoCodec& codec : external_codecs) {
575 // Don't add same codec twice. 594 // Don't add same codec twice.
576 if (!FindMatchingCodec(codecs, codec)) 595 if (!FindMatchingCodec(codecs, codec))
577 codecs.push_back(codec); 596 codecs.push_back(codec);
578 } 597 }
579 LOG(LS_INFO) << "Codecs supported by the external encoder factory: " 598 LOG(LS_INFO) << "Codecs supported by the external encoder factory: "
580 << CodecVectorToString(external_codecs); 599 << CodecVectorToString(external_codecs);
581 } 600 }
582 601
583 return AssignPayloadTypesAndAddAssociatedRtxCodecs(codecs); 602 return AssignPayloadTypesAndAddAssociatedRtxCodecs(codecs);
584 } 603 }
585 604
586 WebRtcVideoChannel::WebRtcVideoChannel( 605 WebRtcVideoChannel::WebRtcVideoChannel(webrtc::Call* call,
587 webrtc::Call* call, 606 const MediaConfig& config,
588 const MediaConfig& config, 607 const VideoOptions& options,
589 const VideoOptions& options, 608 EncoderFactoryAdapter* encoder_factory,
590 const EncoderFactoryAdapter* encoder_factory, 609 DecoderFactoryAdapter* decoder_factory)
591 const DecoderFactoryAdapter* decoder_factory)
592 : VideoMediaChannel(config), 610 : VideoMediaChannel(config),
593 call_(call), 611 call_(call),
594 unsignalled_ssrc_handler_(&default_unsignalled_ssrc_handler_), 612 unsignalled_ssrc_handler_(&default_unsignalled_ssrc_handler_),
595 video_config_(config.video), 613 video_config_(config.video),
596 encoder_factory_(encoder_factory), 614 encoder_factory_(encoder_factory),
597 decoder_factory_(decoder_factory), 615 decoder_factory_(decoder_factory),
598 default_send_options_(options), 616 default_send_options_(options),
599 last_stats_log_ms_(-1) { 617 last_stats_log_ms_(-1) {
600 RTC_DCHECK(thread_checker_.CalledOnValidThread()); 618 RTC_DCHECK(thread_checker_.CalledOnValidThread());
601 619
(...skipping 10 matching lines...) Expand all
612 delete kv.second; 630 delete kv.second;
613 } 631 }
614 632
615 rtc::Optional<WebRtcVideoChannel::VideoCodecSettings> 633 rtc::Optional<WebRtcVideoChannel::VideoCodecSettings>
616 WebRtcVideoChannel::SelectSendVideoCodec( 634 WebRtcVideoChannel::SelectSendVideoCodec(
617 const std::vector<VideoCodecSettings>& remote_mapped_codecs) const { 635 const std::vector<VideoCodecSettings>& remote_mapped_codecs) const {
618 const std::vector<VideoCodec> local_supported_codecs = 636 const std::vector<VideoCodec> local_supported_codecs =
619 encoder_factory_->GetSupportedCodecs(); 637 encoder_factory_->GetSupportedCodecs();
620 // Select the first remote codec that is supported locally. 638 // Select the first remote codec that is supported locally.
621 for (const VideoCodecSettings& remote_mapped_codec : remote_mapped_codecs) { 639 for (const VideoCodecSettings& remote_mapped_codec : remote_mapped_codecs) {
640 // HARDCODE TO ALPHA
641 if (!cricket::VideoCodec::IsStereoCodec(remote_mapped_codec.codec))
642 continue;
622 // For H264, we will limit the encode level to the remote offered level 643 // For H264, we will limit the encode level to the remote offered level
623 // regardless if level asymmetry is allowed or not. This is strictly not 644 // regardless if level asymmetry is allowed or not. This is strictly not
624 // following the spec in https://tools.ietf.org/html/rfc6184#section-8.2.2 645 // following the spec in https://tools.ietf.org/html/rfc6184#section-8.2.2
625 // since we should limit the encode level to the lower of local and remote 646 // since we should limit the encode level to the lower of local and remote
626 // level when level asymmetry is not allowed. 647 // level when level asymmetry is not allowed.
627 if (FindMatchingCodec(local_supported_codecs, remote_mapped_codec.codec)) 648 if (FindMatchingCodec(local_supported_codecs, remote_mapped_codec.codec))
628 return rtc::Optional<VideoCodecSettings>(remote_mapped_codec); 649 return rtc::Optional<VideoCodecSettings>(remote_mapped_codec);
629 } 650 }
630 // No remote codec was supported. 651 // No remote codec was supported.
631 return rtc::Optional<VideoCodecSettings>(); 652 return rtc::Optional<VideoCodecSettings>();
632 } 653 }
633 654
655 rtc::Optional<WebRtcVideoChannel::VideoCodecSettings>
656 WebRtcVideoChannel::SelectStereoAssociatedVideoCodec(
657 const std::vector<VideoCodecSettings>& remote_mapped_codecs) const {
658 const std::vector<VideoCodec> local_supported_codecs =
659 encoder_factory_->GetSupportedCodecs();
660
661 // Select the first remote codec that is supported locally.
662 for (const VideoCodecSettings& remote_mapped_codec : remote_mapped_codecs) {
663 // HARDCODE TO VP9
664 if (!CodecNamesEq(remote_mapped_codec.codec.name.c_str(), kVp9CodecName))
665 continue;
666 if (!cricket::VideoCodec::IsStereoCodec(remote_mapped_codec.codec) &&
667 FindMatchingCodec(local_supported_codecs, remote_mapped_codec.codec))
668 return rtc::Optional<VideoCodecSettings>(remote_mapped_codec);
669 }
670 return rtc::Optional<VideoCodecSettings>();
671 }
672
634 bool WebRtcVideoChannel::NonFlexfecReceiveCodecsHaveChanged( 673 bool WebRtcVideoChannel::NonFlexfecReceiveCodecsHaveChanged(
635 std::vector<VideoCodecSettings> before, 674 std::vector<VideoCodecSettings> before,
636 std::vector<VideoCodecSettings> after) { 675 std::vector<VideoCodecSettings> after) {
637 if (before.size() != after.size()) { 676 if (before.size() != after.size()) {
638 return true; 677 return true;
639 } 678 }
640 679
641 // The receive codec order doesn't matter, so we sort the codecs before 680 // The receive codec order doesn't matter, so we sort the codecs before
642 // comparing. This is necessary because currently the 681 // comparing. This is necessary because currently the
643 // only way to change the send codec is to munge SDP, which causes 682 // only way to change the send codec is to munge SDP, which causes
(...skipping 26 matching lines...) Expand all
670 709
671 // Select one of the remote codecs that will be used as send codec. 710 // Select one of the remote codecs that will be used as send codec.
672 rtc::Optional<VideoCodecSettings> selected_send_codec = 711 rtc::Optional<VideoCodecSettings> selected_send_codec =
673 SelectSendVideoCodec(MapCodecs(params.codecs)); 712 SelectSendVideoCodec(MapCodecs(params.codecs));
674 713
675 if (!selected_send_codec) { 714 if (!selected_send_codec) {
676 LOG(LS_ERROR) << "No video codecs supported."; 715 LOG(LS_ERROR) << "No video codecs supported.";
677 return false; 716 return false;
678 } 717 }
679 718
719 if (VideoCodec::IsStereoCodec(selected_send_codec->codec)) {
720 rtc::Optional<VideoCodecSettings> associated_codec_settings =
721 SelectStereoAssociatedVideoCodec(MapCodecs(params.codecs));
722 LOG(LS_ERROR) << __func__ << associated_codec_settings->codec.ToString();
723 if (!associated_codec_settings) {
724 LOG(LS_ERROR)
725 << "Stereo codec is not associated with any supported codec.";
726 return false;
727 }
728 associated_codec_settings->stereo_codec.emplace(selected_send_codec->codec);
729 selected_send_codec = associated_codec_settings;
730 }
731
680 // Never enable sending FlexFEC, unless we are in the experiment. 732 // Never enable sending FlexFEC, unless we are in the experiment.
681 if (!IsFlexfecFieldTrialEnabled()) { 733 if (!IsFlexfecFieldTrialEnabled()) {
682 if (selected_send_codec->flexfec_payload_type != -1) { 734 if (selected_send_codec->flexfec_payload_type != -1) {
683 LOG(LS_INFO) << "Remote supports flexfec-03, but we will not send since " 735 LOG(LS_INFO) << "Remote supports flexfec-03, but we will not send since "
684 << "WebRTC-FlexFEC-03 field trial is not enabled."; 736 << "WebRTC-FlexFEC-03 field trial is not enabled.";
685 } 737 }
686 selected_send_codec->flexfec_payload_type = -1; 738 selected_send_codec->flexfec_payload_type = -1;
687 } 739 }
688 740
689 if (!send_codec_ || *selected_send_codec != *send_codec_) 741 if (!send_codec_ || *selected_send_codec != *send_codec_)
(...skipping 852 matching lines...) Expand 10 before | Expand all | Expand 10 after
1542 bool has_internal_source) 1594 bool has_internal_source)
1543 : encoder(std::move(encoder)), 1595 : encoder(std::move(encoder)),
1544 is_hardware_accelerated(is_hardware_accelerated), 1596 is_hardware_accelerated(is_hardware_accelerated),
1545 has_internal_source(has_internal_source) {} 1597 has_internal_source(has_internal_source) {}
1546 1598
1547 WebRtcVideoChannel::WebRtcVideoSendStream::WebRtcVideoSendStream( 1599 WebRtcVideoChannel::WebRtcVideoSendStream::WebRtcVideoSendStream(
1548 webrtc::Call* call, 1600 webrtc::Call* call,
1549 const StreamParams& sp, 1601 const StreamParams& sp,
1550 webrtc::VideoSendStream::Config config, 1602 webrtc::VideoSendStream::Config config,
1551 const VideoOptions& options, 1603 const VideoOptions& options,
1552 const EncoderFactoryAdapter* encoder_factory, 1604 EncoderFactoryAdapter* encoder_factory,
1553 bool enable_cpu_overuse_detection, 1605 bool enable_cpu_overuse_detection,
1554 int max_bitrate_bps, 1606 int max_bitrate_bps,
1555 const rtc::Optional<VideoCodecSettings>& codec_settings, 1607 const rtc::Optional<VideoCodecSettings>& codec_settings,
1556 const rtc::Optional<std::vector<webrtc::RtpExtension>>& rtp_extensions, 1608 const rtc::Optional<std::vector<webrtc::RtpExtension>>& rtp_extensions,
1557 // TODO(deadbeef): Don't duplicate information between send_params, 1609 // TODO(deadbeef): Don't duplicate information between send_params,
1558 // rtp_extensions, options, etc. 1610 // rtp_extensions, options, etc.
1559 const VideoSendParameters& send_params) 1611 const VideoSendParameters& send_params)
1560 : worker_thread_(rtc::Thread::Current()), 1612 : worker_thread_(rtc::Thread::Current()),
1561 ssrcs_(sp.ssrcs), 1613 ssrcs_(sp.ssrcs),
1562 ssrc_groups_(sp.ssrc_groups), 1614 ssrc_groups_(sp.ssrc_groups),
(...skipping 129 matching lines...) Expand 10 before | Expand all | Expand 10 after
1692 } 1744 }
1693 1745
1694 const std::vector<uint32_t>& 1746 const std::vector<uint32_t>&
1695 WebRtcVideoChannel::WebRtcVideoSendStream::GetSsrcs() const { 1747 WebRtcVideoChannel::WebRtcVideoSendStream::GetSsrcs() const {
1696 return ssrcs_; 1748 return ssrcs_;
1697 } 1749 }
1698 1750
1699 EncoderFactoryAdapter::AllocatedEncoder 1751 EncoderFactoryAdapter::AllocatedEncoder
1700 CricketEncoderFactoryAdapter::CreateVideoEncoder( 1752 CricketEncoderFactoryAdapter::CreateVideoEncoder(
1701 const VideoCodec& codec, 1753 const VideoCodec& codec,
1702 bool is_conference_mode_screenshare) const { 1754 bool is_conference_mode_screenshare,
1755 bool is_stereo_codec) const {
1756 if (is_stereo_codec) {
1757 if (external_encoder_factory_ != nullptr &&
1758 FindMatchingCodec(external_encoder_factory_->supported_codecs(),
1759 codec)) {
1760 std::unique_ptr<webrtc::VideoEncoder> stereo_encoder(
1761 new webrtc::StereoEncoderAdapter(external_encoder_factory_));
1762 return AllocatedEncoder(std::move(stereo_encoder),
1763 true /* is_hardware_accelerated */,
1764 false /* is_external */);
1765 }
1766 if (FindMatchingCodec(internal_encoder_factory_->supported_codecs(),
1767 codec)) {
1768 std::unique_ptr<webrtc::VideoEncoder> stereo_encoder(
1769 new webrtc::StereoEncoderAdapter(internal_encoder_factory_.get()));
1770 return AllocatedEncoder(std::move(stereo_encoder),
1771 false /* is_hardware_accelerated */,
1772 false /* is_external */);
1773 }
1774 RTC_NOTREACHED();
1775 return AllocatedEncoder();
1776 }
1777
1703 // Try creating external encoder. 1778 // Try creating external encoder.
1704 if (external_encoder_factory_ != nullptr && 1779 if (external_encoder_factory_ != nullptr &&
1705 FindMatchingCodec(external_encoder_factory_->supported_codecs(), codec)) { 1780 FindMatchingCodec(external_encoder_factory_->supported_codecs(), codec)) {
1706 std::unique_ptr<webrtc::VideoEncoder> external_encoder; 1781 std::unique_ptr<webrtc::VideoEncoder> external_encoder;
1707 if (CodecNamesEq(codec.name.c_str(), kVp8CodecName)) { 1782 if (CodecNamesEq(codec.name.c_str(), kVp8CodecName)) {
1708 // If it's a codec type we can simulcast, create a wrapped encoder. 1783 // If it's a codec type we can simulcast, create a wrapped encoder.
1709 external_encoder = std::unique_ptr<webrtc::VideoEncoder>( 1784 external_encoder = std::unique_ptr<webrtc::VideoEncoder>(
1710 new webrtc::SimulcastEncoderAdapter(external_encoder_factory_)); 1785 new webrtc::SimulcastEncoderAdapter(external_encoder_factory_));
1711 } else { 1786 } else {
1712 external_encoder = 1787 external_encoder =
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after
1750 return AllocatedEncoder(); 1825 return AllocatedEncoder();
1751 } 1826 }
1752 1827
1753 void WebRtcVideoChannel::WebRtcVideoSendStream::SetCodec( 1828 void WebRtcVideoChannel::WebRtcVideoSendStream::SetCodec(
1754 const VideoCodecSettings& codec_settings, 1829 const VideoCodecSettings& codec_settings,
1755 bool force_encoder_allocation) { 1830 bool force_encoder_allocation) {
1756 RTC_DCHECK_RUN_ON(&thread_checker_); 1831 RTC_DCHECK_RUN_ON(&thread_checker_);
1757 parameters_.encoder_config = CreateVideoEncoderConfig(codec_settings.codec); 1832 parameters_.encoder_config = CreateVideoEncoderConfig(codec_settings.codec);
1758 RTC_DCHECK_GT(parameters_.encoder_config.number_of_streams, 0); 1833 RTC_DCHECK_GT(parameters_.encoder_config.number_of_streams, 0);
1759 1834
1835 const bool is_stereo_codec = codec_settings.stereo_codec.has_value();
1836
1760 // Do not re-create encoders of the same type. We can't overwrite 1837 // Do not re-create encoders of the same type. We can't overwrite
1761 // |allocated_encoder_| immediately, because we need to release it after the 1838 // |allocated_encoder_| immediately, because we need to release it after the
1762 // RecreateWebRtcStream() call. 1839 // RecreateWebRtcStream() call.
1763 std::unique_ptr<webrtc::VideoEncoder> new_encoder; 1840 std::unique_ptr<webrtc::VideoEncoder> new_encoder;
1764 if (force_encoder_allocation || !allocated_encoder_ || 1841 if (force_encoder_allocation || !allocated_encoder_ ||
1765 allocated_codec_ != codec_settings.codec) { 1842 allocated_codec_ != codec_settings.codec) {
1766 const bool is_conference_mode_screenshare = 1843 const bool is_conference_mode_screenshare =
1767 parameters_.encoder_config.content_type == 1844 parameters_.encoder_config.content_type ==
1768 webrtc::VideoEncoderConfig::ContentType::kScreen && 1845 webrtc::VideoEncoderConfig::ContentType::kScreen &&
1769 parameters_.conference_mode; 1846 parameters_.conference_mode;
1770 EncoderFactoryAdapter::AllocatedEncoder new_allocated_encoder = 1847 EncoderFactoryAdapter::AllocatedEncoder new_allocated_encoder =
1771 encoder_factory_->CreateVideoEncoder(codec_settings.codec, 1848 encoder_factory_->CreateVideoEncoder(codec_settings.codec,
1772 is_conference_mode_screenshare); 1849 is_conference_mode_screenshare,
1850 is_stereo_codec);
1773 new_encoder = std::unique_ptr<webrtc::VideoEncoder>( 1851 new_encoder = std::unique_ptr<webrtc::VideoEncoder>(
1774 std::move(new_allocated_encoder.encoder)); 1852 std::move(new_allocated_encoder.encoder));
1775 parameters_.config.encoder_settings.encoder = new_encoder.get(); 1853 parameters_.config.encoder_settings.encoder = new_encoder.get();
1776 parameters_.config.encoder_settings.full_overuse_time = 1854 parameters_.config.encoder_settings.full_overuse_time =
1777 new_allocated_encoder.is_hardware_accelerated; 1855 new_allocated_encoder.is_hardware_accelerated;
1778 parameters_.config.encoder_settings.internal_source = 1856 parameters_.config.encoder_settings.internal_source =
1779 new_allocated_encoder.has_internal_source; 1857 new_allocated_encoder.has_internal_source;
1780 } else { 1858 } else {
1781 new_encoder = std::move(allocated_encoder_); 1859 new_encoder = std::move(allocated_encoder_);
1782 } 1860 }
1783 parameters_.config.encoder_settings.payload_name = codec_settings.codec.name; 1861 VideoCodec payload_codec = is_stereo_codec
1784 parameters_.config.encoder_settings.payload_type = codec_settings.codec.id; 1862 ? codec_settings.stereo_codec.value()
1863 : codec_settings.codec;
1864 parameters_.config.encoder_settings.payload_name = payload_codec.name;
1865 parameters_.config.encoder_settings.payload_type = payload_codec.id;
1866 parameters_.config.encoder_settings.stereo_associated_payload_name =
1867 codec_settings.codec.name;
1785 parameters_.config.rtp.ulpfec = codec_settings.ulpfec; 1868 parameters_.config.rtp.ulpfec = codec_settings.ulpfec;
1786 parameters_.config.rtp.flexfec.payload_type = 1869 parameters_.config.rtp.flexfec.payload_type =
1787 codec_settings.flexfec_payload_type; 1870 codec_settings.flexfec_payload_type;
1788 1871
1789 // Set RTX payload type if RTX is enabled. 1872 // Set RTX payload type if RTX is enabled.
1790 if (!parameters_.config.rtp.rtx.ssrcs.empty()) { 1873 if (!parameters_.config.rtp.rtx.ssrcs.empty()) {
1791 if (codec_settings.rtx_payload_type == -1) { 1874 if (codec_settings.rtx_payload_type == -1) {
1792 LOG(LS_WARNING) << "RTX SSRCs configured but there's no configured RTX " 1875 LOG(LS_WARNING) << "RTX SSRCs configured but there's no configured RTX "
1793 "payload type. Ignoring."; 1876 "payload type. Ignoring.";
1794 parameters_.config.rtp.rtx.ssrcs.clear(); 1877 parameters_.config.rtp.rtx.ssrcs.clear();
(...skipping 222 matching lines...) Expand 10 before | Expand all | Expand 10 after
2017 } 2100 }
2018 } 2101 }
2019 2102
2020 VideoSenderInfo WebRtcVideoChannel::WebRtcVideoSendStream::GetVideoSenderInfo( 2103 VideoSenderInfo WebRtcVideoChannel::WebRtcVideoSendStream::GetVideoSenderInfo(
2021 bool log_stats) { 2104 bool log_stats) {
2022 VideoSenderInfo info; 2105 VideoSenderInfo info;
2023 RTC_DCHECK_RUN_ON(&thread_checker_); 2106 RTC_DCHECK_RUN_ON(&thread_checker_);
2024 for (uint32_t ssrc : parameters_.config.rtp.ssrcs) 2107 for (uint32_t ssrc : parameters_.config.rtp.ssrcs)
2025 info.add_ssrc(ssrc); 2108 info.add_ssrc(ssrc);
2026 2109
2110 // TODO(emircan): Add stereo codec case.
2027 if (parameters_.codec_settings) { 2111 if (parameters_.codec_settings) {
2028 info.codec_name = parameters_.codec_settings->codec.name; 2112 info.codec_name = parameters_.codec_settings->codec.name;
2029 info.codec_payload_type = rtc::Optional<int>( 2113 info.codec_payload_type = rtc::Optional<int>(
2030 parameters_.codec_settings->codec.id); 2114 parameters_.codec_settings->codec.id);
2031 } 2115 }
2032 2116
2033 if (stream_ == NULL) 2117 if (stream_ == NULL)
2034 return info; 2118 return info;
2035 2119
2036 webrtc::VideoSendStream::Stats stats = stream_->GetStats(); 2120 webrtc::VideoSendStream::Stats stats = stream_->GetStats();
(...skipping 106 matching lines...) Expand 10 before | Expand all | Expand 10 after
2143 } 2227 }
2144 2228
2145 // Call stream_->Start() if necessary conditions are met. 2229 // Call stream_->Start() if necessary conditions are met.
2146 UpdateSendState(); 2230 UpdateSendState();
2147 } 2231 }
2148 2232
2149 WebRtcVideoChannel::WebRtcVideoReceiveStream::WebRtcVideoReceiveStream( 2233 WebRtcVideoChannel::WebRtcVideoReceiveStream::WebRtcVideoReceiveStream(
2150 webrtc::Call* call, 2234 webrtc::Call* call,
2151 const StreamParams& sp, 2235 const StreamParams& sp,
2152 webrtc::VideoReceiveStream::Config config, 2236 webrtc::VideoReceiveStream::Config config,
2153 const DecoderFactoryAdapter* decoder_factory, 2237 DecoderFactoryAdapter* decoder_factory,
2154 bool default_stream, 2238 bool default_stream,
2155 const std::vector<VideoCodecSettings>& recv_codecs, 2239 const std::vector<VideoCodecSettings>& recv_codecs,
2156 const webrtc::FlexfecReceiveStream::Config& flexfec_config) 2240 const webrtc::FlexfecReceiveStream::Config& flexfec_config)
2157 : call_(call), 2241 : call_(call),
2158 stream_params_(sp), 2242 stream_params_(sp),
2159 stream_(NULL), 2243 stream_(NULL),
2160 default_stream_(default_stream), 2244 default_stream_(default_stream),
2161 config_(std::move(config)), 2245 config_(std::move(config)),
2162 flexfec_config_(flexfec_config), 2246 flexfec_config_(flexfec_config),
2163 flexfec_stream_(nullptr), 2247 flexfec_stream_(nullptr),
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
2197 LOG(LS_WARNING) << "Empty primary ssrcs vector, returning empty optional"; 2281 LOG(LS_WARNING) << "Empty primary ssrcs vector, returning empty optional";
2198 return rtc::Optional<uint32_t>(); 2282 return rtc::Optional<uint32_t>();
2199 } else { 2283 } else {
2200 return rtc::Optional<uint32_t>(primary_ssrcs[0]); 2284 return rtc::Optional<uint32_t>(primary_ssrcs[0]);
2201 } 2285 }
2202 } 2286 }
2203 2287
2204 std::unique_ptr<webrtc::VideoDecoder> 2288 std::unique_ptr<webrtc::VideoDecoder>
2205 CricketDecoderFactoryAdapter::CreateVideoDecoder( 2289 CricketDecoderFactoryAdapter::CreateVideoDecoder(
2206 const VideoCodec& codec, 2290 const VideoCodec& codec,
2207 const VideoDecoderParams& decoder_params) const { 2291 const VideoDecoderParams& decoder_params,
2292 bool is_stereo_codec) const {
2293 if (is_stereo_codec) {
2294 if (external_decoder_factory_ != nullptr) {
2295 std::unique_ptr<webrtc::VideoDecoder> external_decoder(
2296 new webrtc::StereoDecoderAdapter(external_decoder_factory_));
2297 return external_decoder;
2298 }
2299 std::unique_ptr<webrtc::VideoDecoder> internal_decoder(
2300 new webrtc::StereoDecoderAdapter(internal_decoder_factory_.get()));
2301 return internal_decoder;
2302 }
2303
2208 if (external_decoder_factory_ != nullptr) { 2304 if (external_decoder_factory_ != nullptr) {
2209 std::unique_ptr<webrtc::VideoDecoder> external_decoder = 2305 std::unique_ptr<webrtc::VideoDecoder> external_decoder =
2210 CreateScopedVideoDecoder(external_decoder_factory_, codec, 2306 CreateScopedVideoDecoder(external_decoder_factory_, codec,
2211 decoder_params); 2307 decoder_params);
2212 if (external_decoder) { 2308 if (external_decoder) {
2213 webrtc::VideoCodecType type = 2309 webrtc::VideoCodecType type =
2214 webrtc::PayloadStringToCodecType(codec.name); 2310 webrtc::PayloadStringToCodecType(codec.name);
2215 std::unique_ptr<webrtc::VideoDecoder> internal_decoder( 2311 std::unique_ptr<webrtc::VideoDecoder> internal_decoder(
2216 new webrtc::VideoDecoderSoftwareFallbackWrapper( 2312 new webrtc::VideoDecoderSoftwareFallbackWrapper(
2217 type, std::move(external_decoder))); 2313 type, std::move(external_decoder)));
2218 return internal_decoder; 2314 return internal_decoder;
2219 } 2315 }
2220 } 2316 }
2221 2317
2222 std::unique_ptr<webrtc::VideoDecoder> internal_decoder( 2318 std::unique_ptr<webrtc::VideoDecoder> internal_decoder(
2223 internal_decoder_factory_->CreateVideoDecoderWithParams(codec, 2319 internal_decoder_factory_->CreateVideoDecoderWithParams(codec,
2224 decoder_params)); 2320 decoder_params));
2225 return internal_decoder; 2321 return internal_decoder;
2226 } 2322 }
2227 2323
2228 void WebRtcVideoChannel::WebRtcVideoReceiveStream::ConfigureCodecs( 2324 void WebRtcVideoChannel::WebRtcVideoReceiveStream::ConfigureCodecs(
2229 const std::vector<VideoCodecSettings>& recv_codecs, 2325 const std::vector<VideoCodecSettings>& recv_codecs,
2230 DecoderMap* old_decoders) { 2326 DecoderMap* old_decoders) {
2231 *old_decoders = std::move(allocated_decoders_); 2327 *old_decoders = std::move(allocated_decoders_);
2232 config_.decoders.clear(); 2328 config_.decoders.clear();
2233 config_.rtp.rtx_associated_payload_types.clear(); 2329 config_.rtp.rtx_associated_payload_types.clear();
2234 for (const auto& recv_codec : recv_codecs) { 2330 for (const auto& recv_codec : recv_codecs) {
2331 const bool is_stereo_codec =
2332 cricket::VideoCodec::IsStereoCodec(recv_codec.codec);
2235 webrtc::SdpVideoFormat video_format(recv_codec.codec.name, 2333 webrtc::SdpVideoFormat video_format(recv_codec.codec.name,
2236 recv_codec.codec.params); 2334 recv_codec.codec.params);
2237 std::unique_ptr<webrtc::VideoDecoder> new_decoder; 2335 std::unique_ptr<webrtc::VideoDecoder> new_decoder;
2238 2336
2239 auto it = old_decoders->find(video_format); 2337 auto it = old_decoders->find(video_format);
2240 if (it != old_decoders->end()) { 2338 if (it != old_decoders->end() && !is_stereo_codec) {
2241 new_decoder = std::move(it->second); 2339 new_decoder = std::move(it->second);
2242 old_decoders->erase(it); 2340 old_decoders->erase(it);
2243 } 2341 }
2244 2342
2245 if (!new_decoder) { 2343 if (!new_decoder) {
2246 new_decoder = decoder_factory_->CreateVideoDecoder(recv_codec.codec, 2344 new_decoder = decoder_factory_->CreateVideoDecoder(
2247 {stream_params_.id}); 2345 recv_codec.codec, {stream_params_.id}, is_stereo_codec);
2248 } 2346 }
2249 2347
2250 webrtc::VideoReceiveStream::Decoder decoder; 2348 webrtc::VideoReceiveStream::Decoder decoder;
2251 decoder.decoder = new_decoder.get(); 2349 decoder.decoder = new_decoder.get();
2252 decoder.payload_type = recv_codec.codec.id; 2350 decoder.payload_type = recv_codec.codec.id;
2253 decoder.payload_name = recv_codec.codec.name; 2351 decoder.payload_name = recv_codec.codec.name;
2254 decoder.codec_params = recv_codec.codec.params; 2352 decoder.codec_params = recv_codec.codec.params;
2255 config_.decoders.push_back(decoder); 2353 config_.decoders.push_back(decoder);
2256 config_.rtp.rtx_associated_payload_types[recv_codec.rtx_payload_type] = 2354 config_.rtp.rtx_associated_payload_types[recv_codec.rtx_payload_type] =
2257 recv_codec.codec.id; 2355 recv_codec.codec.id;
(...skipping 423 matching lines...) Expand 10 before | Expand all | Expand 10 after
2681 stream.temporal_layer_thresholds_bps.resize(GetDefaultVp9TemporalLayers() - 2779 stream.temporal_layer_thresholds_bps.resize(GetDefaultVp9TemporalLayers() -
2682 1); 2780 1);
2683 } 2781 }
2684 2782
2685 std::vector<webrtc::VideoStream> streams; 2783 std::vector<webrtc::VideoStream> streams;
2686 streams.push_back(stream); 2784 streams.push_back(stream);
2687 return streams; 2785 return streams;
2688 } 2786 }
2689 2787
2690 } // namespace cricket 2788 } // namespace cricket
OLDNEW
« no previous file with comments | « media/engine/webrtcvideoengine.h ('k') | modules/include/module_common_types.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698