xref: /aosp_15_r20/external/webrtc/pc/rtp_transport.cc (revision d9f758449e529ab9291ac668be2861e7a55c2422)
1*d9f75844SAndroid Build Coastguard Worker /*
2*d9f75844SAndroid Build Coastguard Worker  *  Copyright 2017 The WebRTC project authors. All Rights Reserved.
3*d9f75844SAndroid Build Coastguard Worker  *
4*d9f75844SAndroid Build Coastguard Worker  *  Use of this source code is governed by a BSD-style license
5*d9f75844SAndroid Build Coastguard Worker  *  that can be found in the LICENSE file in the root of the source
6*d9f75844SAndroid Build Coastguard Worker  *  tree. An additional intellectual property rights grant can be found
7*d9f75844SAndroid Build Coastguard Worker  *  in the file PATENTS.  All contributing project authors may
8*d9f75844SAndroid Build Coastguard Worker  *  be found in the AUTHORS file in the root of the source tree.
9*d9f75844SAndroid Build Coastguard Worker  */
10*d9f75844SAndroid Build Coastguard Worker 
11*d9f75844SAndroid Build Coastguard Worker #include "pc/rtp_transport.h"
12*d9f75844SAndroid Build Coastguard Worker 
13*d9f75844SAndroid Build Coastguard Worker #include <errno.h>
14*d9f75844SAndroid Build Coastguard Worker 
15*d9f75844SAndroid Build Coastguard Worker #include <cstdint>
16*d9f75844SAndroid Build Coastguard Worker #include <utility>
17*d9f75844SAndroid Build Coastguard Worker 
18*d9f75844SAndroid Build Coastguard Worker #include "absl/strings/string_view.h"
19*d9f75844SAndroid Build Coastguard Worker #include "api/array_view.h"
20*d9f75844SAndroid Build Coastguard Worker #include "api/units/timestamp.h"
21*d9f75844SAndroid Build Coastguard Worker #include "media/base/rtp_utils.h"
22*d9f75844SAndroid Build Coastguard Worker #include "modules/rtp_rtcp/source/rtp_packet_received.h"
23*d9f75844SAndroid Build Coastguard Worker #include "rtc_base/checks.h"
24*d9f75844SAndroid Build Coastguard Worker #include "rtc_base/copy_on_write_buffer.h"
25*d9f75844SAndroid Build Coastguard Worker #include "rtc_base/logging.h"
26*d9f75844SAndroid Build Coastguard Worker #include "rtc_base/trace_event.h"
27*d9f75844SAndroid Build Coastguard Worker 
28*d9f75844SAndroid Build Coastguard Worker namespace webrtc {
29*d9f75844SAndroid Build Coastguard Worker 
SetRtcpMuxEnabled(bool enable)30*d9f75844SAndroid Build Coastguard Worker void RtpTransport::SetRtcpMuxEnabled(bool enable) {
31*d9f75844SAndroid Build Coastguard Worker   rtcp_mux_enabled_ = enable;
32*d9f75844SAndroid Build Coastguard Worker   MaybeSignalReadyToSend();
33*d9f75844SAndroid Build Coastguard Worker }
34*d9f75844SAndroid Build Coastguard Worker 
transport_name() const35*d9f75844SAndroid Build Coastguard Worker const std::string& RtpTransport::transport_name() const {
36*d9f75844SAndroid Build Coastguard Worker   return rtp_packet_transport_->transport_name();
37*d9f75844SAndroid Build Coastguard Worker }
38*d9f75844SAndroid Build Coastguard Worker 
SetRtpOption(rtc::Socket::Option opt,int value)39*d9f75844SAndroid Build Coastguard Worker int RtpTransport::SetRtpOption(rtc::Socket::Option opt, int value) {
40*d9f75844SAndroid Build Coastguard Worker   return rtp_packet_transport_->SetOption(opt, value);
41*d9f75844SAndroid Build Coastguard Worker }
42*d9f75844SAndroid Build Coastguard Worker 
SetRtcpOption(rtc::Socket::Option opt,int value)43*d9f75844SAndroid Build Coastguard Worker int RtpTransport::SetRtcpOption(rtc::Socket::Option opt, int value) {
44*d9f75844SAndroid Build Coastguard Worker   if (rtcp_packet_transport_) {
45*d9f75844SAndroid Build Coastguard Worker     return rtcp_packet_transport_->SetOption(opt, value);
46*d9f75844SAndroid Build Coastguard Worker   }
47*d9f75844SAndroid Build Coastguard Worker   return -1;
48*d9f75844SAndroid Build Coastguard Worker }
49*d9f75844SAndroid Build Coastguard Worker 
SetRtpPacketTransport(rtc::PacketTransportInternal * new_packet_transport)50*d9f75844SAndroid Build Coastguard Worker void RtpTransport::SetRtpPacketTransport(
51*d9f75844SAndroid Build Coastguard Worker     rtc::PacketTransportInternal* new_packet_transport) {
52*d9f75844SAndroid Build Coastguard Worker   if (new_packet_transport == rtp_packet_transport_) {
53*d9f75844SAndroid Build Coastguard Worker     return;
54*d9f75844SAndroid Build Coastguard Worker   }
55*d9f75844SAndroid Build Coastguard Worker   if (rtp_packet_transport_) {
56*d9f75844SAndroid Build Coastguard Worker     rtp_packet_transport_->SignalReadyToSend.disconnect(this);
57*d9f75844SAndroid Build Coastguard Worker     rtp_packet_transport_->SignalReadPacket.disconnect(this);
58*d9f75844SAndroid Build Coastguard Worker     rtp_packet_transport_->SignalNetworkRouteChanged.disconnect(this);
59*d9f75844SAndroid Build Coastguard Worker     rtp_packet_transport_->SignalWritableState.disconnect(this);
60*d9f75844SAndroid Build Coastguard Worker     rtp_packet_transport_->SignalSentPacket.disconnect(this);
61*d9f75844SAndroid Build Coastguard Worker     // Reset the network route of the old transport.
62*d9f75844SAndroid Build Coastguard Worker     SignalNetworkRouteChanged(absl::optional<rtc::NetworkRoute>());
63*d9f75844SAndroid Build Coastguard Worker   }
64*d9f75844SAndroid Build Coastguard Worker   if (new_packet_transport) {
65*d9f75844SAndroid Build Coastguard Worker     new_packet_transport->SignalReadyToSend.connect(
66*d9f75844SAndroid Build Coastguard Worker         this, &RtpTransport::OnReadyToSend);
67*d9f75844SAndroid Build Coastguard Worker     new_packet_transport->SignalReadPacket.connect(this,
68*d9f75844SAndroid Build Coastguard Worker                                                    &RtpTransport::OnReadPacket);
69*d9f75844SAndroid Build Coastguard Worker     new_packet_transport->SignalNetworkRouteChanged.connect(
70*d9f75844SAndroid Build Coastguard Worker         this, &RtpTransport::OnNetworkRouteChanged);
71*d9f75844SAndroid Build Coastguard Worker     new_packet_transport->SignalWritableState.connect(
72*d9f75844SAndroid Build Coastguard Worker         this, &RtpTransport::OnWritableState);
73*d9f75844SAndroid Build Coastguard Worker     new_packet_transport->SignalSentPacket.connect(this,
74*d9f75844SAndroid Build Coastguard Worker                                                    &RtpTransport::OnSentPacket);
75*d9f75844SAndroid Build Coastguard Worker     // Set the network route for the new transport.
76*d9f75844SAndroid Build Coastguard Worker     SignalNetworkRouteChanged(new_packet_transport->network_route());
77*d9f75844SAndroid Build Coastguard Worker   }
78*d9f75844SAndroid Build Coastguard Worker 
79*d9f75844SAndroid Build Coastguard Worker   rtp_packet_transport_ = new_packet_transport;
80*d9f75844SAndroid Build Coastguard Worker   // Assumes the transport is ready to send if it is writable. If we are wrong,
81*d9f75844SAndroid Build Coastguard Worker   // ready to send will be updated the next time we try to send.
82*d9f75844SAndroid Build Coastguard Worker   SetReadyToSend(false,
83*d9f75844SAndroid Build Coastguard Worker                  rtp_packet_transport_ && rtp_packet_transport_->writable());
84*d9f75844SAndroid Build Coastguard Worker }
85*d9f75844SAndroid Build Coastguard Worker 
SetRtcpPacketTransport(rtc::PacketTransportInternal * new_packet_transport)86*d9f75844SAndroid Build Coastguard Worker void RtpTransport::SetRtcpPacketTransport(
87*d9f75844SAndroid Build Coastguard Worker     rtc::PacketTransportInternal* new_packet_transport) {
88*d9f75844SAndroid Build Coastguard Worker   if (new_packet_transport == rtcp_packet_transport_) {
89*d9f75844SAndroid Build Coastguard Worker     return;
90*d9f75844SAndroid Build Coastguard Worker   }
91*d9f75844SAndroid Build Coastguard Worker   if (rtcp_packet_transport_) {
92*d9f75844SAndroid Build Coastguard Worker     rtcp_packet_transport_->SignalReadyToSend.disconnect(this);
93*d9f75844SAndroid Build Coastguard Worker     rtcp_packet_transport_->SignalReadPacket.disconnect(this);
94*d9f75844SAndroid Build Coastguard Worker     rtcp_packet_transport_->SignalNetworkRouteChanged.disconnect(this);
95*d9f75844SAndroid Build Coastguard Worker     rtcp_packet_transport_->SignalWritableState.disconnect(this);
96*d9f75844SAndroid Build Coastguard Worker     rtcp_packet_transport_->SignalSentPacket.disconnect(this);
97*d9f75844SAndroid Build Coastguard Worker     // Reset the network route of the old transport.
98*d9f75844SAndroid Build Coastguard Worker     SignalNetworkRouteChanged(absl::optional<rtc::NetworkRoute>());
99*d9f75844SAndroid Build Coastguard Worker   }
100*d9f75844SAndroid Build Coastguard Worker   if (new_packet_transport) {
101*d9f75844SAndroid Build Coastguard Worker     new_packet_transport->SignalReadyToSend.connect(
102*d9f75844SAndroid Build Coastguard Worker         this, &RtpTransport::OnReadyToSend);
103*d9f75844SAndroid Build Coastguard Worker     new_packet_transport->SignalReadPacket.connect(this,
104*d9f75844SAndroid Build Coastguard Worker                                                    &RtpTransport::OnReadPacket);
105*d9f75844SAndroid Build Coastguard Worker     new_packet_transport->SignalNetworkRouteChanged.connect(
106*d9f75844SAndroid Build Coastguard Worker         this, &RtpTransport::OnNetworkRouteChanged);
107*d9f75844SAndroid Build Coastguard Worker     new_packet_transport->SignalWritableState.connect(
108*d9f75844SAndroid Build Coastguard Worker         this, &RtpTransport::OnWritableState);
109*d9f75844SAndroid Build Coastguard Worker     new_packet_transport->SignalSentPacket.connect(this,
110*d9f75844SAndroid Build Coastguard Worker                                                    &RtpTransport::OnSentPacket);
111*d9f75844SAndroid Build Coastguard Worker     // Set the network route for the new transport.
112*d9f75844SAndroid Build Coastguard Worker     SignalNetworkRouteChanged(new_packet_transport->network_route());
113*d9f75844SAndroid Build Coastguard Worker   }
114*d9f75844SAndroid Build Coastguard Worker   rtcp_packet_transport_ = new_packet_transport;
115*d9f75844SAndroid Build Coastguard Worker 
116*d9f75844SAndroid Build Coastguard Worker   // Assumes the transport is ready to send if it is writable. If we are wrong,
117*d9f75844SAndroid Build Coastguard Worker   // ready to send will be updated the next time we try to send.
118*d9f75844SAndroid Build Coastguard Worker   SetReadyToSend(true,
119*d9f75844SAndroid Build Coastguard Worker                  rtcp_packet_transport_ && rtcp_packet_transport_->writable());
120*d9f75844SAndroid Build Coastguard Worker }
121*d9f75844SAndroid Build Coastguard Worker 
IsWritable(bool rtcp) const122*d9f75844SAndroid Build Coastguard Worker bool RtpTransport::IsWritable(bool rtcp) const {
123*d9f75844SAndroid Build Coastguard Worker   rtc::PacketTransportInternal* transport = rtcp && !rtcp_mux_enabled_
124*d9f75844SAndroid Build Coastguard Worker                                                 ? rtcp_packet_transport_
125*d9f75844SAndroid Build Coastguard Worker                                                 : rtp_packet_transport_;
126*d9f75844SAndroid Build Coastguard Worker   return transport && transport->writable();
127*d9f75844SAndroid Build Coastguard Worker }
128*d9f75844SAndroid Build Coastguard Worker 
SendRtpPacket(rtc::CopyOnWriteBuffer * packet,const rtc::PacketOptions & options,int flags)129*d9f75844SAndroid Build Coastguard Worker bool RtpTransport::SendRtpPacket(rtc::CopyOnWriteBuffer* packet,
130*d9f75844SAndroid Build Coastguard Worker                                  const rtc::PacketOptions& options,
131*d9f75844SAndroid Build Coastguard Worker                                  int flags) {
132*d9f75844SAndroid Build Coastguard Worker   return SendPacket(false, packet, options, flags);
133*d9f75844SAndroid Build Coastguard Worker }
134*d9f75844SAndroid Build Coastguard Worker 
SendRtcpPacket(rtc::CopyOnWriteBuffer * packet,const rtc::PacketOptions & options,int flags)135*d9f75844SAndroid Build Coastguard Worker bool RtpTransport::SendRtcpPacket(rtc::CopyOnWriteBuffer* packet,
136*d9f75844SAndroid Build Coastguard Worker                                   const rtc::PacketOptions& options,
137*d9f75844SAndroid Build Coastguard Worker                                   int flags) {
138*d9f75844SAndroid Build Coastguard Worker   return SendPacket(true, packet, options, flags);
139*d9f75844SAndroid Build Coastguard Worker }
140*d9f75844SAndroid Build Coastguard Worker 
SendPacket(bool rtcp,rtc::CopyOnWriteBuffer * packet,const rtc::PacketOptions & options,int flags)141*d9f75844SAndroid Build Coastguard Worker bool RtpTransport::SendPacket(bool rtcp,
142*d9f75844SAndroid Build Coastguard Worker                               rtc::CopyOnWriteBuffer* packet,
143*d9f75844SAndroid Build Coastguard Worker                               const rtc::PacketOptions& options,
144*d9f75844SAndroid Build Coastguard Worker                               int flags) {
145*d9f75844SAndroid Build Coastguard Worker   rtc::PacketTransportInternal* transport = rtcp && !rtcp_mux_enabled_
146*d9f75844SAndroid Build Coastguard Worker                                                 ? rtcp_packet_transport_
147*d9f75844SAndroid Build Coastguard Worker                                                 : rtp_packet_transport_;
148*d9f75844SAndroid Build Coastguard Worker   int ret = transport->SendPacket(packet->cdata<char>(), packet->size(),
149*d9f75844SAndroid Build Coastguard Worker                                   options, flags);
150*d9f75844SAndroid Build Coastguard Worker   if (ret != static_cast<int>(packet->size())) {
151*d9f75844SAndroid Build Coastguard Worker     if (transport->GetError() == ENOTCONN) {
152*d9f75844SAndroid Build Coastguard Worker       RTC_LOG(LS_WARNING) << "Got ENOTCONN from transport.";
153*d9f75844SAndroid Build Coastguard Worker       SetReadyToSend(rtcp, false);
154*d9f75844SAndroid Build Coastguard Worker     }
155*d9f75844SAndroid Build Coastguard Worker     return false;
156*d9f75844SAndroid Build Coastguard Worker   }
157*d9f75844SAndroid Build Coastguard Worker   return true;
158*d9f75844SAndroid Build Coastguard Worker }
159*d9f75844SAndroid Build Coastguard Worker 
UpdateRtpHeaderExtensionMap(const cricket::RtpHeaderExtensions & header_extensions)160*d9f75844SAndroid Build Coastguard Worker void RtpTransport::UpdateRtpHeaderExtensionMap(
161*d9f75844SAndroid Build Coastguard Worker     const cricket::RtpHeaderExtensions& header_extensions) {
162*d9f75844SAndroid Build Coastguard Worker   header_extension_map_ = RtpHeaderExtensionMap(header_extensions);
163*d9f75844SAndroid Build Coastguard Worker }
164*d9f75844SAndroid Build Coastguard Worker 
RegisterRtpDemuxerSink(const RtpDemuxerCriteria & criteria,RtpPacketSinkInterface * sink)165*d9f75844SAndroid Build Coastguard Worker bool RtpTransport::RegisterRtpDemuxerSink(const RtpDemuxerCriteria& criteria,
166*d9f75844SAndroid Build Coastguard Worker                                           RtpPacketSinkInterface* sink) {
167*d9f75844SAndroid Build Coastguard Worker   rtp_demuxer_.RemoveSink(sink);
168*d9f75844SAndroid Build Coastguard Worker   if (!rtp_demuxer_.AddSink(criteria, sink)) {
169*d9f75844SAndroid Build Coastguard Worker     RTC_LOG(LS_ERROR) << "Failed to register the sink for RTP demuxer.";
170*d9f75844SAndroid Build Coastguard Worker     return false;
171*d9f75844SAndroid Build Coastguard Worker   }
172*d9f75844SAndroid Build Coastguard Worker   return true;
173*d9f75844SAndroid Build Coastguard Worker }
174*d9f75844SAndroid Build Coastguard Worker 
UnregisterRtpDemuxerSink(RtpPacketSinkInterface * sink)175*d9f75844SAndroid Build Coastguard Worker bool RtpTransport::UnregisterRtpDemuxerSink(RtpPacketSinkInterface* sink) {
176*d9f75844SAndroid Build Coastguard Worker   if (!rtp_demuxer_.RemoveSink(sink)) {
177*d9f75844SAndroid Build Coastguard Worker     RTC_LOG(LS_ERROR) << "Failed to unregister the sink for RTP demuxer.";
178*d9f75844SAndroid Build Coastguard Worker     return false;
179*d9f75844SAndroid Build Coastguard Worker   }
180*d9f75844SAndroid Build Coastguard Worker   return true;
181*d9f75844SAndroid Build Coastguard Worker }
182*d9f75844SAndroid Build Coastguard Worker 
DemuxPacket(rtc::CopyOnWriteBuffer packet,int64_t packet_time_us)183*d9f75844SAndroid Build Coastguard Worker void RtpTransport::DemuxPacket(rtc::CopyOnWriteBuffer packet,
184*d9f75844SAndroid Build Coastguard Worker                                int64_t packet_time_us) {
185*d9f75844SAndroid Build Coastguard Worker   webrtc::RtpPacketReceived parsed_packet(
186*d9f75844SAndroid Build Coastguard Worker       &header_extension_map_, packet_time_us == -1
187*d9f75844SAndroid Build Coastguard Worker                                   ? Timestamp::MinusInfinity()
188*d9f75844SAndroid Build Coastguard Worker                                   : Timestamp::Micros(packet_time_us));
189*d9f75844SAndroid Build Coastguard Worker   if (!parsed_packet.Parse(std::move(packet))) {
190*d9f75844SAndroid Build Coastguard Worker     RTC_LOG(LS_ERROR)
191*d9f75844SAndroid Build Coastguard Worker         << "Failed to parse the incoming RTP packet before demuxing. Drop it.";
192*d9f75844SAndroid Build Coastguard Worker     return;
193*d9f75844SAndroid Build Coastguard Worker   }
194*d9f75844SAndroid Build Coastguard Worker 
195*d9f75844SAndroid Build Coastguard Worker   if (!rtp_demuxer_.OnRtpPacket(parsed_packet)) {
196*d9f75844SAndroid Build Coastguard Worker     RTC_LOG(LS_WARNING) << "Failed to demux RTP packet: "
197*d9f75844SAndroid Build Coastguard Worker                         << RtpDemuxer::DescribePacket(parsed_packet);
198*d9f75844SAndroid Build Coastguard Worker   }
199*d9f75844SAndroid Build Coastguard Worker }
200*d9f75844SAndroid Build Coastguard Worker 
IsTransportWritable()201*d9f75844SAndroid Build Coastguard Worker bool RtpTransport::IsTransportWritable() {
202*d9f75844SAndroid Build Coastguard Worker   auto rtcp_packet_transport =
203*d9f75844SAndroid Build Coastguard Worker       rtcp_mux_enabled_ ? nullptr : rtcp_packet_transport_;
204*d9f75844SAndroid Build Coastguard Worker   return rtp_packet_transport_ && rtp_packet_transport_->writable() &&
205*d9f75844SAndroid Build Coastguard Worker          (!rtcp_packet_transport || rtcp_packet_transport->writable());
206*d9f75844SAndroid Build Coastguard Worker }
207*d9f75844SAndroid Build Coastguard Worker 
OnReadyToSend(rtc::PacketTransportInternal * transport)208*d9f75844SAndroid Build Coastguard Worker void RtpTransport::OnReadyToSend(rtc::PacketTransportInternal* transport) {
209*d9f75844SAndroid Build Coastguard Worker   SetReadyToSend(transport == rtcp_packet_transport_, true);
210*d9f75844SAndroid Build Coastguard Worker }
211*d9f75844SAndroid Build Coastguard Worker 
OnNetworkRouteChanged(absl::optional<rtc::NetworkRoute> network_route)212*d9f75844SAndroid Build Coastguard Worker void RtpTransport::OnNetworkRouteChanged(
213*d9f75844SAndroid Build Coastguard Worker     absl::optional<rtc::NetworkRoute> network_route) {
214*d9f75844SAndroid Build Coastguard Worker   SignalNetworkRouteChanged(network_route);
215*d9f75844SAndroid Build Coastguard Worker }
216*d9f75844SAndroid Build Coastguard Worker 
OnWritableState(rtc::PacketTransportInternal * packet_transport)217*d9f75844SAndroid Build Coastguard Worker void RtpTransport::OnWritableState(
218*d9f75844SAndroid Build Coastguard Worker     rtc::PacketTransportInternal* packet_transport) {
219*d9f75844SAndroid Build Coastguard Worker   RTC_DCHECK(packet_transport == rtp_packet_transport_ ||
220*d9f75844SAndroid Build Coastguard Worker              packet_transport == rtcp_packet_transport_);
221*d9f75844SAndroid Build Coastguard Worker   SignalWritableState(IsTransportWritable());
222*d9f75844SAndroid Build Coastguard Worker }
223*d9f75844SAndroid Build Coastguard Worker 
OnSentPacket(rtc::PacketTransportInternal * packet_transport,const rtc::SentPacket & sent_packet)224*d9f75844SAndroid Build Coastguard Worker void RtpTransport::OnSentPacket(rtc::PacketTransportInternal* packet_transport,
225*d9f75844SAndroid Build Coastguard Worker                                 const rtc::SentPacket& sent_packet) {
226*d9f75844SAndroid Build Coastguard Worker   RTC_DCHECK(packet_transport == rtp_packet_transport_ ||
227*d9f75844SAndroid Build Coastguard Worker              packet_transport == rtcp_packet_transport_);
228*d9f75844SAndroid Build Coastguard Worker   SignalSentPacket(sent_packet);
229*d9f75844SAndroid Build Coastguard Worker }
230*d9f75844SAndroid Build Coastguard Worker 
OnRtpPacketReceived(rtc::CopyOnWriteBuffer packet,int64_t packet_time_us)231*d9f75844SAndroid Build Coastguard Worker void RtpTransport::OnRtpPacketReceived(rtc::CopyOnWriteBuffer packet,
232*d9f75844SAndroid Build Coastguard Worker                                        int64_t packet_time_us) {
233*d9f75844SAndroid Build Coastguard Worker   DemuxPacket(packet, packet_time_us);
234*d9f75844SAndroid Build Coastguard Worker }
235*d9f75844SAndroid Build Coastguard Worker 
OnRtcpPacketReceived(rtc::CopyOnWriteBuffer packet,int64_t packet_time_us)236*d9f75844SAndroid Build Coastguard Worker void RtpTransport::OnRtcpPacketReceived(rtc::CopyOnWriteBuffer packet,
237*d9f75844SAndroid Build Coastguard Worker                                         int64_t packet_time_us) {
238*d9f75844SAndroid Build Coastguard Worker   SignalRtcpPacketReceived(&packet, packet_time_us);
239*d9f75844SAndroid Build Coastguard Worker }
240*d9f75844SAndroid Build Coastguard Worker 
OnReadPacket(rtc::PacketTransportInternal * transport,const char * data,size_t len,const int64_t & packet_time_us,int flags)241*d9f75844SAndroid Build Coastguard Worker void RtpTransport::OnReadPacket(rtc::PacketTransportInternal* transport,
242*d9f75844SAndroid Build Coastguard Worker                                 const char* data,
243*d9f75844SAndroid Build Coastguard Worker                                 size_t len,
244*d9f75844SAndroid Build Coastguard Worker                                 const int64_t& packet_time_us,
245*d9f75844SAndroid Build Coastguard Worker                                 int flags) {
246*d9f75844SAndroid Build Coastguard Worker   TRACE_EVENT0("webrtc", "RtpTransport::OnReadPacket");
247*d9f75844SAndroid Build Coastguard Worker 
248*d9f75844SAndroid Build Coastguard Worker   // When using RTCP multiplexing we might get RTCP packets on the RTP
249*d9f75844SAndroid Build Coastguard Worker   // transport. We check the RTP payload type to determine if it is RTCP.
250*d9f75844SAndroid Build Coastguard Worker   auto array_view = rtc::MakeArrayView(data, len);
251*d9f75844SAndroid Build Coastguard Worker   cricket::RtpPacketType packet_type = cricket::InferRtpPacketType(array_view);
252*d9f75844SAndroid Build Coastguard Worker   // Filter out the packet that is neither RTP nor RTCP.
253*d9f75844SAndroid Build Coastguard Worker   if (packet_type == cricket::RtpPacketType::kUnknown) {
254*d9f75844SAndroid Build Coastguard Worker     return;
255*d9f75844SAndroid Build Coastguard Worker   }
256*d9f75844SAndroid Build Coastguard Worker 
257*d9f75844SAndroid Build Coastguard Worker   // Protect ourselves against crazy data.
258*d9f75844SAndroid Build Coastguard Worker   if (!cricket::IsValidRtpPacketSize(packet_type, len)) {
259*d9f75844SAndroid Build Coastguard Worker     RTC_LOG(LS_ERROR) << "Dropping incoming "
260*d9f75844SAndroid Build Coastguard Worker                       << cricket::RtpPacketTypeToString(packet_type)
261*d9f75844SAndroid Build Coastguard Worker                       << " packet: wrong size=" << len;
262*d9f75844SAndroid Build Coastguard Worker     return;
263*d9f75844SAndroid Build Coastguard Worker   }
264*d9f75844SAndroid Build Coastguard Worker 
265*d9f75844SAndroid Build Coastguard Worker   rtc::CopyOnWriteBuffer packet(data, len);
266*d9f75844SAndroid Build Coastguard Worker   if (packet_type == cricket::RtpPacketType::kRtcp) {
267*d9f75844SAndroid Build Coastguard Worker     OnRtcpPacketReceived(std::move(packet), packet_time_us);
268*d9f75844SAndroid Build Coastguard Worker   } else {
269*d9f75844SAndroid Build Coastguard Worker     OnRtpPacketReceived(std::move(packet), packet_time_us);
270*d9f75844SAndroid Build Coastguard Worker   }
271*d9f75844SAndroid Build Coastguard Worker }
272*d9f75844SAndroid Build Coastguard Worker 
SetReadyToSend(bool rtcp,bool ready)273*d9f75844SAndroid Build Coastguard Worker void RtpTransport::SetReadyToSend(bool rtcp, bool ready) {
274*d9f75844SAndroid Build Coastguard Worker   if (rtcp) {
275*d9f75844SAndroid Build Coastguard Worker     rtcp_ready_to_send_ = ready;
276*d9f75844SAndroid Build Coastguard Worker   } else {
277*d9f75844SAndroid Build Coastguard Worker     rtp_ready_to_send_ = ready;
278*d9f75844SAndroid Build Coastguard Worker   }
279*d9f75844SAndroid Build Coastguard Worker 
280*d9f75844SAndroid Build Coastguard Worker   MaybeSignalReadyToSend();
281*d9f75844SAndroid Build Coastguard Worker }
282*d9f75844SAndroid Build Coastguard Worker 
MaybeSignalReadyToSend()283*d9f75844SAndroid Build Coastguard Worker void RtpTransport::MaybeSignalReadyToSend() {
284*d9f75844SAndroid Build Coastguard Worker   bool ready_to_send =
285*d9f75844SAndroid Build Coastguard Worker       rtp_ready_to_send_ && (rtcp_ready_to_send_ || rtcp_mux_enabled_);
286*d9f75844SAndroid Build Coastguard Worker   if (ready_to_send != ready_to_send_) {
287*d9f75844SAndroid Build Coastguard Worker     ready_to_send_ = ready_to_send;
288*d9f75844SAndroid Build Coastguard Worker     SignalReadyToSend(ready_to_send);
289*d9f75844SAndroid Build Coastguard Worker   }
290*d9f75844SAndroid Build Coastguard Worker }
291*d9f75844SAndroid Build Coastguard Worker 
292*d9f75844SAndroid Build Coastguard Worker }  // namespace webrtc
293