OLD | NEW |
---|---|
(Empty) | |
1 /* | |
2 * Copyright 2017 The WebRTC project authors. All Rights Reserved. | |
3 * | |
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 | |
6 * tree. An additional intellectual property rights grant can be found | |
7 * in the file PATENTS. All contributing project authors may | |
8 * be found in the AUTHORS file in the root of the source tree. | |
9 */ | |
10 | |
11 #include "webrtc/ortc/rtpsendershim.h" | |
12 | |
13 #include "webrtc/base/checks.h" | |
14 | |
15 namespace { | |
16 | |
17 static const int kVideoClockrate = 90000; | |
18 | |
19 void FillAudioSenderParameters(webrtc::RtpParameters* parameters) { | |
20 for (webrtc::RtpCodecParameters& codec : parameters->codecs) { | |
21 if (!codec.num_channels) { | |
22 codec.num_channels = rtc::Optional<int>(1); | |
23 } | |
24 } | |
25 } | |
26 | |
27 void FillVideoSenderParameters(webrtc::RtpParameters* parameters) { | |
28 for (webrtc::RtpCodecParameters& codec : parameters->codecs) { | |
29 if (!codec.clock_rate) { | |
30 codec.clock_rate = rtc::Optional<int>(kVideoClockrate); | |
31 } | |
32 } | |
pthatcher1
2017/02/10 22:36:52
Would it make sense to de-dup the code above?
Taylor Brandstetter
2017/02/14 06:55:05
I don't see duplicated code above
| |
33 } | |
34 | |
35 } // namespace | |
36 | |
37 namespace webrtc { | |
38 | |
39 BEGIN_OWNED_PROXY_MAP(OrtcRtpSender) | |
40 PROXY_SIGNALING_THREAD_DESTRUCTOR() | |
41 PROXY_METHOD1(RTCError, SetTrack, MediaStreamTrackInterface*) | |
42 PROXY_CONSTMETHOD0(rtc::scoped_refptr<MediaStreamTrackInterface>, GetTrack) | |
43 PROXY_METHOD1(RTCError, SetTransport, RtpTransportInterface*) | |
44 PROXY_CONSTMETHOD0(RtpTransportInterface*, GetTransport) | |
45 PROXY_METHOD1(RTCError, Send, const RtpParameters&) | |
46 PROXY_CONSTMETHOD0(RtpParameters, GetParameters) | |
47 PROXY_CONSTMETHOD0(cricket::MediaType, GetKind) | |
48 END_PROXY_MAP() | |
49 | |
50 // static | |
51 RTCErrorOr<std::unique_ptr<OrtcRtpSenderInterface>> | |
52 RtpSenderShim::CreateProxied(cricket::MediaType kind, | |
53 RtpTransportShim* transport) { | |
54 RTC_DCHECK(transport); | |
55 RtpTransportControllerShim* rtp_transport_controller = | |
56 transport->rtp_transport_controller(); | |
57 // Call "attach" method to ensure more than one sender of the same type | |
58 // isn't attached to the same transport. | |
59 RTCError err; | |
60 switch (kind) { | |
61 case cricket::MEDIA_TYPE_AUDIO: | |
62 err = rtp_transport_controller->AttachAudioSender(transport); | |
63 break; | |
64 case cricket::MEDIA_TYPE_VIDEO: | |
65 err = rtp_transport_controller->AttachVideoSender(transport); | |
66 break; | |
67 case cricket::MEDIA_TYPE_DATA: | |
68 RTC_NOTREACHED(); | |
69 } | |
70 if (!err.ok()) { | |
71 return err; | |
72 } | |
73 | |
74 return OrtcRtpSenderProxy::Create( | |
75 rtp_transport_controller->signaling_thread(), | |
76 rtp_transport_controller->worker_thread(), | |
77 new RtpSenderShim(kind, transport, rtp_transport_controller)); | |
78 } | |
79 | |
80 RtpSenderShim::~RtpSenderShim() { | |
81 internal_sender_ = nullptr; | |
82 // Need to detach from transport (was attached in Create method). | |
83 switch (kind_) { | |
84 case cricket::MEDIA_TYPE_AUDIO: | |
85 rtp_transport_controller_->DetachAudioSender(); | |
86 break; | |
87 case cricket::MEDIA_TYPE_VIDEO: | |
88 rtp_transport_controller_->DetachVideoSender(); | |
89 break; | |
90 case cricket::MEDIA_TYPE_DATA: | |
91 RTC_NOTREACHED(); | |
92 } | |
93 } | |
94 | |
95 RTCError RtpSenderShim::SetTrack(MediaStreamTrackInterface* track) { | |
96 if (cricket::MediaTypeFromString(track->kind()) != kind_) { | |
97 return CreateAndLogError( | |
98 RTCErrorType::INVALID_PARAMETER, | |
99 "Track kind (audio/video) doesn't match the kind of this sender."); | |
100 } | |
101 if (!internal_sender_->SetTrack(track)) { | |
102 // Since we checked the track type above, this should never happen... | |
103 RTC_NOTREACHED(); | |
104 return RTCError(RTCErrorType::INTERNAL_ERROR); | |
105 } | |
106 return RTCError(); | |
107 } | |
108 | |
109 rtc::scoped_refptr<MediaStreamTrackInterface> RtpSenderShim::GetTrack() const { | |
110 return internal_sender_->track(); | |
111 } | |
112 | |
113 RTCError RtpSenderShim::SetTransport(RtpTransportInterface* transport) { | |
114 LOG(LS_ERROR) << "Changing the transport of an RtpSender is not yet " | |
115 << "supported."; | |
116 return RTCError(RTCErrorType::UNSUPPORTED_PARAMETER); | |
117 } | |
118 | |
119 RtpTransportInterface* RtpSenderShim::GetTransport() const { | |
120 return transport_; | |
121 } | |
122 | |
123 RTCError RtpSenderShim::Send(const RtpParameters& parameters) { | |
124 RtpParameters filled_parameters = parameters; | |
125 RTCError err; | |
126 uint32_t ssrc = 0; | |
127 switch (kind_) { | |
128 case cricket::MEDIA_TYPE_AUDIO: | |
129 FillAudioSenderParameters(&filled_parameters); | |
130 err = rtp_transport_controller_->ValidateAndApplyAudioSenderParameters( | |
131 filled_parameters, &ssrc); | |
132 if (!err.ok()) { | |
133 return err; | |
134 } | |
135 break; | |
136 case cricket::MEDIA_TYPE_VIDEO: | |
137 FillVideoSenderParameters(&filled_parameters); | |
138 err = rtp_transport_controller_->ValidateAndApplyVideoSenderParameters( | |
139 filled_parameters, &ssrc); | |
140 if (!err.ok()) { | |
141 return err; | |
142 } | |
143 break; | |
144 case cricket::MEDIA_TYPE_DATA: | |
145 RTC_NOTREACHED(); | |
146 return webrtc::RTCError(webrtc::RTCErrorType::INTERNAL_ERROR); | |
147 } | |
148 last_applied_parameters_ = filled_parameters; | |
149 | |
150 // Now that parameters were applied, can call SetSsrc on the internal sender. | |
151 // This is analogous to a PeerConnection calling SetSsrc after | |
152 // SetLocalDescription is successful. | |
153 // | |
154 // If there were no encodings, this SSRC may be 0, which is valid. | |
155 internal_sender_->SetSsrc(ssrc); | |
156 | |
157 return RTCError(); | |
158 } | |
159 | |
160 RtpParameters RtpSenderShim::GetParameters() const { | |
161 return last_applied_parameters_; | |
162 } | |
163 | |
164 cricket::MediaType RtpSenderShim::GetKind() const { | |
165 return internal_sender_->media_type(); | |
166 } | |
167 | |
168 RtpSenderShim::RtpSenderShim( | |
169 cricket::MediaType kind, | |
170 RtpTransportShim* transport, | |
171 RtpTransportControllerShim* rtp_transport_controller) | |
172 : kind_(kind), | |
173 transport_(transport), | |
174 rtp_transport_controller_(rtp_transport_controller) { | |
175 CreateInternalSender(); | |
176 } | |
177 | |
178 void RtpSenderShim::CreateInternalSender() { | |
179 switch (kind_) { | |
180 case cricket::MEDIA_TYPE_AUDIO: | |
181 internal_sender_ = new AudioRtpSender( | |
182 rtp_transport_controller_->voice_channel(), nullptr); | |
183 break; | |
184 case cricket::MEDIA_TYPE_VIDEO: | |
185 internal_sender_ = | |
186 new VideoRtpSender(rtp_transport_controller_->video_channel()); | |
187 break; | |
188 case cricket::MEDIA_TYPE_DATA: | |
189 RTC_NOTREACHED(); | |
pthatcher1
2017/02/10 22:36:52
I'm going to stop commenting on these. Perhaps I
Taylor Brandstetter
2017/02/14 06:55:05
Yes.
| |
190 } | |
191 } | |
192 | |
193 } // namespace webrtc | |
OLD | NEW |