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 MediaInformationAtom Class                       */
21/*     -------------------------------------------------------------------       */
22/*********************************************************************************/
23/*
24    This MediaInformationAtom Class contains all the objects that declare
25    characteristic information about the media data within the stream.
26*/
27
28
29#ifndef MEDIAINFORMATIONATOM_H_INCLUDED
30#define MEDIAINFORMATIONATOM_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 MEDIAINFORMATIONHEADERATOM_H_INCLUDED
41#include "mediainformationheaderatom.h"
42#endif
43
44#ifndef DATAINFORMATIONATOM_H_INCLUDED
45#include "datainformationatom.h"
46#endif
47
48#ifndef SAMPLETABLEATOM_H_INCLUDED
49#include "sampletableatom.h"
50#endif
51
52#ifndef ESDESCRIPTOR_H_INCLUDED
53#include "esdescriptor.h"
54#endif
55
56#ifndef OSCL_MEDIA_DATA_H_INCLUDED
57#include "oscl_media_data.h"
58#endif
59
60#ifndef PV_GAU_H_INCLUDED
61#include "pv_gau.h"
62#endif
63
64class AVCSampleEntry;
65
66class MediaInformationAtom : public Atom
67{
68
69    public:
70        MediaInformationAtom(MP4_FF_FILE *fp,
71                             uint32 mediaType,
72                             OSCL_wString& filename,
73                             bool oPVContentDownloadable = false,
74                             uint32 parsingMode = 0);
75
76        virtual ~MediaInformationAtom();
77
78        // Member gets and creates
79        const MediaInformationHeaderAtom* getMediaInformationHeader() const
80        {
81            return _pmediaInformationHeader;
82        }
83
84        MediaInformationHeaderAtom* getMutableMediaInformationHeader()
85        {
86            return _pmediaInformationHeader;
87        }
88
89        const DataInformationAtom& getDataInformationAtom() const
90        {
91            return *_pdataInformationAtom;
92        }
93
94        const SampleTableAtom& getSampleTableAtom() const
95        {
96            return *_psampleTableAtom;
97        }
98
99        int32 getTimestampForRandomAccessPoints(uint32 *num, uint32 *tsBuf, uint32* numBuf, uint32* offsetBuf)
100        {
101            if (_psampleTableAtom != NULL)
102            {
103                return _psampleTableAtom->getTimestampForRandomAccessPoints(num, tsBuf, numBuf, offsetBuf);
104            }
105            else
106            {
107                return 0;
108            }
109        }
110
111        int32 getTimestampForRandomAccessPointsBeforeAfter(uint32 ts, uint32 *tsBuf, uint32* numBuf,
112                uint32& numsamplestoget,
113                uint32 howManyKeySamples)
114        {
115            if (_psampleTableAtom != NULL)
116            {
117                return _psampleTableAtom->getTimestampForRandomAccessPointsBeforeAfter(ts, tsBuf, numBuf, numsamplestoget, howManyKeySamples);
118            }
119            else
120            {
121                return 0;
122            }
123
124        }
125
126        // Get the type of SampleEntry in this track (MPEG_SAMPLE_ENTRY, VIDEO_SAMPLE_ENTRY , etc...)
127        uint32 getSampleProtocol()
128        {
129            if (_psampleTableAtom != NULL)
130            {
131                return _psampleTableAtom->getSampleProtocol();
132            }
133            else
134            {
135                return 0;
136            }
137        }
138
139        // Return the ESID for the track - undefined if a HINT track
140        uint32 getESID() const
141        {
142            if (_psampleTableAtom != NULL)
143            {
144                return _psampleTableAtom->getESID();
145            }
146            else
147            {
148                return 0;
149            }
150        }
151
152        // Return the first ESDescriptor for the track - undefined if a HINT track
153        const ESDescriptor *getESDescriptor() const
154        {
155            if (_psampleTableAtom != NULL)
156            {
157                return _psampleTableAtom->getESDescriptor();
158            }
159            else
160            {
161                return NULL;
162            }
163        }
164
165
166        int32 updateFileSize(uint32 filesize)
167        {
168            if (_psampleTableAtom != NULL)
169            {
170                return _psampleTableAtom->updateFileSize(filesize);
171            }
172            return DEFAULT_ERROR;
173        }
174
175        // Returns next video frame
176        int32 getNextSample(uint8 *buf, int32 &size, uint32 &index, uint32 &SampleOffset)
177        {
178            if (_psampleTableAtom == NULL)
179            {
180                return READ_SAMPLE_TABLE_ATOM_FAILED;
181            }
182            return _psampleTableAtom->getNextSample(buf, size, index, SampleOffset);
183        }
184
185        MP4_ERROR_CODE getKeyMediaSampleNumAt(uint32 aKeySampleNum,
186                                              GAU    *pgau)
187        {
188            if (_psampleTableAtom == NULL)
189            {
190                return READ_SAMPLE_TABLE_ATOM_FAILED;
191            }
192            return _psampleTableAtom->getKeyMediaSampleNumAt(aKeySampleNum, pgau);
193        }
194
195        uint32 getNumKeyFrames()
196        {
197            if (_psampleTableAtom != NULL)
198            {
199                return (_psampleTableAtom->getNumKeyFrames());
200            }
201            else
202            {
203                return 0;
204            }
205
206        }
207
208        int32 getPrevKeyMediaSample(uint32 inputtimestamp,
209                                    uint32 &aKeySampleNum,
210                                    uint32 *n,
211                                    GAU    *pgau)
212        {
213            if (_psampleTableAtom == NULL)
214            {
215                return READ_SAMPLE_TABLE_ATOM_FAILED;
216            }
217            return _psampleTableAtom->getPrevKeyMediaSample(inputtimestamp, aKeySampleNum, n, pgau);
218        }
219
220        int32 getNextKeyMediaSample(uint32 inputtimestamp,
221                                    uint32 &aKeySampleNum,
222                                    uint32 *n,
223                                    GAU    *pgau)
224        {
225            if (_psampleTableAtom == NULL)
226            {
227                return READ_SAMPLE_TABLE_ATOM_FAILED;
228            }
229            return _psampleTableAtom->getNextKeyMediaSample(inputtimestamp, aKeySampleNum, n, pgau);
230        }
231
232        int32 getMediaSample(uint32 sampleNumber, uint8 *buf, int32 &size, uint32 &index, uint32 &SampleOffset)
233        {
234            if (_psampleTableAtom == NULL)
235            {
236                return READ_SAMPLE_TABLE_ATOM_FAILED;
237            }
238            return _psampleTableAtom->getSample(sampleNumber, buf, size, index, SampleOffset);
239        }
240
241        int32 getOffsetByTime(uint32 ts, int32* sampleFileOffset)
242        {
243            if (_psampleTableAtom == NULL)
244            {
245                return DEFAULT_ERROR;
246            }
247            return _psampleTableAtom->getOffsetByTime(ts, sampleFileOffset);
248        }
249
250        void resetPlayBack()
251        {
252            if (_psampleTableAtom != NULL)
253            {
254                _psampleTableAtom->resetPlayBack();
255            }
256        }
257
258        void resetTrackToEOT()
259        {
260            if (_psampleTableAtom != NULL)
261            {
262                _psampleTableAtom->resetTrackToEOT();
263            }
264        }
265
266        int32 resetPlayBack(int32 time, bool oDependsOn)
267        {
268            if (_psampleTableAtom != NULL)
269            {
270                return _psampleTableAtom->resetPlayBackbyTime(time, oDependsOn);
271            }
272            else
273            {
274                return 0;
275            }
276        }
277
278        int32 queryRepositionTime(int32 time, bool oDependsOn, bool bBeforeRequestedTime)
279        {
280            if (_psampleTableAtom != NULL)
281            {
282                return _psampleTableAtom->queryRepositionTime(time, oDependsOn, bBeforeRequestedTime);
283            }
284            else
285            {
286                return 0;
287            }
288        }
289
290
291        int32 IsResetNeeded(int32 time)
292        {
293            if (_psampleTableAtom == NULL)
294                return READ_SAMPLE_TABLE_ATOM_FAILED;
295            return _psampleTableAtom->IsResetNeeded(time);
296        }
297
298        uint32 getTimestampForSampleNumber(uint32 sampleNumber)
299        {
300            if (_psampleTableAtom != NULL)
301            {
302                return _psampleTableAtom->getTimestampForSampleNumber(sampleNumber);
303            }
304            else
305            {
306                return 0;
307            }
308        }
309
310        int32 getSampleSizeAt(int32 sampleNum)
311        {
312            if (_psampleTableAtom != NULL)
313            {
314                return   _psampleTableAtom->getSampleSizeAt(sampleNum);
315            }
316            else
317            {
318                return 0;
319            }
320        }
321
322        // Returns the timestamp  from the last video sample
323        // This is mainly to be used when seeking in the bitstream - you request a video frame at timestamp
324        // X, but the actual frame you get is Y, this method returns the timestamp for Y so you know which
325        // audio sample to request.
326        int32 getTimestampForCurrentSample()
327        {
328            if (_psampleTableAtom != NULL)
329            {
330                return _psampleTableAtom->getTimestampForCurrentSample();
331            }
332            else
333            {
334                return 0;
335            }
336        }
337
338        // Returns the sample number of the last samplle returned
339        // Used when requesting a hint sample for a specific randomly accessed sample
340        int32 getSampleNumberForCurrentSample()
341        {
342            if (_psampleTableAtom != NULL)
343            {
344                return _psampleTableAtom->getSampleNumberForCurrentSample();
345            }
346            else
347            {
348                return 0;
349            }
350        }
351
352        void advance()
353        {
354            if (_psampleTableAtom != NULL)
355            {
356                _psampleTableAtom->advance();
357            }
358        } // Advances the currentPlayback number
359
360        void advance(int32 sampleNum)
361        {
362            if (_psampleTableAtom != NULL)
363            {
364                _psampleTableAtom->advance(sampleNum);
365            }
366        } // Advances the currentPlayback number to sampleNum
367
368        void seek(int32 baseLayerSampleNum)
369        {
370            if (_psampleTableAtom != NULL)
371            {
372                _psampleTableAtom->seek(baseLayerSampleNum);
373            }
374        } // Seeks to the base-layer sample in the hint track
375
376        uint32 getNumSampleEntries()
377        {
378            if (_psampleTableAtom != NULL)
379            {
380                return _psampleTableAtom->getNumSampleEntries();
381            }
382            else
383            {
384                return 0;
385            }
386        }
387
388        // Getting and setting the Mpeg4 VOL header
389        DecoderSpecificInfo *getDecoderSpecificInfo() const
390        {
391            if (_psampleTableAtom != NULL)
392            {
393                return _psampleTableAtom->getDecoderSpecificInfo();
394            }
395            else
396            {
397                return NULL;
398            }
399        }
400
401        DecoderSpecificInfo *getDecoderSpecificInfoForSDI(uint32 index) const
402        {
403            if (_psampleTableAtom != NULL)
404            {
405                return _psampleTableAtom->getDecoderSpecificInfoForSDI(index);
406            }
407            else
408            {
409                return NULL;
410            }
411        }
412
413        void getMIMEType(OSCL_String& aMimeType)
414        {
415            if (_psampleTableAtom != NULL)
416            {
417                _psampleTableAtom->getMIMEType(aMimeType);
418            }
419        }
420
421        uint8  getObjectTypeIndication()
422        {
423            if (_psampleTableAtom != NULL)
424            {
425                return _psampleTableAtom->getObjectTypeIndication();
426            }
427            else
428            {
429                return (0xFF);
430            }
431        }
432
433        uint32 getMaxBufferSizeDB() const
434        {
435            if (_psampleTableAtom != NULL)
436            {
437                return _psampleTableAtom->getMaxBufferSizeDB();
438            }
439            else
440            {
441                return 0;
442            }
443        }
444
445        int32 getAverageBitrate()
446        {
447            if (_psampleTableAtom != NULL)
448            {
449                return _psampleTableAtom->getAverageBitrate();
450            }
451            else
452            {
453                return 0;
454            }
455        }
456
457        int32 getHeight()
458        {
459            if (_psampleTableAtom != NULL)
460            {
461                return _psampleTableAtom->getHeight();
462            }
463            else
464            {
465                return 0;
466            }
467
468        }
469
470        int32 getWidth()
471        {
472            if (_psampleTableAtom != NULL)
473            {
474                return _psampleTableAtom->getWidth();
475            }
476            else
477            {
478                return 0;
479            }
480        }
481
482        //PASP Box
483        uint32 getHspacing()
484        {
485            if (_psampleTableAtom != NULL)
486            {
487                return _psampleTableAtom->getHspacing();
488            }
489            else
490            {
491                return 0;
492            }
493        }
494
495        uint32 getVspacing()
496        {
497            if (_psampleTableAtom != NULL)
498            {
499                return _psampleTableAtom->getVspacing();
500            }
501            else
502            {
503                return 0;
504            }
505        }
506
507        // TS offset value for the start of the media track.  The STTS
508        // Atom only holds TS deltas.  For a track that does not begin at 0s, we need to hold an
509        // offset timestamp value.
510        void setTrackTSOffset(uint32 ts)
511        {
512            _trackStartOffset = ts;
513
514            if (_psampleTableAtom != NULL)
515            {
516                _psampleTableAtom->setTrackTSOffset(ts);
517            }
518        }
519
520        uint32 getSampleDescriptionIndex()
521        {
522            if (_psampleTableAtom != NULL)
523            {
524                return _psampleTableAtom->getSampleDescriptionIndex();
525            }
526            else
527            {
528                return 0;
529            }
530        }
531
532        int32 getNextBundledAccessUnits(uint32 *n,
533                                        GAU    *pgau)
534        {
535            if (_psampleTableAtom != NULL)
536            {
537                return _psampleTableAtom->getNextBundledAccessUnits(n, pgau);
538            }
539            else
540            {
541                return -1;
542            }
543        }
544
545        int32 peekNextBundledAccessUnits(uint32 *n,
546                                         MediaMetaInfo *mInfo)
547        {
548            if (_psampleTableAtom != NULL)
549            {
550                return _psampleTableAtom->peekNextBundledAccessUnits(n, mInfo);
551            }
552            else
553            {
554                return -1;
555            }
556        }
557
558        uint32 getSampleCount()
559        {
560            if (_psampleTableAtom != NULL)
561            {
562                return (_psampleTableAtom->getSampleCount());
563            }
564            else
565            {
566                return 0;
567            }
568        }
569
570        SampleEntry *getTextSampleEntryAt(uint32 index)
571        {
572            if (_psampleTableAtom != NULL)
573            {
574                return (_psampleTableAtom-> getTextSampleEntryAt(index));
575            }
576            else
577            {
578                return NULL;
579            }
580        }
581
582        int32 getNumAMRFramesPerSample()
583        {
584            if (_psampleTableAtom != NULL)
585            {
586                return (_psampleTableAtom->getNumAMRFramesPerSample());
587            }
588            else
589            {
590                return 0;
591            }
592        }
593
594        MP4_ERROR_CODE getMaxTrackTimeStamp(uint32 fileSize, uint32& timeStamp)
595        {
596            if (_psampleTableAtom != NULL)
597            {
598                return (_psampleTableAtom->getMaxTrackTimeStamp(fileSize, timeStamp));
599            }
600            else
601            {
602                return DEFAULT_ERROR;
603            }
604        }
605
606        MP4_ERROR_CODE getSampleNumberClosestToTimeStamp(uint32 &sampleNumber,
607                uint32 timeStamp,
608                uint32 sampleOffset = 0)
609        {
610            if (_psampleTableAtom != NULL)
611            {
612                return
613                    (_psampleTableAtom->getSampleNumberClosestToTimeStamp(sampleNumber,
614                            timeStamp,
615                            sampleOffset));
616            }
617            else
618            {
619                return (READ_FAILED);
620            }
621        }
622
623        AVCSampleEntry* getAVCSampleEntry(uint32 index)
624        {
625            if (_psampleTableAtom != NULL)
626            {
627                return (_psampleTableAtom->getAVCSampleEntry(index));
628            }
629            return (NULL);
630        }
631
632        uint32 getAVCNALLengthSize(uint32 index)
633        {
634            if (_psampleTableAtom != NULL)
635            {
636                return (_psampleTableAtom->getAVCNALLengthSize(index));
637            }
638            return 0;
639        }
640
641        uint32 getNumAVCSampleEntries()
642        {
643            if (_psampleTableAtom != NULL)
644            {
645                return (_psampleTableAtom->getNumAVCSampleEntries());
646            }
647            return 0;
648        }
649
650        uint32 getTrackLevelOMA2DRMInfoSize()
651        {
652            if (_psampleTableAtom != NULL)
653            {
654                return (_psampleTableAtom->getTrackLevelOMA2DRMInfoSize());
655            }
656            return 0;
657        }
658
659        uint8* getTrackLevelOMA2DRMInfo()
660        {
661            if (_psampleTableAtom != NULL)
662            {
663                return (_psampleTableAtom->getTrackLevelOMA2DRMInfo());
664            }
665            return NULL;
666        }
667
668        bool isMultipleSampleDescriptionAvailable()
669        {
670            if (_psampleTableAtom != NULL)
671            {
672                return (_psampleTableAtom->isMultipleSampleDescriptionAvailable());
673            }
674            return 0;
675        }
676
677    private:
678
679        // This is actually a pointer to the base class.  The possible
680        // derived classes include VideoMediaHeaderAtom, SoundMediaHeaderAtom,
681        // HintMediaHeaderAtom, and Mpeg4MediaHeaderAtom.
682        MediaInformationHeaderAtom *_pmediaInformationHeader;
683        DataInformationAtom        *_pdataInformationAtom;
684        SampleTableAtom            *_psampleTableAtom;
685
686        uint32 _trackStartOffset;
687
688};
689
690#endif // MEDIAINFORMATIONATOM_H_INCLUDED
691
692