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

Side by Side Diff: webrtc/modules/rtp_rtcp/source/fec_receiver_impl.cc

Issue 2110763002: Style updates to ProducerFec/FecReceiver. (Closed) Base URL: https://chromium.googlesource.com/external/webrtc.git@master
Patch Set: Rebase + 'git cl format'. Created 4 years, 4 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
OLDNEW
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/fec_receiver_impl.h" 11 #include "webrtc/modules/rtp_rtcp/source/fec_receiver_impl.h"
12 12
13 #include <memory> 13 #include <memory>
14 #include <utility> 14 #include <utility>
15 15
16 #include "webrtc/base/checks.h" 16 #include "webrtc/base/checks.h"
17 #include "webrtc/base/logging.h" 17 #include "webrtc/base/logging.h"
18 #include "webrtc/modules/rtp_rtcp/source/byte_io.h" 18 #include "webrtc/modules/rtp_rtcp/source/byte_io.h"
19 #include "webrtc/modules/rtp_rtcp/source/rtp_receiver_video.h" 19 #include "webrtc/modules/rtp_rtcp/source/rtp_receiver_video.h"
20 20
21 // RFC 5109
22 namespace webrtc { 21 namespace webrtc {
23 22
24 FecReceiver* FecReceiver::Create(RtpData* callback) { 23 FecReceiver* FecReceiver::Create(RtpData* callback) {
25 return new FecReceiverImpl(callback); 24 return new FecReceiverImpl(callback);
26 } 25 }
27 26
28 FecReceiverImpl::FecReceiverImpl(RtpData* callback) 27 FecReceiverImpl::FecReceiverImpl(RtpData* callback)
29 : recovered_packet_callback_(callback), 28 : recovered_packet_callback_(callback) {}
30 fec_(new ForwardErrorCorrection()) {}
31 29
32 FecReceiverImpl::~FecReceiverImpl() { 30 FecReceiverImpl::~FecReceiverImpl() {
33 received_packet_list_.clear(); 31 received_packets_.clear();
34 if (fec_ != NULL) { 32 fec_.ResetState(&recovered_packets_);
35 fec_->ResetState(&recovered_packet_list_);
36 delete fec_;
37 }
38 } 33 }
39 34
40 FecPacketCounter FecReceiverImpl::GetPacketCounter() const { 35 FecPacketCounter FecReceiverImpl::GetPacketCounter() const {
41 rtc::CritScope cs(&crit_sect_); 36 rtc::CritScope cs(&crit_sect_);
42 return packet_counter_; 37 return packet_counter_;
43 } 38 }
44 39
45 // 0 1 2 3 40 // 0 1 2 3
46 // 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 41 // 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
47 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 42 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
(...skipping 19 matching lines...) Expand all
67 // timestamp to determine the timestamp of the data for which this 62 // timestamp to determine the timestamp of the data for which this
68 // block is the redundancy. 63 // block is the redundancy.
69 // 64 //
70 // block length: 10 bits Length in bytes of the corresponding data 65 // block length: 10 bits Length in bytes of the corresponding data
71 // block excluding header. 66 // block excluding header.
72 67
73 int32_t FecReceiverImpl::AddReceivedRedPacket( 68 int32_t FecReceiverImpl::AddReceivedRedPacket(
74 const RTPHeader& header, const uint8_t* incoming_rtp_packet, 69 const RTPHeader& header, const uint8_t* incoming_rtp_packet,
75 size_t packet_length, uint8_t ulpfec_payload_type) { 70 size_t packet_length, uint8_t ulpfec_payload_type) {
76 rtc::CritScope cs(&crit_sect_); 71 rtc::CritScope cs(&crit_sect_);
77 uint8_t REDHeaderLength = 1; 72
73 uint8_t red_header_length = 1;
78 size_t payload_data_length = packet_length - header.headerLength; 74 size_t payload_data_length = packet_length - header.headerLength;
79 75
80 if (payload_data_length == 0) { 76 if (payload_data_length == 0) {
81 LOG(LS_WARNING) << "Corrupt/truncated FEC packet."; 77 LOG(LS_WARNING) << "Corrupt/truncated FEC packet.";
82 return -1; 78 return -1;
83 } 79 }
84 80
85 // Add to list without RED header, aka a virtual RTP packet 81 // Remove RED header of incoming packet and store as a virtual RTP packet.
86 // we remove the RED header
87
88 std::unique_ptr<ForwardErrorCorrection::ReceivedPacket> received_packet( 82 std::unique_ptr<ForwardErrorCorrection::ReceivedPacket> received_packet(
89 new ForwardErrorCorrection::ReceivedPacket()); 83 new ForwardErrorCorrection::ReceivedPacket());
90 received_packet->pkt = new ForwardErrorCorrection::Packet(); 84 received_packet->pkt = new ForwardErrorCorrection::Packet();
91 85
92 // get payload type from RED header 86 // Get payload type from RED header and sequence number from RTP header.
93 uint8_t payload_type = 87 uint8_t payload_type = incoming_rtp_packet[header.headerLength] & 0x7f;
94 incoming_rtp_packet[header.headerLength] & 0x7f;
95
96 received_packet->is_fec = payload_type == ulpfec_payload_type; 88 received_packet->is_fec = payload_type == ulpfec_payload_type;
97 received_packet->seq_num = header.sequenceNumber; 89 received_packet->seq_num = header.sequenceNumber;
98 90
99 uint16_t blockLength = 0; 91 uint16_t block_length = 0;
100 if (incoming_rtp_packet[header.headerLength] & 0x80) { 92 if (incoming_rtp_packet[header.headerLength] & 0x80) {
101 // f bit set in RED header 93 // f bit set in RED header, i.e. there are more than one RED header blocks.
102 REDHeaderLength = 4; 94 red_header_length = 4;
103 if (payload_data_length < REDHeaderLength + 1u) { 95 if (payload_data_length < red_header_length + 1u) {
104 LOG(LS_WARNING) << "Corrupt/truncated FEC packet."; 96 LOG(LS_WARNING) << "Corrupt/truncated FEC packet.";
105 return -1; 97 return -1;
106 } 98 }
107 99
108 uint16_t timestamp_offset = 100 uint16_t timestamp_offset = incoming_rtp_packet[header.headerLength + 1]
109 (incoming_rtp_packet[header.headerLength + 1]) << 8; 101 << 8;
110 timestamp_offset += 102 timestamp_offset +=
111 incoming_rtp_packet[header.headerLength + 2]; 103 incoming_rtp_packet[header.headerLength + 2];
112 timestamp_offset = timestamp_offset >> 2; 104 timestamp_offset = timestamp_offset >> 2;
113 if (timestamp_offset != 0) { 105 if (timestamp_offset != 0) {
114 LOG(LS_WARNING) << "Corrupt payload found."; 106 LOG(LS_WARNING) << "Corrupt payload found.";
115 return -1; 107 return -1;
116 } 108 }
117 109
118 blockLength = 110 block_length = (0x3 & incoming_rtp_packet[header.headerLength + 2]) << 8;
119 (0x03 & incoming_rtp_packet[header.headerLength + 2]) << 8; 111 block_length += incoming_rtp_packet[header.headerLength + 3];
120 blockLength += (incoming_rtp_packet[header.headerLength + 3]);
121 112
122 // check next RED header 113 // Check next RED header block.
123 if (incoming_rtp_packet[header.headerLength + 4] & 0x80) { 114 if (incoming_rtp_packet[header.headerLength + 4] & 0x80) {
124 LOG(LS_WARNING) << "More than 2 blocks in packet not supported."; 115 LOG(LS_WARNING) << "More than 2 blocks in packet not supported.";
125 return -1; 116 return -1;
126 } 117 }
127 // Check that the packet is long enough to contain data in the following 118 // Check that the packet is long enough to contain data in the following
128 // block. 119 // block.
129 if (blockLength > payload_data_length - (REDHeaderLength + 1)) { 120 if (block_length > payload_data_length - (red_header_length + 1)) {
130 LOG(LS_WARNING) << "Block length longer than packet."; 121 LOG(LS_WARNING) << "Block length longer than packet.";
131 return -1; 122 return -1;
132 } 123 }
133 } 124 }
134 ++packet_counter_.num_packets; 125 ++packet_counter_.num_packets;
135 126
136 std::unique_ptr<ForwardErrorCorrection::ReceivedPacket> 127 std::unique_ptr<ForwardErrorCorrection::ReceivedPacket>
137 second_received_packet; 128 second_received_packet;
138 if (blockLength > 0) { 129 if (block_length > 0) {
139 // handle block length, split into 2 packets 130 // Handle block length, split into two packets.
140 REDHeaderLength = 5; 131 red_header_length = 5;
141 132
142 // copy the RTP header 133 // Copy RTP header.
143 memcpy(received_packet->pkt->data, incoming_rtp_packet, 134 memcpy(received_packet->pkt->data, incoming_rtp_packet,
144 header.headerLength); 135 header.headerLength);
145 136
146 // replace the RED payload type 137 // Set payload type.
147 received_packet->pkt->data[1] &= 0x80; // reset the payload 138 received_packet->pkt->data[1] &= 0x80; // Reset RED payload type.
148 received_packet->pkt->data[1] += 139 received_packet->pkt->data[1] += payload_type; // Set media payload type.
149 payload_type; // set the media payload type
150 140
151 // copy the payload data 141 // Copy payload data.
152 memcpy( 142 memcpy(received_packet->pkt->data + header.headerLength,
153 received_packet->pkt->data + header.headerLength, 143 incoming_rtp_packet + header.headerLength + red_header_length,
154 incoming_rtp_packet + header.headerLength + REDHeaderLength, 144 block_length);
155 blockLength); 145 received_packet->pkt->length = block_length;
156 146
157 received_packet->pkt->length = blockLength; 147 second_received_packet.reset(new ForwardErrorCorrection::ReceivedPacket);
158 148 second_received_packet->pkt = new ForwardErrorCorrection::Packet;
159 second_received_packet.reset(new ForwardErrorCorrection::ReceivedPacket());
160 second_received_packet->pkt = new ForwardErrorCorrection::Packet();
161 149
162 second_received_packet->is_fec = true; 150 second_received_packet->is_fec = true;
163 second_received_packet->seq_num = header.sequenceNumber; 151 second_received_packet->seq_num = header.sequenceNumber;
164 ++packet_counter_.num_fec_packets; 152 ++packet_counter_.num_fec_packets;
165 153
166 // copy the FEC payload data 154 // Copy FEC payload data.
167 memcpy(second_received_packet->pkt->data, 155 memcpy(second_received_packet->pkt->data,
168 incoming_rtp_packet + header.headerLength + 156 incoming_rtp_packet + header.headerLength + red_header_length +
169 REDHeaderLength + blockLength, 157 block_length,
170 payload_data_length - REDHeaderLength - blockLength); 158 payload_data_length - red_header_length - block_length);
171 159
172 second_received_packet->pkt->length = 160 second_received_packet->pkt->length =
173 payload_data_length - REDHeaderLength - blockLength; 161 payload_data_length - red_header_length - block_length;
174 162
175 } else if (received_packet->is_fec) { 163 } else if (received_packet->is_fec) {
176 ++packet_counter_.num_fec_packets; 164 ++packet_counter_.num_fec_packets;
177 // everything behind the RED header 165 // everything behind the RED header
178 memcpy( 166 memcpy(received_packet->pkt->data,
179 received_packet->pkt->data, 167 incoming_rtp_packet + header.headerLength + red_header_length,
180 incoming_rtp_packet + header.headerLength + REDHeaderLength, 168 payload_data_length - red_header_length);
181 payload_data_length - REDHeaderLength); 169 received_packet->pkt->length = payload_data_length - red_header_length;
182 received_packet->pkt->length = payload_data_length - REDHeaderLength;
183 received_packet->ssrc = 170 received_packet->ssrc =
184 ByteReader<uint32_t>::ReadBigEndian(&incoming_rtp_packet[8]); 171 ByteReader<uint32_t>::ReadBigEndian(&incoming_rtp_packet[8]);
185 172
186 } else { 173 } else {
187 // copy the RTP header 174 // Copy RTP header.
188 memcpy(received_packet->pkt->data, incoming_rtp_packet, 175 memcpy(received_packet->pkt->data, incoming_rtp_packet,
189 header.headerLength); 176 header.headerLength);
190 177
191 // replace the RED payload type 178 // Set payload type.
192 received_packet->pkt->data[1] &= 0x80; // reset the payload 179 received_packet->pkt->data[1] &= 0x80; // Reset RED payload type.
193 received_packet->pkt->data[1] += 180 received_packet->pkt->data[1] += payload_type; // Set media payload type.
194 payload_type; // set the media payload type
195 181
196 // copy the media payload data 182 // Copy payload data.
197 memcpy( 183 memcpy(received_packet->pkt->data + header.headerLength,
198 received_packet->pkt->data + header.headerLength, 184 incoming_rtp_packet + header.headerLength + red_header_length,
199 incoming_rtp_packet + header.headerLength + REDHeaderLength, 185 payload_data_length - red_header_length);
200 payload_data_length - REDHeaderLength);
201
202 received_packet->pkt->length = 186 received_packet->pkt->length =
203 header.headerLength + payload_data_length - REDHeaderLength; 187 header.headerLength + payload_data_length - red_header_length;
204 } 188 }
205 189
206 if (received_packet->pkt->length == 0) { 190 if (received_packet->pkt->length == 0) {
207 return 0; 191 return 0;
208 } 192 }
209 193
210 received_packet_list_.push_back(std::move(received_packet)); 194 received_packets_.push_back(std::move(received_packet));
211 if (second_received_packet) { 195 if (second_received_packet) {
212 received_packet_list_.push_back(std::move(second_received_packet)); 196 received_packets_.push_back(std::move(second_received_packet));
213 } 197 }
214 return 0; 198 return 0;
215 } 199 }
216 200
217 int32_t FecReceiverImpl::ProcessReceivedFec() { 201 int32_t FecReceiverImpl::ProcessReceivedFec() {
218 crit_sect_.Enter(); 202 crit_sect_.Enter();
219 if (!received_packet_list_.empty()) { 203 if (!received_packets_.empty()) {
220 // Send received media packet to VCM. 204 // Send received media packet to VCM.
221 if (!received_packet_list_.front()->is_fec) { 205 if (!received_packets_.front()->is_fec) {
222 ForwardErrorCorrection::Packet* packet = 206 ForwardErrorCorrection::Packet* packet = received_packets_.front()->pkt;
223 received_packet_list_.front()->pkt;
224 crit_sect_.Leave(); 207 crit_sect_.Leave();
225 if (!recovered_packet_callback_->OnRecoveredPacket(packet->data, 208 if (!recovered_packet_callback_->OnRecoveredPacket(packet->data,
226 packet->length)) { 209 packet->length)) {
227 return -1; 210 return -1;
228 } 211 }
229 crit_sect_.Enter(); 212 crit_sect_.Enter();
230 } 213 }
231 if (fec_->DecodeFec(&received_packet_list_, &recovered_packet_list_) != 0) { 214 if (fec_.DecodeFec(&received_packets_, &recovered_packets_) != 0) {
232 crit_sect_.Leave(); 215 crit_sect_.Leave();
233 return -1; 216 return -1;
234 } 217 }
235 RTC_DCHECK(received_packet_list_.empty()); 218 RTC_DCHECK(received_packets_.empty());
236 } 219 }
237 // Send any recovered media packets to VCM. 220 // Send any recovered media packets to VCM.
238 for (const auto& recovered_packet : recovered_packet_list_) { 221 for (const auto& recovered_packet : recovered_packets_) {
239 if (recovered_packet->returned) { 222 if (recovered_packet->returned) {
240 // Already sent to the VCM and the jitter buffer. 223 // Already sent to the VCM and the jitter buffer.
241 continue; 224 continue;
242 } 225 }
243 ForwardErrorCorrection::Packet* packet = recovered_packet->pkt; 226 ForwardErrorCorrection::Packet* packet = recovered_packet->pkt;
244 ++packet_counter_.num_recovered_packets; 227 ++packet_counter_.num_recovered_packets;
245 crit_sect_.Leave(); 228 crit_sect_.Leave();
246 if (!recovered_packet_callback_->OnRecoveredPacket(packet->data, 229 if (!recovered_packet_callback_->OnRecoveredPacket(packet->data,
247 packet->length)) { 230 packet->length)) {
248 return -1; 231 return -1;
249 } 232 }
250 crit_sect_.Enter(); 233 crit_sect_.Enter();
251 recovered_packet->returned = true; 234 recovered_packet->returned = true;
252 } 235 }
253 crit_sect_.Leave(); 236 crit_sect_.Leave();
254 return 0; 237 return 0;
255 } 238 }
256 239
257 } // namespace webrtc 240 } // namespace webrtc
OLDNEW
« no previous file with comments | « webrtc/modules/rtp_rtcp/source/fec_receiver_impl.h ('k') | webrtc/modules/rtp_rtcp/source/fec_receiver_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698