| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. | 2 * Copyright (c) 2012 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/modules/rtp_rtcp/source/rtcp_sender.h" | 11 #include "webrtc/modules/rtp_rtcp/source/rtcp_sender.h" |
| 12 | 12 |
| 13 #include <assert.h> // assert | |
| 14 #include <string.h> // memcpy | 13 #include <string.h> // memcpy |
| 15 | 14 |
| 16 #include <algorithm> // min | |
| 17 #include <limits> // max | |
| 18 #include <utility> | |
| 19 | |
| 20 #include "webrtc/base/checks.h" | 15 #include "webrtc/base/checks.h" |
| 21 #include "webrtc/base/logging.h" | 16 #include "webrtc/base/logging.h" |
| 22 #include "webrtc/base/trace_event.h" | 17 #include "webrtc/base/trace_event.h" |
| 23 #include "webrtc/call.h" | 18 #include "webrtc/call.h" |
| 24 #include "webrtc/call/rtc_event_log.h" | 19 #include "webrtc/call/rtc_event_log.h" |
| 25 #include "webrtc/common_types.h" | 20 #include "webrtc/common_types.h" |
| 26 #include "webrtc/modules/rtp_rtcp/source/byte_io.h" | |
| 27 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/app.h" | 21 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/app.h" |
| 28 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/bye.h" | 22 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/bye.h" |
| 29 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/compound_packet.h" | 23 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/compound_packet.h" |
| 30 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/extended_reports.h" | 24 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/extended_reports.h" |
| 31 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/fir.h" | 25 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/fir.h" |
| 32 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/nack.h" | 26 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/nack.h" |
| 33 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/pli.h" | 27 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/pli.h" |
| 34 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/receiver_report.h" | 28 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/receiver_report.h" |
| 35 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/remb.h" | 29 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/remb.h" |
| 36 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/rpsi.h" | 30 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/rpsi.h" |
| 37 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/sdes.h" | 31 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/sdes.h" |
| 38 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/sender_report.h" | 32 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/sender_report.h" |
| 39 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/sli.h" | 33 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/sli.h" |
| 40 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/tmmbn.h" | 34 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/tmmbn.h" |
| 41 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/tmmbr.h" | 35 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/tmmbr.h" |
| 42 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/transport_feedback.h" | 36 #include "webrtc/modules/rtp_rtcp/source/rtcp_packet/transport_feedback.h" |
| 43 #include "webrtc/modules/rtp_rtcp/source/rtp_rtcp_impl.h" | 37 #include "webrtc/modules/rtp_rtcp/source/rtp_rtcp_impl.h" |
| 44 #include "webrtc/system_wrappers/include/critical_section_wrapper.h" | |
| 45 | 38 |
| 46 namespace webrtc { | 39 namespace webrtc { |
| 47 | 40 |
| 48 using RTCPUtility::RTCPCnameInformation; | |
| 49 | |
| 50 NACKStringBuilder::NACKStringBuilder() | 41 NACKStringBuilder::NACKStringBuilder() |
| 51 : stream_(""), count_(0), prevNack_(0), consecutive_(false) {} | 42 : stream_(""), count_(0), prevNack_(0), consecutive_(false) {} |
| 52 | 43 |
| 53 NACKStringBuilder::~NACKStringBuilder() {} | 44 NACKStringBuilder::~NACKStringBuilder() {} |
| 54 | 45 |
| 55 void NACKStringBuilder::PushNACK(uint16_t nack) { | 46 void NACKStringBuilder::PushNACK(uint16_t nack) { |
| 56 if (count_ == 0) { | 47 if (count_ == 0) { |
| 57 stream_ << nack; | 48 stream_ << nack; |
| 58 } else if (nack == prevNack_ + 1) { | 49 } else if (nack == prevNack_ + 1) { |
| 59 consecutive_ = true; | 50 consecutive_ = true; |
| (...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 122 }; | 113 }; |
| 123 | 114 |
| 124 class RTCPSender::RtcpContext { | 115 class RTCPSender::RtcpContext { |
| 125 public: | 116 public: |
| 126 RtcpContext(const FeedbackState& feedback_state, | 117 RtcpContext(const FeedbackState& feedback_state, |
| 127 int32_t nack_size, | 118 int32_t nack_size, |
| 128 const uint16_t* nack_list, | 119 const uint16_t* nack_list, |
| 129 bool repeat, | 120 bool repeat, |
| 130 uint64_t picture_id, | 121 uint64_t picture_id, |
| 131 uint32_t ntp_sec, | 122 uint32_t ntp_sec, |
| 132 uint32_t ntp_frac, | 123 uint32_t ntp_frac) |
| 133 PacketContainer* container) | |
| 134 : feedback_state_(feedback_state), | 124 : feedback_state_(feedback_state), |
| 135 nack_size_(nack_size), | 125 nack_size_(nack_size), |
| 136 nack_list_(nack_list), | 126 nack_list_(nack_list), |
| 137 repeat_(repeat), | 127 repeat_(repeat), |
| 138 picture_id_(picture_id), | 128 picture_id_(picture_id), |
| 139 ntp_sec_(ntp_sec), | 129 ntp_sec_(ntp_sec), |
| 140 ntp_frac_(ntp_frac), | 130 ntp_frac_(ntp_frac) {} |
| 141 container_(container) {} | |
| 142 | |
| 143 virtual ~RtcpContext() {} | |
| 144 | 131 |
| 145 const FeedbackState& feedback_state_; | 132 const FeedbackState& feedback_state_; |
| 146 const int32_t nack_size_; | 133 const int32_t nack_size_; |
| 147 const uint16_t* nack_list_; | 134 const uint16_t* nack_list_; |
| 148 const bool repeat_; | 135 const bool repeat_; |
| 149 const uint64_t picture_id_; | 136 const uint64_t picture_id_; |
| 150 const uint32_t ntp_sec_; | 137 const uint32_t ntp_sec_; |
| 151 const uint32_t ntp_frac_; | 138 const uint32_t ntp_frac_; |
| 152 | |
| 153 PacketContainer* const container_; | |
| 154 }; | 139 }; |
| 155 | 140 |
| 156 RTCPSender::RTCPSender( | 141 RTCPSender::RTCPSender( |
| 157 bool audio, | 142 bool audio, |
| 158 Clock* clock, | 143 Clock* clock, |
| 159 ReceiveStatistics* receive_statistics, | 144 ReceiveStatistics* receive_statistics, |
| 160 RtcpPacketTypeCounterObserver* packet_type_counter_observer, | 145 RtcpPacketTypeCounterObserver* packet_type_counter_observer, |
| 161 RtcEventLog* event_log, | 146 RtcEventLog* event_log, |
| 162 Transport* outgoing_transport) | 147 Transport* outgoing_transport) |
| 163 : audio_(audio), | 148 : audio_(audio), |
| 164 clock_(clock), | 149 clock_(clock), |
| 165 random_(clock_->TimeInMicroseconds()), | 150 random_(clock_->TimeInMicroseconds()), |
| 166 method_(RtcpMode::kOff), | 151 method_(RtcpMode::kOff), |
| 167 event_log_(event_log), | 152 event_log_(event_log), |
| 168 transport_(outgoing_transport), | 153 transport_(outgoing_transport), |
| 169 | |
| 170 critical_section_rtcp_sender_( | |
| 171 CriticalSectionWrapper::CreateCriticalSection()), | |
| 172 using_nack_(false), | 154 using_nack_(false), |
| 173 sending_(false), | 155 sending_(false), |
| 174 remb_enabled_(false), | 156 remb_enabled_(false), |
| 175 next_time_to_send_rtcp_(0), | 157 next_time_to_send_rtcp_(0), |
| 176 start_timestamp_(0), | 158 start_timestamp_(0), |
| 177 last_rtp_timestamp_(0), | 159 last_rtp_timestamp_(0), |
| 178 last_frame_capture_time_ms_(-1), | 160 last_frame_capture_time_ms_(-1), |
| 179 ssrc_(0), | 161 ssrc_(0), |
| 180 remote_ssrc_(0), | 162 remote_ssrc_(0), |
| 181 receive_statistics_(receive_statistics), | 163 receive_statistics_(receive_statistics), |
| (...skipping 30 matching lines...) Expand all Loading... |
| 212 builders_[kRtcpNack] = &RTCPSender::BuildNACK; | 194 builders_[kRtcpNack] = &RTCPSender::BuildNACK; |
| 213 builders_[kRtcpXrVoipMetric] = &RTCPSender::BuildVoIPMetric; | 195 builders_[kRtcpXrVoipMetric] = &RTCPSender::BuildVoIPMetric; |
| 214 builders_[kRtcpXrReceiverReferenceTime] = | 196 builders_[kRtcpXrReceiverReferenceTime] = |
| 215 &RTCPSender::BuildReceiverReferenceTime; | 197 &RTCPSender::BuildReceiverReferenceTime; |
| 216 builders_[kRtcpXrDlrrReportBlock] = &RTCPSender::BuildDlrr; | 198 builders_[kRtcpXrDlrrReportBlock] = &RTCPSender::BuildDlrr; |
| 217 } | 199 } |
| 218 | 200 |
| 219 RTCPSender::~RTCPSender() {} | 201 RTCPSender::~RTCPSender() {} |
| 220 | 202 |
| 221 RtcpMode RTCPSender::Status() const { | 203 RtcpMode RTCPSender::Status() const { |
| 222 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 204 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 223 return method_; | 205 return method_; |
| 224 } | 206 } |
| 225 | 207 |
| 226 void RTCPSender::SetRTCPStatus(RtcpMode method) { | 208 void RTCPSender::SetRTCPStatus(RtcpMode method) { |
| 227 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 209 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 228 method_ = method; | 210 method_ = method; |
| 229 | 211 |
| 230 if (method == RtcpMode::kOff) | 212 if (method == RtcpMode::kOff) |
| 231 return; | 213 return; |
| 232 next_time_to_send_rtcp_ = | 214 next_time_to_send_rtcp_ = |
| 233 clock_->TimeInMilliseconds() + | 215 clock_->TimeInMilliseconds() + |
| 234 (audio_ ? RTCP_INTERVAL_AUDIO_MS / 2 : RTCP_INTERVAL_VIDEO_MS / 2); | 216 (audio_ ? RTCP_INTERVAL_AUDIO_MS / 2 : RTCP_INTERVAL_VIDEO_MS / 2); |
| 235 } | 217 } |
| 236 | 218 |
| 237 bool RTCPSender::Sending() const { | 219 bool RTCPSender::Sending() const { |
| 238 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 220 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 239 return sending_; | 221 return sending_; |
| 240 } | 222 } |
| 241 | 223 |
| 242 int32_t RTCPSender::SetSendingStatus(const FeedbackState& feedback_state, | 224 int32_t RTCPSender::SetSendingStatus(const FeedbackState& feedback_state, |
| 243 bool sending) { | 225 bool sending) { |
| 244 bool sendRTCPBye = false; | 226 bool sendRTCPBye = false; |
| 245 { | 227 { |
| 246 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 228 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 247 | 229 |
| 248 if (method_ != RtcpMode::kOff) { | 230 if (method_ != RtcpMode::kOff) { |
| 249 if (sending == false && sending_ == true) { | 231 if (sending == false && sending_ == true) { |
| 250 // Trigger RTCP bye | 232 // Trigger RTCP bye |
| 251 sendRTCPBye = true; | 233 sendRTCPBye = true; |
| 252 } | 234 } |
| 253 } | 235 } |
| 254 sending_ = sending; | 236 sending_ = sending; |
| 255 } | 237 } |
| 256 if (sendRTCPBye) | 238 if (sendRTCPBye) |
| 257 return SendRTCP(feedback_state, kRtcpBye); | 239 return SendRTCP(feedback_state, kRtcpBye); |
| 258 return 0; | 240 return 0; |
| 259 } | 241 } |
| 260 | 242 |
| 261 bool RTCPSender::REMB() const { | 243 bool RTCPSender::REMB() const { |
| 262 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 244 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 263 return remb_enabled_; | 245 return remb_enabled_; |
| 264 } | 246 } |
| 265 | 247 |
| 266 void RTCPSender::SetREMBStatus(bool enable) { | 248 void RTCPSender::SetREMBStatus(bool enable) { |
| 267 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 249 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 268 remb_enabled_ = enable; | 250 remb_enabled_ = enable; |
| 269 } | 251 } |
| 270 | 252 |
| 271 void RTCPSender::SetREMBData(uint32_t bitrate, | 253 void RTCPSender::SetREMBData(uint32_t bitrate, |
| 272 const std::vector<uint32_t>& ssrcs) { | 254 const std::vector<uint32_t>& ssrcs) { |
| 273 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 255 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 274 remb_bitrate_ = bitrate; | 256 remb_bitrate_ = bitrate; |
| 275 remb_ssrcs_ = ssrcs; | 257 remb_ssrcs_ = ssrcs; |
| 276 | 258 |
| 277 if (remb_enabled_) | 259 if (remb_enabled_) |
| 278 SetFlag(kRtcpRemb, false); | 260 SetFlag(kRtcpRemb, false); |
| 279 // Send a REMB immediately if we have a new REMB. The frequency of REMBs is | 261 // Send a REMB immediately if we have a new REMB. The frequency of REMBs is |
| 280 // throttled by the caller. | 262 // throttled by the caller. |
| 281 next_time_to_send_rtcp_ = clock_->TimeInMilliseconds(); | 263 next_time_to_send_rtcp_ = clock_->TimeInMilliseconds(); |
| 282 } | 264 } |
| 283 | 265 |
| 284 bool RTCPSender::TMMBR() const { | 266 bool RTCPSender::TMMBR() const { |
| 285 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 267 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 286 return IsFlagPresent(RTCPPacketType::kRtcpTmmbr); | 268 return IsFlagPresent(RTCPPacketType::kRtcpTmmbr); |
| 287 } | 269 } |
| 288 | 270 |
| 289 void RTCPSender::SetTMMBRStatus(bool enable) { | 271 void RTCPSender::SetTMMBRStatus(bool enable) { |
| 290 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 272 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 291 if (enable) { | 273 if (enable) { |
| 292 SetFlag(RTCPPacketType::kRtcpTmmbr, false); | 274 SetFlag(RTCPPacketType::kRtcpTmmbr, false); |
| 293 } else { | 275 } else { |
| 294 ConsumeFlag(RTCPPacketType::kRtcpTmmbr, true); | 276 ConsumeFlag(RTCPPacketType::kRtcpTmmbr, true); |
| 295 } | 277 } |
| 296 } | 278 } |
| 297 | 279 |
| 298 void RTCPSender::SetStartTimestamp(uint32_t start_timestamp) { | 280 void RTCPSender::SetStartTimestamp(uint32_t start_timestamp) { |
| 299 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 281 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 300 start_timestamp_ = start_timestamp; | 282 start_timestamp_ = start_timestamp; |
| 301 } | 283 } |
| 302 | 284 |
| 303 void RTCPSender::SetLastRtpTime(uint32_t rtp_timestamp, | 285 void RTCPSender::SetLastRtpTime(uint32_t rtp_timestamp, |
| 304 int64_t capture_time_ms) { | 286 int64_t capture_time_ms) { |
| 305 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 287 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 306 last_rtp_timestamp_ = rtp_timestamp; | 288 last_rtp_timestamp_ = rtp_timestamp; |
| 307 if (capture_time_ms < 0) { | 289 if (capture_time_ms < 0) { |
| 308 // We don't currently get a capture time from VoiceEngine. | 290 // We don't currently get a capture time from VoiceEngine. |
| 309 last_frame_capture_time_ms_ = clock_->TimeInMilliseconds(); | 291 last_frame_capture_time_ms_ = clock_->TimeInMilliseconds(); |
| 310 } else { | 292 } else { |
| 311 last_frame_capture_time_ms_ = capture_time_ms; | 293 last_frame_capture_time_ms_ = capture_time_ms; |
| 312 } | 294 } |
| 313 } | 295 } |
| 314 | 296 |
| 315 void RTCPSender::SetSSRC(uint32_t ssrc) { | 297 void RTCPSender::SetSSRC(uint32_t ssrc) { |
| 316 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 298 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 317 | 299 |
| 318 if (ssrc_ != 0) { | 300 if (ssrc_ != 0) { |
| 319 // not first SetSSRC, probably due to a collision | 301 // not first SetSSRC, probably due to a collision |
| 320 // schedule a new RTCP report | 302 // schedule a new RTCP report |
| 321 // make sure that we send a RTP packet | 303 // make sure that we send a RTP packet |
| 322 next_time_to_send_rtcp_ = clock_->TimeInMilliseconds() + 100; | 304 next_time_to_send_rtcp_ = clock_->TimeInMilliseconds() + 100; |
| 323 } | 305 } |
| 324 ssrc_ = ssrc; | 306 ssrc_ = ssrc; |
| 325 } | 307 } |
| 326 | 308 |
| 327 void RTCPSender::SetRemoteSSRC(uint32_t ssrc) { | 309 void RTCPSender::SetRemoteSSRC(uint32_t ssrc) { |
| 328 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 310 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 329 remote_ssrc_ = ssrc; | 311 remote_ssrc_ = ssrc; |
| 330 } | 312 } |
| 331 | 313 |
| 332 int32_t RTCPSender::SetCNAME(const char* c_name) { | 314 int32_t RTCPSender::SetCNAME(const char* c_name) { |
| 333 if (!c_name) | 315 if (!c_name) |
| 334 return -1; | 316 return -1; |
| 335 | 317 |
| 336 RTC_DCHECK_LT(strlen(c_name), static_cast<size_t>(RTCP_CNAME_SIZE)); | 318 RTC_DCHECK_LT(strlen(c_name), static_cast<size_t>(RTCP_CNAME_SIZE)); |
| 337 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 319 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 338 cname_ = c_name; | 320 cname_ = c_name; |
| 339 return 0; | 321 return 0; |
| 340 } | 322 } |
| 341 | 323 |
| 342 int32_t RTCPSender::AddMixedCNAME(uint32_t SSRC, const char* c_name) { | 324 int32_t RTCPSender::AddMixedCNAME(uint32_t SSRC, const char* c_name) { |
| 343 assert(c_name); | 325 RTC_DCHECK(c_name); |
| 344 RTC_DCHECK_LT(strlen(c_name), static_cast<size_t>(RTCP_CNAME_SIZE)); | 326 RTC_DCHECK_LT(strlen(c_name), static_cast<size_t>(RTCP_CNAME_SIZE)); |
| 345 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 327 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 346 if (csrc_cnames_.size() >= kRtpCsrcSize) | 328 if (csrc_cnames_.size() >= kRtpCsrcSize) |
| 347 return -1; | 329 return -1; |
| 348 | 330 |
| 349 csrc_cnames_[SSRC] = c_name; | 331 csrc_cnames_[SSRC] = c_name; |
| 350 return 0; | 332 return 0; |
| 351 } | 333 } |
| 352 | 334 |
| 353 int32_t RTCPSender::RemoveMixedCNAME(uint32_t SSRC) { | 335 int32_t RTCPSender::RemoveMixedCNAME(uint32_t SSRC) { |
| 354 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 336 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 355 auto it = csrc_cnames_.find(SSRC); | 337 auto it = csrc_cnames_.find(SSRC); |
| 356 | 338 |
| 357 if (it == csrc_cnames_.end()) | 339 if (it == csrc_cnames_.end()) |
| 358 return -1; | 340 return -1; |
| 359 | 341 |
| 360 csrc_cnames_.erase(it); | 342 csrc_cnames_.erase(it); |
| 361 return 0; | 343 return 0; |
| 362 } | 344 } |
| 363 | 345 |
| 364 bool RTCPSender::TimeToSendRTCPReport(bool sendKeyframeBeforeRTP) const { | 346 bool RTCPSender::TimeToSendRTCPReport(bool sendKeyframeBeforeRTP) const { |
| (...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 415 4. The calculated interval T is set to a number uniformly distributed | 397 4. The calculated interval T is set to a number uniformly distributed |
| 416 between 0.5 and 1.5 times the deterministic calculated interval. | 398 between 0.5 and 1.5 times the deterministic calculated interval. |
| 417 | 399 |
| 418 5. The resulting value of T is divided by e-3/2=1.21828 to compensate | 400 5. The resulting value of T is divided by e-3/2=1.21828 to compensate |
| 419 for the fact that the timer reconsideration algorithm converges to | 401 for the fact that the timer reconsideration algorithm converges to |
| 420 a value of the RTCP bandwidth below the intended average | 402 a value of the RTCP bandwidth below the intended average |
| 421 */ | 403 */ |
| 422 | 404 |
| 423 int64_t now = clock_->TimeInMilliseconds(); | 405 int64_t now = clock_->TimeInMilliseconds(); |
| 424 | 406 |
| 425 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 407 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 426 | 408 |
| 427 if (method_ == RtcpMode::kOff) | 409 if (method_ == RtcpMode::kOff) |
| 428 return false; | 410 return false; |
| 429 | 411 |
| 430 if (!audio_ && sendKeyframeBeforeRTP) { | 412 if (!audio_ && sendKeyframeBeforeRTP) { |
| 431 // for video key-frames we want to send the RTCP before the large key-frame | 413 // for video key-frames we want to send the RTCP before the large key-frame |
| 432 // if we have a 100 ms margin | 414 // if we have a 100 ms margin |
| 433 now += RTCP_SEND_BEFORE_KEY_FRAME_MS; | 415 now += RTCP_SEND_BEFORE_KEY_FRAME_MS; |
| 434 } | 416 } |
| 435 | 417 |
| 436 if (now >= next_time_to_send_rtcp_) { | 418 if (now >= next_time_to_send_rtcp_) { |
| 437 return true; | 419 return true; |
| 438 } else if (now < 0x0000ffff && | 420 } else if (now < 0x0000ffff && |
| 439 next_time_to_send_rtcp_ > 0xffff0000) { // 65 sec margin | 421 next_time_to_send_rtcp_ > 0xffff0000) { // 65 sec margin |
| 440 // wrap | 422 // wrap |
| 441 return true; | 423 return true; |
| 442 } | 424 } |
| 443 return false; | 425 return false; |
| 444 } | 426 } |
| 445 | 427 |
| 446 rtc::scoped_ptr<rtcp::RtcpPacket> RTCPSender::BuildSR(const RtcpContext& ctx) { | 428 std::unique_ptr<rtcp::RtcpPacket> RTCPSender::BuildSR(const RtcpContext& ctx) { |
| 447 // The timestamp of this RTCP packet should be estimated as the timestamp of | 429 // The timestamp of this RTCP packet should be estimated as the timestamp of |
| 448 // the frame being captured at this moment. We are calculating that | 430 // the frame being captured at this moment. We are calculating that |
| 449 // timestamp as the last frame's timestamp + the time since the last frame | 431 // timestamp as the last frame's timestamp + the time since the last frame |
| 450 // was captured. | 432 // was captured. |
| 451 uint32_t rtp_timestamp = | 433 uint32_t rtp_timestamp = |
| 452 start_timestamp_ + last_rtp_timestamp_ + | 434 start_timestamp_ + last_rtp_timestamp_ + |
| 453 (clock_->TimeInMilliseconds() - last_frame_capture_time_ms_) * | 435 (clock_->TimeInMilliseconds() - last_frame_capture_time_ms_) * |
| 454 (ctx.feedback_state_.frequency_hz / 1000); | 436 (ctx.feedback_state_.frequency_hz / 1000); |
| 455 | 437 |
| 456 rtcp::SenderReport* report = new rtcp::SenderReport(); | 438 rtcp::SenderReport* report = new rtcp::SenderReport(); |
| 457 report->From(ssrc_); | 439 report->From(ssrc_); |
| 458 report->WithNtp(NtpTime(ctx.ntp_sec_, ctx.ntp_frac_)); | 440 report->WithNtp(NtpTime(ctx.ntp_sec_, ctx.ntp_frac_)); |
| 459 report->WithRtpTimestamp(rtp_timestamp); | 441 report->WithRtpTimestamp(rtp_timestamp); |
| 460 report->WithPacketCount(ctx.feedback_state_.packets_sent); | 442 report->WithPacketCount(ctx.feedback_state_.packets_sent); |
| 461 report->WithOctetCount(ctx.feedback_state_.media_bytes_sent); | 443 report->WithOctetCount(ctx.feedback_state_.media_bytes_sent); |
| 462 | 444 |
| 463 for (auto it : report_blocks_) | 445 for (auto it : report_blocks_) |
| 464 report->WithReportBlock(it.second); | 446 report->WithReportBlock(it.second); |
| 465 | 447 |
| 466 report_blocks_.clear(); | 448 report_blocks_.clear(); |
| 467 | 449 |
| 468 return rtc::scoped_ptr<rtcp::SenderReport>(report); | 450 return std::unique_ptr<rtcp::RtcpPacket>(report); |
| 469 } | 451 } |
| 470 | 452 |
| 471 rtc::scoped_ptr<rtcp::RtcpPacket> RTCPSender::BuildSDES( | 453 std::unique_ptr<rtcp::RtcpPacket> RTCPSender::BuildSDES( |
| 472 const RtcpContext& ctx) { | 454 const RtcpContext& ctx) { |
| 473 size_t length_cname = cname_.length(); | 455 size_t length_cname = cname_.length(); |
| 474 RTC_CHECK_LT(length_cname, static_cast<size_t>(RTCP_CNAME_SIZE)); | 456 RTC_CHECK_LT(length_cname, static_cast<size_t>(RTCP_CNAME_SIZE)); |
| 475 | 457 |
| 476 rtcp::Sdes* sdes = new rtcp::Sdes(); | 458 rtcp::Sdes* sdes = new rtcp::Sdes(); |
| 477 sdes->WithCName(ssrc_, cname_); | 459 sdes->WithCName(ssrc_, cname_); |
| 478 | 460 |
| 479 for (const auto it : csrc_cnames_) | 461 for (const auto it : csrc_cnames_) |
| 480 sdes->WithCName(it.first, it.second); | 462 sdes->WithCName(it.first, it.second); |
| 481 | 463 |
| 482 return rtc::scoped_ptr<rtcp::Sdes>(sdes); | 464 return std::unique_ptr<rtcp::RtcpPacket>(sdes); |
| 483 } | 465 } |
| 484 | 466 |
| 485 rtc::scoped_ptr<rtcp::RtcpPacket> RTCPSender::BuildRR(const RtcpContext& ctx) { | 467 std::unique_ptr<rtcp::RtcpPacket> RTCPSender::BuildRR(const RtcpContext& ctx) { |
| 486 rtcp::ReceiverReport* report = new rtcp::ReceiverReport(); | 468 rtcp::ReceiverReport* report = new rtcp::ReceiverReport(); |
| 487 report->From(ssrc_); | 469 report->From(ssrc_); |
| 488 for (auto it : report_blocks_) | 470 for (auto it : report_blocks_) |
| 489 report->WithReportBlock(it.second); | 471 report->WithReportBlock(it.second); |
| 490 | 472 |
| 491 report_blocks_.clear(); | 473 report_blocks_.clear(); |
| 492 return rtc::scoped_ptr<rtcp::ReceiverReport>(report); | 474 return std::unique_ptr<rtcp::RtcpPacket>(report); |
| 493 } | 475 } |
| 494 | 476 |
| 495 rtc::scoped_ptr<rtcp::RtcpPacket> RTCPSender::BuildPLI(const RtcpContext& ctx) { | 477 std::unique_ptr<rtcp::RtcpPacket> RTCPSender::BuildPLI(const RtcpContext& ctx) { |
| 496 rtcp::Pli* pli = new rtcp::Pli(); | 478 rtcp::Pli* pli = new rtcp::Pli(); |
| 497 pli->From(ssrc_); | 479 pli->From(ssrc_); |
| 498 pli->To(remote_ssrc_); | 480 pli->To(remote_ssrc_); |
| 499 | 481 |
| 500 TRACE_EVENT_INSTANT0(TRACE_DISABLED_BY_DEFAULT("webrtc_rtp"), | 482 TRACE_EVENT_INSTANT0(TRACE_DISABLED_BY_DEFAULT("webrtc_rtp"), |
| 501 "RTCPSender::PLI"); | 483 "RTCPSender::PLI"); |
| 502 ++packet_type_counter_.pli_packets; | 484 ++packet_type_counter_.pli_packets; |
| 503 TRACE_COUNTER_ID1(TRACE_DISABLED_BY_DEFAULT("webrtc_rtp"), "RTCP_PLICount", | 485 TRACE_COUNTER_ID1(TRACE_DISABLED_BY_DEFAULT("webrtc_rtp"), "RTCP_PLICount", |
| 504 ssrc_, packet_type_counter_.pli_packets); | 486 ssrc_, packet_type_counter_.pli_packets); |
| 505 | 487 |
| 506 return rtc::scoped_ptr<rtcp::Pli>(pli); | 488 return std::unique_ptr<rtcp::RtcpPacket>(pli); |
| 507 } | 489 } |
| 508 | 490 |
| 509 rtc::scoped_ptr<rtcp::RtcpPacket> RTCPSender::BuildFIR(const RtcpContext& ctx) { | 491 std::unique_ptr<rtcp::RtcpPacket> RTCPSender::BuildFIR(const RtcpContext& ctx) { |
| 510 if (!ctx.repeat_) | 492 if (!ctx.repeat_) |
| 511 ++sequence_number_fir_; // Do not increase if repetition. | 493 ++sequence_number_fir_; // Do not increase if repetition. |
| 512 | 494 |
| 513 rtcp::Fir* fir = new rtcp::Fir(); | 495 rtcp::Fir* fir = new rtcp::Fir(); |
| 514 fir->From(ssrc_); | 496 fir->From(ssrc_); |
| 515 fir->WithRequestTo(remote_ssrc_, sequence_number_fir_); | 497 fir->WithRequestTo(remote_ssrc_, sequence_number_fir_); |
| 516 | 498 |
| 517 TRACE_EVENT_INSTANT0(TRACE_DISABLED_BY_DEFAULT("webrtc_rtp"), | 499 TRACE_EVENT_INSTANT0(TRACE_DISABLED_BY_DEFAULT("webrtc_rtp"), |
| 518 "RTCPSender::FIR"); | 500 "RTCPSender::FIR"); |
| 519 ++packet_type_counter_.fir_packets; | 501 ++packet_type_counter_.fir_packets; |
| 520 TRACE_COUNTER_ID1(TRACE_DISABLED_BY_DEFAULT("webrtc_rtp"), "RTCP_FIRCount", | 502 TRACE_COUNTER_ID1(TRACE_DISABLED_BY_DEFAULT("webrtc_rtp"), "RTCP_FIRCount", |
| 521 ssrc_, packet_type_counter_.fir_packets); | 503 ssrc_, packet_type_counter_.fir_packets); |
| 522 | 504 |
| 523 return rtc::scoped_ptr<rtcp::Fir>(fir); | 505 return std::unique_ptr<rtcp::RtcpPacket>(fir); |
| 524 } | 506 } |
| 525 | 507 |
| 526 /* | 508 /* |
| 527 0 1 2 3 | 509 0 1 2 3 |
| 528 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 | 510 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
| 529 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | 511 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
| 530 | First | Number | PictureID | | 512 | First | Number | PictureID | |
| 531 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | 513 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
| 532 */ | 514 */ |
| 533 rtc::scoped_ptr<rtcp::RtcpPacket> RTCPSender::BuildSLI(const RtcpContext& ctx) { | 515 std::unique_ptr<rtcp::RtcpPacket> RTCPSender::BuildSLI(const RtcpContext& ctx) { |
| 534 rtcp::Sli* sli = new rtcp::Sli(); | 516 rtcp::Sli* sli = new rtcp::Sli(); |
| 535 sli->From(ssrc_); | 517 sli->From(ssrc_); |
| 536 sli->To(remote_ssrc_); | 518 sli->To(remote_ssrc_); |
| 537 // Crop picture id to 6 least significant bits. | 519 // Crop picture id to 6 least significant bits. |
| 538 sli->WithPictureId(ctx.picture_id_ & 0x3F); | 520 sli->WithPictureId(ctx.picture_id_ & 0x3F); |
| 539 | 521 |
| 540 return rtc::scoped_ptr<rtcp::Sli>(sli); | 522 return std::unique_ptr<rtcp::RtcpPacket>(sli); |
| 541 } | 523 } |
| 542 | 524 |
| 543 /* | 525 /* |
| 544 0 1 2 3 | 526 0 1 2 3 |
| 545 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 | 527 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
| 546 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | 528 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
| 547 | PB |0| Payload Type| Native RPSI bit string | | 529 | PB |0| Payload Type| Native RPSI bit string | |
| 548 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | 530 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
| 549 | defined per codec ... | Padding (0) | | 531 | defined per codec ... | Padding (0) | |
| 550 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | 532 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
| 551 */ | 533 */ |
| 552 /* | 534 /* |
| 553 * Note: not generic made for VP8 | 535 * Note: not generic made for VP8 |
| 554 */ | 536 */ |
| 555 rtc::scoped_ptr<rtcp::RtcpPacket> RTCPSender::BuildRPSI( | 537 std::unique_ptr<rtcp::RtcpPacket> RTCPSender::BuildRPSI( |
| 556 const RtcpContext& ctx) { | 538 const RtcpContext& ctx) { |
| 557 if (ctx.feedback_state_.send_payload_type == 0xFF) | 539 if (ctx.feedback_state_.send_payload_type == 0xFF) |
| 558 return nullptr; | 540 return nullptr; |
| 559 | 541 |
| 560 rtcp::Rpsi* rpsi = new rtcp::Rpsi(); | 542 rtcp::Rpsi* rpsi = new rtcp::Rpsi(); |
| 561 rpsi->From(ssrc_); | 543 rpsi->From(ssrc_); |
| 562 rpsi->To(remote_ssrc_); | 544 rpsi->To(remote_ssrc_); |
| 563 rpsi->WithPayloadType(ctx.feedback_state_.send_payload_type); | 545 rpsi->WithPayloadType(ctx.feedback_state_.send_payload_type); |
| 564 rpsi->WithPictureId(ctx.picture_id_); | 546 rpsi->WithPictureId(ctx.picture_id_); |
| 565 | 547 |
| 566 return rtc::scoped_ptr<rtcp::Rpsi>(rpsi); | 548 return std::unique_ptr<rtcp::RtcpPacket>(rpsi); |
| 567 } | 549 } |
| 568 | 550 |
| 569 rtc::scoped_ptr<rtcp::RtcpPacket> RTCPSender::BuildREMB( | 551 std::unique_ptr<rtcp::RtcpPacket> RTCPSender::BuildREMB( |
| 570 const RtcpContext& ctx) { | 552 const RtcpContext& ctx) { |
| 571 rtcp::Remb* remb = new rtcp::Remb(); | 553 rtcp::Remb* remb = new rtcp::Remb(); |
| 572 remb->From(ssrc_); | 554 remb->From(ssrc_); |
| 573 for (uint32_t ssrc : remb_ssrcs_) | 555 for (uint32_t ssrc : remb_ssrcs_) |
| 574 remb->AppliesTo(ssrc); | 556 remb->AppliesTo(ssrc); |
| 575 remb->WithBitrateBps(remb_bitrate_); | 557 remb->WithBitrateBps(remb_bitrate_); |
| 576 | 558 |
| 577 TRACE_EVENT_INSTANT0(TRACE_DISABLED_BY_DEFAULT("webrtc_rtp"), | 559 TRACE_EVENT_INSTANT0(TRACE_DISABLED_BY_DEFAULT("webrtc_rtp"), |
| 578 "RTCPSender::REMB"); | 560 "RTCPSender::REMB"); |
| 579 | 561 |
| 580 return rtc::scoped_ptr<rtcp::Remb>(remb); | 562 return std::unique_ptr<rtcp::RtcpPacket>(remb); |
| 581 } | 563 } |
| 582 | 564 |
| 583 void RTCPSender::SetTargetBitrate(unsigned int target_bitrate) { | 565 void RTCPSender::SetTargetBitrate(unsigned int target_bitrate) { |
| 584 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 566 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 585 tmmbr_send_ = target_bitrate / 1000; | 567 tmmbr_send_ = target_bitrate / 1000; |
| 586 } | 568 } |
| 587 | 569 |
| 588 rtc::scoped_ptr<rtcp::RtcpPacket> RTCPSender::BuildTMMBR( | 570 std::unique_ptr<rtcp::RtcpPacket> RTCPSender::BuildTMMBR( |
| 589 const RtcpContext& ctx) { | 571 const RtcpContext& ctx) { |
| 590 if (ctx.feedback_state_.module == nullptr) | 572 if (ctx.feedback_state_.module == nullptr) |
| 591 return nullptr; | 573 return nullptr; |
| 592 // Before sending the TMMBR check the received TMMBN, only an owner is | 574 // Before sending the TMMBR check the received TMMBN, only an owner is |
| 593 // allowed to raise the bitrate: | 575 // allowed to raise the bitrate: |
| 594 // * If the sender is an owner of the TMMBN -> send TMMBR | 576 // * If the sender is an owner of the TMMBN -> send TMMBR |
| 595 // * If not an owner but the TMMBR would enter the TMMBN -> send TMMBR | 577 // * If not an owner but the TMMBR would enter the TMMBN -> send TMMBR |
| 596 | 578 |
| 597 // get current bounding set from RTCP receiver | 579 // get current bounding set from RTCP receiver |
| 598 bool tmmbrOwner = false; | 580 bool tmmbrOwner = false; |
| (...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 636 return nullptr; | 618 return nullptr; |
| 637 | 619 |
| 638 rtcp::Tmmbr* tmmbr = new rtcp::Tmmbr(); | 620 rtcp::Tmmbr* tmmbr = new rtcp::Tmmbr(); |
| 639 tmmbr->From(ssrc_); | 621 tmmbr->From(ssrc_); |
| 640 rtcp::TmmbItem request; | 622 rtcp::TmmbItem request; |
| 641 request.set_ssrc(remote_ssrc_); | 623 request.set_ssrc(remote_ssrc_); |
| 642 request.set_bitrate_bps(tmmbr_send_ * 1000); | 624 request.set_bitrate_bps(tmmbr_send_ * 1000); |
| 643 request.set_packet_overhead(packet_oh_send_); | 625 request.set_packet_overhead(packet_oh_send_); |
| 644 tmmbr->WithTmmbr(request); | 626 tmmbr->WithTmmbr(request); |
| 645 | 627 |
| 646 return rtc::scoped_ptr<rtcp::Tmmbr>(tmmbr); | 628 return std::unique_ptr<rtcp::RtcpPacket>(tmmbr); |
| 647 } | 629 } |
| 648 | 630 |
| 649 rtc::scoped_ptr<rtcp::RtcpPacket> RTCPSender::BuildTMMBN( | 631 std::unique_ptr<rtcp::RtcpPacket> RTCPSender::BuildTMMBN( |
| 650 const RtcpContext& ctx) { | 632 const RtcpContext& ctx) { |
| 651 TMMBRSet* boundingSet = tmmbr_help_.BoundingSetToSend(); | 633 TMMBRSet* boundingSet = tmmbr_help_.BoundingSetToSend(); |
| 652 if (boundingSet == nullptr) | 634 if (boundingSet == nullptr) |
| 653 return nullptr; | 635 return nullptr; |
| 654 | 636 |
| 655 rtcp::Tmmbn* tmmbn = new rtcp::Tmmbn(); | 637 rtcp::Tmmbn* tmmbn = new rtcp::Tmmbn(); |
| 656 tmmbn->From(ssrc_); | 638 tmmbn->From(ssrc_); |
| 657 for (uint32_t i = 0; i < boundingSet->lengthOfSet(); i++) { | 639 for (uint32_t i = 0; i < boundingSet->lengthOfSet(); i++) { |
| 658 if (boundingSet->Tmmbr(i) > 0) { | 640 if (boundingSet->Tmmbr(i) > 0) { |
| 659 tmmbn->WithTmmbr(boundingSet->Ssrc(i), boundingSet->Tmmbr(i), | 641 tmmbn->WithTmmbr(boundingSet->Ssrc(i), boundingSet->Tmmbr(i), |
| 660 boundingSet->PacketOH(i)); | 642 boundingSet->PacketOH(i)); |
| 661 } | 643 } |
| 662 } | 644 } |
| 663 | 645 |
| 664 return rtc::scoped_ptr<rtcp::Tmmbn>(tmmbn); | 646 return std::unique_ptr<rtcp::RtcpPacket>(tmmbn); |
| 665 } | 647 } |
| 666 | 648 |
| 667 rtc::scoped_ptr<rtcp::RtcpPacket> RTCPSender::BuildAPP(const RtcpContext& ctx) { | 649 std::unique_ptr<rtcp::RtcpPacket> RTCPSender::BuildAPP(const RtcpContext& ctx) { |
| 668 rtcp::App* app = new rtcp::App(); | 650 rtcp::App* app = new rtcp::App(); |
| 669 app->From(ssrc_); | 651 app->From(ssrc_); |
| 670 app->WithSubType(app_sub_type_); | 652 app->WithSubType(app_sub_type_); |
| 671 app->WithName(app_name_); | 653 app->WithName(app_name_); |
| 672 app->WithData(app_data_.get(), app_length_); | 654 app->WithData(app_data_.get(), app_length_); |
| 673 | 655 |
| 674 return rtc::scoped_ptr<rtcp::App>(app); | 656 return std::unique_ptr<rtcp::RtcpPacket>(app); |
| 675 } | 657 } |
| 676 | 658 |
| 677 rtc::scoped_ptr<rtcp::RtcpPacket> RTCPSender::BuildNACK( | 659 std::unique_ptr<rtcp::RtcpPacket> RTCPSender::BuildNACK( |
| 678 const RtcpContext& ctx) { | 660 const RtcpContext& ctx) { |
| 679 rtcp::Nack* nack = new rtcp::Nack(); | 661 rtcp::Nack* nack = new rtcp::Nack(); |
| 680 nack->From(ssrc_); | 662 nack->From(ssrc_); |
| 681 nack->To(remote_ssrc_); | 663 nack->To(remote_ssrc_); |
| 682 nack->WithList(ctx.nack_list_, ctx.nack_size_); | 664 nack->WithList(ctx.nack_list_, ctx.nack_size_); |
| 683 | 665 |
| 684 // Report stats. | 666 // Report stats. |
| 685 NACKStringBuilder stringBuilder; | 667 NACKStringBuilder stringBuilder; |
| 686 for (int idx = 0; idx < ctx.nack_size_; ++idx) { | 668 for (int idx = 0; idx < ctx.nack_size_; ++idx) { |
| 687 stringBuilder.PushNACK(ctx.nack_list_[idx]); | 669 stringBuilder.PushNACK(ctx.nack_list_[idx]); |
| 688 nack_stats_.ReportRequest(ctx.nack_list_[idx]); | 670 nack_stats_.ReportRequest(ctx.nack_list_[idx]); |
| 689 } | 671 } |
| 690 packet_type_counter_.nack_requests = nack_stats_.requests(); | 672 packet_type_counter_.nack_requests = nack_stats_.requests(); |
| 691 packet_type_counter_.unique_nack_requests = nack_stats_.unique_requests(); | 673 packet_type_counter_.unique_nack_requests = nack_stats_.unique_requests(); |
| 692 | 674 |
| 693 TRACE_EVENT_INSTANT1(TRACE_DISABLED_BY_DEFAULT("webrtc_rtp"), | 675 TRACE_EVENT_INSTANT1(TRACE_DISABLED_BY_DEFAULT("webrtc_rtp"), |
| 694 "RTCPSender::NACK", "nacks", | 676 "RTCPSender::NACK", "nacks", |
| 695 TRACE_STR_COPY(stringBuilder.GetResult().c_str())); | 677 TRACE_STR_COPY(stringBuilder.GetResult().c_str())); |
| 696 ++packet_type_counter_.nack_packets; | 678 ++packet_type_counter_.nack_packets; |
| 697 TRACE_COUNTER_ID1(TRACE_DISABLED_BY_DEFAULT("webrtc_rtp"), "RTCP_NACKCount", | 679 TRACE_COUNTER_ID1(TRACE_DISABLED_BY_DEFAULT("webrtc_rtp"), "RTCP_NACKCount", |
| 698 ssrc_, packet_type_counter_.nack_packets); | 680 ssrc_, packet_type_counter_.nack_packets); |
| 699 | 681 |
| 700 return rtc::scoped_ptr<rtcp::Nack>(nack); | 682 return std::unique_ptr<rtcp::RtcpPacket>(nack); |
| 701 } | 683 } |
| 702 | 684 |
| 703 rtc::scoped_ptr<rtcp::RtcpPacket> RTCPSender::BuildBYE(const RtcpContext& ctx) { | 685 std::unique_ptr<rtcp::RtcpPacket> RTCPSender::BuildBYE(const RtcpContext& ctx) { |
| 704 rtcp::Bye* bye = new rtcp::Bye(); | 686 rtcp::Bye* bye = new rtcp::Bye(); |
| 705 bye->From(ssrc_); | 687 bye->From(ssrc_); |
| 706 for (uint32_t csrc : csrcs_) | 688 for (uint32_t csrc : csrcs_) |
| 707 bye->WithCsrc(csrc); | 689 bye->WithCsrc(csrc); |
| 708 | 690 |
| 709 return rtc::scoped_ptr<rtcp::Bye>(bye); | 691 return std::unique_ptr<rtcp::RtcpPacket>(bye); |
| 710 } | 692 } |
| 711 | 693 |
| 712 rtc::scoped_ptr<rtcp::RtcpPacket> RTCPSender::BuildReceiverReferenceTime( | 694 std::unique_ptr<rtcp::RtcpPacket> RTCPSender::BuildReceiverReferenceTime( |
| 713 const RtcpContext& ctx) { | 695 const RtcpContext& ctx) { |
| 714 | 696 |
| 715 rtcp::ExtendedReports* xr = new rtcp::ExtendedReports(); | 697 rtcp::ExtendedReports* xr = new rtcp::ExtendedReports(); |
| 716 xr->From(ssrc_); | 698 xr->From(ssrc_); |
| 717 | 699 |
| 718 rtcp::Rrtr rrtr; | 700 rtcp::Rrtr rrtr; |
| 719 rrtr.WithNtp(NtpTime(ctx.ntp_sec_, ctx.ntp_frac_)); | 701 rrtr.WithNtp(NtpTime(ctx.ntp_sec_, ctx.ntp_frac_)); |
| 720 | 702 |
| 721 xr->WithRrtr(rrtr); | 703 xr->WithRrtr(rrtr); |
| 722 | 704 |
| 723 // TODO(sprang): Merge XR report sending to contain all of RRTR, DLRR, VOIP? | 705 // TODO(sprang): Merge XR report sending to contain all of RRTR, DLRR, VOIP? |
| 724 | 706 |
| 725 return rtc::scoped_ptr<rtcp::RtcpPacket>(xr); | 707 return std::unique_ptr<rtcp::RtcpPacket>(xr); |
| 726 } | 708 } |
| 727 | 709 |
| 728 rtc::scoped_ptr<rtcp::RtcpPacket> RTCPSender::BuildDlrr( | 710 std::unique_ptr<rtcp::RtcpPacket> RTCPSender::BuildDlrr( |
| 729 const RtcpContext& ctx) { | 711 const RtcpContext& ctx) { |
| 730 rtcp::ExtendedReports* xr = new rtcp::ExtendedReports(); | 712 rtcp::ExtendedReports* xr = new rtcp::ExtendedReports(); |
| 731 xr->From(ssrc_); | 713 xr->From(ssrc_); |
| 732 | 714 |
| 733 rtcp::Dlrr dlrr; | 715 rtcp::Dlrr dlrr; |
| 734 const RtcpReceiveTimeInfo& info = ctx.feedback_state_.last_xr_rr; | 716 const RtcpReceiveTimeInfo& info = ctx.feedback_state_.last_xr_rr; |
| 735 dlrr.WithDlrrItem(info.sourceSSRC, info.lastRR, info.delaySinceLastRR); | 717 dlrr.WithDlrrItem(info.sourceSSRC, info.lastRR, info.delaySinceLastRR); |
| 736 | 718 |
| 737 xr->WithDlrr(dlrr); | 719 xr->WithDlrr(dlrr); |
| 738 | 720 |
| 739 return rtc::scoped_ptr<rtcp::RtcpPacket>(xr); | 721 return std::unique_ptr<rtcp::RtcpPacket>(xr); |
| 740 } | 722 } |
| 741 | 723 |
| 742 // TODO(sprang): Add a unit test for this, or remove if the code isn't used. | 724 // TODO(sprang): Add a unit test for this, or remove if the code isn't used. |
| 743 rtc::scoped_ptr<rtcp::RtcpPacket> RTCPSender::BuildVoIPMetric( | 725 std::unique_ptr<rtcp::RtcpPacket> RTCPSender::BuildVoIPMetric( |
| 744 const RtcpContext& context) { | 726 const RtcpContext& context) { |
| 745 rtcp::ExtendedReports* xr = new rtcp::ExtendedReports(); | 727 rtcp::ExtendedReports* xr = new rtcp::ExtendedReports(); |
| 746 xr->From(ssrc_); | 728 xr->From(ssrc_); |
| 747 | 729 |
| 748 rtcp::VoipMetric voip; | 730 rtcp::VoipMetric voip; |
| 749 voip.To(remote_ssrc_); | 731 voip.To(remote_ssrc_); |
| 750 voip.WithVoipMetric(xr_voip_metric_); | 732 voip.WithVoipMetric(xr_voip_metric_); |
| 751 | 733 |
| 752 xr->WithVoipMetric(voip); | 734 xr->WithVoipMetric(voip); |
| 753 | 735 |
| 754 return rtc::scoped_ptr<rtcp::RtcpPacket>(xr); | 736 return std::unique_ptr<rtcp::RtcpPacket>(xr); |
| 755 } | 737 } |
| 756 | 738 |
| 757 int32_t RTCPSender::SendRTCP(const FeedbackState& feedback_state, | 739 int32_t RTCPSender::SendRTCP(const FeedbackState& feedback_state, |
| 758 RTCPPacketType packetType, | 740 RTCPPacketType packetType, |
| 759 int32_t nack_size, | 741 int32_t nack_size, |
| 760 const uint16_t* nack_list, | 742 const uint16_t* nack_list, |
| 761 bool repeat, | 743 bool repeat, |
| 762 uint64_t pictureID) { | 744 uint64_t pictureID) { |
| 763 return SendCompoundRTCP( | 745 return SendCompoundRTCP( |
| 764 feedback_state, std::set<RTCPPacketType>(&packetType, &packetType + 1), | 746 feedback_state, std::set<RTCPPacketType>(&packetType, &packetType + 1), |
| 765 nack_size, nack_list, repeat, pictureID); | 747 nack_size, nack_list, repeat, pictureID); |
| 766 } | 748 } |
| 767 | 749 |
| 768 int32_t RTCPSender::SendCompoundRTCP( | 750 int32_t RTCPSender::SendCompoundRTCP( |
| 769 const FeedbackState& feedback_state, | 751 const FeedbackState& feedback_state, |
| 770 const std::set<RTCPPacketType>& packet_types, | 752 const std::set<RTCPPacketType>& packet_types, |
| 771 int32_t nack_size, | 753 int32_t nack_size, |
| 772 const uint16_t* nack_list, | 754 const uint16_t* nack_list, |
| 773 bool repeat, | 755 bool repeat, |
| 774 uint64_t pictureID) { | 756 uint64_t pictureID) { |
| 775 PacketContainer container(transport_, event_log_); | 757 PacketContainer container(transport_, event_log_); |
| 776 { | 758 { |
| 777 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 759 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 778 if (method_ == RtcpMode::kOff) { | 760 if (method_ == RtcpMode::kOff) { |
| 779 LOG(LS_WARNING) << "Can't send rtcp if it is disabled."; | 761 LOG(LS_WARNING) << "Can't send rtcp if it is disabled."; |
| 780 return -1; | 762 return -1; |
| 781 } | 763 } |
| 782 | 764 |
| 783 // We need to send our NTP even if we haven't received any reports. | 765 // We need to send our NTP even if we haven't received any reports. |
| 784 uint32_t ntp_sec; | 766 uint32_t ntp_sec; |
| 785 uint32_t ntp_frac; | 767 uint32_t ntp_frac; |
| 786 clock_->CurrentNtp(ntp_sec, ntp_frac); | 768 clock_->CurrentNtp(ntp_sec, ntp_frac); |
| 787 RtcpContext context(feedback_state, nack_size, nack_list, repeat, pictureID, | 769 RtcpContext context(feedback_state, nack_size, nack_list, repeat, pictureID, |
| 788 ntp_sec, ntp_frac, &container); | 770 ntp_sec, ntp_frac); |
| 789 | 771 |
| 790 PrepareReport(packet_types, feedback_state); | 772 PrepareReport(packet_types, feedback_state); |
| 791 | 773 |
| 792 rtc::scoped_ptr<rtcp::RtcpPacket> packet_bye; | 774 std::unique_ptr<rtcp::RtcpPacket> packet_bye; |
| 793 | 775 |
| 794 auto it = report_flags_.begin(); | 776 auto it = report_flags_.begin(); |
| 795 while (it != report_flags_.end()) { | 777 while (it != report_flags_.end()) { |
| 796 auto builder_it = builders_.find(it->type); | 778 auto builder_it = builders_.find(it->type); |
| 797 RTC_DCHECK(builder_it != builders_.end()); | 779 RTC_DCHECK(builder_it != builders_.end()); |
| 798 if (it->is_volatile) { | 780 if (it->is_volatile) { |
| 799 report_flags_.erase(it++); | 781 report_flags_.erase(it++); |
| 800 } else { | 782 } else { |
| 801 ++it; | 783 ++it; |
| 802 } | 784 } |
| 803 | 785 |
| 804 BuilderFunc func = builder_it->second; | 786 BuilderFunc func = builder_it->second; |
| 805 rtc::scoped_ptr<rtcp::RtcpPacket> packet = (this->*func)(context); | 787 std::unique_ptr<rtcp::RtcpPacket> packet = (this->*func)(context); |
| 806 if (packet.get() == nullptr) | 788 if (packet.get() == nullptr) |
| 807 return -1; | 789 return -1; |
| 808 // If there is a BYE, don't append now - save it and append it | 790 // If there is a BYE, don't append now - save it and append it |
| 809 // at the end later. | 791 // at the end later. |
| 810 if (builder_it->first == kRtcpBye) { | 792 if (builder_it->first == kRtcpBye) { |
| 811 packet_bye = std::move(packet); | 793 packet_bye = std::move(packet); |
| 812 } else { | 794 } else { |
| 813 container.Append(packet.release()); | 795 container.Append(packet.release()); |
| 814 } | 796 } |
| 815 } | 797 } |
| (...skipping 116 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 932 uint32_t receiveTime = feedback_state.last_rr_ntp_secs & 0x0000FFFF; | 914 uint32_t receiveTime = feedback_state.last_rr_ntp_secs & 0x0000FFFF; |
| 933 receiveTime <<= 16; | 915 receiveTime <<= 16; |
| 934 receiveTime += (feedback_state.last_rr_ntp_frac & 0xffff0000) >> 16; | 916 receiveTime += (feedback_state.last_rr_ntp_frac & 0xffff0000) >> 16; |
| 935 | 917 |
| 936 block->WithDelayLastSr(now - receiveTime); | 918 block->WithDelayLastSr(now - receiveTime); |
| 937 } | 919 } |
| 938 return true; | 920 return true; |
| 939 } | 921 } |
| 940 | 922 |
| 941 void RTCPSender::SetCsrcs(const std::vector<uint32_t>& csrcs) { | 923 void RTCPSender::SetCsrcs(const std::vector<uint32_t>& csrcs) { |
| 942 assert(csrcs.size() <= kRtpCsrcSize); | 924 RTC_DCHECK_LE(csrcs.size(), static_cast<size_t>(kRtpCsrcSize)); |
| 943 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 925 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 944 csrcs_ = csrcs; | 926 csrcs_ = csrcs; |
| 945 } | 927 } |
| 946 | 928 |
| 947 int32_t RTCPSender::SetApplicationSpecificData(uint8_t subType, | 929 int32_t RTCPSender::SetApplicationSpecificData(uint8_t subType, |
| 948 uint32_t name, | 930 uint32_t name, |
| 949 const uint8_t* data, | 931 const uint8_t* data, |
| 950 uint16_t length) { | 932 uint16_t length) { |
| 951 if (length % 4 != 0) { | 933 if (length % 4 != 0) { |
| 952 LOG(LS_ERROR) << "Failed to SetApplicationSpecificData."; | 934 LOG(LS_ERROR) << "Failed to SetApplicationSpecificData."; |
| 953 return -1; | 935 return -1; |
| 954 } | 936 } |
| 955 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 937 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 956 | 938 |
| 957 SetFlag(kRtcpApp, true); | 939 SetFlag(kRtcpApp, true); |
| 958 app_sub_type_ = subType; | 940 app_sub_type_ = subType; |
| 959 app_name_ = name; | 941 app_name_ = name; |
| 960 app_data_.reset(new uint8_t[length]); | 942 app_data_.reset(new uint8_t[length]); |
| 961 app_length_ = length; | 943 app_length_ = length; |
| 962 memcpy(app_data_.get(), data, length); | 944 memcpy(app_data_.get(), data, length); |
| 963 return 0; | 945 return 0; |
| 964 } | 946 } |
| 965 | 947 |
| 966 int32_t RTCPSender::SetRTCPVoIPMetrics(const RTCPVoIPMetric* VoIPMetric) { | 948 int32_t RTCPSender::SetRTCPVoIPMetrics(const RTCPVoIPMetric* VoIPMetric) { |
| 967 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 949 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 968 memcpy(&xr_voip_metric_, VoIPMetric, sizeof(RTCPVoIPMetric)); | 950 memcpy(&xr_voip_metric_, VoIPMetric, sizeof(RTCPVoIPMetric)); |
| 969 | 951 |
| 970 SetFlag(kRtcpXrVoipMetric, true); | 952 SetFlag(kRtcpXrVoipMetric, true); |
| 971 return 0; | 953 return 0; |
| 972 } | 954 } |
| 973 | 955 |
| 974 void RTCPSender::SendRtcpXrReceiverReferenceTime(bool enable) { | 956 void RTCPSender::SendRtcpXrReceiverReferenceTime(bool enable) { |
| 975 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 957 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 976 xr_send_receiver_reference_time_enabled_ = enable; | 958 xr_send_receiver_reference_time_enabled_ = enable; |
| 977 } | 959 } |
| 978 | 960 |
| 979 bool RTCPSender::RtcpXrReceiverReferenceTime() const { | 961 bool RTCPSender::RtcpXrReceiverReferenceTime() const { |
| 980 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 962 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 981 return xr_send_receiver_reference_time_enabled_; | 963 return xr_send_receiver_reference_time_enabled_; |
| 982 } | 964 } |
| 983 | 965 |
| 984 // no callbacks allowed inside this function | 966 // no callbacks allowed inside this function |
| 985 int32_t RTCPSender::SetTMMBN(const TMMBRSet* boundingSet) { | 967 int32_t RTCPSender::SetTMMBN(const TMMBRSet* boundingSet) { |
| 986 CriticalSectionScoped lock(critical_section_rtcp_sender_.get()); | 968 rtc::CritScope lock(&critical_section_rtcp_sender_); |
| 987 | 969 |
| 988 if (0 == tmmbr_help_.SetTMMBRBoundingSetToSend(boundingSet)) { | 970 if (0 == tmmbr_help_.SetTMMBRBoundingSetToSend(boundingSet)) { |
| 989 SetFlag(kRtcpTmmbn, true); | 971 SetFlag(kRtcpTmmbn, true); |
| 990 return 0; | 972 return 0; |
| 991 } | 973 } |
| 992 return -1; | 974 return -1; |
| 993 } | 975 } |
| 994 | 976 |
| 995 void RTCPSender::SetFlag(RTCPPacketType type, bool is_volatile) { | 977 void RTCPSender::SetFlag(RTCPPacketType type, bool is_volatile) { |
| 996 report_flags_.insert(ReportFlag(type, is_volatile)); | 978 report_flags_.insert(ReportFlag(type, is_volatile)); |
| (...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1047 // RTC_DISALLOW_IMPLICIT_CONSTRUCTORS(Sender); | 1029 // RTC_DISALLOW_IMPLICIT_CONSTRUCTORS(Sender); |
| 1048 // but we can't because of an incorrect warning (C4822) in MVS 2013. | 1030 // but we can't because of an incorrect warning (C4822) in MVS 2013. |
| 1049 } sender(transport_, event_log_); | 1031 } sender(transport_, event_log_); |
| 1050 | 1032 |
| 1051 uint8_t buffer[IP_PACKET_SIZE]; | 1033 uint8_t buffer[IP_PACKET_SIZE]; |
| 1052 return packet.BuildExternalBuffer(buffer, IP_PACKET_SIZE, &sender) && | 1034 return packet.BuildExternalBuffer(buffer, IP_PACKET_SIZE, &sender) && |
| 1053 !sender.send_failure_; | 1035 !sender.send_failure_; |
| 1054 } | 1036 } |
| 1055 | 1037 |
| 1056 } // namespace webrtc | 1038 } // namespace webrtc |
| OLD | NEW |