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/* MPEG-4 SampleTableAtom Class */ 21/* ------------------------------------------------------------------- */ 22/*********************************************************************************/ 23/* 24 This SampleTableAtom Class contains all the time and data indexing of the 25 media samples in a track. 26*/ 27 28 29#ifndef SAMPLETABLEATOM_H_INCLUDED 30#define SAMPLETABLEATOM_H_INCLUDED 31 32#ifndef OSCL_FILE_IO_H_INCLUDED 33#include "oscl_file_io.h" 34#endif 35 36#ifndef ATOM_H_INCLUDED 37#include "atom.h" 38#endif 39 40#ifndef TIMETOSAMPLEATOM_H_INCLUDED 41#include "timetosampleatom.h" 42#endif 43 44#ifndef COMPOSITIONOFFSETATOM_H_INCLUDED 45#include "compositionoffsetatom.h" 46#endif 47 48#ifndef SAMPLESIZEATOM_H_INCLUDED 49#include "samplesizeatom.h" 50#endif 51 52#ifndef CHUNKOFFSETATOM_H_INCLUDED 53#include "chunkoffsetatom.h" 54#endif 55 56#ifndef SAMPLETOCHUNKATOM_H_INCLUDED 57#include "sampletochunkatom.h" 58#endif 59 60#ifndef SAMPLEDESCRIPTIONATOM_H_INCLUDED 61#include "sampledescriptionatom.h" 62#endif 63 64#ifndef SYNCSAMPLEATOM_H_INCLUDED 65#include "syncsampleatom.h" 66#endif 67 68#ifndef ESDESCRIPTOR_H_INCLUDED 69#include "esdescriptor.h" 70#endif 71 72#ifndef ATOMDEFS_H_INCLUDED 73#include "atomdefs.h" 74#endif 75 76#ifndef OSCL_MEDIA_DATA_H_INCLUDED 77#include "oscl_media_data.h" 78#endif 79 80#ifndef PV_GAU_H_INCLUDED 81#include "pv_gau.h" 82#endif 83 84#ifndef AVCSAMPLEDEPENDENCYTYPE_H_INCLUDED 85#include "avcsampledependencytype.h" 86#endif 87 88#ifndef AVCSAMPLETOGROUPBOX_H_INCLUDED 89#include "avcsampletogroupbox.h" 90#endif 91 92#ifndef AVCSAMPLEDEPENDENCY_H_INCLUDED 93#include "avcsampledependency.h" 94#endif 95 96//Macro to give number of frames that one must go back 97//in order to retrieve sample number corresponding to requested timestamp 98#define BACK_TRAVERSE_FRAME_COUNT 10 99 100class AVCSampleEntry; 101 102class SampleTableAtom : public Atom 103{ 104 105 public: 106 SampleTableAtom(MP4_FF_FILE *fp, 107 uint32 mediaType, 108 OSCL_wString& filename, 109 uint32 size, 110 uint32 type, 111 bool oPVContentDownloadable = false, 112 uint32 parsingMode = 0); 113 114 virtual ~SampleTableAtom(); 115 116 // Member gets and sets 117 TimeToSampleAtom &getTimeToSampleAtom() 118 { 119 return *_ptimeToSampleAtom; 120 } 121 TimeToSampleAtom &getMutableTimeToSampleAtom() 122 { 123 return *_ptimeToSampleAtom; 124 } 125 126 const SampleDescriptionAtom &getSampleDescriptionAtom() const 127 { 128 return *_psampleDescriptionAtom; 129 } 130 SampleDescriptionAtom &getMutableSampleDescriptionAtom() 131 { 132 return *_psampleDescriptionAtom; 133 } 134 135 SampleSizeAtom &getSampleSizeAtom() 136 { 137 return *_psampleSizeAtom; 138 } 139 SampleSizeAtom &getMutableSampleSizeAtom() 140 { 141 return *_psampleSizeAtom; 142 } 143 144 const SampleToChunkAtom &getSampleToChunkAtom() const 145 { 146 return *_psampleToChunkAtom; 147 } 148 SampleToChunkAtom &getMutableSampleToChunkAtom() 149 { 150 return *_psampleToChunkAtom; 151 } 152 153 const ChunkOffsetAtom &getChunkOffsetAtom() const 154 { 155 return *_pchunkOffsetAtom; 156 } 157 ChunkOffsetAtom &getMutableChunkOffsetAtom() 158 { 159 return *_pchunkOffsetAtom; 160 } 161 162 void resetPlayBack(); 163 void resetTrackToEOT(); 164 int32 resetPlayBackbyTime(int32 time, bool oDependsOn); 165 int32 queryRepositionTime(int32 time, bool oDependsOn, bool bBeforeRequestedTime); 166 167 int32 IsResetNeeded(int32 time); 168 169 uint32 getTimestampForSampleNumber(uint32 sampleNumber); 170 int32 getCttsOffsetForSampleNumber(uint32 sampleNumber); 171 int32 getCttsOffsetForSampleNumberPeek(uint32 sampleNumber); 172 int32 getCttsOffsetForSampleNumberGet(uint32 sampleNumber); 173 int32 getSampleSizeAt(int32 sampleNum) 174 { 175 return getSampleSizeAtom().getSampleSizeAt(sampleNum); 176 } 177 178 // Get the type of SampleEntry atom (i.e. MPEG_SAMPLE_ENTRY, ... '<protocol>', etc.) 179 uint32 getSampleProtocol() 180 { 181 if (_psampleDescriptionAtom != NULL) 182 { 183 return _psampleDescriptionAtom->getSampleProtocol(_SDIndex); 184 } 185 else 186 { 187 return 0; 188 } 189 } 190 191 // Return the ESID for the track - undefined if a HINT track 192 uint32 getESID() const 193 { 194 if (_psampleDescriptionAtom != NULL) 195 { 196 return _psampleDescriptionAtom->getESID(_SDIndex); 197 } 198 else 199 { 200 return 0; 201 } 202 } 203 204 // Return the first ESDescriptor for the track - undefined if a HINT track 205 const ESDescriptor *getESDescriptor() const 206 { 207 if (_psampleDescriptionAtom != NULL) 208 { 209 return _psampleDescriptionAtom->getESDescriptor(_SDIndex); 210 } 211 else 212 { 213 return NULL; 214 } 215 } 216 217 uint32 getNumSampleEntries() 218 { 219 if (_psampleDescriptionAtom != NULL) 220 { 221 return _psampleDescriptionAtom->getNumSampleEntries(); 222 } 223 else 224 { 225 return 0; 226 } 227 } 228 229 uint32 getMaxBufferSizeDB() const 230 { 231 if (_psampleDescriptionAtom != NULL) 232 { 233 return _psampleDescriptionAtom->getMaxBufferSizeDB(); 234 } 235 else 236 { 237 return 0; 238 } 239 } 240 241 // Getting and setting the Mpeg4 VOL header 242 DecoderSpecificInfo *getDecoderSpecificInfo() const 243 { 244 if (_psampleDescriptionAtom != NULL) 245 { 246 return _psampleDescriptionAtom->getDecoderSpecificInfo(_SDIndex); 247 } 248 else 249 { 250 return NULL; 251 } 252 } 253 254 DecoderSpecificInfo *getDecoderSpecificInfoForSDI(uint32 index) const 255 { 256 if (_psampleDescriptionAtom != NULL) 257 { 258 return _psampleDescriptionAtom->getDecoderSpecificInfo(index); 259 } 260 else 261 { 262 return NULL; 263 } 264 } 265 266 void getMIMEType(OSCL_String& aMimeType) 267 { 268 if (_psampleDescriptionAtom != NULL) 269 { 270 _psampleDescriptionAtom->getMIMEType(aMimeType); 271 } 272 } 273 274 uint8 getObjectTypeIndication() 275 { 276 if (_psampleDescriptionAtom != NULL) 277 { 278 return _psampleDescriptionAtom->getObjectTypeIndication(); 279 } 280 else 281 { 282 return 0; 283 } 284 } 285 286 287 int32 getAverageBitrate() 288 { 289 if (_psampleDescriptionAtom != NULL) 290 { 291 return _psampleDescriptionAtom->getAverageBitrate(); 292 } 293 else 294 { 295 return 0; 296 } 297 } 298 299 int32 getHeight() 300 { 301 if (_psampleDescriptionAtom != NULL) 302 { 303 return _psampleDescriptionAtom->getHeight(); 304 } 305 else 306 { 307 return 0; 308 } 309 310 } 311 312 int32 getWidth() 313 { 314 if (_psampleDescriptionAtom != NULL) 315 { 316 return _psampleDescriptionAtom->getWidth(); 317 } 318 else 319 { 320 return 0; 321 } 322 } 323 324 //PASP 325 uint32 getHspacing() 326 { 327 if (_psampleDescriptionAtom != NULL) 328 { 329 return _psampleDescriptionAtom->getHspacing(); 330 } 331 else 332 { 333 return 0; 334 } 335 } 336 337 uint32 getVspacing() 338 { 339 if (_psampleDescriptionAtom != NULL) 340 { 341 return _psampleDescriptionAtom->getVspacing(); 342 } 343 else 344 { 345 return 0; 346 } 347 } 348 349 // Gets for optional member atoms 350 int32 getTimestampForRandomAccessPoints(uint32 *num, uint32 *tsBuf, uint32* numBuf, uint32* offsetBuf); 351 const SyncSampleAtom *getSyncSampleAtom() const 352 { 353 return _psyncSampleAtom; 354 } 355 356 // Returns next video frame 357 int32 getNextSample(uint8 *buf, int32 &size, uint32 &index, uint32 &SampleOffset); 358 359 int32 getMediaSample(uint32 sampleNumber, uint8 *buf, int32 &size, uint32 &index, uint32 &SampleOffset); 360 361 // Returns next I-frame at time ts (in milliseconds) - or the very next I-frame in the stream 362 int32 getNextSampleAtTime(uint32 ts, uint8 *buf, int32 &size, uint32 &index, uint32 &SampleOffset); 363 364 MP4_ERROR_CODE getKeyMediaSampleNumAt(uint32 aKeySampleNum, 365 GAU *pgau); 366 int32 getPrevKeyMediaSample(uint32 inputtimestamp, uint32 &aKeySampleNum, uint32 *n, GAU *pgau); 367 int32 getNextKeyMediaSample(uint32 inputtimestamp, uint32 &aKeySampleNum, uint32 *n, GAU *pgau); 368 369 // Returns the timestamp (in milliseconds) for the last sample returned 370 // This is mainly to be used when seeking in the bitstream - you request a frame at timestamp 371 // X, but the actual frame you get is Y, this method returns the timestamp for Y so you know which 372 // audio sample to request. 373 int32 getTimestampForCurrentSample(); 374 375 // Returns the sample number of the last samplle returned 376 // Used when requesting a hint sample for a specific randomly accessed sample 377 int32 getSampleNumberForCurrentSample() 378 { 379 return _currentPlaybackSampleNumber; 380 } 381 int32 getSampleNumberAdjustedWithCTTS(uint32 aTs, int32 aSampleNumber); 382 383 void advance() 384 { 385 _currentPlaybackSampleNumber++; // Advances the currentPlayback number 386 } 387 void advance(int32 sampleNum) 388 { 389 _currentPlaybackSampleNumber = sampleNum; // Advances the currentPlayback number to sampleNum 390 } 391 void seek(int32 baseLayerSampleNum); // Seeks to the base-layer sample in the hint track 392 393 394 // TS offset value for the start of the media track. The STTS 395 // Atom only holds TS deltas. For a track that does not begin at 0s, we need to hold an 396 // offset timestamp value. 397 void setTrackTSOffset(uint32 ts) 398 { 399 _trackStartTSOffset = ts; 400 } 401 402 int32 updateFileSize(uint32 filesize); 403 404 uint32 getSampleDescriptionIndex() 405 { 406 return _SDIndex; 407 } 408 409 int32 getNextBundledAccessUnits(uint32 *n, 410 GAU *pgau); 411 412 int32 peekNextBundledAccessUnits(uint32 *n, 413 MediaMetaInfo *mInfo); 414 415 int32 getNextNSamples(uint32 startSampleNum, 416 uint32 *n, 417 GAU *pgau); 418 419 420 int32 peekNextNSamples(uint32 startSampleNum, 421 uint32 *n, 422 MediaMetaInfo *mInfo); 423 424 uint32 getSampleCount() 425 { 426 if (_psampleSizeAtom != NULL) 427 { 428 return (_psampleSizeAtom->getSampleCount()); 429 } 430 else 431 { 432 return 0; 433 } 434 } 435 436 bool IsSyncSample(uint32 sampleNum) 437 { 438 if (_psyncSampleAtom != NULL) 439 { 440 return (_psyncSampleAtom->IsSyncSample(sampleNum)); 441 } 442 else 443 { 444 return false; 445 } 446 } 447 448 uint32 getNumKeyFrames() 449 { 450 if (_psyncSampleAtom != NULL) 451 { 452 return (_psyncSampleAtom->getEntryCount()); 453 } 454 else 455 { 456 if (_psampleSizeAtom != NULL) 457 { 458 return (_psampleSizeAtom->getSampleCount()); 459 } 460 else 461 return 0; 462 } 463 } 464 SampleEntry *getTextSampleEntryAt(uint32 index) 465 { 466 if (_psampleDescriptionAtom != NULL) 467 { 468 return (_psampleDescriptionAtom->getTextSampleEntryAt(index)); 469 } 470 else 471 { 472 return NULL; 473 } 474 } 475 476 int32 getOffsetByTime(uint32 ts, int32* sampleFileOffset); 477 478 int32 getNumAMRFramesPerSample() 479 { 480 return _numAMRFramesPerSample; 481 } 482 483 MP4_ERROR_CODE getMaxTrackTimeStamp(uint32 fileSize, uint32& timeStamp); 484 485 MP4_ERROR_CODE getSampleNumberClosestToTimeStamp(uint32 &sampleNumber, 486 uint32 timeStamp, 487 uint32 sampleOffset = 0); 488 489 AVCSampleEntry* getAVCSampleEntry(uint32 index) 490 { 491 if (_psampleDescriptionAtom != NULL) 492 { 493 return (_psampleDescriptionAtom->getAVCSampleEntry(index)); 494 } 495 return (NULL); 496 } 497 498 uint32 getAVCNALLengthSize(uint32 index) 499 { 500 if (_psampleDescriptionAtom != NULL) 501 { 502 return (_psampleDescriptionAtom->getAVCNALLengthSize(index)); 503 } 504 return 0; 505 } 506 507 uint32 getNumAVCSampleEntries() 508 { 509 if (_psampleDescriptionAtom != NULL) 510 { 511 return (_psampleDescriptionAtom->getNumAVCSampleEntries()); 512 } 513 return 0; 514 } 515 bool isMultipleSampleDescriptionAvailable() 516 { 517 return _oMultipleSampleDescription; 518 } 519 520 int32 getSample(uint32 sampleNum, uint8 *buf, int32 &size, uint32 &index, uint32 &SampleOffset); 521 int32 getTimestampForRandomAccessPointsBeforeAfter(uint32 ts, uint32 *tsBuf, uint32* numBuf, 522 uint32& numsamplestoget, 523 uint32 howManyKeySamples); 524 525 uint32 getTrackLevelOMA2DRMInfoSize() 526 { 527 if (_psampleDescriptionAtom != NULL) 528 { 529 return (_psampleDescriptionAtom->getTrackLevelOMA2DRMInfoSize()); 530 } 531 return 0; 532 } 533 534 uint8* getTrackLevelOMA2DRMInfo() 535 { 536 if (_psampleDescriptionAtom != NULL) 537 { 538 return (_psampleDescriptionAtom->getTrackLevelOMA2DRMInfo()); 539 } 540 return NULL; 541 } 542 543 private: 544 545 TimeToSampleAtom *_ptimeToSampleAtom; 546 CompositionOffsetAtom *_pcompositionOffsetAtom; 547 SampleDescriptionAtom *_psampleDescriptionAtom; 548 SampleSizeAtom *_psampleSizeAtom; 549 SampleToChunkAtom *_psampleToChunkAtom; 550 ChunkOffsetAtom *_pchunkOffsetAtom; 551 AVCSampleDependencyType *_pavcSampleDependencyType; 552 AVCSampleToGroup *_pavcSampleToGroup; 553 AVCSampleDependency *_pavcSampleDependency; 554 555 // Optional member atoms 556 SyncSampleAtom *_psyncSampleAtom; 557 558 uint32 _currentPlaybackSampleTimestamp; 559 int32 _currentPlaybackSampleNumber; 560 561 // TS offset value for the start of the media track. The STTS 562 // Atom only holds TS deltas. For a track that does not begin at 0s, we need to hold an 563 // offset timestamp value. 564 uint32 _trackStartTSOffset; 565 566 uint32 _SDIndex; 567 568 OSCL_wHeapString<OsclMemAllocator> _filename; 569 MP4_FF_FILE *_pinput; 570 571 uint32 _fileSize; 572 uint32 _IsUpdateFileSize; 573 574 int32 _numAMRFramesPerSample; 575 576 uint8 *_pAMRTempBuffer; 577 bool _oResidualSample; 578 int32 _remainingFramesInSample; 579 uint32 _amrTempBufferOffset; 580 int32 _amrFrameDelta; 581 int32 _amrFrameTimeStamp; 582 int32 _amrSampleSize; 583 584 uint32 SamplesCount; 585 MP4_FF_FILE *_commonFilePtr; 586 587 bool _oPVContentDownloadable; 588 uint32 _parsingMode; 589 PVLogger *iLogger, *iStateVarLogger, *iParsedDataLogger, *iDiagnosticsLogger; 590 bool _oMultipleSampleDescription; 591 592 OSCL_wStackString<16> _defaultMimeType; 593 uint32 _currChunkOffset; 594 595}; 596 597#endif // SAMPLETABLEATOM_H_INCLUDED 598 599