|
1 /* |
|
2 * Copyright (c) 2002-2003 Nokia Corporation and/or its subsidiary(-ies). |
|
3 * All rights reserved. |
|
4 * This component and the accompanying materials are made available |
|
5 * under the terms of "Eclipse Public License v1.0" |
|
6 * which accompanies this distribution, and is available |
|
7 * at the URL "http://www.eclipse.org/legal/epl-v10.html". |
|
8 * |
|
9 * Initial Contributors: |
|
10 * Nokia Corporation - initial contribution. |
|
11 * |
|
12 * Contributors: |
|
13 * |
|
14 * Description: |
|
15 * |
|
16 */ |
|
17 |
|
18 |
|
19 |
|
20 |
|
21 // INCLUDE FILES |
|
22 #include <e32base.h> |
|
23 #include <e32std.h> |
|
24 |
|
25 #include "rtputil.h" |
|
26 #include "rtpsdes.h" |
|
27 #include "rtppacket.h" |
|
28 #include "rtpmanager.h" |
|
29 |
|
30 // CONSTANTS |
|
31 const TInt KRtpVersion = 2; // Current protocol version |
|
32 const TUint8 KNullTerm( '\0' ); |
|
33 const TUint KMinRtpHeaderLen( 12 ); |
|
34 const TUint KMinRtcpAppLen( 3 ); |
|
35 |
|
36 const TInt KCSRCListMax = 15; |
|
37 |
|
38 // ================= MEMBER FUNCTIONS ======================= |
|
39 |
|
40 // --------------------------------------------------------------------------- |
|
41 // C++ default constructor can NOT contain any code, that |
|
42 // might leave. |
|
43 // --------------------------------------------------------------------------- |
|
44 // |
|
45 CRtpPacket::CRtpPacket( const TUint32* aRtpTimeRates ) : |
|
46 iSize( 0 ), |
|
47 iProfileRTPTimeRates( aRtpTimeRates ) |
|
48 { |
|
49 } |
|
50 |
|
51 // --------------------------------------------------------------------------- |
|
52 // Symbian 2nd phase constructor can leave. |
|
53 // --------------------------------------------------------------------------- |
|
54 // |
|
55 void CRtpPacket::ConstructL( TUint aPacketSize ) |
|
56 { |
|
57 iBuf = HBufC8::NewL( aPacketSize ); |
|
58 iData = const_cast<TUint8*>( iBuf->Des().Ptr() ); |
|
59 iDataPtr = iData; |
|
60 iExdataAlloc =EFalse; |
|
61 iCsrcAlloc= EFalse; |
|
62 } |
|
63 |
|
64 // --------------------------------------------------------------------------- |
|
65 // Two-phased constructor. |
|
66 // --------------------------------------------------------------------------- |
|
67 // |
|
68 CRtpPacket* CRtpPacket::NewL( TUint aPacketSize, const TUint32* aRtpTimeRates ) |
|
69 { |
|
70 CRtpPacket* self = new ( ELeave ) CRtpPacket( aRtpTimeRates ); |
|
71 CleanupStack::PushL( self ); |
|
72 self->ConstructL( aPacketSize ); |
|
73 CleanupStack::Pop(); //self |
|
74 return self; |
|
75 } |
|
76 |
|
77 // --------------------------------------------------------------------------- |
|
78 // Destructor |
|
79 // --------------------------------------------------------------------------- |
|
80 // |
|
81 CRtpPacket::~CRtpPacket() |
|
82 { |
|
83 delete iBuf; iBuf = NULL; |
|
84 } |
|
85 |
|
86 // --------------------------------------------------------------------------- |
|
87 // |
|
88 // |
|
89 // --------------------------------------------------------------------------- |
|
90 // |
|
91 void CRtpPacket::RtpPacketReset() |
|
92 { |
|
93 iSize = 0; |
|
94 iDataPtr = iData; |
|
95 } |
|
96 |
|
97 // --------------------------------------------------------------------------- |
|
98 // CRtpPacket::RtpPacketResetPtr() |
|
99 // |
|
100 // --------------------------------------------------------------------------- |
|
101 // |
|
102 void CRtpPacket::RtpPacketResetPtr() |
|
103 { |
|
104 iDataPtr = iData; |
|
105 } |
|
106 |
|
107 // --------------------------------------------------------------------------- |
|
108 // CRtpPacket::RtpPacketBuildRtp() |
|
109 // |
|
110 // --------------------------------------------------------------------------- |
|
111 // |
|
112 TInt CRtpPacket::RtpPacketBuildRtp( TRtpPacketStreamParam* aStreamParam, |
|
113 TRtpPacketIOParam* aInitParam ) |
|
114 { |
|
115 //Get a pointer to the beginning of iBuf |
|
116 TUint8* dataP = iData; |
|
117 |
|
118 //Fill dataP with binary zeroes (i.e. 0x00), replacing any existing content |
|
119 Mem::FillZ( dataP, KMinRtpHeaderLen ); |
|
120 |
|
121 /**************************** |
|
122 * dataP[0] = 8 bit * |
|
123 * * |
|
124 * 2 bit = version * |
|
125 * 1 bit = padding * |
|
126 * 1 bit = CRSRC Count * |
|
127 * 4 bit = extension * |
|
128 ****************************/ |
|
129 |
|
130 //version (2 bit) |
|
131 // 0111001 |
|
132 // 1100000 |
|
133 // ------- |
|
134 // 1111001 |
|
135 dataP[0] |= ( KRtpVersion << 6 ); |
|
136 |
|
137 // padding (1 bit) |
|
138 dataP[0] |= static_cast<TUint8>( ( aInitParam->TRTP.padding << 5 ) ); |
|
139 |
|
140 // header extension (1 bit) |
|
141 if ( aInitParam->TRTP.fHeaderExtension) |
|
142 { |
|
143 dataP[0] |= ( 1 << 4 ); |
|
144 } |
|
145 |
|
146 // CC = 0 (1 bit) |
|
147 |
|
148 /**************************** |
|
149 * dataP[1] = 8 bit * |
|
150 * * |
|
151 * 1 bit = marker * |
|
152 * 1 bit = payload type * |
|
153 ****************************/ |
|
154 |
|
155 // marker (1 bit) |
|
156 dataP[1] |= static_cast<TUint8>( aInitParam->TRTP.marker << 7 ); |
|
157 |
|
158 // payload type (7 bit) |
|
159 // confirm that payload can fit the 7 bit (0 - 127) |
|
160 if(aStreamParam->TRTP.payload > KPayloadTypeMax ) |
|
161 { |
|
162 return KErrTooBig; |
|
163 } |
|
164 |
|
165 |
|
166 dataP[1] |= aStreamParam->TRTP.payload; |
|
167 |
|
168 //set the pointer to point at the beginning of the sequence number. |
|
169 dataP += 2; |
|
170 // sequence number (16 bit) |
|
171 Write16( dataP, aStreamParam->TRTP.seqNum ); |
|
172 |
|
173 //set the pointer to point at the beginning of the time stamp. |
|
174 dataP += 2; |
|
175 // RTP timestamp (32 bit) |
|
176 Write32( dataP, aStreamParam->TRTP.timeStamp ); |
|
177 |
|
178 //set the pointer to point at the beginning of SSRC. |
|
179 dataP += 4; |
|
180 // SSRC (32 bit) |
|
181 Write32( dataP, aStreamParam->TRTP.SSRC ); |
|
182 |
|
183 //set the pointer to point to the first bit after SSRC |
|
184 dataP += 4; |
|
185 |
|
186 if ( aInitParam->TRTP.fHeaderExtension ) |
|
187 { |
|
188 |
|
189 //calculate 8 bit values to 32 bit words |
|
190 TInt16 length32 = |
|
191 static_cast<TInt16>( aInitParam->TRTP.extension.length / 4 ); |
|
192 |
|
193 //if length mod 4 != 0, |
|
194 if ( aInitParam->TRTP.extension.length % 4 ) |
|
195 { |
|
196 length32++; |
|
197 } |
|
198 |
|
199 // header extension type defined by profile |
|
200 // aInitParam->TRTP.extension.type is 32-bit and part of the API |
|
201 // (i.e. unchangeable), so we have to extract the 16-LSB |
|
202 Write16( dataP, aInitParam->TRTP.extension.type & 0xFFFF ); |
|
203 dataP += 2; |
|
204 |
|
205 // header extension length in number of 32-bit words |
|
206 Write16( dataP, length32 ); |
|
207 dataP += 2; |
|
208 |
|
209 // header extension data |
|
210 if (length32 && aInitParam->TRTP.extension.data ) |
|
211 { |
|
212 Mem::FillZ( dataP, length32 * 4 ); |
|
213 for ( TInt i = 0; i < aInitParam->TRTP.extension.length; i++ ) |
|
214 { |
|
215 dataP[i] = aInitParam->TRTP.extension.data[i]; |
|
216 } |
|
217 dataP += ( length32 * 4 ); |
|
218 } |
|
219 } |
|
220 |
|
221 //Copy(Target, Source, Length) |
|
222 Mem::Copy( dataP, aInitParam->TRTP.payloadData, |
|
223 aInitParam->TRTP.payloadDataLen ); |
|
224 iSize = aInitParam->TRTP.payloadDataLen + ( dataP - iData ); |
|
225 return KErrNone; |
|
226 |
|
227 } |
|
228 |
|
229 // --------------------------------------------------------------------------- |
|
230 // TInt CRtpPacket::RtpPacketBuildRtcp() |
|
231 // |
|
232 // --------------------------------------------------------------------------- |
|
233 // |
|
234 TInt CRtpPacket::RtpPacketBuildRtcp( TRtpPacketStreamParam* aStreamParam, |
|
235 TRtpPacketIOParam* aInitParam ) |
|
236 { |
|
237 Mem::FillZ( iDataPtr, 4 ); |
|
238 |
|
239 // version |
|
240 iDataPtr[0] |= ( KRtpVersion << 6 ); |
|
241 |
|
242 // padding = 0 |
|
243 iDataPtr[0] |= ( 0 << 5 ); |
|
244 |
|
245 // source count |
|
246 iDataPtr[0] |= static_cast<TUint8>( aInitParam->TRTCP_HEADER.sourceCount ); |
|
247 |
|
248 // packet type |
|
249 iDataPtr[1] = static_cast<TUint8>( aInitParam->TRTCP_HEADER.pt ); |
|
250 iDataPtr += 2; |
|
251 |
|
252 // length of RTCP packet |
|
253 // aInitParam->TRTCP_HEADER.length is 32-bit and part of the API |
|
254 // (i.e. unchangeable), so we have to extract the 16-LSB |
|
255 Write16( iDataPtr, aInitParam->TRTCP_HEADER.length & 0xFFFF ); |
|
256 iDataPtr += 2; |
|
257 |
|
258 // SSRC of sender in case of RR |
|
259 if ( aInitParam->TRTCP_HEADER.pt == ERTCP_RR ) |
|
260 { |
|
261 Write32( iDataPtr, aStreamParam->TRTCP_HEADER.SSRC ); |
|
262 iDataPtr += 4; |
|
263 } |
|
264 |
|
265 iSize += ( aInitParam->TRTCP_HEADER.length + 1 ) * 4; |
|
266 |
|
267 return KErrNone; |
|
268 } |
|
269 |
|
270 // --------------------------------------------------------------------------- |
|
271 // TInt CRtpPacket::RtpPacketBuildApp() |
|
272 // |
|
273 // --------------------------------------------------------------------------- |
|
274 // |
|
275 TInt CRtpPacket::RtpPacketBuildApp( TRtpPacketStreamParam* aStreamParam, |
|
276 TRtpPacketIOParam* aInitParam ) |
|
277 { |
|
278 // SSRC |
|
279 Write32( iDataPtr, aStreamParam->TRTCP_APP.SSRC ); |
|
280 iDataPtr += 4; |
|
281 |
|
282 // name |
|
283 Mem::Copy( iDataPtr, aInitParam->TRTCP_APP.name, 4 ); |
|
284 iDataPtr += 4; |
|
285 |
|
286 // application data |
|
287 Mem::Copy( iDataPtr, aInitParam->TRTCP_APP.appData, |
|
288 aInitParam->TRTCP_APP.appDataLen ); |
|
289 |
|
290 iDataPtr += aInitParam->TRTCP_APP.appDataLen; |
|
291 |
|
292 return KErrNone; |
|
293 } |
|
294 |
|
295 // --------------------------------------------------------------------------- |
|
296 // TInt CRtpPacket::RtpPacketBuildBye() |
|
297 // |
|
298 // --------------------------------------------------------------------------- |
|
299 // |
|
300 TInt CRtpPacket::RtpPacketBuildBye( TRtpPacketStreamParam* aStreamParam, |
|
301 TRtpPacketIOParam* aInitParam ) |
|
302 { |
|
303 TUint8 theIndex( 0 ); |
|
304 // SSRC |
|
305 Write32( iDataPtr, aStreamParam->TRTCP_BYE.SSRC ); |
|
306 iDataPtr += 4; |
|
307 |
|
308 // reason |
|
309 iDataPtr[0] = static_cast<TUint8>( aInitParam->TRTCP_BYE.reasonSize ); |
|
310 iDataPtr += 1; |
|
311 |
|
312 Mem::Copy( iDataPtr, aInitParam->TRTCP_BYE.reason, |
|
313 aInitParam->TRTCP_BYE.reasonSize ); |
|
314 |
|
315 iDataPtr += aInitParam->TRTCP_BYE.reasonSize; |
|
316 |
|
317 // padding |
|
318 if ( aInitParam->TRTCP_BYE.paddingSize != 0 ) |
|
319 { |
|
320 for ( theIndex = 0; theIndex < aInitParam->TRTCP_BYE.paddingSize; |
|
321 theIndex++ ) |
|
322 { |
|
323 iDataPtr[theIndex] = KNullTerm; |
|
324 } |
|
325 |
|
326 iDataPtr += aInitParam->TRTCP_BYE.paddingSize; |
|
327 } |
|
328 |
|
329 return KErrNone; |
|
330 } |
|
331 |
|
332 // --------------------------------------------------------------------------- |
|
333 // TInt CRtpPacket::RtpPacketBuildRr() |
|
334 // |
|
335 // --------------------------------------------------------------------------- |
|
336 // |
|
337 TInt CRtpPacket::RtpPacketBuildRr( TRtpPacketStreamParam* aStreamParam, |
|
338 TRtpPacketIOParam* aInitParam ) |
|
339 { |
|
340 // SSRC |
|
341 Write32( iDataPtr, aStreamParam->TRTCP_RR.SSRC ); |
|
342 iDataPtr += 4; |
|
343 |
|
344 // fraction lost |
|
345 iDataPtr[0] = aStreamParam->TRTCP_RR.fractionLost; |
|
346 iDataPtr++; |
|
347 |
|
348 // cumulative number of packets lost |
|
349 Write24( iDataPtr, aStreamParam->TRTCP_RR.cumNumPacketsLost ); |
|
350 iDataPtr += 3; |
|
351 |
|
352 // extended highest sequence number received |
|
353 Write32( iDataPtr, aStreamParam->TRTCP_RR.seqNumReceived ); |
|
354 iDataPtr += 4; |
|
355 |
|
356 // interarrival jitter |
|
357 Write32( iDataPtr, aStreamParam->TRTCP_RR.arrivalJitter ); |
|
358 iDataPtr += 4; |
|
359 |
|
360 // last SR timestamp |
|
361 Write32( iDataPtr, aInitParam->TRTCP_RR.lastSRTimeStamp ); |
|
362 iDataPtr += 4; |
|
363 |
|
364 // delay since last SR timestamp |
|
365 Write32( iDataPtr, aInitParam->TRTCP_RR.delaySinceLSR ); |
|
366 iDataPtr += 4; |
|
367 |
|
368 return KErrNone; |
|
369 } |
|
370 |
|
371 // --------------------------------------------------------------------------- |
|
372 // TInt CRtpPacket::RtpPacketBuildSr() |
|
373 // |
|
374 // --------------------------------------------------------------------------- |
|
375 // |
|
376 TInt CRtpPacket::RtpPacketBuildSr( TRtpPacketStreamParam* aStreamParam, |
|
377 TRtpPacketIOParam* aInitParam ) |
|
378 { |
|
379 // SSRC |
|
380 Write32( iDataPtr, aStreamParam->TRTCP_SR.SSRC ); |
|
381 iDataPtr += 4; |
|
382 |
|
383 // NTP timestamp (seconds) |
|
384 Write32( iDataPtr, aInitParam->TRTCP_SR.NTPTimeStampSec ); |
|
385 iDataPtr += 4; |
|
386 |
|
387 // NTP timestamp (fraction) |
|
388 Write32( iDataPtr, aInitParam->TRTCP_SR.NTPTimeStampFrac ); |
|
389 iDataPtr += 4; |
|
390 |
|
391 // RTP timestamp |
|
392 Write32( iDataPtr, aInitParam->TRTCP_SR.timeStamp ); |
|
393 iDataPtr += 4; |
|
394 |
|
395 // sender's packet count |
|
396 Write32( iDataPtr, aStreamParam->TRTCP_SR.numPacketsSent ); |
|
397 iDataPtr += 4; |
|
398 |
|
399 // sender's octet count |
|
400 Write32( iDataPtr, aStreamParam->TRTCP_SR.cumNumOctetsSent ); |
|
401 iDataPtr += 4; |
|
402 |
|
403 return KErrNone; |
|
404 } |
|
405 |
|
406 // --------------------------------------------------------------------------- |
|
407 // TInt CRtpPacket::RtpPacketBuildSdes() |
|
408 // |
|
409 // --------------------------------------------------------------------------- |
|
410 // |
|
411 TInt CRtpPacket::RtpPacketBuildSdes( TRtpPacketStreamParam* aStreamParam, |
|
412 TRtpPacketIOParam* aInitParam ) |
|
413 { |
|
414 TUint8 theIndex( 0 ); |
|
415 |
|
416 // SSRC |
|
417 Write32( iDataPtr, aStreamParam->TRTCP_SDES.SSRC ); |
|
418 iDataPtr += 4; |
|
419 |
|
420 // SDES items |
|
421 for ( theIndex = 0; theIndex < ERTCP_NUM_OF_SDES_ITEMS; theIndex++ ) |
|
422 { |
|
423 if ( aInitParam->TRTCP_SDES.sdesItemsSize[theIndex] != 0 ) |
|
424 { |
|
425 |
|
426 iDataPtr[0] = static_cast<TUint8>( theIndex + 1 ); |
|
427 iDataPtr[1] = static_cast<TUint8>( |
|
428 aInitParam->TRTCP_SDES.sdesItemsSize[theIndex] ); |
|
429 iDataPtr += 2; |
|
430 |
|
431 Mem::Copy( iDataPtr, |
|
432 aInitParam->TRTCP_SDES.sdesItems[theIndex], |
|
433 aInitParam->TRTCP_SDES.sdesItemsSize[theIndex] ); |
|
434 |
|
435 iDataPtr += aInitParam->TRTCP_SDES.sdesItemsSize[theIndex]; |
|
436 } |
|
437 } |
|
438 |
|
439 // include end of list null octet |
|
440 iDataPtr[0] = KNullTerm; |
|
441 iDataPtr++; |
|
442 |
|
443 // padding |
|
444 if ( aInitParam->TRTCP_SDES.paddingSize != 0 ) |
|
445 { |
|
446 for ( theIndex = 0; theIndex < aInitParam->TRTCP_SDES.paddingSize; |
|
447 theIndex++ ) |
|
448 { |
|
449 iDataPtr[theIndex] = KNullTerm; |
|
450 } |
|
451 |
|
452 iDataPtr += aInitParam->TRTCP_SDES.paddingSize; |
|
453 } |
|
454 |
|
455 return KErrNone; |
|
456 } |
|
457 |
|
458 // --------------------------------------------------------------------------- |
|
459 // TInt CRtpPacket::RtpPacketBuild() |
|
460 // |
|
461 // --------------------------------------------------------------------------- |
|
462 // |
|
463 TInt CRtpPacket::RtpPacketBuild( TRtpPacketStreamParam* aStreamParam, |
|
464 TRtpPacketIOParam* aInitParam ) |
|
465 { |
|
466 TInt result( KErrNone ); |
|
467 if ( !aStreamParam || !aInitParam ) |
|
468 { |
|
469 return KErrUnderflow; |
|
470 } |
|
471 |
|
472 // build the packet content |
|
473 switch ( iType ) |
|
474 { |
|
475 case ERTP: |
|
476 result = RtpPacketBuildRtp( aStreamParam, aInitParam ); |
|
477 break; |
|
478 |
|
479 case ERTCP_HEADER: |
|
480 result = RtpPacketBuildRtcp( aStreamParam, aInitParam ); |
|
481 break; |
|
482 |
|
483 case ERTCP_SR: |
|
484 result = RtpPacketBuildSr( aStreamParam, aInitParam ); |
|
485 break; |
|
486 |
|
487 case ERTCP_RR: |
|
488 result = RtpPacketBuildRr( aStreamParam, aInitParam ); |
|
489 break; |
|
490 |
|
491 case ERTCP_SDES: |
|
492 result = RtpPacketBuildSdes( aStreamParam, aInitParam ); |
|
493 break; |
|
494 |
|
495 case ERTCP_BYE: |
|
496 result = RtpPacketBuildBye( aStreamParam, aInitParam ); |
|
497 break; |
|
498 |
|
499 case ERTCP_APP: |
|
500 result = RtpPacketBuildApp( aStreamParam, aInitParam ); |
|
501 break; |
|
502 |
|
503 default: |
|
504 result = ERTCP_PACKET_ERROR; //unknown packet type |
|
505 break; |
|
506 } |
|
507 |
|
508 return result; |
|
509 } |
|
510 |
|
511 // --------------------------------------------------------------------------- |
|
512 // TRtpSSRC CRtpPacket::RtpPacketGetSSRC() |
|
513 // assumed to be called for an RTCP packet only after |
|
514 // RTCP_HEADER has determined the packet type |
|
515 // --------------------------------------------------------------------------- |
|
516 TRtpSSRC CRtpPacket::RtpPacketGetSSRC() |
|
517 { |
|
518 TUint8* dataP; |
|
519 |
|
520 // parse the packet content |
|
521 switch ( iType ) |
|
522 { |
|
523 case ERTP: |
|
524 { |
|
525 dataP = iData + 8; |
|
526 return ( Read32( dataP ) ); |
|
527 } |
|
528 |
|
529 case ERTCP_HEADER: |
|
530 { |
|
531 dataP = iData + 4; |
|
532 return ( Read32( dataP ) ); |
|
533 } |
|
534 |
|
535 case ERTCP_SR: |
|
536 case ERTCP_RR: |
|
537 case ERTCP_SDES: |
|
538 case ERTCP_BYE: |
|
539 case ERTCP_APP: |
|
540 { |
|
541 dataP = iDataPtr; |
|
542 return ( Read32( dataP ) ); |
|
543 } |
|
544 |
|
545 default: |
|
546 break; |
|
547 } |
|
548 |
|
549 return 0; |
|
550 } |
|
551 // ---------------------------------------------------------------------------- |
|
552 // CRtpPacket::RtpPacketGetPayloadType() |
|
553 // ---------------------------------------------------------------------------- |
|
554 // |
|
555 TRtpPayloadType CRtpPacket::RtpPacketGetPayloadType() |
|
556 { |
|
557 TUint8* dataP = iData; |
|
558 // payload type |
|
559 return static_cast<TUint8>( dataP[1] & 0x7F ); |
|
560 |
|
561 } |
|
562 |
|
563 // ---------------------------------------------------------------------------- |
|
564 // CRtpPacket::RtpPacketProcessRtp() |
|
565 // ---------------------------------------------------------------------------- |
|
566 // |
|
567 TRtpRtcpEnum CRtpPacket::RtpPacketProcessRtpL( |
|
568 TRtpPacketStreamParam* aStreamParam, |
|
569 TRtpPacketIOParam* aExtractParam ) |
|
570 { |
|
571 RTP_DEBUG_PACKET( "CRtpPacket::RtpPacketProcessRtpL Entry" ); |
|
572 TInt k; |
|
573 TInt err( KErrNone ); |
|
574 TUint8* dataP = iData; |
|
575 |
|
576 // version |
|
577 // 0xC0 = 1100 0000 |
|
578 // & 0xC0 removes all ones except the version number from the bit stream |
|
579 // |
|
580 // 11011011 |
|
581 // 11000000 |
|
582 // -------- |
|
583 // 11000000 >> 6 = 00000011 |
|
584 if ( ( ( dataP[0] & 0xC0 ) >> 6 ) != KRtpVersion ) |
|
585 { |
|
586 RTP_DEBUG_DETAIL( "RtpPacketProcess: invalid version" ); |
|
587 |
|
588 return ERTCP_PACKET_ERROR; |
|
589 } |
|
590 |
|
591 // padding |
|
592 // 0x20 = 0010 0000 |
|
593 // |
|
594 // Checks if padding bit is set |
|
595 if ( dataP[0] & 0x20 ) |
|
596 { |
|
597 |
|
598 // The last octet of the packet must contain a valid octet count |
|
599 // ( octet count < the total packet lenght minus the header size) |
|
600 if ( ( iSize - iData[ iSize - 1] - KMinRtpHeaderSize ) > 0 ) |
|
601 { |
|
602 aExtractParam->TRTP.padding = 1; |
|
603 |
|
604 // The last octet of the padding contains a count of how many |
|
605 // padding octets should be ignored, including itself. |
|
606 iSize -= iData[iSize - 1]; |
|
607 } |
|
608 else |
|
609 { |
|
610 // Invalid padding value |
|
611 RTP_DEBUG_DETAIL( "RtpPacketProcess: invalid padding size" ); |
|
612 |
|
613 return ERTCP_PACKET_ERROR; |
|
614 } |
|
615 } |
|
616 else //padding bit == 0 |
|
617 { |
|
618 aExtractParam->TRTP.padding = 0; |
|
619 } |
|
620 |
|
621 // header extension |
|
622 aExtractParam->TRTP.fHeaderExtension = |
|
623 static_cast<TUint8>( ( dataP[0] & 0x10 ) >> 4 ); |
|
624 |
|
625 // CC |
|
626 aExtractParam->TRTP.numCSRC = static_cast<TUint8>( dataP[0] & 0x0F ); |
|
627 |
|
628 // marker |
|
629 aExtractParam->TRTP.marker = |
|
630 static_cast<TUint8>( ( dataP[1] & 0x80 ) >> 7 ); |
|
631 |
|
632 // payload type |
|
633 aStreamParam->TRTP.payload = static_cast<TUint8>( dataP[1] & 0x7F ); |
|
634 |
|
635 |
|
636 /** |
|
637 * The payload type must be known, and in particular it must not |
|
638 * be equal to SR or RR[RFC3550] |
|
639 * |
|
640 * 7 bit (= 127) is only reserved for payload, so no need to check |
|
641 * that payload differ from SR (SR = 200) and RR (RR = 201) |
|
642 * Since it always &0x7F so there is no possiblility to be more than |
|
643 * 127 |
|
644 **/ |
|
645 |
|
646 dataP += 2; |
|
647 |
|
648 // sequence number |
|
649 aStreamParam->TRTP.seqNum = static_cast<TUint16>( Read16( dataP ) ); |
|
650 dataP += 2; |
|
651 |
|
652 // RTP timestamp |
|
653 aStreamParam->TRTP.timeStamp = Read32( dataP ); |
|
654 dataP += 4; |
|
655 |
|
656 // SSRC |
|
657 aStreamParam->TRTP.SSRC = Read32( dataP ); |
|
658 dataP += 4; |
|
659 |
|
660 // CSRCs |
|
661 if ( aExtractParam->TRTP.numCSRC >0 ) |
|
662 { |
|
663 // Calculate the minimum required size of the remainder of this |
|
664 // packet, in number of 8-bit words |
|
665 TInt minRequiredSizeLeft = aExtractParam->TRTP.numCSRC * 4; |
|
666 |
|
667 // Make sure there is are CSRCs to read |
|
668 if ( ( iSize - ( dataP - iData ) ) < minRequiredSizeLeft ) |
|
669 { |
|
670 RTP_DEBUG_DETAIL( "RtpPacketProcess: invalid CSRC size" ); |
|
671 |
|
672 return ERTCP_PACKET_ERROR; |
|
673 } |
|
674 |
|
675 // Originally Allocate memory for all CSRC:s |
|
676 //it will have memeory resouce problem so only allocate when |
|
677 // CSRC<2 |
|
678 if ( aExtractParam->TRTP.numCSRC < KCSRCListMax ) |
|
679 { |
|
680 if ( !aExtractParam->TRTP.CSRCarray ) |
|
681 { |
|
682 TRAP( err, |
|
683 aExtractParam->TRTP.CSRCarray = |
|
684 static_cast<TUint32*>( |
|
685 User::AllocL( sizeof(TUint32) * aExtractParam->TRTP.numCSRC ) ) |
|
686 ); |
|
687 |
|
688 if (err==0) |
|
689 { |
|
690 iCsrcAlloc = ETrue; |
|
691 } |
|
692 } |
|
693 if ( err || !aExtractParam->TRTP.CSRCarray ) |
|
694 { |
|
695 RTP_DEBUG_DETAIL( "RtpPacketProcess: CSRC missing" ); |
|
696 |
|
697 return ERTCP_PACKET_ERROR; |
|
698 } |
|
699 int count=0; |
|
700 for ( k = 0; k < aExtractParam->TRTP.numCSRC; k++ ) |
|
701 { |
|
702 // CSRCs ignored |
|
703 TUint32 temp =Read32( dataP ); |
|
704 if (!temp) |
|
705 { |
|
706 return ERTCP_PACKET_ERROR; |
|
707 } |
|
708 aExtractParam->TRTP.CSRCarray[k] = Read32( dataP ); |
|
709 dataP += 4; |
|
710 count ++; |
|
711 } |
|
712 if (count!= aExtractParam->TRTP.numCSRC) |
|
713 { |
|
714 RTP_DEBUG_DETAIL( "RtpPacketProcess: numCSRC is not matched" ); |
|
715 return ERTCP_PACKET_ERROR; |
|
716 } |
|
717 } |
|
718 else |
|
719 { |
|
720 for ( k = 0; k < aExtractParam->TRTP.numCSRC; k++ ) |
|
721 { |
|
722 // CSRCs ignored |
|
723 dataP += 4; |
|
724 } |
|
725 } |
|
726 } |
|
727 if ( aExtractParam->TRTP.fHeaderExtension ) |
|
728 { |
|
729 // Make sure there is a header extension to read |
|
730 if ( ( iSize - ( dataP - iData ) ) < 4 ) |
|
731 { |
|
732 RTP_DEBUG_DETAIL( "RtpPacketProcess: invalid extension size" ); |
|
733 return ERTCP_PACKET_ERROR; |
|
734 } |
|
735 |
|
736 // header extension type defined by profile |
|
737 aExtractParam->TRTP.extension.type = Read16( dataP ); |
|
738 dataP += 2; |
|
739 |
|
740 // header extension length in number of 32-bit words |
|
741 aExtractParam->TRTP.extension.length = Read16( dataP ); |
|
742 dataP += 2; |
|
743 |
|
744 // Calculate the extension length in number of 8-bit words |
|
745 TInt extensionLen8 = aExtractParam->TRTP.extension.length * 4; |
|
746 |
|
747 // Make sure the extension length is valid |
|
748 if ( ( iSize - ( dataP - iData ) ) < extensionLen8 ) |
|
749 { |
|
750 RTP_DEBUG_DETAIL( "RtpPacketProcess: invalid extension length" ); |
|
751 |
|
752 return ERTCP_PACKET_ERROR; |
|
753 } |
|
754 |
|
755 if ( !aExtractParam->TRTP.extension.data ) |
|
756 { |
|
757 TRAP( err, |
|
758 aExtractParam->TRTP.extension.data = static_cast<TUint8*>( |
|
759 User::AllocL( aExtractParam->TRTP.extension.length * 4 ) ) |
|
760 ); |
|
761 if(err==KErrNone) |
|
762 { |
|
763 iExdataAlloc= ETrue; |
|
764 } |
|
765 } |
|
766 if ( err || !aExtractParam->TRTP.extension.data ) |
|
767 { |
|
768 RTP_DEBUG_DETAIL( "RtpPacketProcess: extension missing" ); |
|
769 |
|
770 return ERTCP_PACKET_ERROR; |
|
771 } |
|
772 |
|
773 // header extension data |
|
774 for ( k = 0; k < aExtractParam->TRTP.extension.length*4; k++ ) |
|
775 { |
|
776 aExtractParam->TRTP.extension.data[k] = dataP[k]; |
|
777 } |
|
778 dataP += ( aExtractParam->TRTP.extension.length * 4 ); |
|
779 } |
|
780 |
|
781 // Make sure there is a payload |
|
782 if ( ( iSize - ( dataP - iData ) ) > 0 ) |
|
783 { |
|
784 aExtractParam->TRTP.payloadDataLen = iSize - ( dataP - iData ); |
|
785 aExtractParam->TRTP.payloadData = static_cast<TText8*>( dataP ); |
|
786 } |
|
787 else |
|
788 { |
|
789 aExtractParam->TRTP.payloadDataLen = 0; |
|
790 aExtractParam->TRTP.payloadData = NULL; |
|
791 |
|
792 RTP_DEBUG_DETAIL( "RtpPacketProcess: packet length is 0" ); |
|
793 } |
|
794 RTP_DEBUG_PACKET( "CRtpPacket::RtpPacketProcessRtpL Exit" ); |
|
795 return ERTCP_NO_ERROR; |
|
796 } |
|
797 |
|
798 // ---------------------------------------------------------------------------- |
|
799 // CRtpPacket::RtpPacketProcessRtcp() |
|
800 // ---------------------------------------------------------------------------- |
|
801 // |
|
802 TRtpRtcpEnum CRtpPacket::RtpPacketProcessRtcp( |
|
803 TRtpPacketStreamParam* aStreamParam, |
|
804 TRtpPacketIOParam* aExtractParam ) |
|
805 { |
|
806 // version |
|
807 if ( ( ( iDataPtr[0] & 0xC0 ) >> 6 ) != KRtpVersion ) |
|
808 { |
|
809 RTP_DEBUG_DETAIL( "ERROR: Wrong Rtp version in header" ); |
|
810 return ERTCP_PACKET_ERROR; |
|
811 } |
|
812 |
|
813 // padding |
|
814 if ( iDataPtr[0] & 0x20 ) |
|
815 { |
|
816 iSize -= iData[iSize - 1]; |
|
817 } |
|
818 |
|
819 // determine RTCP packet type |
|
820 aExtractParam->TRTCP_HEADER.pt = |
|
821 static_cast<TRtpPacketType>( iDataPtr[1] ); |
|
822 |
|
823 if ( ( aExtractParam->TRTCP_HEADER.pt != ERTCP_SR ) && |
|
824 ( aExtractParam->TRTCP_HEADER.pt != ERTCP_RR ) && |
|
825 ( aExtractParam->TRTCP_HEADER.pt != ERTCP_SDES ) && |
|
826 ( aExtractParam->TRTCP_HEADER.pt != ERTCP_BYE ) && |
|
827 ( aExtractParam->TRTCP_HEADER.pt != ERTCP_APP ) ) |
|
828 { |
|
829 |
|
830 RTP_DEBUG_DETAIL( "ERROR: Incorrect packet type in header" ); |
|
831 |
|
832 return ERTCP_PACKET_ERROR; |
|
833 } |
|
834 |
|
835 // source/report Count |
|
836 aExtractParam->TRTCP_HEADER.sourceCount = ( iDataPtr[0] & 0x1F ); |
|
837 |
|
838 iDataPtr += 2; |
|
839 |
|
840 aExtractParam->TRTCP_HEADER.length = |
|
841 static_cast<TInt>( Read16( iDataPtr ) ); |
|
842 |
|
843 if ( aExtractParam->TRTCP_HEADER.length * 4 > iSize ) |
|
844 { |
|
845 RTP_DEBUG_DETAIL( "ERROR: Incorrect packet size in header" ); |
|
846 return ERTCP_PACKET_ERROR; |
|
847 } |
|
848 iDataPtr += 2; |
|
849 |
|
850 // SSRC of sender in case of RR |
|
851 if ( aExtractParam->TRTCP_HEADER.pt == ERTCP_RR ) |
|
852 { |
|
853 aStreamParam->TRTCP_HEADER.SSRC = Read32( iDataPtr ); |
|
854 iDataPtr += 4; |
|
855 } |
|
856 |
|
857 return ERTCP_NO_ERROR; |
|
858 } |
|
859 |
|
860 // ---------------------------------------------------------------------------- |
|
861 // CRtpPacket::RtpPacketProcessApp() |
|
862 // ---------------------------------------------------------------------------- |
|
863 // |
|
864 TRtpRtcpEnum CRtpPacket::RtpPacketProcessAppL( |
|
865 TRtpPacketStreamParam* aStreamParam, |
|
866 TRtpPacketIOParam* aExtractParam ) |
|
867 { |
|
868 TInt err( KErrNone ); |
|
869 |
|
870 // TRTCP_APP.totalPacketLen is the 32-bit packet length MINUS ONE. |
|
871 TUint totalLen( aStreamParam->TRTCP_APP.totalPacketLen ); |
|
872 |
|
873 // Calculate the length of the data in the packet in number of 8-bit words |
|
874 TUint appDataLen8 = ( totalLen + 1 - KMinRtcpAppLen ) * 4; |
|
875 |
|
876 // The packet is faulty if the total length of the packet is results in a |
|
877 // negative memory allocation . Also, it cannot be too big due to framework |
|
878 // restrictions on memory allocation. |
|
879 if ( ( totalLen + 1 < KMinRtcpAppLen ) || |
|
880 ( sizeof( TUint8 ) * appDataLen8 > ( KMaxTInt / 2 ) ) ) |
|
881 { |
|
882 return ERTCP_PACKET_ERROR; |
|
883 } |
|
884 |
|
885 // SSRC |
|
886 aStreamParam->TRTCP_APP.SSRC = Read32( iDataPtr ); |
|
887 iDataPtr += 4; |
|
888 |
|
889 // name |
|
890 Mem::Copy( aExtractParam->TRTCP_APP.name, iDataPtr, 4 ); |
|
891 |
|
892 iDataPtr += 4; |
|
893 |
|
894 // Allocate memory for application data |
|
895 TRAP ( err, |
|
896 aExtractParam->TRTCP_APP.appData = |
|
897 static_cast<TUint8*> |
|
898 ( |
|
899 User::AllocL( sizeof( TUint8 ) * appDataLen8 ) ) |
|
900 ); |
|
901 |
|
902 if ( err ) |
|
903 { |
|
904 return ERTCP_PACKET_ERROR; |
|
905 } |
|
906 |
|
907 Mem::Copy( aExtractParam->TRTCP_APP.appData, iDataPtr, appDataLen8 ); |
|
908 iDataPtr += appDataLen8; |
|
909 aExtractParam->TRTCP_APP.appDataLen = appDataLen8; |
|
910 |
|
911 return ERTCP_NO_ERROR; |
|
912 } |
|
913 |
|
914 // ---------------------------------------------------------------------------- |
|
915 // CRtpPacket::RtpPacketProcessBye() |
|
916 // ---------------------------------------------------------------------------- |
|
917 // |
|
918 TRtpRtcpEnum CRtpPacket::RtpPacketProcessByeL( |
|
919 TRtpPacketStreamParam* aStreamParam, |
|
920 TRtpPacketIOParam* aExtractParam ) |
|
921 { |
|
922 TInt err; |
|
923 TUint8 theIndex( 0 ); |
|
924 |
|
925 // SSRC |
|
926 aStreamParam->TRTCP_BYE.SSRC = Read32( iDataPtr ); |
|
927 iDataPtr += 4; |
|
928 |
|
929 // reason |
|
930 aExtractParam->TRTCP_BYE.reasonSize = iDataPtr[0]; |
|
931 |
|
932 iDataPtr += 1; |
|
933 |
|
934 TRAP ( err, aExtractParam->TRTCP_BYE.reason = static_cast<TText8*>( |
|
935 User::AllocL( sizeof( TText8 ) * |
|
936 ( aExtractParam->TRTCP_BYE.reasonSize + 1 /* trailing NULL */) ) ) |
|
937 ); |
|
938 |
|
939 if ( err ) |
|
940 { |
|
941 return ERTCP_PACKET_ERROR; |
|
942 } |
|
943 |
|
944 Mem::Copy( aExtractParam->TRTCP_BYE.reason, iDataPtr, |
|
945 aExtractParam->TRTCP_BYE.reasonSize ); |
|
946 |
|
947 *( aExtractParam->TRTCP_BYE.reason + aExtractParam->TRTCP_BYE.reasonSize ) |
|
948 = KNullTerm; |
|
949 |
|
950 iDataPtr += aExtractParam->TRTCP_BYE.reasonSize; |
|
951 |
|
952 // calculate size of padding |
|
953 if ( ( 1 + aExtractParam->TRTCP_BYE.reasonSize ) % 4 != 0 ) |
|
954 { |
|
955 aExtractParam->TRTCP_BYE.paddingSize = |
|
956 4 - ( 1 + aExtractParam->TRTCP_BYE.reasonSize ) % 4; |
|
957 } |
|
958 else |
|
959 { |
|
960 aExtractParam->TRTCP_BYE.paddingSize = 0; |
|
961 } |
|
962 |
|
963 for ( theIndex = 0; theIndex < aExtractParam->TRTCP_BYE.paddingSize; |
|
964 theIndex++ ) |
|
965 { |
|
966 iDataPtr++; |
|
967 } |
|
968 return ERTCP_NO_ERROR; |
|
969 } |
|
970 |
|
971 // ---------------------------------------------------------------------------- |
|
972 // CRtpPacket::RtpPacketProcessRr() |
|
973 // ---------------------------------------------------------------------------- |
|
974 // |
|
975 TRtpRtcpEnum CRtpPacket::RtpPacketProcessRr( |
|
976 TRtpPacketStreamParam* aStreamParam, |
|
977 TRtpPacketIOParam* aExtractParam ) |
|
978 { |
|
979 // SSRC |
|
980 aStreamParam->TRTCP_RR.SSRC = Read32( iDataPtr ); |
|
981 iDataPtr += 4; |
|
982 |
|
983 // fraction lost |
|
984 aStreamParam->TRTCP_RR.fractionLost = iDataPtr[0]; |
|
985 iDataPtr++; |
|
986 |
|
987 // cumulative number of packets lost |
|
988 aStreamParam->TRTCP_RR.cumNumPacketsLost = Read24( iDataPtr ); |
|
989 iDataPtr += 3; |
|
990 |
|
991 // extended highest sequence number received |
|
992 aStreamParam->TRTCP_RR.seqNumReceived = Read32( iDataPtr ); |
|
993 iDataPtr += 4; |
|
994 |
|
995 // interarrival jitter |
|
996 aStreamParam->TRTCP_RR.arrivalJitter = Read32( iDataPtr ); |
|
997 iDataPtr += 4; |
|
998 |
|
999 // last SR timestamp |
|
1000 aExtractParam->TRTCP_RR.lastSRTimeStamp = Read32( iDataPtr ); |
|
1001 iDataPtr += 4; |
|
1002 |
|
1003 // delay since last SR timestamp |
|
1004 aExtractParam->TRTCP_RR.delaySinceLSR = Read32( iDataPtr ); |
|
1005 iDataPtr += 4; |
|
1006 |
|
1007 return ERTCP_NO_ERROR; |
|
1008 } |
|
1009 |
|
1010 // ---------------------------------------------------------------------------- |
|
1011 // CRtpPacket::RtpPacketProcessSr() |
|
1012 // ---------------------------------------------------------------------------- |
|
1013 // |
|
1014 TRtpRtcpEnum CRtpPacket::RtpPacketProcessSr( |
|
1015 TRtpPacketStreamParam* aStreamParam, |
|
1016 TRtpPacketIOParam* aExtractParam ) |
|
1017 { |
|
1018 // SSRC |
|
1019 aStreamParam->TRTCP_SR.SSRC = Read32( iDataPtr ); |
|
1020 iDataPtr += 4; |
|
1021 |
|
1022 // NTP timestamp (seconds) |
|
1023 aExtractParam->TRTCP_SR.NTPTimeStampSec = Read32( iDataPtr ); |
|
1024 iDataPtr += 4; |
|
1025 |
|
1026 // NTP timestamp (fraction) |
|
1027 aExtractParam->TRTCP_SR.NTPTimeStampFrac = Read32( iDataPtr ); |
|
1028 iDataPtr += 4; |
|
1029 |
|
1030 // RTP timestamp |
|
1031 aExtractParam->TRTCP_SR.timeStamp = Read32( iDataPtr ); |
|
1032 iDataPtr += 4; |
|
1033 |
|
1034 // sender's packet count |
|
1035 aStreamParam->TRTCP_SR.numPacketsSent = Read32( iDataPtr ); |
|
1036 iDataPtr += 4; |
|
1037 |
|
1038 // sender's octet count |
|
1039 aStreamParam->TRTCP_SR.cumNumOctetsSent = Read32( iDataPtr ); |
|
1040 iDataPtr += 4; |
|
1041 |
|
1042 return ERTCP_NO_ERROR; |
|
1043 } |
|
1044 |
|
1045 // ---------------------------------------------------------------------------- |
|
1046 // CRtpPacket::RtpPacketProcessSdes() |
|
1047 // ---------------------------------------------------------------------------- |
|
1048 // |
|
1049 TRtpRtcpEnum CRtpPacket::RtpPacketProcessSdesL( |
|
1050 TRtpPacketStreamParam* aStreamParam, |
|
1051 TRtpPacketIOParam* aExtractParam ) |
|
1052 { |
|
1053 TUint8 theIndex( 0 ); |
|
1054 TUint8 tempValue( 0 ); |
|
1055 TInt err( KErrNone ); |
|
1056 TUint8 sdesItems = 0; |
|
1057 TUint32 totalSDESSize( 0 ); |
|
1058 |
|
1059 // SSRC |
|
1060 aStreamParam->TRTCP_SDES.SSRC = Read32( iDataPtr ); |
|
1061 iDataPtr += 4; |
|
1062 |
|
1063 for ( theIndex = 0; theIndex < ERTCP_NUM_OF_SDES_ITEMS; theIndex++ ) |
|
1064 { |
|
1065 aExtractParam->TRTCP_SDES.sdesItemsSize[theIndex] = 0; |
|
1066 } |
|
1067 |
|
1068 // Read each SDES items |
|
1069 for ( theIndex = 0; theIndex < ERTCP_NUM_OF_SDES_ITEMS; theIndex++ ) |
|
1070 { |
|
1071 if ( iDataPtr[0] != KNullTerm ) |
|
1072 { |
|
1073 tempValue = iDataPtr[0]; |
|
1074 |
|
1075 if ( tempValue != ( theIndex + 1 ) ) |
|
1076 { |
|
1077 aExtractParam->TRTCP_SDES.sdesItemsSize[theIndex] = 0; |
|
1078 TRAP( err, aExtractParam->TRTCP_SDES.sdesItems[theIndex] = |
|
1079 static_cast<TUint8*>( User::AllocL( sizeof( TUint8 ) ) ) ); |
|
1080 if ( err ) |
|
1081 { |
|
1082 return ERTCP_PACKET_ERROR; |
|
1083 } |
|
1084 |
|
1085 *( aExtractParam->TRTCP_SDES.sdesItems[theIndex] ) = KNullTerm; |
|
1086 } |
|
1087 else |
|
1088 { |
|
1089 aExtractParam->TRTCP_SDES.sdesItemsSize[theIndex] = iDataPtr[1]; |
|
1090 |
|
1091 // keep track of number of SDES items |
|
1092 sdesItems++; |
|
1093 totalSDESSize += |
|
1094 aExtractParam->TRTCP_SDES.sdesItemsSize[theIndex]; |
|
1095 |
|
1096 iDataPtr += 2; |
|
1097 |
|
1098 TRAP( err, aExtractParam->TRTCP_SDES.sdesItems[theIndex] = |
|
1099 static_cast<TUint8*>( |
|
1100 User::AllocL( sizeof( TUint8 ) * ( |
|
1101 aExtractParam->TRTCP_SDES.sdesItemsSize[theIndex] + 1 ) |
|
1102 ) ) ); |
|
1103 |
|
1104 if ( err ) |
|
1105 { |
|
1106 return ERTCP_PACKET_ERROR; |
|
1107 } |
|
1108 |
|
1109 Mem::Copy( aExtractParam->TRTCP_SDES.sdesItems[theIndex], |
|
1110 iDataPtr, |
|
1111 aExtractParam->TRTCP_SDES.sdesItemsSize[theIndex] ); |
|
1112 |
|
1113 *( aExtractParam->TRTCP_SDES.sdesItems[theIndex] + |
|
1114 aExtractParam->TRTCP_SDES.sdesItemsSize[theIndex] ) = KNullTerm; |
|
1115 |
|
1116 iDataPtr += aExtractParam->TRTCP_SDES.sdesItemsSize[theIndex]; |
|
1117 } |
|
1118 } |
|
1119 } |
|
1120 |
|
1121 |
|
1122 iDataPtr++; // take into account end null octet |
|
1123 |
|
1124 for ( theIndex = tempValue; theIndex < ERTCP_NUM_OF_SDES_ITEMS; theIndex++ ) |
|
1125 { |
|
1126 |
|
1127 TRAP( err, aExtractParam->TRTCP_SDES.sdesItems[theIndex] = |
|
1128 static_cast<TUint8*>( User::AllocL( sizeof( TUint8 ) ) ) |
|
1129 ); |
|
1130 |
|
1131 if ( err ) |
|
1132 { |
|
1133 return ERTCP_PACKET_ERROR; |
|
1134 } |
|
1135 |
|
1136 *( aExtractParam->TRTCP_SDES.sdesItems[theIndex] ) = KNullTerm; |
|
1137 } |
|
1138 |
|
1139 // calculate size of padding |
|
1140 if ( ( sdesItems * 2 + totalSDESSize + 1 ) % 4 != 0 ) |
|
1141 { |
|
1142 aExtractParam->TRTCP_SDES.paddingSize = |
|
1143 4 - ( sdesItems * 2 + totalSDESSize + 1 ) % 4; |
|
1144 } |
|
1145 else |
|
1146 { |
|
1147 aExtractParam->TRTCP_SDES.paddingSize = 0; |
|
1148 } |
|
1149 |
|
1150 for ( theIndex = 0; theIndex < aExtractParam->TRTCP_SDES.paddingSize; |
|
1151 theIndex++ ) |
|
1152 { |
|
1153 iDataPtr++; |
|
1154 } |
|
1155 return ERTCP_NO_ERROR; |
|
1156 } |
|
1157 |
|
1158 // --------------------------------------------------------------------------- |
|
1159 // Return Value: |
|
1160 // 0 : if RTP packet has been processed OK or |
|
1161 // if RTCP packet has been processed OK and there are no more RTCP |
|
1162 // packets in this compound packet to be processed |
|
1163 // 1 : if RTCP packet has been processed OK and there is still RTCP |
|
1164 // packets in this compound packet to be processed |
|
1165 // -1 : if packet is invalid or some other error has occured |
|
1166 // --------------------------------------------------------------------------- |
|
1167 TRtpRtcpEnum CRtpPacket::RtpPacketProcessL( TRtpPacketStreamParam* aStreamParam, |
|
1168 TRtpPacketIOParam* aExtractParam ) |
|
1169 { |
|
1170 TRtpRtcpEnum result( ERTCP_NO_ERROR ); |
|
1171 |
|
1172 // parse the packet content |
|
1173 switch ( iType ) |
|
1174 { |
|
1175 case ERTP: |
|
1176 result = RtpPacketProcessRtpL( aStreamParam, aExtractParam ); |
|
1177 return result; |
|
1178 // no break necessary |
|
1179 |
|
1180 case ERTCP_HEADER: |
|
1181 result = RtpPacketProcessRtcp( aStreamParam, aExtractParam ); |
|
1182 break; |
|
1183 |
|
1184 case ERTCP_SR: |
|
1185 result = RtpPacketProcessSr( aStreamParam, aExtractParam ); |
|
1186 break; |
|
1187 |
|
1188 case ERTCP_RR: |
|
1189 result = RtpPacketProcessRr( aStreamParam, aExtractParam ); |
|
1190 break; |
|
1191 |
|
1192 case ERTCP_SDES: |
|
1193 result = RtpPacketProcessSdesL( aStreamParam, aExtractParam ); |
|
1194 break; |
|
1195 |
|
1196 case ERTCP_BYE: |
|
1197 result = RtpPacketProcessByeL( aStreamParam, aExtractParam ); |
|
1198 break; |
|
1199 |
|
1200 case ERTCP_APP: |
|
1201 result = RtpPacketProcessAppL( aStreamParam, aExtractParam ); |
|
1202 break; |
|
1203 |
|
1204 default: |
|
1205 // unknown packet type, return error |
|
1206 result = ERTCP_PACKET_ERROR; |
|
1207 break; |
|
1208 } |
|
1209 |
|
1210 // Only RTCP packets get this far |
|
1211 if ( result != ERTCP_NO_ERROR ) |
|
1212 { |
|
1213 return result; |
|
1214 } |
|
1215 |
|
1216 // check if RTCP compound is ready |
|
1217 if ( iDataPtr == ( iData + iSize ) ) |
|
1218 { |
|
1219 iDataPtr = iData; |
|
1220 return ERTCP_NO_ERROR; |
|
1221 } |
|
1222 else if ( iDataPtr < ( iData + iSize ) ) |
|
1223 { |
|
1224 return ERTCP_PACKET_MORE; |
|
1225 } |
|
1226 else |
|
1227 { |
|
1228 return ERTCP_PACKET_ERROR; |
|
1229 } |
|
1230 } |
|
1231 |
|
1232 // --------------------------------------------------------------------------- |
|
1233 // CRtpPacket::Write16() |
|
1234 // Write a 16-bit value as 2 consecutive bytes in MSB order |
|
1235 // Memory (at least 2 bytes) must have been allocated to pointer |
|
1236 // before the function is called. |
|
1237 // --------------------------------------------------------------------------- |
|
1238 void CRtpPacket::Write16( TUint8* const aPointer, TUint16 aValue ) |
|
1239 { |
|
1240 // check value range (16 bits) |
|
1241 aPointer[0] = static_cast<TUint8>( ( aValue & 0xFF00 ) >> 8 ); |
|
1242 aPointer[1] = static_cast<TUint8>( aValue & 0x00FF ); |
|
1243 } |
|
1244 |
|
1245 // --------------------------------------------------------------------------- |
|
1246 // TUint16 CRtpPacket::Read16() |
|
1247 // Read a 16-bit value given as 2 consecutive bytes in MSB order |
|
1248 // Memory (at least 2 bytes) must have been allocated to pointer |
|
1249 // before the function is called. |
|
1250 // --------------------------------------------------------------------------- |
|
1251 TUint16 CRtpPacket::Read16( const TUint8* const aPointer ) |
|
1252 { |
|
1253 return static_cast<TUint16>( aPointer[1] + ( aPointer[0] << 8 ) ); |
|
1254 } |
|
1255 |
|
1256 // --------------------------------------------------------------------------- |
|
1257 // CRtpPacket::Write32() |
|
1258 // Write a 32-bit aValue as 4 consecutive bytes in MSB order |
|
1259 // Memory (at least 4 bytes) must have been allocated to aPointer |
|
1260 // before the function is called. |
|
1261 // --------------------------------------------------------------------------- |
|
1262 void CRtpPacket::Write32( TUint8* const aPointer, TUint32 aValue ) |
|
1263 { |
|
1264 aPointer[0] = static_cast<TUint8>( ( aValue & 0xFF000000 ) >> 24 ); |
|
1265 aPointer[1] = static_cast<TUint8>( ( aValue & 0x00FF0000 ) >> 16 ); |
|
1266 aPointer[2] = static_cast<TUint8>( ( aValue & 0x0000FF00 ) >> 8 ); |
|
1267 aPointer[3] = static_cast<TUint8>( aValue & 0x000000FF ); |
|
1268 } |
|
1269 |
|
1270 // --------------------------------------------------------------------------- |
|
1271 // TUint32 CRtpPacket::Read32() |
|
1272 // Read a 32-bit aValue given as 4 consecutive bytes in MSB order |
|
1273 // Memory (at least 4 bytes) must have been allocated to aPointer |
|
1274 // before the function is called. |
|
1275 // --------------------------------------------------------------------------- |
|
1276 TUint32 CRtpPacket::Read32( const TUint8* const aPointer ) |
|
1277 { |
|
1278 return ( aPointer[3] + |
|
1279 ( static_cast<TUint32>( aPointer[2] ) << 8 ) + |
|
1280 ( static_cast<TUint32>( aPointer[1] ) << 16 ) + |
|
1281 ( static_cast<TUint32>( aPointer[0] ) << 24 ) ); |
|
1282 } |
|
1283 |
|
1284 // --------------------------------------------------------------------------- |
|
1285 // CRtpPacket::Write24() |
|
1286 // |
|
1287 // --------------------------------------------------------------------------- |
|
1288 // |
|
1289 void CRtpPacket::Write24( TUint8* const aPointer, TUint32 aValue ) |
|
1290 { |
|
1291 aPointer[0] = static_cast<TUint8>( ( aValue & 0xFF0000 ) >> 16 ); |
|
1292 aPointer[1] = static_cast<TUint8>( ( aValue & 0x00FF00 ) >> 8 ); |
|
1293 aPointer[2] = static_cast<TUint8>( aValue & 0x0000FF ); |
|
1294 } |
|
1295 |
|
1296 // --------------------------------------------------------------------------- |
|
1297 // TUint32 CRtpPacket::Read24() |
|
1298 // |
|
1299 // --------------------------------------------------------------------------- |
|
1300 // |
|
1301 TUint32 CRtpPacket::Read24( const TUint8 *const aPointer ) |
|
1302 { |
|
1303 return ( aPointer[2] + ( static_cast<TUint32>( aPointer[1] ) << 8 ) + |
|
1304 ( static_cast<TUint32>( aPointer[0] ) << 16 ) ); |
|
1305 } |
|
1306 |
|
1307 |
|
1308 // End of File |