• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /* ------------------------------------------------------------------
2  * Copyright (C) 1998-2009 PacketVideo
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
13  * express or implied.
14  * See the License for the specific language governing permissions
15  * and limitations under the License.
16  * -------------------------------------------------------------------
17  */
18 #include "h264_media_info_parser.h"
19 #include "oscl_string_utils.h"
20 #include "oscl_string_containers.h"
21 #include "sdp_parsing_utils.h"
22 
23 #define MIN_ENCODED_BYTES 4
24 #define AVC_NALTYPE_MASK 0x1F
25 #define AVC_NALTYPE_SPS 7
26 #define AVC_NALTYPE_PPS 8
27 
28 SDP_ERROR_CODE
parseMediaInfo(const char * buff,const int index,SDPInfo * sdp,payloadVector payload_vec,bool isSipSdp,int alt_id,bool alt_def_id)29 SDPH264MediaInfoParser::parseMediaInfo(const char *buff,
30                                        const int index,
31                                        SDPInfo *sdp,
32                                        payloadVector payload_vec,
33                                        bool isSipSdp,
34                                        int alt_id,
35                                        bool alt_def_id)
36 {
37     //Pointer to the beginning of the media text
38     const char *current_start = buff;
39     //Pointer to the end of the media text
40     const char *end = buff + index;
41     const char *line_start_ptr, *line_end_ptr;
42     int fmtp_cnt = 0;
43     bool altMedia = false;
44 
45     if (!alt_id || (alt_def_id == true))
46     {
47         altMedia = false;
48     }
49     else
50     {
51         altMedia = true;
52     }
53     void *memory = sdp->alloc(sizeof(h264_mediaInfo), altMedia);
54     if (NULL == memory)
55     {
56         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Memory allocation failure"));
57         return SDP_NO_MEMORY;
58     }
59     else
60     {
61         h264_mediaInfo *h264V = OSCL_PLACEMENT_NEW(memory, h264_mediaInfo());
62 
63         h264V->setMediaInfoID(sdp->getMediaObjectIndex());
64 
65         // Allocate memory to the payload specific objects
66         for (uint32 ii = 0; ii < payload_vec.size(); ii++)
67         {
68             void* mem = h264V->alloc(sizeof(H264PayloadSpecificInfoType));
69             if (mem == NULL)
70             {
71                 PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Memory allocation failure"));
72                 return SDP_NO_MEMORY;
73             }
74             else
75             {
76                 H264PayloadSpecificInfoType* h264Payload = OSCL_PLACEMENT_NEW(mem, H264PayloadSpecificInfoType(payload_vec[ii]));
77                 (void) h264Payload;
78             }
79         }
80 
81 
82         if (alt_id && !alt_def_id)
83         {
84             sdp->copyFmDefMedia(h264V);
85             //empty alternate & default track ID vectors.
86             h264V->resetAlternateTrackId();
87             h264V->resetDependentTrackId();
88         }
89 
90         SDP_ERROR_CODE status =
91             baseMediaInfoParser(buff, h264V, index, alt_id, alt_def_id, isSipSdp);
92         if (status != SDP_SUCCESS)
93         {
94             return status;
95         }
96 
97         while (get_next_line(current_start,
98                              end,
99                              line_start_ptr,
100                              line_end_ptr))
101         {
102             switch (*line_start_ptr)
103             {
104                 case 'a':
105                 {
106                     if ((!oscl_strncmp(line_start_ptr,
107                                        "a=alt:",
108                                        oscl_strlen("a=alt:"))) &&
109                             (alt_def_id == false))
110                     {
111                         line_start_ptr += oscl_strlen("a=alt:");
112                         for (; *line_start_ptr != ':'; line_start_ptr++);
113                         line_start_ptr = line_start_ptr + 1;
114                     }
115                     if (!oscl_strncmp(line_start_ptr,
116                                       "a=fmtp:",
117                                       oscl_strlen("a=fmtp:")))
118                     {
119                         const char *tmp_start_line, *tmp_end_line;
120                         fmtp_cnt++ ;
121 
122                         tmp_start_line = line_start_ptr + oscl_strlen("a=fmtp:");
123                         tmp_start_line =
124                             skip_whitespace(tmp_start_line, line_end_ptr);
125                         if (tmp_start_line >= line_end_ptr)
126                         {
127                             break;
128                         }
129                         tmp_end_line =
130                             skip_to_whitespace(tmp_start_line, line_end_ptr);
131                         if (tmp_end_line < tmp_start_line)
132                         {
133                             break;
134                         }
135                         uint32 payloadNumber;
136                         if (PV_atoi(tmp_start_line,
137                                     'd',
138                                     (tmp_end_line - tmp_start_line),
139                                     payloadNumber) == false)
140                         {
141                             PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format - Bad payload number"));
142                             return SDP_BAD_MEDIA_FMTP;
143                         }
144                         else
145                         {
146                             int p;
147                             if (!h264V->lookupPayloadNumber(payloadNumber, p))
148                             {
149                                 fmtp_cnt--;
150                                 break;
151                             }
152                         }
153 
154                         // payloadNumber is present in the mediaInfo. get the payload
155                         // Specific pointer corresponding to this payload
156                         H264PayloadSpecificInfoType* payloadPtr =
157                             (H264PayloadSpecificInfoType*)h264V->getPayloadSpecificInfoTypePtr(payloadNumber);
158                         if (payloadPtr == NULL)
159                         {
160                             PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: Payload pointer not found for payload"));
161                             return SDP_PAYLOAD_MISMATCH;
162                         }
163 
164                         PVMF_SDP_PARSER_LOGINFO((0, "SDPH264MediaInfoParser::parseMediaInfo - processing payload number : %d", payloadNumber));
165 
166                         tmp_start_line = tmp_end_line + 1;
167                         tmp_start_line =
168                             skip_whitespace(tmp_start_line, line_end_ptr);
169                         if (tmp_start_line >= line_end_ptr)
170                         {
171                             break;
172                         }
173                         int ii = 0;
174                         const char *temp = tmp_start_line;
175                         for (ii = 0; ii < (line_end_ptr - tmp_start_line); ii++)
176                         {
177                             if ((tmp_start_line[ii] == ';') ||
178                                     (ii == (line_end_ptr - tmp_start_line) - 1))
179                             {
180                                 tmp_end_line = tmp_start_line + ii;
181                                 if (ii == (line_end_ptr - tmp_start_line) - 1)
182                                 {
183                                     tmp_end_line += 1;
184                                 }
185                                 if (!oscl_strncmp(temp,
186                                                   "profile-level-id=",
187                                                   oscl_strlen("profile-level-id=")))
188                                 {
189                                     temp += oscl_strlen("profile-level-id=");
190                                     temp = skip_whitespace(temp, tmp_end_line);
191                                     if (temp > tmp_end_line)
192                                     {
193                                         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format - Bad profile-level-id: field"));
194                                         return SDP_BAD_MEDIA_FMTP;
195                                     }
196                                     uint32 val;
197                                     if (PV_atoi(temp,
198                                                 'x',
199                                                 (tmp_end_line - temp),
200                                                 val) == true)
201                                     {
202                                         payloadPtr->setProfileLevelID(val);
203                                     }
204 
205                                 }
206                                 if (!oscl_strncmp(temp,
207                                                   "max-mbps=",
208                                                   oscl_strlen("max-mbps=")))
209                                 {
210                                     temp += oscl_strlen("max-mbps=");
211                                     temp = skip_whitespace(temp, tmp_end_line);
212                                     if (temp > tmp_end_line)
213                                     {
214                                         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format - Bad max-mbps: field"));
215                                         return SDP_BAD_MEDIA_FMTP;
216                                     }
217                                     uint32 val;
218                                     if (PV_atoi(temp,
219                                                 'd',
220                                                 (tmp_end_line - temp),
221                                                 val) == true)
222                                     {
223                                         payloadPtr->setMaxMbps(val);
224                                     }
225                                 }
226                                 if (!oscl_strncmp(temp,
227                                                   "max-fs=",
228                                                   oscl_strlen("max-fs=")))
229                                 {
230                                     temp += oscl_strlen("max-fs=");
231                                     temp = skip_whitespace(temp, tmp_end_line);
232                                     if (temp > tmp_end_line)
233                                     {
234                                         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format - Bad max-fs field"));
235                                         return SDP_BAD_MEDIA_FMTP;
236                                     }
237                                     uint32 val;
238                                     if (PV_atoi(temp,
239                                                 'd',
240                                                 (tmp_end_line - temp),
241                                                 val) == true)
242                                     {
243                                         payloadPtr->setMaxFs(val);
244                                     }
245                                 }
246                                 if (!oscl_strncmp(temp,
247                                                   "max-cpb=",
248                                                   oscl_strlen("max-cpb=")))
249                                 {
250                                     temp += oscl_strlen("max-cpb=");
251                                     temp = skip_whitespace(temp, tmp_end_line);
252                                     if (temp > tmp_end_line)
253                                     {
254                                         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format - Bad max-cpb: field"));
255                                         return SDP_BAD_MEDIA_FMTP;
256                                     }
257                                     uint32 val;
258                                     if (PV_atoi(temp,
259                                                 'd',
260                                                 (tmp_end_line - temp),
261                                                 val) == true)
262                                     {
263                                         payloadPtr->setMaxCpb(val);
264                                     }
265                                 }
266                                 if (!oscl_strncmp(temp,
267                                                   "max-dpb=",
268                                                   oscl_strlen("max-dpb=")))
269                                 {
270                                     temp += oscl_strlen("max-dpb=");
271                                     temp = skip_whitespace(temp, tmp_end_line);
272                                     if (temp > tmp_end_line)
273                                     {
274                                         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format - Bad max-dpb field"));
275                                         return SDP_BAD_MEDIA_FMTP;
276                                     }
277                                     uint32 val;
278                                     if (PV_atoi(temp,
279                                                 'd',
280                                                 (tmp_end_line - temp),
281                                                 val) == true)
282                                     {
283                                         payloadPtr->setMaxDpb(val);
284                                     }
285                                 }
286                                 if (!oscl_strncmp(temp,
287                                                   "max-br=",
288                                                   oscl_strlen("max-br=")))
289                                 {
290                                     temp += oscl_strlen("max-br=");
291                                     temp = skip_whitespace(temp, tmp_end_line);
292                                     if (temp > tmp_end_line)
293                                     {
294                                         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format - Bad max-br field"));
295                                         return SDP_BAD_MEDIA_FMTP;
296                                     }
297                                     uint32 val;
298                                     if (PV_atoi(temp,
299                                                 'd',
300                                                 (tmp_end_line - temp),
301                                                 val) == true)
302                                     {
303                                         payloadPtr->setMaxBr(val);
304                                     }
305                                 }
306                                 if (!oscl_strncmp(temp,
307                                                   "redundant-pic-cap=",
308                                                   oscl_strlen("redundant-pic-cap=")))
309                                 {
310                                     temp += oscl_strlen("redundant-pic-cap=");
311                                     temp = skip_whitespace(temp, tmp_end_line);
312                                     if (temp > tmp_end_line)
313                                     {
314                                         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format - Bad redundant-pic-cap field"));
315                                         return SDP_BAD_MEDIA_FMTP;
316                                     }
317                                     uint32 val;
318                                     if (PV_atoi(temp,
319                                                 'd',
320                                                 (tmp_end_line - temp),
321                                                 val) == true)
322                                     {
323                                         payloadPtr->setRedundantPicCap(val);
324                                     }
325                                 }
326                                 if (!oscl_strncmp(temp,
327                                                   "sprop-parameter-sets=",
328                                                   oscl_strlen("sprop-parameter-sets=")))
329                                 {
330                                     temp += oscl_strlen("sprop-parameter-sets=");
331                                     temp = skip_whitespace(temp, line_end_ptr);
332                                     if (temp >= line_end_ptr)
333                                     {
334                                         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format - Bad sprop-parameter-sets field"));
335                                         return SDP_BAD_MEDIA_FMTP;
336                                     }
337                                     uint32 parameterSetLength = (int)(tmp_end_line - temp);
338                                     SDP_ERROR_CODE errCode =
339                                         parseParameterSets(temp,
340                                                            parameterSetLength,
341                                                            h264V,
342                                                            payloadNumber);
343 
344                                     if (errCode != SDP_SUCCESS)
345                                     {
346                                         return errCode;
347                                     }
348 
349                                 }
350                                 if (!oscl_strncmp(temp,
351                                                   "packetization-mode=",
352                                                   oscl_strlen("packetization-mode=")))
353                                 {
354                                     temp += oscl_strlen("packetization-mode=");
355                                     temp = skip_whitespace(temp, tmp_end_line);
356                                     if (temp > tmp_end_line)
357                                     {
358                                         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format - Bad packetization-mode field"));
359                                         return SDP_BAD_MEDIA_FMTP;
360                                     }
361                                     uint32 val;
362                                     if (PV_atoi(temp,
363                                                 'd',
364                                                 (tmp_end_line - temp),
365                                                 val) == true)
366                                     {
367                                         payloadPtr->setPacketizationMode(val);
368                                     }
369                                 }
370                                 if (!oscl_strncmp(temp,
371                                                   "sprop-interleaving-depth=",
372                                                   oscl_strlen("sprop-interleaving-depth=")))
373                                 {
374                                     temp += oscl_strlen("sprop-interleaving-depth=");
375                                     temp = skip_whitespace(temp, tmp_end_line);
376                                     if (temp > tmp_end_line)
377                                     {
378                                         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format - Bad sprop-interleaving-depth field"));
379                                         return SDP_BAD_MEDIA_FMTP;
380                                     }
381                                     uint32 val;
382                                     if (PV_atoi(temp,
383                                                 'd',
384                                                 (tmp_end_line - temp),
385                                                 val) == true)
386                                     {
387                                         payloadPtr->setSpropInterleavingDepth(val);
388                                     }
389                                 }
390                                 if (!oscl_strncmp(temp,
391                                                   "deint-buf-cap=",
392                                                   oscl_strlen("deint-buf-cap=")))
393                                 {
394                                     temp += oscl_strlen("deint-buf-cap=");
395                                     temp = skip_whitespace(temp, tmp_end_line);
396                                     if (temp > tmp_end_line)
397                                     {
398                                         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format - Bad deint-buf-cap field"));
399                                         return SDP_BAD_MEDIA_FMTP;
400                                     }
401                                     uint32 val;
402                                     if (PV_atoi(temp,
403                                                 'd',
404                                                 (tmp_end_line - temp),
405                                                 val) == true)
406                                     {
407                                         payloadPtr->setDeintBufCap(val);
408                                     }
409                                 }
410                                 if (!oscl_strncmp(temp,
411                                                   "sprop-deint-buf-req=",
412                                                   oscl_strlen("sprop-deint-buf-req=")))
413                                 {
414                                     temp += oscl_strlen("sprop-deint-buf-req=");
415                                     temp = skip_whitespace(temp, tmp_end_line);
416                                     if (temp > tmp_end_line)
417                                     {
418                                         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format - Bad sprop-deint-buf-req field"));
419                                         return SDP_BAD_MEDIA_FMTP;
420                                     }
421                                     uint32 val;
422                                     if (PV_atoi(temp,
423                                                 'd',
424                                                 (tmp_end_line - temp),
425                                                 val) == true)
426                                     {
427                                         payloadPtr->setSpropDeintBufReq(val);
428                                     }
429                                 }
430                                 if (!oscl_strncmp(temp,
431                                                   "sprop-init-buf-time=",
432                                                   oscl_strlen("sprop-init-buf-time=")))
433                                 {
434                                     temp += oscl_strlen("sprop-init-buf-time=");
435                                     temp = skip_whitespace(temp, tmp_end_line);
436                                     if (temp > tmp_end_line)
437                                     {
438                                         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format - Bad sprop-init-buf-time field"));
439                                         return SDP_BAD_MEDIA_FMTP;
440                                     }
441                                     uint32 val;
442                                     if (PV_atoi(temp,
443                                                 'd',
444                                                 (tmp_end_line - temp),
445                                                 val) == true)
446                                     {
447                                         payloadPtr->setSpropInitBufTime(val);
448                                     }
449                                 }
450                                 if (!oscl_strncmp(temp,
451                                                   "sprop-max-don-diff=",
452                                                   oscl_strlen("sprop-max-don-diff=")))
453                                 {
454                                     temp += oscl_strlen("sprop-max-don-diff=");
455                                     temp = skip_whitespace(temp, tmp_end_line);
456                                     if (temp > tmp_end_line)
457                                     {
458                                         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format - Bad sprop-max-don-diff field"));
459                                         return SDP_BAD_MEDIA_FMTP;
460                                     }
461                                     uint32 val;
462                                     if (PV_atoi(temp,
463                                                 'd',
464                                                 (tmp_end_line - temp),
465                                                 val) == true)
466                                     {
467                                         payloadPtr->setSpropMaxDonDiff(val);
468                                     }
469                                 }
470                                 if (!oscl_strncmp(temp,
471                                                   "max-rcmd-nalu-size=",
472                                                   oscl_strlen("max-rcmd-nalu-size=")))
473                                 {
474                                     temp += oscl_strlen("max-rcmd-nalu-size=");
475                                     temp = skip_whitespace(temp, tmp_end_line);
476                                     if (temp > tmp_end_line)
477                                     {
478                                         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format - Bad max-rcmd-nalu-size field"));
479                                         return SDP_BAD_MEDIA_FMTP;
480                                     }
481                                     uint32 val;
482                                     if (PV_atoi(temp,
483                                                 'd',
484                                                 (tmp_end_line - temp),
485                                                 val) == true)
486                                     {
487                                         payloadPtr->setMaxRcmdNaluSize(val);
488                                     }
489                                 }
490                                 if (!oscl_strncmp(temp,
491                                                   "decode_buf=",
492                                                   oscl_strlen("decode_buf=")))
493                                 {
494                                     temp += oscl_strlen("decode_buf=");
495                                     temp = skip_whitespace(temp, tmp_end_line);
496                                     if (temp > tmp_end_line)
497                                     {
498                                         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format - Bad decode-buf field"));
499                                         return SDP_BAD_MEDIA_FMTP;
500                                     }
501                                     uint32 decode_buf;
502                                     if (PV_atoi(temp,
503                                                 'd',
504                                                 (tmp_end_line - temp),
505                                                 decode_buf) == true)
506                                     {
507                                         payloadPtr->setMaxBufferSize(decode_buf);
508                                     }
509                                 }
510                                 if (tmp_end_line != line_end_ptr)
511                                 {
512                                     temp = tmp_end_line + 1;
513                                 }
514                                 temp = skip_whitespace(temp, line_end_ptr);
515                                 if (temp >= line_end_ptr)
516                                 {
517                                     PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - Bad a=fmtp: line format"));
518                                     return SDP_BAD_MEDIA_FMTP;
519                                 }
520                             }
521                         }
522                     }// end a=fmtp
523                 }
524                 break;
525                 default:
526                 {
527                 }
528                 break;
529             }
530             current_start = line_end_ptr;
531         }
532 
533         sessionDescription *session = sdp->getSessionInfo();
534 
535         const char *altGroupBW = session->getAltGroupBW();
536         int length = session->getAltGroupBWLength();
537 
538         if (length > 0)
539         {
540             status = setDependentMediaId(altGroupBW, length, h264V, alt_id);
541             if (status != SDP_SUCCESS)
542                 return SDP_BAD_MEDIA_ALT_ID;
543         }
544 
545         const char *altGroupLANG = session->getAltGroupLANG();
546         length = session->getAltGroupLANGLength();
547 
548         if (length > 0)
549         {
550             status = setDependentMediaId(altGroupLANG, length, h264V, alt_id);
551             if (status != SDP_SUCCESS)
552                 return SDP_BAD_MEDIA_ALT_ID;
553         }
554 
555         if ((fmtp_cnt == h264V->getMediaPayloadNumberCount()) &&
556                 (h264V->getCFieldStatus() || session->getCFieldStatus()))
557 
558             return SDP_SUCCESS;
559         else
560         {
561             PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseMediaInfo - no c field present"));
562             return SDP_FAILURE_NO_C_FIELD;
563         }
564 
565     }
566 
567 
568 }
569 
parseParameterSets(const char * aParamSetBuf,int aParamSetBufLen,h264_mediaInfo * aH264MediaInfo,uint32 aPayLoadNumber)570 SDP_ERROR_CODE SDPH264MediaInfoParser::parseParameterSets(const char* aParamSetBuf,
571         int   aParamSetBufLen,
572         h264_mediaInfo* aH264MediaInfo,
573         uint32 aPayLoadNumber)
574 {
575     /*Determine number of parameter sets */
576     const char *tmp_start_line = aParamSetBuf;
577     int i;
578     uint32 numParamSets = 0;
579     Oscl_Vector<uint8*, OsclMemAllocator> paramSetStartBufVec;
580     Oscl_Vector<uint32, OsclMemAllocator> paramSetBufSizeVec;
581     paramSetStartBufVec.push_back((uint8*)tmp_start_line);
582     uint32 prevIndex = 0;
583     for (i = 0; i < aParamSetBufLen; i++)
584     {
585         if (tmp_start_line[i] == ',')
586         {
587             uint8* ptr = (uint8*)(tmp_start_line + (i + 1));
588             paramSetStartBufVec.push_back(ptr);
589             uint32 size = (i - prevIndex);
590             prevIndex = i + 1;
591             paramSetBufSizeVec.push_back(size);
592             numParamSets++;
593         }
594     }
595     numParamSets++;
596     paramSetBufSizeVec.push_back((aParamSetBufLen - prevIndex));
597 
598     if (paramSetBufSizeVec[0] >= MIN_ENCODED_BYTES)
599     {
600         uint8  decoded[MIN_ENCODED_BYTES];
601         uint32 outBufLen = 0;
602         //Decode the minimum amount required to extract the NAL type.
603         if (sdp_decodebase64(paramSetStartBufVec[0],
604                              MIN_ENCODED_BYTES,
605                              decoded,
606                              outBufLen,
607                              sizeof(decoded)
608                             ))
609         {
610             uint8 nal_type = decoded[0] & AVC_NALTYPE_MASK;
611             switch (nal_type)
612             {
613                     //Rather than modify every codec to accept SPS and PPS in any order,
614                     //it is best to simply swap the order in the SDP parser so SPS
615                     //always comes before PPS.
616                     //If PPS comes before SPS, swap the order.
617                 case AVC_NALTYPE_PPS:
618                 {
619                     uint8* tempBuf = paramSetStartBufVec.back();
620                     paramSetStartBufVec.pop_back();
621                     paramSetStartBufVec.push_front(tempBuf);
622                     uint32 tempSize = paramSetBufSizeVec.back();
623                     paramSetBufSizeVec.pop_back();
624                     paramSetBufSizeVec.push_front(tempSize);
625                 }
626                 break;
627 
628                 case AVC_NALTYPE_SPS:
629                 default:
630                     break;
631             }
632         }
633     }
634 
635     int configBufLength = aParamSetBufLen + numParamSets * (sizeof(uint16));
636     SDPAllocDestructDealloc<uint8> SDP_alloc;
637     uint8 *configPtr = SDP_alloc.allocate(configBufLength);
638     OsclRefCounterSA< SDPAllocDestructDealloc<uint8> > *refcnt =
639         new OsclRefCounterSA< SDPAllocDestructDealloc<uint8> >(configPtr);
640     OsclSharedPtr<uint8> parameterSetPtr(configPtr, refcnt);
641 
642     uint32 offset = 0;
643     for (uint32 j = 0; j < paramSetStartBufVec.size(); j++)
644     {
645         uint8* inBuf = paramSetStartBufVec[j];
646         uint32 inBufLen = paramSetBufSizeVec[j];
647         uint32 outBufLen = 0;
648         uint8* paramSetSizePtr = configPtr + offset;
649         offset += 2; // for param set size
650         uint8* outPtr = configPtr + offset;
651         uint32 maxOutBufLen = configBufLength - offset;
652         if (!sdp_decodebase64(inBuf,
653                               inBufLen,
654                               outPtr,
655                               outBufLen,
656                               maxOutBufLen))
657         {
658             PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseParameterSets : unable to set decodebase"));
659             return SDP_BAD_MEDIA_FMTP;
660         }
661         uint16 len = (uint16)outBufLen;
662         oscl_memcpy(paramSetSizePtr, &len, sizeof(uint16));
663         offset += outBufLen;
664     }
665 
666     H264PayloadSpecificInfoType* payloadPtr =
667         (H264PayloadSpecificInfoType*)aH264MediaInfo->getPayloadSpecificInfoTypePtr(aPayLoadNumber);
668     if (payloadPtr == NULL)
669     {
670         PVMF_SDP_PARSER_LOGERROR((0, "SDPH264MediaInfoParser::parseParameterSets - Unable to find payload ptr for payload"));
671         return SDP_PAYLOAD_MISMATCH;
672     }
673 
674     PVMF_SDP_PARSER_LOGINFO((0, "SDPH264MediaInfoParser::parseParameterSets - processing payload number : %d", aPayLoadNumber));
675 
676     payloadPtr->setDecoderSpecificInfo(parameterSetPtr);
677     payloadPtr->setDecoderSpecificInfoSize(offset);
678 
679     //if sample rate is zero override with defaults
680     Oscl_Vector<PayloadSpecificInfoTypeBase*, SDPParserAlloc> payloadSpecificInfoVector =
681         aH264MediaInfo->getPayloadSpecificInfoVector();
682     for (int ii = 0; ii < (int)payloadSpecificInfoVector.size(); ii++)
683     {
684         if (payloadSpecificInfoVector[ii]->getSampleRate() == 0)
685         {
686             payloadSpecificInfoVector[ii]->sampleRate =
687                 PVMF_SDP_DEFAULT_H264_SAMPLE_RATE;
688         }
689     }
690     return SDP_SUCCESS;
691 }
692 
693 
694