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

Side by Side Diff: media/cast/rtcp/rtcp_sender.cc

Issue 192843002: Cast:Adding signaling and infrastructure for adjustable delay (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: nit Created 6 years, 9 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 | Annotate | Revision Log
« no previous file with comments | « media/cast/rtcp/rtcp_sender.h ('k') | media/cast/rtcp/rtcp_sender_unittest.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2013 The Chromium Authors. All rights reserved. 1 // Copyright 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "media/cast/rtcp/rtcp_sender.h" 5 #include "media/cast/rtcp/rtcp_sender.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <vector> 8 #include <vector>
9 9
10 #include "base/big_endian.h" 10 #include "base/big_endian.h"
(...skipping 145 matching lines...) Expand 10 before | Expand all | Expand 10 after
156 VLOG(3) << "number of frames: " << *number_of_frames; 156 VLOG(3) << "number of frames: " << *number_of_frames;
157 VLOG(3) << "total messages to send: " << *total_number_of_messages_to_send; 157 VLOG(3) << "total messages to send: " << *total_number_of_messages_to_send;
158 VLOG(3) << "rtcp log size: " << *rtcp_log_size; 158 VLOG(3) << "rtcp log size: " << *rtcp_log_size;
159 return *number_of_frames > 0; 159 return *number_of_frames > 0;
160 } 160 }
161 } // namespace 161 } // namespace
162 162
163 // TODO(mikhal): This is only used by the receiver. Consider renaming. 163 // TODO(mikhal): This is only used by the receiver. Consider renaming.
164 RtcpSender::RtcpSender(scoped_refptr<CastEnvironment> cast_environment, 164 RtcpSender::RtcpSender(scoped_refptr<CastEnvironment> cast_environment,
165 transport::PacedPacketSender* outgoing_transport, 165 transport::PacedPacketSender* outgoing_transport,
166 uint32 sending_ssrc, const std::string& c_name) 166 uint32 sending_ssrc,
167 const std::string& c_name)
167 : ssrc_(sending_ssrc), 168 : ssrc_(sending_ssrc),
168 c_name_(c_name), 169 c_name_(c_name),
169 transport_(outgoing_transport), 170 transport_(outgoing_transport),
170 cast_environment_(cast_environment) { 171 cast_environment_(cast_environment) {
171 DCHECK_LT(c_name_.length(), kRtcpCnameSize) << "Invalid config"; 172 DCHECK_LT(c_name_.length(), kRtcpCnameSize) << "Invalid config";
172 } 173 }
173 174
174 RtcpSender::~RtcpSender() {} 175 RtcpSender::~RtcpSender() {}
175 176
176 // static 177 // static
177 bool RtcpSender::IsReceiverEvent(const CastLoggingEvent& event) { 178 bool RtcpSender::IsReceiverEvent(const CastLoggingEvent& event) {
178 return ConvertEventTypeToWireFormat(event) != 0; 179 return ConvertEventTypeToWireFormat(event) != 0;
179 } 180 }
180 181
181 void RtcpSender::SendRtcpFromRtpReceiver( 182 void RtcpSender::SendRtcpFromRtpReceiver(
182 uint32 packet_type_flags, 183 uint32 packet_type_flags,
183 const transport::RtcpReportBlock* report_block, 184 const transport::RtcpReportBlock* report_block,
184 const RtcpReceiverReferenceTimeReport* rrtr, 185 const RtcpReceiverReferenceTimeReport* rrtr,
185 const RtcpCastMessage* cast_message, 186 const RtcpCastMessage* cast_message,
186 const ReceiverRtcpEventSubscriber* event_subscriber) { 187 const ReceiverRtcpEventSubscriber* event_subscriber,
187 if (packet_type_flags & kRtcpSr || packet_type_flags & kRtcpDlrr || 188 uint16 target_delay_ms) {
188 packet_type_flags & kRtcpSenderLog) { 189 if (packet_type_flags & transport::kRtcpSr ||
190 packet_type_flags & transport::kRtcpDlrr ||
191 packet_type_flags & transport::kRtcpSenderLog) {
189 NOTREACHED() << "Invalid argument"; 192 NOTREACHED() << "Invalid argument";
190 } 193 }
191 if (packet_type_flags & kRtcpPli || packet_type_flags & kRtcpRpsi || 194 if (packet_type_flags & transport::kRtcpPli ||
192 packet_type_flags & kRtcpRemb || packet_type_flags & kRtcpNack) { 195 packet_type_flags & transport::kRtcpRpsi ||
196 packet_type_flags & transport::kRtcpRemb ||
197 packet_type_flags & transport::kRtcpNack) {
193 // Implement these for webrtc interop. 198 // Implement these for webrtc interop.
194 NOTIMPLEMENTED(); 199 NOTIMPLEMENTED();
195 } 200 }
196 Packet packet; 201 Packet packet;
197 packet.reserve(kMaxIpPacketSize); 202 packet.reserve(kMaxIpPacketSize);
198 203
199 if (packet_type_flags & kRtcpRr) { 204 if (packet_type_flags & transport::kRtcpRr) {
200 BuildRR(report_block, &packet); 205 BuildRR(report_block, &packet);
201 if (!c_name_.empty()) { 206 if (!c_name_.empty()) {
202 BuildSdec(&packet); 207 BuildSdec(&packet);
203 } 208 }
204 } 209 }
205 if (packet_type_flags & kRtcpBye) { 210 if (packet_type_flags & transport::kRtcpBye) {
206 BuildBye(&packet); 211 BuildBye(&packet);
207 } 212 }
208 if (packet_type_flags & kRtcpRrtr) { 213 if (packet_type_flags & transport::kRtcpRrtr) {
209 DCHECK(rrtr) << "Invalid argument"; 214 DCHECK(rrtr) << "Invalid argument";
210 BuildRrtr(rrtr, &packet); 215 BuildRrtr(rrtr, &packet);
211 } 216 }
212 if (packet_type_flags & kRtcpCast) { 217 if (packet_type_flags & transport::kRtcpCast) {
213 DCHECK(cast_message) << "Invalid argument"; 218 DCHECK(cast_message) << "Invalid argument";
214 BuildCast(cast_message, &packet); 219 BuildCast(cast_message, target_delay_ms, &packet);
215 } 220 }
216 if (packet_type_flags & kRtcpReceiverLog) { 221 if (packet_type_flags & transport::kRtcpReceiverLog) {
217 DCHECK(event_subscriber) << "Invalid argument"; 222 DCHECK(event_subscriber) << "Invalid argument";
218 BuildReceiverLog(event_subscriber->get_rtcp_events(), &packet); 223 BuildReceiverLog(event_subscriber->get_rtcp_events(), &packet);
219 } 224 }
220 if (packet.empty()) return; // Sanity don't send empty packets. 225
226 if (packet.empty())
227 return; // Sanity don't send empty packets.
221 228
222 transport_->SendRtcpPacket(packet); 229 transport_->SendRtcpPacket(packet);
223 } 230 }
224 231
225 void RtcpSender::BuildRR(const transport::RtcpReportBlock* report_block, 232 void RtcpSender::BuildRR(const transport::RtcpReportBlock* report_block,
226 Packet* packet) const { 233 Packet* packet) const {
227 size_t start_size = packet->size(); 234 size_t start_size = packet->size();
228 DCHECK_LT(start_size + 32, kMaxIpPacketSize) << "Not enough buffer space"; 235 DCHECK_LT(start_size + 32, kMaxIpPacketSize) << "Not enough buffer space";
229 if (start_size + 32 > kMaxIpPacketSize) return; 236 if (start_size + 32 > kMaxIpPacketSize)
237 return;
230 238
231 uint16 number_of_rows = (report_block) ? 7 : 1; 239 uint16 number_of_rows = (report_block) ? 7 : 1;
232 packet->resize(start_size + 8); 240 packet->resize(start_size + 8);
233 241
234 base::BigEndianWriter big_endian_writer( 242 base::BigEndianWriter big_endian_writer(
235 reinterpret_cast<char*>(&((*packet)[start_size])), 8); 243 reinterpret_cast<char*>(&((*packet)[start_size])), 8);
236 big_endian_writer.WriteU8(0x80 + (report_block ? 1 : 0)); 244 big_endian_writer.WriteU8(0x80 + (report_block ? 1 : 0));
237 big_endian_writer.WriteU8(transport::kPacketTypeReceiverReport); 245 big_endian_writer.WriteU8(transport::kPacketTypeReceiverReport);
238 big_endian_writer.WriteU16(number_of_rows); 246 big_endian_writer.WriteU16(number_of_rows);
239 big_endian_writer.WriteU32(ssrc_); 247 big_endian_writer.WriteU32(ssrc_);
240 248
241 if (report_block) { 249 if (report_block) {
242 AddReportBlocks(*report_block, packet); // Adds 24 bytes. 250 AddReportBlocks(*report_block, packet); // Adds 24 bytes.
243 } 251 }
244 } 252 }
245 253
246 void RtcpSender::AddReportBlocks(const transport::RtcpReportBlock& report_block, 254 void RtcpSender::AddReportBlocks(const transport::RtcpReportBlock& report_block,
247 Packet* packet) const { 255 Packet* packet) const {
248 size_t start_size = packet->size(); 256 size_t start_size = packet->size();
249 DCHECK_LT(start_size + 24, kMaxIpPacketSize) << "Not enough buffer space"; 257 DCHECK_LT(start_size + 24, kMaxIpPacketSize) << "Not enough buffer space";
250 if (start_size + 24 > kMaxIpPacketSize) return; 258 if (start_size + 24 > kMaxIpPacketSize)
259 return;
251 260
252 packet->resize(start_size + 24); 261 packet->resize(start_size + 24);
253 262
254 base::BigEndianWriter big_endian_writer( 263 base::BigEndianWriter big_endian_writer(
255 reinterpret_cast<char*>(&((*packet)[start_size])), 24); 264 reinterpret_cast<char*>(&((*packet)[start_size])), 24);
256 big_endian_writer.WriteU32(report_block.media_ssrc); 265 big_endian_writer.WriteU32(report_block.media_ssrc);
257 big_endian_writer.WriteU8(report_block.fraction_lost); 266 big_endian_writer.WriteU8(report_block.fraction_lost);
258 big_endian_writer.WriteU8(report_block.cumulative_lost >> 16); 267 big_endian_writer.WriteU8(report_block.cumulative_lost >> 16);
259 big_endian_writer.WriteU8(report_block.cumulative_lost >> 8); 268 big_endian_writer.WriteU8(report_block.cumulative_lost >> 8);
260 big_endian_writer.WriteU8(report_block.cumulative_lost); 269 big_endian_writer.WriteU8(report_block.cumulative_lost);
261 270
262 // Extended highest seq_no, contain the highest sequence number received. 271 // Extended highest seq_no, contain the highest sequence number received.
263 big_endian_writer.WriteU32(report_block.extended_high_sequence_number); 272 big_endian_writer.WriteU32(report_block.extended_high_sequence_number);
264 big_endian_writer.WriteU32(report_block.jitter); 273 big_endian_writer.WriteU32(report_block.jitter);
265 274
266 // Last SR timestamp; our NTP time when we received the last report. 275 // Last SR timestamp; our NTP time when we received the last report.
267 // This is the value that we read from the send report packet not when we 276 // This is the value that we read from the send report packet not when we
268 // received it. 277 // received it.
269 big_endian_writer.WriteU32(report_block.last_sr); 278 big_endian_writer.WriteU32(report_block.last_sr);
270 279
271 // Delay since last received report, time since we received the report. 280 // Delay since last received report, time since we received the report.
272 big_endian_writer.WriteU32(report_block.delay_since_last_sr); 281 big_endian_writer.WriteU32(report_block.delay_since_last_sr);
273 } 282 }
274 283
275 void RtcpSender::BuildSdec(Packet* packet) const { 284 void RtcpSender::BuildSdec(Packet* packet) const {
276 size_t start_size = packet->size(); 285 size_t start_size = packet->size();
277 DCHECK_LT(start_size + 12 + c_name_.length(), kMaxIpPacketSize) 286 DCHECK_LT(start_size + 12 + c_name_.length(), kMaxIpPacketSize)
278 << "Not enough buffer space"; 287 << "Not enough buffer space";
279 if (start_size + 12 > kMaxIpPacketSize) return; 288 if (start_size + 12 > kMaxIpPacketSize)
289 return;
280 290
281 // SDES Source Description. 291 // SDES Source Description.
282 packet->resize(start_size + 10); 292 packet->resize(start_size + 10);
283 293
284 base::BigEndianWriter big_endian_writer( 294 base::BigEndianWriter big_endian_writer(
285 reinterpret_cast<char*>(&((*packet)[start_size])), 10); 295 reinterpret_cast<char*>(&((*packet)[start_size])), 10);
286 // We always need to add one SDES CNAME. 296 // We always need to add one SDES CNAME.
287 big_endian_writer.WriteU8(0x80 + 1); 297 big_endian_writer.WriteU8(0x80 + 1);
288 big_endian_writer.WriteU8(transport::kPacketTypeSdes); 298 big_endian_writer.WriteU8(transport::kPacketTypeSdes);
289 299
290 // Handle SDES length later on. 300 // Handle SDES length later on.
291 uint32 sdes_length_position = static_cast<uint32>(start_size) + 3; 301 uint32 sdes_length_position = static_cast<uint32>(start_size) + 3;
292 big_endian_writer.WriteU16(0); 302 big_endian_writer.WriteU16(0);
293 big_endian_writer.WriteU32(ssrc_); // Add our own SSRC. 303 big_endian_writer.WriteU32(ssrc_); // Add our own SSRC.
294 big_endian_writer.WriteU8(1); // CNAME = 1 304 big_endian_writer.WriteU8(1); // CNAME = 1
295 big_endian_writer.WriteU8(static_cast<uint8>(c_name_.length())); 305 big_endian_writer.WriteU8(static_cast<uint8>(c_name_.length()));
296 306
297 size_t sdes_length = 10 + c_name_.length(); 307 size_t sdes_length = 10 + c_name_.length();
298 packet->insert(packet->end(), c_name_.c_str(), 308 packet->insert(
299 c_name_.c_str() + c_name_.length()); 309 packet->end(), c_name_.c_str(), c_name_.c_str() + c_name_.length());
300 310
301 size_t padding = 0; 311 size_t padding = 0;
302 312
303 // We must have a zero field even if we have an even multiple of 4 bytes. 313 // We must have a zero field even if we have an even multiple of 4 bytes.
304 if ((packet->size() % 4) == 0) { 314 if ((packet->size() % 4) == 0) {
305 padding++; 315 padding++;
306 packet->push_back(0); 316 packet->push_back(0);
307 } 317 }
308 while ((packet->size() % 4) != 0) { 318 while ((packet->size() % 4) != 0) {
309 padding++; 319 padding++;
310 packet->push_back(0); 320 packet->push_back(0);
311 } 321 }
312 sdes_length += padding; 322 sdes_length += padding;
313 323
314 // In 32-bit words minus one and we don't count the header. 324 // In 32-bit words minus one and we don't count the header.
315 uint8 buffer_length = static_cast<uint8>((sdes_length / 4) - 1); 325 uint8 buffer_length = static_cast<uint8>((sdes_length / 4) - 1);
316 (*packet)[sdes_length_position] = buffer_length; 326 (*packet)[sdes_length_position] = buffer_length;
317 } 327 }
318 328
319 void RtcpSender::BuildPli(uint32 remote_ssrc, Packet* packet) const { 329 void RtcpSender::BuildPli(uint32 remote_ssrc, Packet* packet) const {
320 size_t start_size = packet->size(); 330 size_t start_size = packet->size();
321 DCHECK_LT(start_size + 12, kMaxIpPacketSize) << "Not enough buffer space"; 331 DCHECK_LT(start_size + 12, kMaxIpPacketSize) << "Not enough buffer space";
322 if (start_size + 12 > kMaxIpPacketSize) return; 332 if (start_size + 12 > kMaxIpPacketSize)
333 return;
323 334
324 packet->resize(start_size + 12); 335 packet->resize(start_size + 12);
325 336
326 base::BigEndianWriter big_endian_writer( 337 base::BigEndianWriter big_endian_writer(
327 reinterpret_cast<char*>(&((*packet)[start_size])), 12); 338 reinterpret_cast<char*>(&((*packet)[start_size])), 12);
328 uint8 FMT = 1; // Picture loss indicator. 339 uint8 FMT = 1; // Picture loss indicator.
329 big_endian_writer.WriteU8(0x80 + FMT); 340 big_endian_writer.WriteU8(0x80 + FMT);
330 big_endian_writer.WriteU8(transport::kPacketTypePayloadSpecific); 341 big_endian_writer.WriteU8(transport::kPacketTypePayloadSpecific);
331 big_endian_writer.WriteU16(2); // Used fixed length of 2. 342 big_endian_writer.WriteU16(2); // Used fixed length of 2.
332 big_endian_writer.WriteU32(ssrc_); // Add our own SSRC. 343 big_endian_writer.WriteU32(ssrc_); // Add our own SSRC.
333 big_endian_writer.WriteU32(remote_ssrc); // Add the remote SSRC. 344 big_endian_writer.WriteU32(remote_ssrc); // Add the remote SSRC.
334 } 345 }
335 346
336 /* 347 /*
337 0 1 2 3 348 0 1 2 3
338 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 349 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
339 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 350 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
340 | PB |0| Payload Type| Native Rpsi bit string | 351 | PB |0| Payload Type| Native Rpsi bit string |
341 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 352 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
342 | defined per codec ... | Padding (0) | 353 | defined per codec ... | Padding (0) |
343 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 354 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
344 */ 355 */
345 void RtcpSender::BuildRpsi(const RtcpRpsiMessage* rpsi, Packet* packet) const { 356 void RtcpSender::BuildRpsi(const RtcpRpsiMessage* rpsi, Packet* packet) const {
346 size_t start_size = packet->size(); 357 size_t start_size = packet->size();
347 DCHECK_LT(start_size + 24, kMaxIpPacketSize) << "Not enough buffer space"; 358 DCHECK_LT(start_size + 24, kMaxIpPacketSize) << "Not enough buffer space";
348 if (start_size + 24 > kMaxIpPacketSize) return; 359 if (start_size + 24 > kMaxIpPacketSize)
360 return;
349 361
350 packet->resize(start_size + 24); 362 packet->resize(start_size + 24);
351 363
352 base::BigEndianWriter big_endian_writer( 364 base::BigEndianWriter big_endian_writer(
353 reinterpret_cast<char*>(&((*packet)[start_size])), 24); 365 reinterpret_cast<char*>(&((*packet)[start_size])), 24);
354 uint8 FMT = 3; // Reference Picture Selection Indication. 366 uint8 FMT = 3; // Reference Picture Selection Indication.
355 big_endian_writer.WriteU8(0x80 + FMT); 367 big_endian_writer.WriteU8(0x80 + FMT);
356 big_endian_writer.WriteU8(transport::kPacketTypePayloadSpecific); 368 big_endian_writer.WriteU8(transport::kPacketTypePayloadSpecific);
357 369
358 // Calculate length. 370 // Calculate length.
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after
393 for (int j = 0; j < padding_bytes; ++j) { 405 for (int j = 0; j < padding_bytes; ++j) {
394 big_endian_writer.WriteU8(0); 406 big_endian_writer.WriteU8(0);
395 } 407 }
396 } 408 }
397 409
398 void RtcpSender::BuildRemb(const RtcpRembMessage* remb, Packet* packet) const { 410 void RtcpSender::BuildRemb(const RtcpRembMessage* remb, Packet* packet) const {
399 size_t start_size = packet->size(); 411 size_t start_size = packet->size();
400 size_t remb_size = 20 + 4 * remb->remb_ssrcs.size(); 412 size_t remb_size = 20 + 4 * remb->remb_ssrcs.size();
401 DCHECK_LT(start_size + remb_size, kMaxIpPacketSize) 413 DCHECK_LT(start_size + remb_size, kMaxIpPacketSize)
402 << "Not enough buffer space"; 414 << "Not enough buffer space";
403 if (start_size + remb_size > kMaxIpPacketSize) return; 415 if (start_size + remb_size > kMaxIpPacketSize)
416 return;
404 417
405 packet->resize(start_size + remb_size); 418 packet->resize(start_size + remb_size);
406 419
407 base::BigEndianWriter big_endian_writer( 420 base::BigEndianWriter big_endian_writer(
408 reinterpret_cast<char*>(&((*packet)[start_size])), remb_size); 421 reinterpret_cast<char*>(&((*packet)[start_size])), remb_size);
409 422
410 // Add application layer feedback. 423 // Add application layer feedback.
411 uint8 FMT = 15; 424 uint8 FMT = 15;
412 big_endian_writer.WriteU8(0x80 + FMT); 425 big_endian_writer.WriteU8(0x80 + FMT);
413 big_endian_writer.WriteU8(transport::kPacketTypePayloadSpecific); 426 big_endian_writer.WriteU8(transport::kPacketTypePayloadSpecific);
414 big_endian_writer.WriteU8(0); 427 big_endian_writer.WriteU8(0);
415 big_endian_writer.WriteU8(static_cast<uint8>(remb->remb_ssrcs.size() + 4)); 428 big_endian_writer.WriteU8(static_cast<uint8>(remb->remb_ssrcs.size() + 4));
416 big_endian_writer.WriteU32(ssrc_); // Add our own SSRC. 429 big_endian_writer.WriteU32(ssrc_); // Add our own SSRC.
417 big_endian_writer.WriteU32(0); // Remote SSRC must be 0. 430 big_endian_writer.WriteU32(0); // Remote SSRC must be 0.
418 big_endian_writer.WriteU32(kRemb); 431 big_endian_writer.WriteU32(kRemb);
419 big_endian_writer.WriteU8(static_cast<uint8>(remb->remb_ssrcs.size())); 432 big_endian_writer.WriteU8(static_cast<uint8>(remb->remb_ssrcs.size()));
420 433
421 // 6 bit exponent and a 18 bit mantissa. 434 // 6 bit exponent and a 18 bit mantissa.
422 uint8 bitrate_exponent; 435 uint8 bitrate_exponent;
423 uint32 bitrate_mantissa; 436 uint32 bitrate_mantissa;
424 BitrateToRembExponentBitrate(remb->remb_bitrate, &bitrate_exponent, 437 BitrateToRembExponentBitrate(
425 &bitrate_mantissa); 438 remb->remb_bitrate, &bitrate_exponent, &bitrate_mantissa);
426 439
427 big_endian_writer.WriteU8(static_cast<uint8>( 440 big_endian_writer.WriteU8(static_cast<uint8>(
428 (bitrate_exponent << 2) + ((bitrate_mantissa >> 16) & 0x03))); 441 (bitrate_exponent << 2) + ((bitrate_mantissa >> 16) & 0x03)));
429 big_endian_writer.WriteU8(static_cast<uint8>(bitrate_mantissa >> 8)); 442 big_endian_writer.WriteU8(static_cast<uint8>(bitrate_mantissa >> 8));
430 big_endian_writer.WriteU8(static_cast<uint8>(bitrate_mantissa)); 443 big_endian_writer.WriteU8(static_cast<uint8>(bitrate_mantissa));
431 444
432 std::list<uint32>::const_iterator it = remb->remb_ssrcs.begin(); 445 std::list<uint32>::const_iterator it = remb->remb_ssrcs.begin();
433 for (; it != remb->remb_ssrcs.end(); ++it) { 446 for (; it != remb->remb_ssrcs.end(); ++it) {
434 big_endian_writer.WriteU32(*it); 447 big_endian_writer.WriteU32(*it);
435 } 448 }
436 base::TimeTicks now = cast_environment_->Clock()->NowTicks(); 449 base::TimeTicks now = cast_environment_->Clock()->NowTicks();
437 cast_environment_->Logging()->InsertGenericEvent(now, kRembBitrate, 450 cast_environment_->Logging()->InsertGenericEvent(
438 remb->remb_bitrate); 451 now, kRembBitrate, remb->remb_bitrate);
439 } 452 }
440 453
441 void RtcpSender::BuildNack(const RtcpNackMessage* nack, Packet* packet) const { 454 void RtcpSender::BuildNack(const RtcpNackMessage* nack, Packet* packet) const {
442 size_t start_size = packet->size(); 455 size_t start_size = packet->size();
443 DCHECK_LT(start_size + 16, kMaxIpPacketSize) << "Not enough buffer space"; 456 DCHECK_LT(start_size + 16, kMaxIpPacketSize) << "Not enough buffer space";
444 if (start_size + 16 > kMaxIpPacketSize) return; 457 if (start_size + 16 > kMaxIpPacketSize)
458 return;
445 459
446 packet->resize(start_size + 16); 460 packet->resize(start_size + 16);
447 461
448 base::BigEndianWriter big_endian_writer( 462 base::BigEndianWriter big_endian_writer(
449 reinterpret_cast<char*>(&((*packet)[start_size])), 16); 463 reinterpret_cast<char*>(&((*packet)[start_size])), 16);
450 464
451 uint8 FMT = 1; 465 uint8 FMT = 1;
452 big_endian_writer.WriteU8(0x80 + FMT); 466 big_endian_writer.WriteU8(0x80 + FMT);
453 big_endian_writer.WriteU8(transport::kPacketTypeGenericRtpFeedback); 467 big_endian_writer.WriteU8(transport::kPacketTypeGenericRtpFeedback);
454 big_endian_writer.WriteU8(0); 468 big_endian_writer.WriteU8(0);
(...skipping 19 matching lines...) Expand all
474 if (shift >= 0 && shift <= 15) { 488 if (shift >= 0 && shift <= 15) {
475 bitmask |= (1 << shift); 489 bitmask |= (1 << shift);
476 ++it; 490 ++it;
477 } else { 491 } else {
478 break; 492 break;
479 } 493 }
480 } 494 }
481 // Write the sequence number and the bitmask to the packet. 495 // Write the sequence number and the bitmask to the packet.
482 start_size = packet->size(); 496 start_size = packet->size();
483 DCHECK_LT(start_size + 4, kMaxIpPacketSize) << "Not enough buffer space"; 497 DCHECK_LT(start_size + 4, kMaxIpPacketSize) << "Not enough buffer space";
484 if (start_size + 4 > kMaxIpPacketSize) return; 498 if (start_size + 4 > kMaxIpPacketSize)
499 return;
485 500
486 packet->resize(start_size + 4); 501 packet->resize(start_size + 4);
487 base::BigEndianWriter big_endian_nack_writer( 502 base::BigEndianWriter big_endian_nack_writer(
488 reinterpret_cast<char*>(&((*packet)[start_size])), 4); 503 reinterpret_cast<char*>(&((*packet)[start_size])), 4);
489 big_endian_nack_writer.WriteU16(nack_sequence_number); 504 big_endian_nack_writer.WriteU16(nack_sequence_number);
490 big_endian_nack_writer.WriteU16(bitmask); 505 big_endian_nack_writer.WriteU16(bitmask);
491 number_of_nack_fields++; 506 number_of_nack_fields++;
492 } 507 }
493 DCHECK_GE(kRtcpMaxNackFields, number_of_nack_fields); 508 DCHECK_GE(kRtcpMaxNackFields, number_of_nack_fields);
494 (*packet)[nack_size_pos] = static_cast<uint8>(2 + number_of_nack_fields); 509 (*packet)[nack_size_pos] = static_cast<uint8>(2 + number_of_nack_fields);
495 } 510 }
496 511
497 void RtcpSender::BuildBye(Packet* packet) const { 512 void RtcpSender::BuildBye(Packet* packet) const {
498 size_t start_size = packet->size(); 513 size_t start_size = packet->size();
499 DCHECK_LT(start_size + 8, kMaxIpPacketSize) << "Not enough buffer space"; 514 DCHECK_LT(start_size + 8, kMaxIpPacketSize) << "Not enough buffer space";
500 if (start_size + 8 > kMaxIpPacketSize) return; 515 if (start_size + 8 > kMaxIpPacketSize)
516 return;
501 517
502 packet->resize(start_size + 8); 518 packet->resize(start_size + 8);
503 519
504 base::BigEndianWriter big_endian_writer( 520 base::BigEndianWriter big_endian_writer(
505 reinterpret_cast<char*>(&((*packet)[start_size])), 8); 521 reinterpret_cast<char*>(&((*packet)[start_size])), 8);
506 big_endian_writer.WriteU8(0x80 + 1); 522 big_endian_writer.WriteU8(0x80 + 1);
507 big_endian_writer.WriteU8(transport::kPacketTypeBye); 523 big_endian_writer.WriteU8(transport::kPacketTypeBye);
508 big_endian_writer.WriteU16(1); // Length. 524 big_endian_writer.WriteU16(1); // Length.
509 big_endian_writer.WriteU32(ssrc_); // Add our own SSRC. 525 big_endian_writer.WriteU32(ssrc_); // Add our own SSRC.
510 } 526 }
511 527
512 void RtcpSender::BuildRrtr(const RtcpReceiverReferenceTimeReport* rrtr, 528 void RtcpSender::BuildRrtr(const RtcpReceiverReferenceTimeReport* rrtr,
513 Packet* packet) const { 529 Packet* packet) const {
514 size_t start_size = packet->size(); 530 size_t start_size = packet->size();
515 DCHECK_LT(start_size + 20, kMaxIpPacketSize) << "Not enough buffer space"; 531 DCHECK_LT(start_size + 20, kMaxIpPacketSize) << "Not enough buffer space";
516 if (start_size + 20 > kMaxIpPacketSize) return; 532 if (start_size + 20 > kMaxIpPacketSize)
533 return;
517 534
518 packet->resize(start_size + 20); 535 packet->resize(start_size + 20);
519 536
520 base::BigEndianWriter big_endian_writer( 537 base::BigEndianWriter big_endian_writer(
521 reinterpret_cast<char*>(&((*packet)[start_size])), 20); 538 reinterpret_cast<char*>(&((*packet)[start_size])), 20);
522 539
523 big_endian_writer.WriteU8(0x80); 540 big_endian_writer.WriteU8(0x80);
524 big_endian_writer.WriteU8(transport::kPacketTypeXr); 541 big_endian_writer.WriteU8(transport::kPacketTypeXr);
525 big_endian_writer.WriteU16(4); // Length. 542 big_endian_writer.WriteU16(4); // Length.
526 big_endian_writer.WriteU32(ssrc_); // Add our own SSRC. 543 big_endian_writer.WriteU32(ssrc_); // Add our own SSRC.
527 big_endian_writer.WriteU8(4); // Add block type. 544 big_endian_writer.WriteU8(4); // Add block type.
528 big_endian_writer.WriteU8(0); // Add reserved. 545 big_endian_writer.WriteU8(0); // Add reserved.
529 big_endian_writer.WriteU16(2); // Block length. 546 big_endian_writer.WriteU16(2); // Block length.
530 547
531 // Add the media (received RTP) SSRC. 548 // Add the media (received RTP) SSRC.
532 big_endian_writer.WriteU32(rrtr->ntp_seconds); 549 big_endian_writer.WriteU32(rrtr->ntp_seconds);
533 big_endian_writer.WriteU32(rrtr->ntp_fraction); 550 big_endian_writer.WriteU32(rrtr->ntp_fraction);
534 } 551 }
535 552
536 void RtcpSender::BuildCast(const RtcpCastMessage* cast, Packet* packet) const { 553 void RtcpSender::BuildCast(const RtcpCastMessage* cast,
554 uint16 target_delay_ms,
555 Packet* packet) const {
537 size_t start_size = packet->size(); 556 size_t start_size = packet->size();
538 DCHECK_LT(start_size + 20, kMaxIpPacketSize) << "Not enough buffer space"; 557 DCHECK_LT(start_size + 20, kMaxIpPacketSize) << "Not enough buffer space";
539 if (start_size + 20 > kMaxIpPacketSize) return; 558 if (start_size + 20 > kMaxIpPacketSize)
559 return;
540 560
541 packet->resize(start_size + 20); 561 packet->resize(start_size + 20);
542 562
543 base::BigEndianWriter big_endian_writer( 563 base::BigEndianWriter big_endian_writer(
544 reinterpret_cast<char*>(&((*packet)[start_size])), 20); 564 reinterpret_cast<char*>(&((*packet)[start_size])), 20);
545 uint8 FMT = 15; // Application layer feedback. 565 uint8 FMT = 15; // Application layer feedback.
546 big_endian_writer.WriteU8(0x80 + FMT); 566 big_endian_writer.WriteU8(0x80 + FMT);
547 big_endian_writer.WriteU8(transport::kPacketTypePayloadSpecific); 567 big_endian_writer.WriteU8(transport::kPacketTypePayloadSpecific);
548 big_endian_writer.WriteU8(0); 568 big_endian_writer.WriteU8(0);
549 size_t cast_size_pos = start_size + 3; // Save length position. 569 size_t cast_size_pos = start_size + 3; // Save length position.
550 big_endian_writer.WriteU8(4); 570 big_endian_writer.WriteU8(4);
551 big_endian_writer.WriteU32(ssrc_); // Add our own SSRC. 571 big_endian_writer.WriteU32(ssrc_); // Add our own SSRC.
552 big_endian_writer.WriteU32(cast->media_ssrc_); // Remote SSRC. 572 big_endian_writer.WriteU32(cast->media_ssrc_); // Remote SSRC.
553 big_endian_writer.WriteU32(kCast); 573 big_endian_writer.WriteU32(kCast);
554 big_endian_writer.WriteU8(static_cast<uint8>(cast->ack_frame_id_)); 574 big_endian_writer.WriteU8(static_cast<uint8>(cast->ack_frame_id_));
555 size_t cast_loss_field_pos = start_size + 17; // Save loss field position. 575 size_t cast_loss_field_pos = start_size + 17; // Save loss field position.
556 big_endian_writer.WriteU8(0); // Overwritten with number_of_loss_fields. 576 big_endian_writer.WriteU8(0); // Overwritten with number_of_loss_fields.
557 big_endian_writer.WriteU8(0); // Reserved. 577 big_endian_writer.WriteU16(target_delay_ms);
558 big_endian_writer.WriteU8(0); // Reserved.
559 578
560 size_t number_of_loss_fields = 0; 579 size_t number_of_loss_fields = 0;
561 size_t max_number_of_loss_fields = std::min<size_t>( 580 size_t max_number_of_loss_fields = std::min<size_t>(
562 kRtcpMaxCastLossFields, (kMaxIpPacketSize - packet->size()) / 4); 581 kRtcpMaxCastLossFields, (kMaxIpPacketSize - packet->size()) / 4);
563 582
564 MissingFramesAndPacketsMap::const_iterator frame_it = 583 MissingFramesAndPacketsMap::const_iterator frame_it =
565 cast->missing_frames_and_packets_.begin(); 584 cast->missing_frames_and_packets_.begin();
566 585
567 for (; frame_it != cast->missing_frames_and_packets_.end() && 586 for (; frame_it != cast->missing_frames_and_packets_.end() &&
568 number_of_loss_fields < max_number_of_loss_fields; 587 number_of_loss_fields < max_number_of_loss_fields;
(...skipping 133 matching lines...) Expand 10 before | Expand all | Expand 10 after
702 if (frame_log_messages.event_log_messages_.empty()) { 721 if (frame_log_messages.event_log_messages_.empty()) {
703 // We sent all messages on this frame; pop the frame header. 722 // We sent all messages on this frame; pop the frame header.
704 receiver_log_message.pop_front(); 723 receiver_log_message.pop_front();
705 } 724 }
706 } 725 }
707 DCHECK_EQ(total_number_of_messages_to_send, 0); 726 DCHECK_EQ(total_number_of_messages_to_send, 0);
708 } 727 }
709 728
710 } // namespace cast 729 } // namespace cast
711 } // namespace media 730 } // namespace media
OLDNEW
« no previous file with comments | « media/cast/rtcp/rtcp_sender.h ('k') | media/cast/rtcp/rtcp_sender_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698