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 /////////////////////////////////////////////////////////////////////////////// 19 // 20 // RFC3640_payload_parser.cpp 21 // 22 // Implementation of payload parser for RFC3640 RTP format. 23 // 24 /////////////////////////////////////////////////////////////////////////////// 25 26 #include "oscl_mem.h" 27 #include "rfc3640_payload_parser.h" 28 #include "bitstreamparser.h" 29 #include "oscl_byte_order.h" 30 #include "rfc3640_media_info.h" 31 32 //Until the fileformat node and decoder are re-worked to handle multiple-fragments 33 //per media message, we'll need to use this switch to control the output of the 34 //payload parser 35 #define RFC3640_ONE_FRAGMENT_PER_MEDIA_MSG 1 36 37 //Default Values 38 #define AAC_HBR_SIZELENGTH_DEFAULT_VALUE 13 39 #define AAC_HBR_INDEXLENGTH_DEFAULT_VALUE 3 40 #define AAC_HBR_INDEXDELTALENGTH_DEFAULT_VALUE 3 41 #define AAC_HBR_CTSDELTALENGTH_DEFAULT_VALUE 0 42 #define AAC_HBR_DTSDELTALENGTH_DEFAULT_VALUE 0 43 #define AAC_HBR_HEADERSLENGTH_DEFAULT_VALUE 16 44 #define AAC_HBR_AUXDATASIZELENGTH_DEFAULT_VALUE 0 45 46 /////////////////////////////////////////////////////////////////////////////// 47 // 48 // Constructor/Destructor 49 // 50 /////////////////////////////////////////////////////////////////////////////// 51 52 OSCL_EXPORT_REF RFC3640PayloadParser::RFC3640PayloadParser() 53 { 54 //Default to no headers at all. 55 //This is just in case Init() is never called. 56 headersPresent = false; 57 headersLength = 0; 58 sizeLength = 0; 59 indexLength = 0; 60 indexDeltaLength = 0; 61 CTSDeltaLength = 0; 62 DTSDeltaLength = 0; 63 randomAccessIndication = false; 64 auxDataSizeLength = 0; 65 } 66 67 OSCL_EXPORT_REF RFC3640PayloadParser::~RFC3640PayloadParser() 68 { 69 } 70 71 /////////////////////////////////////////////////////////////////////////////// 72 // 73 // Initialization 74 // 75 /////////////////////////////////////////////////////////////////////////////// 76 77 OSCL_EXPORT_REF bool RFC3640PayloadParser::Init(mediaInfo* config) 78 { 79 Oscl_Vector<PayloadSpecificInfoTypeBase*, OsclMemAllocator> payloadInfo; 80 payloadInfo = config->getPayloadSpecificInfoVector(); 81 PayloadSpecificInfoTypeBase* payloadInfoBase = payloadInfo[0]; // is this "0" assumption okay??? 82 RFC3640PayloadSpecificInfoType* r3640PayloadInfo = 83 OSCL_STATIC_CAST(RFC3640PayloadSpecificInfoType*, payloadInfoBase); 84 rfc3640_mediaInfo *r3640m = OSCL_STATIC_CAST(rfc3640_mediaInfo *, config); 85 bool retVal = false; 86 87 //TODO: Implement other modes (such as CELP-cbr, CELP-vbr, AAC-lbr, etc...). 88 sizeLength = r3640PayloadInfo->getSizeLength(); 89 indexLength = r3640PayloadInfo->getIndexLength(); 90 indexDeltaLength = r3640PayloadInfo->getIndexDeltaLength(); 91 CTSDeltaLength = r3640PayloadInfo->getCTSDeltaLength(); 92 DTSDeltaLength = r3640PayloadInfo->getDTSDeltaLength(); 93 randomAccessIndication = false; 94 95 //We support AAC-hbr mode only. 96 if (!oscl_strncmp(r3640m->getMode(), "AAC-hbr", oscl_strlen("AAC-hbr"))) 97 { 98 headersPresent = true; 99 headersLength = AAC_HBR_HEADERSLENGTH_DEFAULT_VALUE; 100 auxDataSizeLength = AAC_HBR_AUXDATASIZELENGTH_DEFAULT_VALUE; 101 102 //do sanity check on values. Only supporting AAC_HBR default fixed values. 103 if ((sizeLength != AAC_HBR_SIZELENGTH_DEFAULT_VALUE) || 104 (indexLength != AAC_HBR_INDEXLENGTH_DEFAULT_VALUE) || 105 (indexDeltaLength != AAC_HBR_INDEXDELTALENGTH_DEFAULT_VALUE)) 106 { 107 retVal = true; 108 } 109 110 } 111 else 112 { 113 retVal = true; 114 } 115 116 117 return retVal; 118 } 119 120 /////////////////////////////////////////////////////////////////////////////// 121 // 122 // Payload parsing 123 // 124 /////////////////////////////////////////////////////////////////////////////// 125 126 OSCL_EXPORT_REF PayloadParserStatus 127 RFC3640PayloadParser::Parse(const Payload& inputPacket, 128 Oscl_Vector<Payload, OsclMemAllocator>& vParsedPayloads) 129 { 130 // Many of OsclRefCounterMemFrag's member functions 131 //should be const functions so this casting away constness is not necessary. 132 Payload& input = const_cast<Payload&>(inputPacket); 133 134 //@TODO: Implement AU de-interleaving 135 136 Payload out; 137 138 out.stream = inputPacket.stream; 139 out.marker = inputPacket.marker; 140 out.randAccessPt = inputPacket.randAccessPt; 141 out.sequence = inputPacket.sequence + 1; 142 out.timestamp = inputPacket.timestamp; 143 //Creating a boolean for checking whether RFC3640_ONE_FRAGMENT_PER_MEDIA_MSG is defined or not 144 bool rfc3640_one_fragement_per_media = false; 145 146 #ifndef RFC3640_ONE_FRAGMENT_PER_MEDIA_MSG 147 rfc3640_one_fragement_per_media = true; 148 #endif 149 150 // Many functions calls inside this for loop may Leave because of an 151 // overflow. 152 int32 err; 153 OSCL_TRY(err, 154 //Loop through all of the packets. 155 for (uint32 fragmentNumber = 0; fragmentNumber < inputPacket.vfragments.size(); fragmentNumber++) 156 { 157 // 158 // Strip RFC 3640 header section and auxiliary section. 159 // 160 161 //Establish a pointer to the payload fragment for iterating past the 162 //header and aux section. 163 BitStreamParser fragment((uint8*)input.vfragments[fragmentNumber].getMemFragPtr(), 164 input.vfragments[fragmentNumber].getMemFragSize()); 165 166 //In some cases, such as with fixed-length AUs, the header is not present. 167 //Only process the header if it is present. 168 uint16 headersLength = 0; 169 if (headersPresent) 170 { 171 //Read the header length from the first 2 octets. 172 //Include the size of this headersLength field in the total length. 173 headersLength = fragment.ReadUInt16() + BITS_PER_UINT16; 174 } 175 176 uint8 accessUnits = 0; //controls index field interpretation (index or delta) 177 uint32 size = 0; //size of the AU 178 uint32 index = 0; //used for interleaving 179 uint32 indexDelta = 0; //used for interleaving 180 int CTSFlag = 0; //composition time stamp 181 uint32 CTSDelta = 0; //composition time stamp 182 int DTSFlag = 0; //decoding time stamp 183 uint32 DTSDelta = 0; //decoding time stamp 184 int RAPFlag = 0; //random access point - used to mark a key frame 185 uint32 auxDataSize = 0; 186 187 //Loop through all of the access units in the packet. 188 while (fragment.BitsRead() < headersLength) 189 { 190 //If the header is present, parse it. 191 if (headersLength) 192 { 193 if (0 != sizeLength) 194 { 195 //Read the AU Size field. 196 size = fragment.ReadBits(sizeLength); 197 } 198 199 //If the index field is present... 200 if (0 != indexLength) 201 { 202 //If this is the first access unit header... 203 if (0 == accessUnits) 204 { 205 //The AU index only occurs in the first header. 206 index = fragment.ReadBits(indexLength); 207 } 208 else 209 { 210 indexDelta = fragment.ReadBits(indexDeltaLength); 211 } 212 } 213 214 //From RFC3640: "The CTS-flag field MUST be present in each AU-header 215 // if the length of the CTS-delta field is signaled to 216 // be larger than zero." 217 if (0 != CTSDeltaLength) 218 { 219 CTSFlag = fragment.ReadBits(1); 220 if (CTSFlag) 221 { 222 CTSDelta = fragment.ReadBits(CTSDeltaLength); 223 } 224 } 225 226 if (0 != DTSDeltaLength) 227 { 228 DTSFlag = fragment.ReadBits(1); 229 if (DTSFlag) 230 { 231 DTSDelta = fragment.ReadBits(DTSDeltaLength); 232 } 233 } 234 235 if (randomAccessIndication) 236 { 237 RAPFlag = fragment.ReadBits(1); 238 } 239 } 240 241 242 if (rfc3640_one_fragement_per_media == true) 243 { 244 // At this time the decoder cannot handle multiple fragments. 245 246 OsclMemoryFragment memfrag; 247 //memfrag.ptr = NULL; //Unknown at this time. 248 memfrag.len = size; 249 input.vfragments[fragmentNumber].getRefCounter()->addRef(); 250 OsclRefCounterMemFrag refCntMemFrag(memfrag, 251 input.vfragments[fragmentNumber].getRefCounter(), 252 memfrag.len); 253 out.vfragments.push_back(refCntMemFrag); 254 } 255 else 256 { 257 // Instead of creating multiple fragments, point to the first fragment, but 258 // increment the size field to span all access units. The decoder is still 259 // getting multiple frames in memory, but the data structure makes it appear as just one. 260 // This only works for non-interleaved access units & can only be a temporary solution 261 if (accessUnits == 0) 262 { 263 OsclMemoryFragment memfrag; 264 memfrag.ptr = (uint8*)(input.vfragments[fragmentNumber].getMemFragPtr()) + (headersLength / 8); 265 memfrag.len = input.vfragments[fragmentNumber].getMemFragSize() - (headersLength / 8); 266 input.vfragments[fragmentNumber].getRefCounter()->addRef(); 267 OsclRefCounterMemFrag refCntMemFrag(memfrag, 268 input.vfragments[fragmentNumber].getRefCounter(), 269 memfrag.len); 270 out.vfragments.push_back(refCntMemFrag); 271 } 272 } 273 274 accessUnits++; 275 } 276 277 //Processed the header. Skip past any padding. 278 if (fragment.GetBitPos() != MOST_SIG_BIT) 279 { 280 fragment.NextBits(fragment.GetBitPos() + 1); 281 } 282 283 //Now skip over the aux data region. 284 if (auxDataSizeLength) 285 { 286 auxDataSize = fragment.ReadBits(auxDataSizeLength); 287 if (auxDataSize) 288 { 289 //Skip over the aux data region. 290 fragment.NextBits(auxDataSize); 291 //Skip past any padding. 292 if (fragment.GetBitPos() != MOST_SIG_BIT) 293 { 294 fragment.NextBits(fragment.GetBitPos() + 1); 295 } 296 } 297 } 298 299 if (rfc3640_one_fragement_per_media == true) 300 { 301 //Update the fragment pointers with real values now that we have 302 //parsed the headers. 303 //The output vector may contain fragments from previous runs, so 304 //start with the last fragments that we pushed on the back of the vector. 305 for (uint32 i = (out.vfragments.size() - accessUnits); i < out.vfragments.size(); i++) 306 { 307 out.vfragments[i].getMemFrag().ptr = fragment.GetBytePos(); 308 fragment.NextBits(out.vfragments[i].getMemFrag().len * BITS_PER_BYTE); 309 } 310 } 311 312 } 313 ); // End of OSCL_TRY 314 315 if (err != OsclErrNone) 316 { 317 return PayloadParserStatus_Failure; 318 } 319 vParsedPayloads.push_back(out); 320 321 return PayloadParserStatus_Success; 322 } 323 324 /////////////////////////////////////////////////////////////////////////////// 325 // 326 // Repositioning related 327 // 328 /////////////////////////////////////////////////////////////////////////////// 329 330 OSCL_EXPORT_REF void RFC3640PayloadParser::Reposition(const bool adjustSequence, const uint32 stream, const uint32 seqnum) 331 { 332 OSCL_UNUSED_ARG(adjustSequence); 333 OSCL_UNUSED_ARG(stream); 334 OSCL_UNUSED_ARG(seqnum); 335 } 336 337 OSCL_EXPORT_REF uint32 RFC3640PayloadParser::GetMinCurrTimestamp() 338 { 339 return 0; 340 } 341