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 |
(...skipping 525 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
536 } else if (frame_type == kVideoFrameDelta) { | 536 } else if (frame_type == kVideoFrameDelta) { |
537 ++frame_counts_.delta_frames; | 537 ++frame_counts_.delta_frames; |
538 } | 538 } |
539 if (frame_count_observer_) { | 539 if (frame_count_observer_) { |
540 frame_count_observer_->FrameCountUpdated(frame_counts_, ssrc); | 540 frame_count_observer_->FrameCountUpdated(frame_counts_, ssrc); |
541 } | 541 } |
542 | 542 |
543 return ret_val; | 543 return ret_val; |
544 } | 544 } |
545 | 545 |
546 size_t RTPSender::TrySendRedundantPayloads(size_t bytes_to_send, | 546 size_t RTPSender::TrySendRedundantPayloads(size_t bytes_to_send) { |
547 int probe_cluster_id) { | |
548 { | 547 { |
549 rtc::CritScope lock(&send_critsect_); | 548 rtc::CritScope lock(&send_critsect_); |
550 if (!sending_media_) | 549 if (!sending_media_) |
551 return 0; | 550 return 0; |
552 if ((rtx_ & kRtxRedundantPayloads) == 0) | 551 if ((rtx_ & kRtxRedundantPayloads) == 0) |
553 return 0; | 552 return 0; |
554 } | 553 } |
555 | 554 |
556 uint8_t buffer[IP_PACKET_SIZE]; | 555 uint8_t buffer[IP_PACKET_SIZE]; |
557 int bytes_left = static_cast<int>(bytes_to_send); | 556 int bytes_left = static_cast<int>(bytes_to_send); |
558 while (bytes_left > 0) { | 557 while (bytes_left > 0) { |
559 size_t length = bytes_left; | 558 size_t length = bytes_left; |
560 int64_t capture_time_ms; | 559 int64_t capture_time_ms; |
561 if (!packet_history_.GetBestFittingPacket(buffer, &length, | 560 if (!packet_history_.GetBestFittingPacket(buffer, &length, |
562 &capture_time_ms)) { | 561 &capture_time_ms)) { |
563 break; | 562 break; |
564 } | 563 } |
565 if (!PrepareAndSendPacket(buffer, length, capture_time_ms, true, false, | 564 if (!PrepareAndSendPacket(buffer, length, capture_time_ms, true, false)) |
566 probe_cluster_id)) | |
567 break; | 565 break; |
568 RtpUtility::RtpHeaderParser rtp_parser(buffer, length); | 566 RtpUtility::RtpHeaderParser rtp_parser(buffer, length); |
569 RTPHeader rtp_header; | 567 RTPHeader rtp_header; |
570 rtp_parser.Parse(&rtp_header); | 568 rtp_parser.Parse(&rtp_header); |
571 bytes_left -= static_cast<int>(length - rtp_header.headerLength); | 569 bytes_left -= static_cast<int>(length - rtp_header.headerLength); |
572 } | 570 } |
573 return bytes_to_send - bytes_left; | 571 return bytes_to_send - bytes_left; |
574 } | 572 } |
575 | 573 |
576 void RTPSender::BuildPaddingPacket(uint8_t* packet, | 574 void RTPSender::BuildPaddingPacket(uint8_t* packet, |
577 size_t header_length, | 575 size_t header_length, |
578 size_t padding_length) { | 576 size_t padding_length) { |
579 packet[0] |= 0x20; // Set padding bit. | 577 packet[0] |= 0x20; // Set padding bit. |
580 int32_t* data = reinterpret_cast<int32_t*>(&(packet[header_length])); | 578 int32_t* data = reinterpret_cast<int32_t*>(&(packet[header_length])); |
581 | 579 |
582 // Fill data buffer with random data. | 580 // Fill data buffer with random data. |
583 for (size_t j = 0; j < (padding_length >> 2); ++j) { | 581 for (size_t j = 0; j < (padding_length >> 2); ++j) { |
584 data[j] = rand(); // NOLINT | 582 data[j] = rand(); // NOLINT |
585 } | 583 } |
586 // Set number of padding bytes in the last byte of the packet. | 584 // Set number of padding bytes in the last byte of the packet. |
587 packet[header_length + padding_length - 1] = | 585 packet[header_length + padding_length - 1] = |
588 static_cast<uint8_t>(padding_length); | 586 static_cast<uint8_t>(padding_length); |
589 } | 587 } |
590 | 588 |
591 size_t RTPSender::SendPadData(size_t bytes, | 589 size_t RTPSender::SendPadData(size_t bytes, |
592 bool timestamp_provided, | 590 bool timestamp_provided, |
593 uint32_t timestamp, | 591 uint32_t timestamp, |
594 int64_t capture_time_ms, | 592 int64_t capture_time_ms) { |
595 int probe_cluster_id) { | |
596 // Always send full padding packets. This is accounted for by the | 593 // Always send full padding packets. This is accounted for by the |
597 // RtpPacketSender, | 594 // RtpPacketSender, |
598 // which will make sure we don't send too much padding even if a single packet | 595 // which will make sure we don't send too much padding even if a single packet |
599 // is larger than requested. | 596 // is larger than requested. |
600 size_t padding_bytes_in_packet = | 597 size_t padding_bytes_in_packet = |
601 std::min(MaxDataPayloadLength(), kMaxPaddingLength); | 598 std::min(MaxDataPayloadLength(), kMaxPaddingLength); |
602 size_t bytes_sent = 0; | 599 size_t bytes_sent = 0; |
603 bool using_transport_seq = rtp_header_extension_map_.IsRegistered( | 600 bool using_transport_seq = rtp_header_extension_map_.IsRegistered( |
604 kRtpExtensionTransportSequenceNumber) && | 601 kRtpExtensionTransportSequenceNumber) && |
605 transport_sequence_number_allocator_; | 602 transport_sequence_number_allocator_; |
(...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
673 } | 670 } |
674 | 671 |
675 UpdateAbsoluteSendTime(padding_packet, length, rtp_header, now_ms); | 672 UpdateAbsoluteSendTime(padding_packet, length, rtp_header, now_ms); |
676 | 673 |
677 PacketOptions options; | 674 PacketOptions options; |
678 if (AllocateTransportSequenceNumber(&options.packet_id)) { | 675 if (AllocateTransportSequenceNumber(&options.packet_id)) { |
679 if (UpdateTransportSequenceNumber(options.packet_id, padding_packet, | 676 if (UpdateTransportSequenceNumber(options.packet_id, padding_packet, |
680 length, rtp_header)) { | 677 length, rtp_header)) { |
681 if (transport_feedback_observer_) | 678 if (transport_feedback_observer_) |
682 transport_feedback_observer_->AddPacket(options.packet_id, length, | 679 transport_feedback_observer_->AddPacket(options.packet_id, length, |
683 true, probe_cluster_id); | 680 true); |
684 } | 681 } |
685 } | 682 } |
686 | 683 |
687 if (!SendPacketToNetwork(padding_packet, length, options)) | 684 if (!SendPacketToNetwork(padding_packet, length, options)) |
688 break; | 685 break; |
689 | 686 |
690 bytes_sent += padding_bytes_in_packet; | 687 bytes_sent += padding_bytes_in_packet; |
691 UpdateRtpStats(padding_packet, length, rtp_header, over_rtx, false); | 688 UpdateRtpStats(padding_packet, length, rtp_header, over_rtx, false); |
692 } | 689 } |
693 | 690 |
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
729 corrected_capture_tims_ms, length - header.headerLength, true); | 726 corrected_capture_tims_ms, length - header.headerLength, true); |
730 | 727 |
731 return length; | 728 return length; |
732 } | 729 } |
733 int rtx = kRtxOff; | 730 int rtx = kRtxOff; |
734 { | 731 { |
735 rtc::CritScope lock(&send_critsect_); | 732 rtc::CritScope lock(&send_critsect_); |
736 rtx = rtx_; | 733 rtx = rtx_; |
737 } | 734 } |
738 if (!PrepareAndSendPacket(data_buffer, length, capture_time_ms, | 735 if (!PrepareAndSendPacket(data_buffer, length, capture_time_ms, |
739 (rtx & kRtxRetransmitted) > 0, true, | 736 (rtx & kRtxRetransmitted) > 0, true)) { |
740 PacketInfo::kNotAProbe)) { | |
741 return -1; | 737 return -1; |
742 } | 738 } |
743 return static_cast<int32_t>(length); | 739 return static_cast<int32_t>(length); |
744 } | 740 } |
745 | 741 |
746 bool RTPSender::SendPacketToNetwork(const uint8_t* packet, | 742 bool RTPSender::SendPacketToNetwork(const uint8_t* packet, |
747 size_t size, | 743 size_t size, |
748 const PacketOptions& options) { | 744 const PacketOptions& options) { |
749 int bytes_sent = -1; | 745 int bytes_sent = -1; |
750 if (transport_) { | 746 if (transport_) { |
(...skipping 115 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
866 nack_byte_count_[i + 1] = nack_byte_count_[i]; | 862 nack_byte_count_[i + 1] = nack_byte_count_[i]; |
867 nack_byte_count_times_[i + 1] = nack_byte_count_times_[i]; | 863 nack_byte_count_times_[i + 1] = nack_byte_count_times_[i]; |
868 } | 864 } |
869 nack_byte_count_[0] = bytes; | 865 nack_byte_count_[0] = bytes; |
870 nack_byte_count_times_[0] = now; | 866 nack_byte_count_times_[0] = now; |
871 } | 867 } |
872 | 868 |
873 // Called from pacer when we can send the packet. | 869 // Called from pacer when we can send the packet. |
874 bool RTPSender::TimeToSendPacket(uint16_t sequence_number, | 870 bool RTPSender::TimeToSendPacket(uint16_t sequence_number, |
875 int64_t capture_time_ms, | 871 int64_t capture_time_ms, |
876 bool retransmission, | 872 bool retransmission) { |
877 int probe_cluster_id) { | |
878 size_t length = IP_PACKET_SIZE; | 873 size_t length = IP_PACKET_SIZE; |
879 uint8_t data_buffer[IP_PACKET_SIZE]; | 874 uint8_t data_buffer[IP_PACKET_SIZE]; |
880 int64_t stored_time_ms; | 875 int64_t stored_time_ms; |
881 | 876 |
882 if (!packet_history_.GetPacketAndSetSendTime(sequence_number, | 877 if (!packet_history_.GetPacketAndSetSendTime(sequence_number, |
883 0, | 878 0, |
884 retransmission, | 879 retransmission, |
885 data_buffer, | 880 data_buffer, |
886 &length, | 881 &length, |
887 &stored_time_ms)) { | 882 &stored_time_ms)) { |
888 // Packet cannot be found. Allow sending to continue. | 883 // Packet cannot be found. Allow sending to continue. |
889 return true; | 884 return true; |
890 } | 885 } |
891 | 886 |
892 int rtx; | 887 int rtx; |
893 { | 888 { |
894 rtc::CritScope lock(&send_critsect_); | 889 rtc::CritScope lock(&send_critsect_); |
895 rtx = rtx_; | 890 rtx = rtx_; |
896 } | 891 } |
897 return PrepareAndSendPacket(data_buffer, length, capture_time_ms, | 892 return PrepareAndSendPacket(data_buffer, |
| 893 length, |
| 894 capture_time_ms, |
898 retransmission && (rtx & kRtxRetransmitted) > 0, | 895 retransmission && (rtx & kRtxRetransmitted) > 0, |
899 retransmission, probe_cluster_id); | 896 retransmission); |
900 } | 897 } |
901 | 898 |
902 bool RTPSender::PrepareAndSendPacket(uint8_t* buffer, | 899 bool RTPSender::PrepareAndSendPacket(uint8_t* buffer, |
903 size_t length, | 900 size_t length, |
904 int64_t capture_time_ms, | 901 int64_t capture_time_ms, |
905 bool send_over_rtx, | 902 bool send_over_rtx, |
906 bool is_retransmit, | 903 bool is_retransmit) { |
907 int probe_cluster_id) { | |
908 uint8_t* buffer_to_send_ptr = buffer; | 904 uint8_t* buffer_to_send_ptr = buffer; |
909 | 905 |
910 RtpUtility::RtpHeaderParser rtp_parser(buffer, length); | 906 RtpUtility::RtpHeaderParser rtp_parser(buffer, length); |
911 RTPHeader rtp_header; | 907 RTPHeader rtp_header; |
912 rtp_parser.Parse(&rtp_header); | 908 rtp_parser.Parse(&rtp_header); |
913 if (!is_retransmit && rtp_header.markerBit) { | 909 if (!is_retransmit && rtp_header.markerBit) { |
914 TRACE_EVENT_ASYNC_END0(TRACE_DISABLED_BY_DEFAULT("webrtc_rtp"), "PacedSend", | 910 TRACE_EVENT_ASYNC_END0(TRACE_DISABLED_BY_DEFAULT("webrtc_rtp"), "PacedSend", |
915 capture_time_ms); | 911 capture_time_ms); |
916 } | 912 } |
917 | 913 |
(...skipping 11 matching lines...) Expand all Loading... |
929 int64_t diff_ms = now_ms - capture_time_ms; | 925 int64_t diff_ms = now_ms - capture_time_ms; |
930 UpdateTransmissionTimeOffset(buffer_to_send_ptr, length, rtp_header, | 926 UpdateTransmissionTimeOffset(buffer_to_send_ptr, length, rtp_header, |
931 diff_ms); | 927 diff_ms); |
932 UpdateAbsoluteSendTime(buffer_to_send_ptr, length, rtp_header, now_ms); | 928 UpdateAbsoluteSendTime(buffer_to_send_ptr, length, rtp_header, now_ms); |
933 | 929 |
934 PacketOptions options; | 930 PacketOptions options; |
935 if (AllocateTransportSequenceNumber(&options.packet_id)) { | 931 if (AllocateTransportSequenceNumber(&options.packet_id)) { |
936 if (UpdateTransportSequenceNumber(options.packet_id, buffer_to_send_ptr, | 932 if (UpdateTransportSequenceNumber(options.packet_id, buffer_to_send_ptr, |
937 length, rtp_header)) { | 933 length, rtp_header)) { |
938 if (transport_feedback_observer_) | 934 if (transport_feedback_observer_) |
939 transport_feedback_observer_->AddPacket(options.packet_id, length, true, | 935 transport_feedback_observer_->AddPacket(options.packet_id, length, |
940 probe_cluster_id); | 936 true); |
941 } | 937 } |
942 } | 938 } |
943 | 939 |
944 if (!is_retransmit && !send_over_rtx) { | 940 if (!is_retransmit && !send_over_rtx) { |
945 UpdateDelayStatistics(capture_time_ms, now_ms); | 941 UpdateDelayStatistics(capture_time_ms, now_ms); |
946 UpdateOnSendPacket(options.packet_id, capture_time_ms, rtp_header.ssrc); | 942 UpdateOnSendPacket(options.packet_id, capture_time_ms, rtp_header.ssrc); |
947 } | 943 } |
948 | 944 |
949 bool ret = SendPacketToNetwork(buffer_to_send_ptr, length, options); | 945 bool ret = SendPacketToNetwork(buffer_to_send_ptr, length, options); |
950 if (ret) { | 946 if (ret) { |
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
997 } | 993 } |
998 bool fec_enabled; | 994 bool fec_enabled; |
999 uint8_t pt_red; | 995 uint8_t pt_red; |
1000 uint8_t pt_fec; | 996 uint8_t pt_fec; |
1001 video_->GenericFECStatus(&fec_enabled, &pt_red, &pt_fec); | 997 video_->GenericFECStatus(&fec_enabled, &pt_red, &pt_fec); |
1002 return fec_enabled && | 998 return fec_enabled && |
1003 header.payloadType == pt_red && | 999 header.payloadType == pt_red && |
1004 buffer[header.headerLength] == pt_fec; | 1000 buffer[header.headerLength] == pt_fec; |
1005 } | 1001 } |
1006 | 1002 |
1007 size_t RTPSender::TimeToSendPadding(size_t bytes, int probe_cluster_id) { | 1003 size_t RTPSender::TimeToSendPadding(size_t bytes) { |
1008 if (audio_configured_ || bytes == 0) | 1004 if (audio_configured_ || bytes == 0) |
1009 return 0; | 1005 return 0; |
1010 size_t bytes_sent = TrySendRedundantPayloads(bytes, probe_cluster_id); | 1006 size_t bytes_sent = TrySendRedundantPayloads(bytes); |
1011 if (bytes_sent < bytes) | 1007 if (bytes_sent < bytes) |
1012 bytes_sent += | 1008 bytes_sent += SendPadData(bytes - bytes_sent, false, 0, 0); |
1013 SendPadData(bytes - bytes_sent, false, 0, 0, probe_cluster_id); | |
1014 return bytes_sent; | 1009 return bytes_sent; |
1015 } | 1010 } |
1016 | 1011 |
1017 // TODO(pwestin): send in the RtpHeaderParser to avoid parsing it again. | 1012 // TODO(pwestin): send in the RtpHeaderParser to avoid parsing it again. |
1018 int32_t RTPSender::SendToNetwork(uint8_t* buffer, | 1013 int32_t RTPSender::SendToNetwork(uint8_t* buffer, |
1019 size_t payload_length, | 1014 size_t payload_length, |
1020 size_t rtp_header_length, | 1015 size_t rtp_header_length, |
1021 int64_t capture_time_ms, | 1016 int64_t capture_time_ms, |
1022 StorageType storage, | 1017 StorageType storage, |
1023 RtpPacketSender::Priority priority) { | 1018 RtpPacketSender::Priority priority) { |
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1060 "capture_time_ms", corrected_time_ms); | 1055 "capture_time_ms", corrected_time_ms); |
1061 } | 1056 } |
1062 return 0; | 1057 return 0; |
1063 } | 1058 } |
1064 | 1059 |
1065 PacketOptions options; | 1060 PacketOptions options; |
1066 if (AllocateTransportSequenceNumber(&options.packet_id)) { | 1061 if (AllocateTransportSequenceNumber(&options.packet_id)) { |
1067 if (UpdateTransportSequenceNumber(options.packet_id, buffer, length, | 1062 if (UpdateTransportSequenceNumber(options.packet_id, buffer, length, |
1068 rtp_header)) { | 1063 rtp_header)) { |
1069 if (transport_feedback_observer_) | 1064 if (transport_feedback_observer_) |
1070 transport_feedback_observer_->AddPacket(options.packet_id, length, true, | 1065 transport_feedback_observer_->AddPacket(options.packet_id, length, |
1071 PacketInfo::kNotAProbe); | 1066 true); |
1072 } | 1067 } |
1073 } | 1068 } |
1074 UpdateDelayStatistics(capture_time_ms, now_ms); | 1069 UpdateDelayStatistics(capture_time_ms, now_ms); |
1075 UpdateOnSendPacket(options.packet_id, capture_time_ms, rtp_header.ssrc); | 1070 UpdateOnSendPacket(options.packet_id, capture_time_ms, rtp_header.ssrc); |
1076 | 1071 |
1077 bool sent = SendPacketToNetwork(buffer, length, options); | 1072 bool sent = SendPacketToNetwork(buffer, length, options); |
1078 | 1073 |
1079 // Mark the packet as sent in the history even if send failed. Dropping a | 1074 // Mark the packet as sent in the history even if send failed. Dropping a |
1080 // packet here should be treated as any other packet drop so we should be | 1075 // packet here should be treated as any other packet drop so we should be |
1081 // ready for a retransmission. | 1076 // ready for a retransmission. |
(...skipping 834 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1916 rtc::CritScope lock(&send_critsect_); | 1911 rtc::CritScope lock(&send_critsect_); |
1917 | 1912 |
1918 RtpState state; | 1913 RtpState state; |
1919 state.sequence_number = sequence_number_rtx_; | 1914 state.sequence_number = sequence_number_rtx_; |
1920 state.start_timestamp = start_timestamp_; | 1915 state.start_timestamp = start_timestamp_; |
1921 | 1916 |
1922 return state; | 1917 return state; |
1923 } | 1918 } |
1924 | 1919 |
1925 } // namespace webrtc | 1920 } // namespace webrtc |
OLD | NEW |