MPEG4Extractor.cpp revision 4ff2a0dbb178c4ea652f30aa4f1d3deb9fdbc832
1/*
2 * Copyright (C) 2009 The Android Open Source Project
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 express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17//#define LOG_NDEBUG 0
18#define LOG_TAG "MPEG4Extractor"
19
20#include <ctype.h>
21#include <inttypes.h>
22#include <stdint.h>
23#include <stdlib.h>
24#include <string.h>
25
26#include <utils/Log.h>
27
28#include "include/MPEG4Extractor.h"
29#include "include/SampleTable.h"
30#include "include/ESDS.h"
31
32#include <media/stagefright/foundation/ABitReader.h>
33#include <media/stagefright/foundation/ABuffer.h>
34#include <media/stagefright/foundation/ADebug.h>
35#include <media/stagefright/foundation/AMessage.h>
36#include <media/stagefright/MediaBuffer.h>
37#include <media/stagefright/MediaBufferGroup.h>
38#include <media/stagefright/MediaDefs.h>
39#include <media/stagefright/MediaSource.h>
40#include <media/stagefright/MetaData.h>
41#include <utils/String8.h>
42
43#include <byteswap.h>
44#include "include/ID3.h"
45
46namespace android {
47
48class MPEG4Source : public MediaSource {
49public:
50    // Caller retains ownership of both "dataSource" and "sampleTable".
51    MPEG4Source(const sp<MetaData> &format,
52                const sp<DataSource> &dataSource,
53                int32_t timeScale,
54                const sp<SampleTable> &sampleTable,
55                Vector<SidxEntry> &sidx,
56                const Trex *trex,
57                off64_t firstMoofOffset);
58
59    virtual status_t start(MetaData *params = NULL);
60    virtual status_t stop();
61
62    virtual sp<MetaData> getFormat();
63
64    virtual status_t read(MediaBuffer **buffer, const ReadOptions *options = NULL);
65    virtual status_t fragmentedRead(MediaBuffer **buffer, const ReadOptions *options = NULL);
66
67protected:
68    virtual ~MPEG4Source();
69
70private:
71    Mutex mLock;
72
73    sp<MetaData> mFormat;
74    sp<DataSource> mDataSource;
75    int32_t mTimescale;
76    sp<SampleTable> mSampleTable;
77    uint32_t mCurrentSampleIndex;
78    uint32_t mCurrentFragmentIndex;
79    Vector<SidxEntry> &mSegments;
80    const Trex *mTrex;
81    off64_t mFirstMoofOffset;
82    off64_t mCurrentMoofOffset;
83    off64_t mNextMoofOffset;
84    uint32_t mCurrentTime;
85    int32_t mLastParsedTrackId;
86    int32_t mTrackId;
87
88    int32_t mCryptoMode;    // passed in from extractor
89    int32_t mDefaultIVSize; // passed in from extractor
90    uint8_t mCryptoKey[16]; // passed in from extractor
91    uint32_t mCurrentAuxInfoType;
92    uint32_t mCurrentAuxInfoTypeParameter;
93    int32_t mCurrentDefaultSampleInfoSize;
94    uint32_t mCurrentSampleInfoCount;
95    uint32_t mCurrentSampleInfoAllocSize;
96    uint8_t* mCurrentSampleInfoSizes;
97    uint32_t mCurrentSampleInfoOffsetCount;
98    uint32_t mCurrentSampleInfoOffsetsAllocSize;
99    uint64_t* mCurrentSampleInfoOffsets;
100
101    bool mIsAVC;
102    bool mIsHEVC;
103    size_t mNALLengthSize;
104
105    bool mStarted;
106
107    MediaBufferGroup *mGroup;
108
109    MediaBuffer *mBuffer;
110
111    bool mWantsNALFragments;
112
113    uint8_t *mSrcBuffer;
114
115    size_t parseNALSize(const uint8_t *data) const;
116    status_t parseChunk(off64_t *offset);
117    status_t parseTrackFragmentHeader(off64_t offset, off64_t size);
118    status_t parseTrackFragmentRun(off64_t offset, off64_t size);
119    status_t parseSampleAuxiliaryInformationSizes(off64_t offset, off64_t size);
120    status_t parseSampleAuxiliaryInformationOffsets(off64_t offset, off64_t size);
121
122    struct TrackFragmentHeaderInfo {
123        enum Flags {
124            kBaseDataOffsetPresent         = 0x01,
125            kSampleDescriptionIndexPresent = 0x02,
126            kDefaultSampleDurationPresent  = 0x08,
127            kDefaultSampleSizePresent      = 0x10,
128            kDefaultSampleFlagsPresent     = 0x20,
129            kDurationIsEmpty               = 0x10000,
130        };
131
132        uint32_t mTrackID;
133        uint32_t mFlags;
134        uint64_t mBaseDataOffset;
135        uint32_t mSampleDescriptionIndex;
136        uint32_t mDefaultSampleDuration;
137        uint32_t mDefaultSampleSize;
138        uint32_t mDefaultSampleFlags;
139
140        uint64_t mDataOffset;
141    };
142    TrackFragmentHeaderInfo mTrackFragmentHeaderInfo;
143
144    struct Sample {
145        off64_t offset;
146        size_t size;
147        uint32_t duration;
148        int32_t compositionOffset;
149        uint8_t iv[16];
150        Vector<size_t> clearsizes;
151        Vector<size_t> encryptedsizes;
152    };
153    Vector<Sample> mCurrentSamples;
154
155    MPEG4Source(const MPEG4Source &);
156    MPEG4Source &operator=(const MPEG4Source &);
157};
158
159// This custom data source wraps an existing one and satisfies requests
160// falling entirely within a cached range from the cache while forwarding
161// all remaining requests to the wrapped datasource.
162// This is used to cache the full sampletable metadata for a single track,
163// possibly wrapping multiple times to cover all tracks, i.e.
164// Each MPEG4DataSource caches the sampletable metadata for a single track.
165
166struct MPEG4DataSource : public DataSource {
167    MPEG4DataSource(const sp<DataSource> &source);
168
169    virtual status_t initCheck() const;
170    virtual ssize_t readAt(off64_t offset, void *data, size_t size);
171    virtual status_t getSize(off64_t *size);
172    virtual uint32_t flags();
173
174    status_t setCachedRange(off64_t offset, size_t size);
175
176protected:
177    virtual ~MPEG4DataSource();
178
179private:
180    Mutex mLock;
181
182    sp<DataSource> mSource;
183    off64_t mCachedOffset;
184    size_t mCachedSize;
185    uint8_t *mCache;
186
187    void clearCache();
188
189    MPEG4DataSource(const MPEG4DataSource &);
190    MPEG4DataSource &operator=(const MPEG4DataSource &);
191};
192
193MPEG4DataSource::MPEG4DataSource(const sp<DataSource> &source)
194    : mSource(source),
195      mCachedOffset(0),
196      mCachedSize(0),
197      mCache(NULL) {
198}
199
200MPEG4DataSource::~MPEG4DataSource() {
201    clearCache();
202}
203
204void MPEG4DataSource::clearCache() {
205    if (mCache) {
206        free(mCache);
207        mCache = NULL;
208    }
209
210    mCachedOffset = 0;
211    mCachedSize = 0;
212}
213
214status_t MPEG4DataSource::initCheck() const {
215    return mSource->initCheck();
216}
217
218ssize_t MPEG4DataSource::readAt(off64_t offset, void *data, size_t size) {
219    Mutex::Autolock autoLock(mLock);
220
221    if (offset >= mCachedOffset
222            && offset + size <= mCachedOffset + mCachedSize) {
223        memcpy(data, &mCache[offset - mCachedOffset], size);
224        return size;
225    }
226
227    return mSource->readAt(offset, data, size);
228}
229
230status_t MPEG4DataSource::getSize(off64_t *size) {
231    return mSource->getSize(size);
232}
233
234uint32_t MPEG4DataSource::flags() {
235    return mSource->flags();
236}
237
238status_t MPEG4DataSource::setCachedRange(off64_t offset, size_t size) {
239    Mutex::Autolock autoLock(mLock);
240
241    clearCache();
242
243    mCache = (uint8_t *)malloc(size);
244
245    if (mCache == NULL) {
246        return -ENOMEM;
247    }
248
249    mCachedOffset = offset;
250    mCachedSize = size;
251
252    ssize_t err = mSource->readAt(mCachedOffset, mCache, mCachedSize);
253
254    if (err < (ssize_t)size) {
255        clearCache();
256
257        return ERROR_IO;
258    }
259
260    return OK;
261}
262
263////////////////////////////////////////////////////////////////////////////////
264
265static void hexdump(const void *_data, size_t size) {
266    const uint8_t *data = (const uint8_t *)_data;
267    size_t offset = 0;
268    while (offset < size) {
269        printf("0x%04zx  ", offset);
270
271        size_t n = size - offset;
272        if (n > 16) {
273            n = 16;
274        }
275
276        for (size_t i = 0; i < 16; ++i) {
277            if (i == 8) {
278                printf(" ");
279            }
280
281            if (offset + i < size) {
282                printf("%02x ", data[offset + i]);
283            } else {
284                printf("   ");
285            }
286        }
287
288        printf(" ");
289
290        for (size_t i = 0; i < n; ++i) {
291            if (isprint(data[offset + i])) {
292                printf("%c", data[offset + i]);
293            } else {
294                printf(".");
295            }
296        }
297
298        printf("\n");
299
300        offset += 16;
301    }
302}
303
304static const char *FourCC2MIME(uint32_t fourcc) {
305    switch (fourcc) {
306        case FOURCC('m', 'p', '4', 'a'):
307            return MEDIA_MIMETYPE_AUDIO_AAC;
308
309        case FOURCC('s', 'a', 'm', 'r'):
310            return MEDIA_MIMETYPE_AUDIO_AMR_NB;
311
312        case FOURCC('s', 'a', 'w', 'b'):
313            return MEDIA_MIMETYPE_AUDIO_AMR_WB;
314
315        case FOURCC('m', 'p', '4', 'v'):
316            return MEDIA_MIMETYPE_VIDEO_MPEG4;
317
318        case FOURCC('s', '2', '6', '3'):
319        case FOURCC('h', '2', '6', '3'):
320        case FOURCC('H', '2', '6', '3'):
321            return MEDIA_MIMETYPE_VIDEO_H263;
322
323        case FOURCC('a', 'v', 'c', '1'):
324            return MEDIA_MIMETYPE_VIDEO_AVC;
325
326        case FOURCC('h', 'v', 'c', '1'):
327        case FOURCC('h', 'e', 'v', '1'):
328            return MEDIA_MIMETYPE_VIDEO_HEVC;
329        default:
330            CHECK(!"should not be here.");
331            return NULL;
332    }
333}
334
335static bool AdjustChannelsAndRate(uint32_t fourcc, uint32_t *channels, uint32_t *rate) {
336    if (!strcasecmp(MEDIA_MIMETYPE_AUDIO_AMR_NB, FourCC2MIME(fourcc))) {
337        // AMR NB audio is always mono, 8kHz
338        *channels = 1;
339        *rate = 8000;
340        return true;
341    } else if (!strcasecmp(MEDIA_MIMETYPE_AUDIO_AMR_WB, FourCC2MIME(fourcc))) {
342        // AMR WB audio is always mono, 16kHz
343        *channels = 1;
344        *rate = 16000;
345        return true;
346    }
347    return false;
348}
349
350MPEG4Extractor::MPEG4Extractor(const sp<DataSource> &source)
351    : mMoofOffset(0),
352      mDataSource(source),
353      mInitCheck(NO_INIT),
354      mHasVideo(false),
355      mHeaderTimescale(0),
356      mFirstTrack(NULL),
357      mLastTrack(NULL),
358      mFileMetaData(new MetaData),
359      mFirstSINF(NULL),
360      mIsDrm(false) {
361}
362
363MPEG4Extractor::~MPEG4Extractor() {
364    Track *track = mFirstTrack;
365    while (track) {
366        Track *next = track->next;
367
368        delete track;
369        track = next;
370    }
371    mFirstTrack = mLastTrack = NULL;
372
373    SINF *sinf = mFirstSINF;
374    while (sinf) {
375        SINF *next = sinf->next;
376        delete[] sinf->IPMPData;
377        delete sinf;
378        sinf = next;
379    }
380    mFirstSINF = NULL;
381
382    for (size_t i = 0; i < mPssh.size(); i++) {
383        delete [] mPssh[i].data;
384    }
385}
386
387uint32_t MPEG4Extractor::flags() const {
388    return CAN_PAUSE |
389            ((mMoofOffset == 0 || mSidxEntries.size() != 0) ?
390                    (CAN_SEEK_BACKWARD | CAN_SEEK_FORWARD | CAN_SEEK) : 0);
391}
392
393sp<MetaData> MPEG4Extractor::getMetaData() {
394    status_t err;
395    if ((err = readMetaData()) != OK) {
396        return new MetaData;
397    }
398
399    return mFileMetaData;
400}
401
402size_t MPEG4Extractor::countTracks() {
403    status_t err;
404    if ((err = readMetaData()) != OK) {
405        ALOGV("MPEG4Extractor::countTracks: no tracks");
406        return 0;
407    }
408
409    size_t n = 0;
410    Track *track = mFirstTrack;
411    while (track) {
412        ++n;
413        track = track->next;
414    }
415
416    ALOGV("MPEG4Extractor::countTracks: %zu tracks", n);
417    return n;
418}
419
420sp<MetaData> MPEG4Extractor::getTrackMetaData(
421        size_t index, uint32_t flags) {
422    status_t err;
423    if ((err = readMetaData()) != OK) {
424        return NULL;
425    }
426
427    Track *track = mFirstTrack;
428    while (index > 0) {
429        if (track == NULL) {
430            return NULL;
431        }
432
433        track = track->next;
434        --index;
435    }
436
437    if (track == NULL) {
438        return NULL;
439    }
440
441    if ((flags & kIncludeExtensiveMetaData)
442            && !track->includes_expensive_metadata) {
443        track->includes_expensive_metadata = true;
444
445        const char *mime;
446        CHECK(track->meta->findCString(kKeyMIMEType, &mime));
447        if (!strncasecmp("video/", mime, 6)) {
448            if (mMoofOffset > 0) {
449                int64_t duration;
450                if (track->meta->findInt64(kKeyDuration, &duration)) {
451                    // nothing fancy, just pick a frame near 1/4th of the duration
452                    track->meta->setInt64(
453                            kKeyThumbnailTime, duration / 4);
454                }
455            } else {
456                uint32_t sampleIndex;
457                uint32_t sampleTime;
458                if (track->sampleTable->findThumbnailSample(&sampleIndex) == OK
459                        && track->sampleTable->getMetaDataForSample(
460                            sampleIndex, NULL /* offset */, NULL /* size */,
461                            &sampleTime) == OK) {
462                    track->meta->setInt64(
463                            kKeyThumbnailTime,
464                            ((int64_t)sampleTime * 1000000) / track->timescale);
465                }
466            }
467        }
468    }
469
470    return track->meta;
471}
472
473static void MakeFourCCString(uint32_t x, char *s) {
474    s[0] = x >> 24;
475    s[1] = (x >> 16) & 0xff;
476    s[2] = (x >> 8) & 0xff;
477    s[3] = x & 0xff;
478    s[4] = '\0';
479}
480
481status_t MPEG4Extractor::readMetaData() {
482    if (mInitCheck != NO_INIT) {
483        return mInitCheck;
484    }
485
486    off64_t offset = 0;
487    status_t err;
488    while (true) {
489        off64_t orig_offset = offset;
490        err = parseChunk(&offset, 0);
491
492        if (err != OK && err != UNKNOWN_ERROR) {
493            break;
494        } else if (offset <= orig_offset) {
495            // only continue parsing if the offset was advanced,
496            // otherwise we might end up in an infinite loop
497            ALOGE("did not advance: 0x%lld->0x%lld", orig_offset, offset);
498            err = ERROR_MALFORMED;
499            break;
500        } else if (err == OK) {
501            continue;
502        }
503
504        uint32_t hdr[2];
505        if (mDataSource->readAt(offset, hdr, 8) < 8) {
506            break;
507        }
508        uint32_t chunk_type = ntohl(hdr[1]);
509        if (chunk_type == FOURCC('m', 'o', 'o', 'f')) {
510            // store the offset of the first segment
511            mMoofOffset = offset;
512        } else if (chunk_type != FOURCC('m', 'd', 'a', 't')) {
513            // keep parsing until we get to the data
514            continue;
515        }
516        break;
517    }
518
519    if (mInitCheck == OK) {
520        if (mHasVideo) {
521            mFileMetaData->setCString(
522                    kKeyMIMEType, MEDIA_MIMETYPE_CONTAINER_MPEG4);
523        } else {
524            mFileMetaData->setCString(kKeyMIMEType, "audio/mp4");
525        }
526    } else {
527        mInitCheck = err;
528    }
529
530    CHECK_NE(err, (status_t)NO_INIT);
531
532    // copy pssh data into file metadata
533    int psshsize = 0;
534    for (size_t i = 0; i < mPssh.size(); i++) {
535        psshsize += 20 + mPssh[i].datalen;
536    }
537    if (psshsize) {
538        char *buf = (char*)malloc(psshsize);
539        char *ptr = buf;
540        for (size_t i = 0; i < mPssh.size(); i++) {
541            memcpy(ptr, mPssh[i].uuid, 20); // uuid + length
542            memcpy(ptr + 20, mPssh[i].data, mPssh[i].datalen);
543            ptr += (20 + mPssh[i].datalen);
544        }
545        mFileMetaData->setData(kKeyPssh, 'pssh', buf, psshsize);
546        free(buf);
547    }
548    return mInitCheck;
549}
550
551char* MPEG4Extractor::getDrmTrackInfo(size_t trackID, int *len) {
552    if (mFirstSINF == NULL) {
553        return NULL;
554    }
555
556    SINF *sinf = mFirstSINF;
557    while (sinf && (trackID != sinf->trackID)) {
558        sinf = sinf->next;
559    }
560
561    if (sinf == NULL) {
562        return NULL;
563    }
564
565    *len = sinf->len;
566    return sinf->IPMPData;
567}
568
569// Reads an encoded integer 7 bits at a time until it encounters the high bit clear.
570static int32_t readSize(off64_t offset,
571        const sp<DataSource> DataSource, uint8_t *numOfBytes) {
572    uint32_t size = 0;
573    uint8_t data;
574    bool moreData = true;
575    *numOfBytes = 0;
576
577    while (moreData) {
578        if (DataSource->readAt(offset, &data, 1) < 1) {
579            return -1;
580        }
581        offset ++;
582        moreData = (data >= 128) ? true : false;
583        size = (size << 7) | (data & 0x7f); // Take last 7 bits
584        (*numOfBytes) ++;
585    }
586
587    return size;
588}
589
590status_t MPEG4Extractor::parseDrmSINF(
591        off64_t * /* offset */, off64_t data_offset) {
592    uint8_t updateIdTag;
593    if (mDataSource->readAt(data_offset, &updateIdTag, 1) < 1) {
594        return ERROR_IO;
595    }
596    data_offset ++;
597
598    if (0x01/*OBJECT_DESCRIPTOR_UPDATE_ID_TAG*/ != updateIdTag) {
599        return ERROR_MALFORMED;
600    }
601
602    uint8_t numOfBytes;
603    int32_t size = readSize(data_offset, mDataSource, &numOfBytes);
604    if (size < 0) {
605        return ERROR_IO;
606    }
607    int32_t classSize = size;
608    data_offset += numOfBytes;
609
610    while(size >= 11 ) {
611        uint8_t descriptorTag;
612        if (mDataSource->readAt(data_offset, &descriptorTag, 1) < 1) {
613            return ERROR_IO;
614        }
615        data_offset ++;
616
617        if (0x11/*OBJECT_DESCRIPTOR_ID_TAG*/ != descriptorTag) {
618            return ERROR_MALFORMED;
619        }
620
621        uint8_t buffer[8];
622        //ObjectDescriptorID and ObjectDescriptor url flag
623        if (mDataSource->readAt(data_offset, buffer, 2) < 2) {
624            return ERROR_IO;
625        }
626        data_offset += 2;
627
628        if ((buffer[1] >> 5) & 0x0001) { //url flag is set
629            return ERROR_MALFORMED;
630        }
631
632        if (mDataSource->readAt(data_offset, buffer, 8) < 8) {
633            return ERROR_IO;
634        }
635        data_offset += 8;
636
637        if ((0x0F/*ES_ID_REF_TAG*/ != buffer[1])
638                || ( 0x0A/*IPMP_DESCRIPTOR_POINTER_ID_TAG*/ != buffer[5])) {
639            return ERROR_MALFORMED;
640        }
641
642        SINF *sinf = new SINF;
643        sinf->trackID = U16_AT(&buffer[3]);
644        sinf->IPMPDescriptorID = buffer[7];
645        sinf->next = mFirstSINF;
646        mFirstSINF = sinf;
647
648        size -= (8 + 2 + 1);
649    }
650
651    if (size != 0) {
652        return ERROR_MALFORMED;
653    }
654
655    if (mDataSource->readAt(data_offset, &updateIdTag, 1) < 1) {
656        return ERROR_IO;
657    }
658    data_offset ++;
659
660    if(0x05/*IPMP_DESCRIPTOR_UPDATE_ID_TAG*/ != updateIdTag) {
661        return ERROR_MALFORMED;
662    }
663
664    size = readSize(data_offset, mDataSource, &numOfBytes);
665    if (size < 0) {
666        return ERROR_IO;
667    }
668    classSize = size;
669    data_offset += numOfBytes;
670
671    while (size > 0) {
672        uint8_t tag;
673        int32_t dataLen;
674        if (mDataSource->readAt(data_offset, &tag, 1) < 1) {
675            return ERROR_IO;
676        }
677        data_offset ++;
678
679        if (0x0B/*IPMP_DESCRIPTOR_ID_TAG*/ == tag) {
680            uint8_t id;
681            dataLen = readSize(data_offset, mDataSource, &numOfBytes);
682            if (dataLen < 0) {
683                return ERROR_IO;
684            } else if (dataLen < 4) {
685                return ERROR_MALFORMED;
686            }
687            data_offset += numOfBytes;
688
689            if (mDataSource->readAt(data_offset, &id, 1) < 1) {
690                return ERROR_IO;
691            }
692            data_offset ++;
693
694            SINF *sinf = mFirstSINF;
695            while (sinf && (sinf->IPMPDescriptorID != id)) {
696                sinf = sinf->next;
697            }
698            if (sinf == NULL) {
699                return ERROR_MALFORMED;
700            }
701            sinf->len = dataLen - 3;
702            sinf->IPMPData = new (std::nothrow) char[sinf->len];
703            if (sinf->IPMPData == NULL) {
704                return ERROR_MALFORMED;
705            }
706            data_offset += 2;
707
708            if (mDataSource->readAt(data_offset, sinf->IPMPData, sinf->len) < sinf->len) {
709                return ERROR_IO;
710            }
711            data_offset += sinf->len;
712
713            size -= (dataLen + numOfBytes + 1);
714        }
715    }
716
717    if (size != 0) {
718        return ERROR_MALFORMED;
719    }
720
721    return UNKNOWN_ERROR;  // Return a dummy error.
722}
723
724struct PathAdder {
725    PathAdder(Vector<uint32_t> *path, uint32_t chunkType)
726        : mPath(path) {
727        mPath->push(chunkType);
728    }
729
730    ~PathAdder() {
731        mPath->pop();
732    }
733
734private:
735    Vector<uint32_t> *mPath;
736
737    PathAdder(const PathAdder &);
738    PathAdder &operator=(const PathAdder &);
739};
740
741static bool underMetaDataPath(const Vector<uint32_t> &path) {
742    return path.size() >= 5
743        && path[0] == FOURCC('m', 'o', 'o', 'v')
744        && path[1] == FOURCC('u', 'd', 't', 'a')
745        && path[2] == FOURCC('m', 'e', 't', 'a')
746        && path[3] == FOURCC('i', 'l', 's', 't');
747}
748
749// Given a time in seconds since Jan 1 1904, produce a human-readable string.
750static void convertTimeToDate(int64_t time_1904, String8 *s) {
751    time_t time_1970 = time_1904 - (((66 * 365 + 17) * 24) * 3600);
752
753    char tmp[32];
754    strftime(tmp, sizeof(tmp), "%Y%m%dT%H%M%S.000Z", gmtime(&time_1970));
755
756    s->setTo(tmp);
757}
758
759status_t MPEG4Extractor::parseChunk(off64_t *offset, int depth) {
760    ALOGV("entering parseChunk %lld/%d", *offset, depth);
761    uint32_t hdr[2];
762    if (mDataSource->readAt(*offset, hdr, 8) < 8) {
763        return ERROR_IO;
764    }
765    uint64_t chunk_size = ntohl(hdr[0]);
766    uint32_t chunk_type = ntohl(hdr[1]);
767    off64_t data_offset = *offset + 8;
768
769    if (chunk_size == 1) {
770        if (mDataSource->readAt(*offset + 8, &chunk_size, 8) < 8) {
771            return ERROR_IO;
772        }
773        chunk_size = ntoh64(chunk_size);
774        data_offset += 8;
775
776        if (chunk_size < 16) {
777            // The smallest valid chunk is 16 bytes long in this case.
778            return ERROR_MALFORMED;
779        }
780    } else if (chunk_size == 0) {
781        if (depth == 0) {
782            // atom extends to end of file
783            off64_t sourceSize;
784            if (mDataSource->getSize(&sourceSize) == OK) {
785                chunk_size = (sourceSize - *offset);
786            } else {
787                // XXX could we just pick a "sufficiently large" value here?
788                ALOGE("atom size is 0, and data source has no size");
789                return ERROR_MALFORMED;
790            }
791        } else {
792            // not allowed for non-toplevel atoms, skip it
793            *offset += 4;
794            return OK;
795        }
796    } else if (chunk_size < 8) {
797        // The smallest valid chunk is 8 bytes long.
798        ALOGE("invalid chunk size: %" PRIu64, chunk_size);
799        return ERROR_MALFORMED;
800    }
801
802    char chunk[5];
803    MakeFourCCString(chunk_type, chunk);
804    ALOGV("chunk: %s @ %lld, %d", chunk, *offset, depth);
805
806#if 0
807    static const char kWhitespace[] = "                                        ";
808    const char *indent = &kWhitespace[sizeof(kWhitespace) - 1 - 2 * depth];
809    printf("%sfound chunk '%s' of size %" PRIu64 "\n", indent, chunk, chunk_size);
810
811    char buffer[256];
812    size_t n = chunk_size;
813    if (n > sizeof(buffer)) {
814        n = sizeof(buffer);
815    }
816    if (mDataSource->readAt(*offset, buffer, n)
817            < (ssize_t)n) {
818        return ERROR_IO;
819    }
820
821    hexdump(buffer, n);
822#endif
823
824    PathAdder autoAdder(&mPath, chunk_type);
825
826    off64_t chunk_data_size = *offset + chunk_size - data_offset;
827
828    if (chunk_type != FOURCC('c', 'p', 'r', 't')
829            && chunk_type != FOURCC('c', 'o', 'v', 'r')
830            && mPath.size() == 5 && underMetaDataPath(mPath)) {
831        off64_t stop_offset = *offset + chunk_size;
832        *offset = data_offset;
833        while (*offset < stop_offset) {
834            status_t err = parseChunk(offset, depth + 1);
835            if (err != OK) {
836                return err;
837            }
838        }
839
840        if (*offset != stop_offset) {
841            return ERROR_MALFORMED;
842        }
843
844        return OK;
845    }
846
847    switch(chunk_type) {
848        case FOURCC('m', 'o', 'o', 'v'):
849        case FOURCC('t', 'r', 'a', 'k'):
850        case FOURCC('m', 'd', 'i', 'a'):
851        case FOURCC('m', 'i', 'n', 'f'):
852        case FOURCC('d', 'i', 'n', 'f'):
853        case FOURCC('s', 't', 'b', 'l'):
854        case FOURCC('m', 'v', 'e', 'x'):
855        case FOURCC('m', 'o', 'o', 'f'):
856        case FOURCC('t', 'r', 'a', 'f'):
857        case FOURCC('m', 'f', 'r', 'a'):
858        case FOURCC('u', 'd', 't', 'a'):
859        case FOURCC('i', 'l', 's', 't'):
860        case FOURCC('s', 'i', 'n', 'f'):
861        case FOURCC('s', 'c', 'h', 'i'):
862        case FOURCC('e', 'd', 't', 's'):
863        {
864            if (chunk_type == FOURCC('s', 't', 'b', 'l')) {
865                ALOGV("sampleTable chunk is %" PRIu64 " bytes long.", chunk_size);
866
867                if (mDataSource->flags()
868                        & (DataSource::kWantsPrefetching
869                            | DataSource::kIsCachingDataSource)) {
870                    sp<MPEG4DataSource> cachedSource =
871                        new MPEG4DataSource(mDataSource);
872
873                    if (cachedSource->setCachedRange(*offset, chunk_size) == OK) {
874                        mDataSource = cachedSource;
875                    }
876                }
877
878                mLastTrack->sampleTable = new SampleTable(mDataSource);
879            }
880
881            bool isTrack = false;
882            if (chunk_type == FOURCC('t', 'r', 'a', 'k')) {
883                isTrack = true;
884
885                Track *track = new Track;
886                track->next = NULL;
887                if (mLastTrack) {
888                    mLastTrack->next = track;
889                } else {
890                    mFirstTrack = track;
891                }
892                mLastTrack = track;
893
894                track->meta = new MetaData;
895                track->includes_expensive_metadata = false;
896                track->skipTrack = false;
897                track->timescale = 0;
898                track->meta->setCString(kKeyMIMEType, "application/octet-stream");
899            }
900
901            off64_t stop_offset = *offset + chunk_size;
902            *offset = data_offset;
903            while (*offset < stop_offset) {
904                status_t err = parseChunk(offset, depth + 1);
905                if (err != OK) {
906                    return err;
907                }
908            }
909
910            if (*offset != stop_offset) {
911                return ERROR_MALFORMED;
912            }
913
914            if (isTrack) {
915                if (mLastTrack->skipTrack) {
916                    Track *cur = mFirstTrack;
917
918                    if (cur == mLastTrack) {
919                        delete cur;
920                        mFirstTrack = mLastTrack = NULL;
921                    } else {
922                        while (cur && cur->next != mLastTrack) {
923                            cur = cur->next;
924                        }
925                        cur->next = NULL;
926                        delete mLastTrack;
927                        mLastTrack = cur;
928                    }
929
930                    return OK;
931                }
932
933                status_t err = verifyTrack(mLastTrack);
934
935                if (err != OK) {
936                    return err;
937                }
938            } else if (chunk_type == FOURCC('m', 'o', 'o', 'v')) {
939                mInitCheck = OK;
940
941                if (!mIsDrm) {
942                    return UNKNOWN_ERROR;  // Return a dummy error.
943                } else {
944                    return OK;
945                }
946            }
947            break;
948        }
949
950        case FOURCC('e', 'l', 's', 't'):
951        {
952            *offset += chunk_size;
953
954            // See 14496-12 8.6.6
955            uint8_t version;
956            if (mDataSource->readAt(data_offset, &version, 1) < 1) {
957                return ERROR_IO;
958            }
959
960            uint32_t entry_count;
961            if (!mDataSource->getUInt32(data_offset + 4, &entry_count)) {
962                return ERROR_IO;
963            }
964
965            if (entry_count != 1) {
966                // we only support a single entry at the moment, for gapless playback
967                ALOGW("ignoring edit list with %d entries", entry_count);
968            } else if (mHeaderTimescale == 0) {
969                ALOGW("ignoring edit list because timescale is 0");
970            } else {
971                off64_t entriesoffset = data_offset + 8;
972                uint64_t segment_duration;
973                int64_t media_time;
974
975                if (version == 1) {
976                    if (!mDataSource->getUInt64(entriesoffset, &segment_duration) ||
977                            !mDataSource->getUInt64(entriesoffset + 8, (uint64_t*)&media_time)) {
978                        return ERROR_IO;
979                    }
980                } else if (version == 0) {
981                    uint32_t sd;
982                    int32_t mt;
983                    if (!mDataSource->getUInt32(entriesoffset, &sd) ||
984                            !mDataSource->getUInt32(entriesoffset + 4, (uint32_t*)&mt)) {
985                        return ERROR_IO;
986                    }
987                    segment_duration = sd;
988                    media_time = mt;
989                } else {
990                    return ERROR_IO;
991                }
992
993                uint64_t halfscale = mHeaderTimescale / 2;
994                segment_duration = (segment_duration * 1000000 + halfscale)/ mHeaderTimescale;
995                media_time = (media_time * 1000000 + halfscale) / mHeaderTimescale;
996
997                int64_t duration;
998                int32_t samplerate;
999                if (mLastTrack->meta->findInt64(kKeyDuration, &duration) &&
1000                        mLastTrack->meta->findInt32(kKeySampleRate, &samplerate)) {
1001
1002                    int64_t delay = (media_time  * samplerate + 500000) / 1000000;
1003                    mLastTrack->meta->setInt32(kKeyEncoderDelay, delay);
1004
1005                    int64_t paddingus = duration - (segment_duration + media_time);
1006                    if (paddingus < 0) {
1007                        // track duration from media header (which is what kKeyDuration is) might
1008                        // be slightly shorter than the segment duration, which would make the
1009                        // padding negative. Clamp to zero.
1010                        paddingus = 0;
1011                    }
1012                    int64_t paddingsamples = (paddingus * samplerate + 500000) / 1000000;
1013                    mLastTrack->meta->setInt32(kKeyEncoderPadding, paddingsamples);
1014                }
1015            }
1016            break;
1017        }
1018
1019        case FOURCC('f', 'r', 'm', 'a'):
1020        {
1021            *offset += chunk_size;
1022
1023            uint32_t original_fourcc;
1024            if (mDataSource->readAt(data_offset, &original_fourcc, 4) < 4) {
1025                return ERROR_IO;
1026            }
1027            original_fourcc = ntohl(original_fourcc);
1028            ALOGV("read original format: %d", original_fourcc);
1029            mLastTrack->meta->setCString(kKeyMIMEType, FourCC2MIME(original_fourcc));
1030            uint32_t num_channels = 0;
1031            uint32_t sample_rate = 0;
1032            if (AdjustChannelsAndRate(original_fourcc, &num_channels, &sample_rate)) {
1033                mLastTrack->meta->setInt32(kKeyChannelCount, num_channels);
1034                mLastTrack->meta->setInt32(kKeySampleRate, sample_rate);
1035            }
1036            break;
1037        }
1038
1039        case FOURCC('t', 'e', 'n', 'c'):
1040        {
1041            *offset += chunk_size;
1042
1043            if (chunk_size < 32) {
1044                return ERROR_MALFORMED;
1045            }
1046
1047            // tenc box contains 1 byte version, 3 byte flags, 3 byte default algorithm id, one byte
1048            // default IV size, 16 bytes default KeyID
1049            // (ISO 23001-7)
1050            char buf[4];
1051            memset(buf, 0, 4);
1052            if (mDataSource->readAt(data_offset + 4, buf + 1, 3) < 3) {
1053                return ERROR_IO;
1054            }
1055            uint32_t defaultAlgorithmId = ntohl(*((int32_t*)buf));
1056            if (defaultAlgorithmId > 1) {
1057                // only 0 (clear) and 1 (AES-128) are valid
1058                return ERROR_MALFORMED;
1059            }
1060
1061            memset(buf, 0, 4);
1062            if (mDataSource->readAt(data_offset + 7, buf + 3, 1) < 1) {
1063                return ERROR_IO;
1064            }
1065            uint32_t defaultIVSize = ntohl(*((int32_t*)buf));
1066
1067            if ((defaultAlgorithmId == 0 && defaultIVSize != 0) ||
1068                    (defaultAlgorithmId != 0 && defaultIVSize == 0)) {
1069                // only unencrypted data must have 0 IV size
1070                return ERROR_MALFORMED;
1071            } else if (defaultIVSize != 0 &&
1072                    defaultIVSize != 8 &&
1073                    defaultIVSize != 16) {
1074                // only supported sizes are 0, 8 and 16
1075                return ERROR_MALFORMED;
1076            }
1077
1078            uint8_t defaultKeyId[16];
1079
1080            if (mDataSource->readAt(data_offset + 8, &defaultKeyId, 16) < 16) {
1081                return ERROR_IO;
1082            }
1083
1084            mLastTrack->meta->setInt32(kKeyCryptoMode, defaultAlgorithmId);
1085            mLastTrack->meta->setInt32(kKeyCryptoDefaultIVSize, defaultIVSize);
1086            mLastTrack->meta->setData(kKeyCryptoKey, 'tenc', defaultKeyId, 16);
1087            break;
1088        }
1089
1090        case FOURCC('t', 'k', 'h', 'd'):
1091        {
1092            *offset += chunk_size;
1093
1094            status_t err;
1095            if ((err = parseTrackHeader(data_offset, chunk_data_size)) != OK) {
1096                return err;
1097            }
1098
1099            break;
1100        }
1101
1102        case FOURCC('p', 's', 's', 'h'):
1103        {
1104            *offset += chunk_size;
1105
1106            PsshInfo pssh;
1107
1108            if (mDataSource->readAt(data_offset + 4, &pssh.uuid, 16) < 16) {
1109                return ERROR_IO;
1110            }
1111
1112            uint32_t psshdatalen = 0;
1113            if (mDataSource->readAt(data_offset + 20, &psshdatalen, 4) < 4) {
1114                return ERROR_IO;
1115            }
1116            pssh.datalen = ntohl(psshdatalen);
1117            ALOGV("pssh data size: %d", pssh.datalen);
1118            if (pssh.datalen + 20 > chunk_size) {
1119                // pssh data length exceeds size of containing box
1120                return ERROR_MALFORMED;
1121            }
1122
1123            pssh.data = new (std::nothrow) uint8_t[pssh.datalen];
1124            if (pssh.data == NULL) {
1125                return ERROR_MALFORMED;
1126            }
1127            ALOGV("allocated pssh @ %p", pssh.data);
1128            ssize_t requested = (ssize_t) pssh.datalen;
1129            if (mDataSource->readAt(data_offset + 24, pssh.data, requested) < requested) {
1130                return ERROR_IO;
1131            }
1132            mPssh.push_back(pssh);
1133
1134            break;
1135        }
1136
1137        case FOURCC('m', 'd', 'h', 'd'):
1138        {
1139            *offset += chunk_size;
1140
1141            if (chunk_data_size < 4) {
1142                return ERROR_MALFORMED;
1143            }
1144
1145            uint8_t version;
1146            if (mDataSource->readAt(
1147                        data_offset, &version, sizeof(version))
1148                    < (ssize_t)sizeof(version)) {
1149                return ERROR_IO;
1150            }
1151
1152            off64_t timescale_offset;
1153
1154            if (version == 1) {
1155                timescale_offset = data_offset + 4 + 16;
1156            } else if (version == 0) {
1157                timescale_offset = data_offset + 4 + 8;
1158            } else {
1159                return ERROR_IO;
1160            }
1161
1162            uint32_t timescale;
1163            if (mDataSource->readAt(
1164                        timescale_offset, &timescale, sizeof(timescale))
1165                    < (ssize_t)sizeof(timescale)) {
1166                return ERROR_IO;
1167            }
1168
1169            mLastTrack->timescale = ntohl(timescale);
1170
1171            // 14496-12 says all ones means indeterminate, but some files seem to use
1172            // 0 instead. We treat both the same.
1173            int64_t duration = 0;
1174            if (version == 1) {
1175                if (mDataSource->readAt(
1176                            timescale_offset + 4, &duration, sizeof(duration))
1177                        < (ssize_t)sizeof(duration)) {
1178                    return ERROR_IO;
1179                }
1180                if (duration != -1) {
1181                    duration = ntoh64(duration);
1182                }
1183            } else {
1184                uint32_t duration32;
1185                if (mDataSource->readAt(
1186                            timescale_offset + 4, &duration32, sizeof(duration32))
1187                        < (ssize_t)sizeof(duration32)) {
1188                    return ERROR_IO;
1189                }
1190                if (duration32 != 0xffffffff) {
1191                    duration = ntohl(duration32);
1192                }
1193            }
1194            if (duration != 0) {
1195                mLastTrack->meta->setInt64(
1196                        kKeyDuration, (duration * 1000000) / mLastTrack->timescale);
1197            }
1198
1199            uint8_t lang[2];
1200            off64_t lang_offset;
1201            if (version == 1) {
1202                lang_offset = timescale_offset + 4 + 8;
1203            } else if (version == 0) {
1204                lang_offset = timescale_offset + 4 + 4;
1205            } else {
1206                return ERROR_IO;
1207            }
1208
1209            if (mDataSource->readAt(lang_offset, &lang, sizeof(lang))
1210                    < (ssize_t)sizeof(lang)) {
1211                return ERROR_IO;
1212            }
1213
1214            // To get the ISO-639-2/T three character language code
1215            // 1 bit pad followed by 3 5-bits characters. Each character
1216            // is packed as the difference between its ASCII value and 0x60.
1217            char lang_code[4];
1218            lang_code[0] = ((lang[0] >> 2) & 0x1f) + 0x60;
1219            lang_code[1] = ((lang[0] & 0x3) << 3 | (lang[1] >> 5)) + 0x60;
1220            lang_code[2] = (lang[1] & 0x1f) + 0x60;
1221            lang_code[3] = '\0';
1222
1223            mLastTrack->meta->setCString(
1224                    kKeyMediaLanguage, lang_code);
1225
1226            break;
1227        }
1228
1229        case FOURCC('s', 't', 's', 'd'):
1230        {
1231            if (chunk_data_size < 8) {
1232                return ERROR_MALFORMED;
1233            }
1234
1235            uint8_t buffer[8];
1236            if (chunk_data_size < (off64_t)sizeof(buffer)) {
1237                return ERROR_MALFORMED;
1238            }
1239
1240            if (mDataSource->readAt(
1241                        data_offset, buffer, 8) < 8) {
1242                return ERROR_IO;
1243            }
1244
1245            if (U32_AT(buffer) != 0) {
1246                // Should be version 0, flags 0.
1247                return ERROR_MALFORMED;
1248            }
1249
1250            uint32_t entry_count = U32_AT(&buffer[4]);
1251
1252            if (entry_count > 1) {
1253                // For 3GPP timed text, there could be multiple tx3g boxes contain
1254                // multiple text display formats. These formats will be used to
1255                // display the timed text.
1256                // For encrypted files, there may also be more than one entry.
1257                const char *mime;
1258                CHECK(mLastTrack->meta->findCString(kKeyMIMEType, &mime));
1259                if (strcasecmp(mime, MEDIA_MIMETYPE_TEXT_3GPP) &&
1260                        strcasecmp(mime, "application/octet-stream")) {
1261                    // For now we only support a single type of media per track.
1262                    mLastTrack->skipTrack = true;
1263                    *offset += chunk_size;
1264                    break;
1265                }
1266            }
1267            off64_t stop_offset = *offset + chunk_size;
1268            *offset = data_offset + 8;
1269            for (uint32_t i = 0; i < entry_count; ++i) {
1270                status_t err = parseChunk(offset, depth + 1);
1271                if (err != OK) {
1272                    return err;
1273                }
1274            }
1275
1276            if (*offset != stop_offset) {
1277                return ERROR_MALFORMED;
1278            }
1279            break;
1280        }
1281
1282        case FOURCC('m', 'p', '4', 'a'):
1283        case FOURCC('e', 'n', 'c', 'a'):
1284        case FOURCC('s', 'a', 'm', 'r'):
1285        case FOURCC('s', 'a', 'w', 'b'):
1286        {
1287            uint8_t buffer[8 + 20];
1288            if (chunk_data_size < (ssize_t)sizeof(buffer)) {
1289                // Basic AudioSampleEntry size.
1290                return ERROR_MALFORMED;
1291            }
1292
1293            if (mDataSource->readAt(
1294                        data_offset, buffer, sizeof(buffer)) < (ssize_t)sizeof(buffer)) {
1295                return ERROR_IO;
1296            }
1297
1298            uint16_t data_ref_index = U16_AT(&buffer[6]);
1299            uint32_t num_channels = U16_AT(&buffer[16]);
1300
1301            uint16_t sample_size = U16_AT(&buffer[18]);
1302            uint32_t sample_rate = U32_AT(&buffer[24]) >> 16;
1303
1304            if (chunk_type != FOURCC('e', 'n', 'c', 'a')) {
1305                // if the chunk type is enca, we'll get the type from the sinf/frma box later
1306                mLastTrack->meta->setCString(kKeyMIMEType, FourCC2MIME(chunk_type));
1307                AdjustChannelsAndRate(chunk_type, &num_channels, &sample_rate);
1308            }
1309            ALOGV("*** coding='%s' %d channels, size %d, rate %d\n",
1310                   chunk, num_channels, sample_size, sample_rate);
1311            mLastTrack->meta->setInt32(kKeyChannelCount, num_channels);
1312            mLastTrack->meta->setInt32(kKeySampleRate, sample_rate);
1313
1314            off64_t stop_offset = *offset + chunk_size;
1315            *offset = data_offset + sizeof(buffer);
1316            while (*offset < stop_offset) {
1317                status_t err = parseChunk(offset, depth + 1);
1318                if (err != OK) {
1319                    return err;
1320                }
1321            }
1322
1323            if (*offset != stop_offset) {
1324                return ERROR_MALFORMED;
1325            }
1326            break;
1327        }
1328
1329        case FOURCC('m', 'p', '4', 'v'):
1330        case FOURCC('e', 'n', 'c', 'v'):
1331        case FOURCC('s', '2', '6', '3'):
1332        case FOURCC('H', '2', '6', '3'):
1333        case FOURCC('h', '2', '6', '3'):
1334        case FOURCC('a', 'v', 'c', '1'):
1335        case FOURCC('h', 'v', 'c', '1'):
1336        case FOURCC('h', 'e', 'v', '1'):
1337        {
1338            mHasVideo = true;
1339
1340            uint8_t buffer[78];
1341            if (chunk_data_size < (ssize_t)sizeof(buffer)) {
1342                // Basic VideoSampleEntry size.
1343                return ERROR_MALFORMED;
1344            }
1345
1346            if (mDataSource->readAt(
1347                        data_offset, buffer, sizeof(buffer)) < (ssize_t)sizeof(buffer)) {
1348                return ERROR_IO;
1349            }
1350
1351            uint16_t data_ref_index = U16_AT(&buffer[6]);
1352            uint16_t width = U16_AT(&buffer[6 + 18]);
1353            uint16_t height = U16_AT(&buffer[6 + 20]);
1354
1355            // The video sample is not standard-compliant if it has invalid dimension.
1356            // Use some default width and height value, and
1357            // let the decoder figure out the actual width and height (and thus
1358            // be prepared for INFO_FOMRAT_CHANGED event).
1359            if (width == 0)  width  = 352;
1360            if (height == 0) height = 288;
1361
1362            // printf("*** coding='%s' width=%d height=%d\n",
1363            //        chunk, width, height);
1364
1365            if (chunk_type != FOURCC('e', 'n', 'c', 'v')) {
1366                // if the chunk type is encv, we'll get the type from the sinf/frma box later
1367                mLastTrack->meta->setCString(kKeyMIMEType, FourCC2MIME(chunk_type));
1368            }
1369            mLastTrack->meta->setInt32(kKeyWidth, width);
1370            mLastTrack->meta->setInt32(kKeyHeight, height);
1371
1372            off64_t stop_offset = *offset + chunk_size;
1373            *offset = data_offset + sizeof(buffer);
1374            while (*offset < stop_offset) {
1375                status_t err = parseChunk(offset, depth + 1);
1376                if (err != OK) {
1377                    return err;
1378                }
1379            }
1380
1381            if (*offset != stop_offset) {
1382                return ERROR_MALFORMED;
1383            }
1384            break;
1385        }
1386
1387        case FOURCC('s', 't', 'c', 'o'):
1388        case FOURCC('c', 'o', '6', '4'):
1389        {
1390            status_t err =
1391                mLastTrack->sampleTable->setChunkOffsetParams(
1392                        chunk_type, data_offset, chunk_data_size);
1393
1394            *offset += chunk_size;
1395
1396            if (err != OK) {
1397                return err;
1398            }
1399
1400            break;
1401        }
1402
1403        case FOURCC('s', 't', 's', 'c'):
1404        {
1405            status_t err =
1406                mLastTrack->sampleTable->setSampleToChunkParams(
1407                        data_offset, chunk_data_size);
1408
1409            *offset += chunk_size;
1410
1411            if (err != OK) {
1412                return err;
1413            }
1414
1415            break;
1416        }
1417
1418        case FOURCC('s', 't', 's', 'z'):
1419        case FOURCC('s', 't', 'z', '2'):
1420        {
1421            status_t err =
1422                mLastTrack->sampleTable->setSampleSizeParams(
1423                        chunk_type, data_offset, chunk_data_size);
1424
1425            *offset += chunk_size;
1426
1427            if (err != OK) {
1428                return err;
1429            }
1430
1431            size_t max_size;
1432            err = mLastTrack->sampleTable->getMaxSampleSize(&max_size);
1433
1434            if (err != OK) {
1435                return err;
1436            }
1437
1438            if (max_size != 0) {
1439                // Assume that a given buffer only contains at most 10 chunks,
1440                // each chunk originally prefixed with a 2 byte length will
1441                // have a 4 byte header (0x00 0x00 0x00 0x01) after conversion,
1442                // and thus will grow by 2 bytes per chunk.
1443                mLastTrack->meta->setInt32(kKeyMaxInputSize, max_size + 10 * 2);
1444            } else {
1445                // No size was specified. Pick a conservatively large size.
1446                int32_t width, height;
1447                if (!mLastTrack->meta->findInt32(kKeyWidth, &width) ||
1448                    !mLastTrack->meta->findInt32(kKeyHeight, &height)) {
1449                    ALOGE("No width or height, assuming worst case 1080p");
1450                    width = 1920;
1451                    height = 1080;
1452                }
1453
1454                const char *mime;
1455                CHECK(mLastTrack->meta->findCString(kKeyMIMEType, &mime));
1456                if (!strcmp(mime, MEDIA_MIMETYPE_VIDEO_AVC)) {
1457                    // AVC requires compression ratio of at least 2, and uses
1458                    // macroblocks
1459                    max_size = ((width + 15) / 16) * ((height + 15) / 16) * 192;
1460                } else {
1461                    // For all other formats there is no minimum compression
1462                    // ratio. Use compression ratio of 1.
1463                    max_size = width * height * 3 / 2;
1464                }
1465                mLastTrack->meta->setInt32(kKeyMaxInputSize, max_size);
1466            }
1467
1468            // NOTE: setting another piece of metadata invalidates any pointers (such as the
1469            // mimetype) previously obtained, so don't cache them.
1470            const char *mime;
1471            CHECK(mLastTrack->meta->findCString(kKeyMIMEType, &mime));
1472            // Calculate average frame rate.
1473            if (!strncasecmp("video/", mime, 6)) {
1474                size_t nSamples = mLastTrack->sampleTable->countSamples();
1475                int64_t durationUs;
1476                if (mLastTrack->meta->findInt64(kKeyDuration, &durationUs)) {
1477                    if (durationUs > 0) {
1478                        int32_t frameRate = (nSamples * 1000000LL +
1479                                    (durationUs >> 1)) / durationUs;
1480                        mLastTrack->meta->setInt32(kKeyFrameRate, frameRate);
1481                    }
1482                }
1483            }
1484
1485            break;
1486        }
1487
1488        case FOURCC('s', 't', 't', 's'):
1489        {
1490            *offset += chunk_size;
1491
1492            status_t err =
1493                mLastTrack->sampleTable->setTimeToSampleParams(
1494                        data_offset, chunk_data_size);
1495
1496            if (err != OK) {
1497                return err;
1498            }
1499
1500            break;
1501        }
1502
1503        case FOURCC('c', 't', 't', 's'):
1504        {
1505            *offset += chunk_size;
1506
1507            status_t err =
1508                mLastTrack->sampleTable->setCompositionTimeToSampleParams(
1509                        data_offset, chunk_data_size);
1510
1511            if (err != OK) {
1512                return err;
1513            }
1514
1515            break;
1516        }
1517
1518        case FOURCC('s', 't', 's', 's'):
1519        {
1520            *offset += chunk_size;
1521
1522            status_t err =
1523                mLastTrack->sampleTable->setSyncSampleParams(
1524                        data_offset, chunk_data_size);
1525
1526            if (err != OK) {
1527                return err;
1528            }
1529
1530            break;
1531        }
1532
1533        // @xyz
1534        case FOURCC('\xA9', 'x', 'y', 'z'):
1535        {
1536            *offset += chunk_size;
1537
1538            // Best case the total data length inside "@xyz" box
1539            // would be 8, for instance "@xyz" + "\x00\x04\x15\xc7" + "0+0/",
1540            // where "\x00\x04" is the text string length with value = 4,
1541            // "\0x15\xc7" is the language code = en, and "0+0" is a
1542            // location (string) value with longitude = 0 and latitude = 0.
1543            if (chunk_data_size < 8) {
1544                return ERROR_MALFORMED;
1545            }
1546
1547            // Worst case the location string length would be 18,
1548            // for instance +90.0000-180.0000, without the trailing "/" and
1549            // the string length + language code.
1550            char buffer[18];
1551
1552            // Substracting 5 from the data size is because the text string length +
1553            // language code takes 4 bytes, and the trailing slash "/" takes 1 byte.
1554            off64_t location_length = chunk_data_size - 5;
1555            if (location_length >= (off64_t) sizeof(buffer)) {
1556                return ERROR_MALFORMED;
1557            }
1558
1559            if (mDataSource->readAt(
1560                        data_offset + 4, buffer, location_length) < location_length) {
1561                return ERROR_IO;
1562            }
1563
1564            buffer[location_length] = '\0';
1565            mFileMetaData->setCString(kKeyLocation, buffer);
1566            break;
1567        }
1568
1569        case FOURCC('e', 's', 'd', 's'):
1570        {
1571            *offset += chunk_size;
1572
1573            if (chunk_data_size < 4) {
1574                return ERROR_MALFORMED;
1575            }
1576
1577            uint8_t buffer[256];
1578            if (chunk_data_size > (off64_t)sizeof(buffer)) {
1579                return ERROR_BUFFER_TOO_SMALL;
1580            }
1581
1582            if (mDataSource->readAt(
1583                        data_offset, buffer, chunk_data_size) < chunk_data_size) {
1584                return ERROR_IO;
1585            }
1586
1587            if (U32_AT(buffer) != 0) {
1588                // Should be version 0, flags 0.
1589                return ERROR_MALFORMED;
1590            }
1591
1592            mLastTrack->meta->setData(
1593                    kKeyESDS, kTypeESDS, &buffer[4], chunk_data_size - 4);
1594
1595            if (mPath.size() >= 2
1596                    && mPath[mPath.size() - 2] == FOURCC('m', 'p', '4', 'a')) {
1597                // Information from the ESDS must be relied on for proper
1598                // setup of sample rate and channel count for MPEG4 Audio.
1599                // The generic header appears to only contain generic
1600                // information...
1601
1602                status_t err = updateAudioTrackInfoFromESDS_MPEG4Audio(
1603                        &buffer[4], chunk_data_size - 4);
1604
1605                if (err != OK) {
1606                    return err;
1607                }
1608            }
1609
1610            break;
1611        }
1612
1613        case FOURCC('a', 'v', 'c', 'C'):
1614        {
1615            *offset += chunk_size;
1616
1617            sp<ABuffer> buffer = new ABuffer(chunk_data_size);
1618
1619            if (mDataSource->readAt(
1620                        data_offset, buffer->data(), chunk_data_size) < chunk_data_size) {
1621                return ERROR_IO;
1622            }
1623
1624            mLastTrack->meta->setData(
1625                    kKeyAVCC, kTypeAVCC, buffer->data(), chunk_data_size);
1626
1627            break;
1628        }
1629        case FOURCC('h', 'v', 'c', 'C'):
1630        {
1631            sp<ABuffer> buffer = new ABuffer(chunk_data_size);
1632
1633            if (mDataSource->readAt(
1634                        data_offset, buffer->data(), chunk_data_size) < chunk_data_size) {
1635                return ERROR_IO;
1636            }
1637
1638            mLastTrack->meta->setData(
1639                    kKeyHVCC, kTypeHVCC, buffer->data(), chunk_data_size);
1640
1641            *offset += chunk_size;
1642            break;
1643        }
1644
1645        case FOURCC('d', '2', '6', '3'):
1646        {
1647            *offset += chunk_size;
1648            /*
1649             * d263 contains a fixed 7 bytes part:
1650             *   vendor - 4 bytes
1651             *   version - 1 byte
1652             *   level - 1 byte
1653             *   profile - 1 byte
1654             * optionally, "d263" box itself may contain a 16-byte
1655             * bit rate box (bitr)
1656             *   average bit rate - 4 bytes
1657             *   max bit rate - 4 bytes
1658             */
1659            char buffer[23];
1660            if (chunk_data_size != 7 &&
1661                chunk_data_size != 23) {
1662                ALOGE("Incorrect D263 box size %lld", chunk_data_size);
1663                return ERROR_MALFORMED;
1664            }
1665
1666            if (mDataSource->readAt(
1667                    data_offset, buffer, chunk_data_size) < chunk_data_size) {
1668                return ERROR_IO;
1669            }
1670
1671            mLastTrack->meta->setData(kKeyD263, kTypeD263, buffer, chunk_data_size);
1672
1673            break;
1674        }
1675
1676        case FOURCC('m', 'e', 't', 'a'):
1677        {
1678            uint8_t buffer[4];
1679            if (chunk_data_size < (off64_t)sizeof(buffer)) {
1680                *offset += chunk_size;
1681                return ERROR_MALFORMED;
1682            }
1683
1684            if (mDataSource->readAt(
1685                        data_offset, buffer, 4) < 4) {
1686                *offset += chunk_size;
1687                return ERROR_IO;
1688            }
1689
1690            if (U32_AT(buffer) != 0) {
1691                // Should be version 0, flags 0.
1692
1693                // If it's not, let's assume this is one of those
1694                // apparently malformed chunks that don't have flags
1695                // and completely different semantics than what's
1696                // in the MPEG4 specs and skip it.
1697                *offset += chunk_size;
1698                return OK;
1699            }
1700
1701            off64_t stop_offset = *offset + chunk_size;
1702            *offset = data_offset + sizeof(buffer);
1703            while (*offset < stop_offset) {
1704                status_t err = parseChunk(offset, depth + 1);
1705                if (err != OK) {
1706                    return err;
1707                }
1708            }
1709
1710            if (*offset != stop_offset) {
1711                return ERROR_MALFORMED;
1712            }
1713            break;
1714        }
1715
1716        case FOURCC('m', 'e', 'a', 'n'):
1717        case FOURCC('n', 'a', 'm', 'e'):
1718        case FOURCC('d', 'a', 't', 'a'):
1719        {
1720            *offset += chunk_size;
1721
1722            if (mPath.size() == 6 && underMetaDataPath(mPath)) {
1723                status_t err = parseITunesMetaData(data_offset, chunk_data_size);
1724
1725                if (err != OK) {
1726                    return err;
1727                }
1728            }
1729
1730            break;
1731        }
1732
1733        case FOURCC('m', 'v', 'h', 'd'):
1734        {
1735            *offset += chunk_size;
1736
1737            if (chunk_data_size < 32) {
1738                return ERROR_MALFORMED;
1739            }
1740
1741            uint8_t header[32];
1742            if (mDataSource->readAt(
1743                        data_offset, header, sizeof(header))
1744                    < (ssize_t)sizeof(header)) {
1745                return ERROR_IO;
1746            }
1747
1748            uint64_t creationTime;
1749            uint64_t duration = 0;
1750            if (header[0] == 1) {
1751                creationTime = U64_AT(&header[4]);
1752                mHeaderTimescale = U32_AT(&header[20]);
1753                duration = U64_AT(&header[24]);
1754                if (duration == 0xffffffffffffffff) {
1755                    duration = 0;
1756                }
1757            } else if (header[0] != 0) {
1758                return ERROR_MALFORMED;
1759            } else {
1760                creationTime = U32_AT(&header[4]);
1761                mHeaderTimescale = U32_AT(&header[12]);
1762                uint32_t d32 = U32_AT(&header[16]);
1763                if (d32 == 0xffffffff) {
1764                    d32 = 0;
1765                }
1766                duration = d32;
1767            }
1768            if (duration != 0) {
1769                mFileMetaData->setInt64(kKeyDuration, duration * 1000000 / mHeaderTimescale);
1770            }
1771
1772            String8 s;
1773            convertTimeToDate(creationTime, &s);
1774
1775            mFileMetaData->setCString(kKeyDate, s.string());
1776
1777            break;
1778        }
1779
1780        case FOURCC('m', 'e', 'h', 'd'):
1781        {
1782            *offset += chunk_size;
1783
1784            if (chunk_data_size < 8) {
1785                return ERROR_MALFORMED;
1786            }
1787
1788            uint8_t flags[4];
1789            if (mDataSource->readAt(
1790                        data_offset, flags, sizeof(flags))
1791                    < (ssize_t)sizeof(flags)) {
1792                return ERROR_IO;
1793            }
1794
1795            uint64_t duration = 0;
1796            if (flags[0] == 1) {
1797                // 64 bit
1798                if (chunk_data_size < 12) {
1799                    return ERROR_MALFORMED;
1800                }
1801                mDataSource->getUInt64(data_offset + 4, &duration);
1802                if (duration == 0xffffffffffffffff) {
1803                    duration = 0;
1804                }
1805            } else if (flags[0] == 0) {
1806                // 32 bit
1807                uint32_t d32;
1808                mDataSource->getUInt32(data_offset + 4, &d32);
1809                if (d32 == 0xffffffff) {
1810                    d32 = 0;
1811                }
1812                duration = d32;
1813            } else {
1814                return ERROR_MALFORMED;
1815            }
1816
1817            if (duration != 0) {
1818                mFileMetaData->setInt64(kKeyDuration, duration * 1000000 / mHeaderTimescale);
1819            }
1820
1821            break;
1822        }
1823
1824        case FOURCC('m', 'd', 'a', 't'):
1825        {
1826            ALOGV("mdat chunk, drm: %d", mIsDrm);
1827            if (!mIsDrm) {
1828                *offset += chunk_size;
1829                break;
1830            }
1831
1832            if (chunk_size < 8) {
1833                return ERROR_MALFORMED;
1834            }
1835
1836            return parseDrmSINF(offset, data_offset);
1837        }
1838
1839        case FOURCC('h', 'd', 'l', 'r'):
1840        {
1841            *offset += chunk_size;
1842
1843            uint32_t buffer;
1844            if (mDataSource->readAt(
1845                        data_offset + 8, &buffer, 4) < 4) {
1846                return ERROR_IO;
1847            }
1848
1849            uint32_t type = ntohl(buffer);
1850            // For the 3GPP file format, the handler-type within the 'hdlr' box
1851            // shall be 'text'. We also want to support 'sbtl' handler type
1852            // for a practical reason as various MPEG4 containers use it.
1853            if (type == FOURCC('t', 'e', 'x', 't') || type == FOURCC('s', 'b', 't', 'l')) {
1854                mLastTrack->meta->setCString(kKeyMIMEType, MEDIA_MIMETYPE_TEXT_3GPP);
1855            }
1856
1857            break;
1858        }
1859
1860        case FOURCC('t', 'r', 'e', 'x'):
1861        {
1862            *offset += chunk_size;
1863
1864            if (chunk_data_size < 24) {
1865                return ERROR_IO;
1866            }
1867            uint32_t duration;
1868            Trex trex;
1869            if (!mDataSource->getUInt32(data_offset + 4, &trex.track_ID) ||
1870                !mDataSource->getUInt32(data_offset + 8, &trex.default_sample_description_index) ||
1871                !mDataSource->getUInt32(data_offset + 12, &trex.default_sample_duration) ||
1872                !mDataSource->getUInt32(data_offset + 16, &trex.default_sample_size) ||
1873                !mDataSource->getUInt32(data_offset + 20, &trex.default_sample_flags)) {
1874                return ERROR_IO;
1875            }
1876            mTrex.add(trex);
1877            break;
1878        }
1879
1880        case FOURCC('t', 'x', '3', 'g'):
1881        {
1882            uint32_t type;
1883            const void *data;
1884            size_t size = 0;
1885            if (!mLastTrack->meta->findData(
1886                    kKeyTextFormatData, &type, &data, &size)) {
1887                size = 0;
1888            }
1889
1890            uint8_t *buffer = new (std::nothrow) uint8_t[size + chunk_size];
1891            if (buffer == NULL) {
1892                return ERROR_MALFORMED;
1893            }
1894
1895            if (size > 0) {
1896                memcpy(buffer, data, size);
1897            }
1898
1899            if ((size_t)(mDataSource->readAt(*offset, buffer + size, chunk_size))
1900                    < chunk_size) {
1901                delete[] buffer;
1902                buffer = NULL;
1903
1904                // advance read pointer so we don't end up reading this again
1905                *offset += chunk_size;
1906                return ERROR_IO;
1907            }
1908
1909            mLastTrack->meta->setData(
1910                    kKeyTextFormatData, 0, buffer, size + chunk_size);
1911
1912            delete[] buffer;
1913
1914            *offset += chunk_size;
1915            break;
1916        }
1917
1918        case FOURCC('c', 'o', 'v', 'r'):
1919        {
1920            *offset += chunk_size;
1921
1922            if (mFileMetaData != NULL) {
1923                ALOGV("chunk_data_size = %lld and data_offset = %lld",
1924                        chunk_data_size, data_offset);
1925                sp<ABuffer> buffer = new ABuffer(chunk_data_size + 1);
1926                if (mDataSource->readAt(
1927                    data_offset, buffer->data(), chunk_data_size) != (ssize_t)chunk_data_size) {
1928                    return ERROR_IO;
1929                }
1930                const int kSkipBytesOfDataBox = 16;
1931                mFileMetaData->setData(
1932                    kKeyAlbumArt, MetaData::TYPE_NONE,
1933                    buffer->data() + kSkipBytesOfDataBox, chunk_data_size - kSkipBytesOfDataBox);
1934            }
1935
1936            break;
1937        }
1938
1939        case FOURCC('t', 'i', 't', 'l'):
1940        case FOURCC('p', 'e', 'r', 'f'):
1941        case FOURCC('a', 'u', 't', 'h'):
1942        case FOURCC('g', 'n', 'r', 'e'):
1943        case FOURCC('a', 'l', 'b', 'm'):
1944        case FOURCC('y', 'r', 'r', 'c'):
1945        {
1946            *offset += chunk_size;
1947
1948            status_t err = parse3GPPMetaData(data_offset, chunk_data_size, depth);
1949
1950            if (err != OK) {
1951                return err;
1952            }
1953
1954            break;
1955        }
1956
1957        case FOURCC('I', 'D', '3', '2'):
1958        {
1959            *offset += chunk_size;
1960
1961            if (chunk_data_size < 6) {
1962                return ERROR_MALFORMED;
1963            }
1964
1965            parseID3v2MetaData(data_offset + 6);
1966
1967            break;
1968        }
1969
1970        case FOURCC('-', '-', '-', '-'):
1971        {
1972            mLastCommentMean.clear();
1973            mLastCommentName.clear();
1974            mLastCommentData.clear();
1975            *offset += chunk_size;
1976            break;
1977        }
1978
1979        case FOURCC('s', 'i', 'd', 'x'):
1980        {
1981            parseSegmentIndex(data_offset, chunk_data_size);
1982            *offset += chunk_size;
1983            return UNKNOWN_ERROR; // stop parsing after sidx
1984        }
1985
1986        default:
1987        {
1988            *offset += chunk_size;
1989            break;
1990        }
1991    }
1992
1993    return OK;
1994}
1995
1996status_t MPEG4Extractor::parseSegmentIndex(off64_t offset, size_t size) {
1997  ALOGV("MPEG4Extractor::parseSegmentIndex");
1998
1999    if (size < 12) {
2000      return -EINVAL;
2001    }
2002
2003    uint32_t flags;
2004    if (!mDataSource->getUInt32(offset, &flags)) {
2005        return ERROR_MALFORMED;
2006    }
2007
2008    uint32_t version = flags >> 24;
2009    flags &= 0xffffff;
2010
2011    ALOGV("sidx version %d", version);
2012
2013    uint32_t referenceId;
2014    if (!mDataSource->getUInt32(offset + 4, &referenceId)) {
2015        return ERROR_MALFORMED;
2016    }
2017
2018    uint32_t timeScale;
2019    if (!mDataSource->getUInt32(offset + 8, &timeScale)) {
2020        return ERROR_MALFORMED;
2021    }
2022    ALOGV("sidx refid/timescale: %d/%d", referenceId, timeScale);
2023
2024    uint64_t earliestPresentationTime;
2025    uint64_t firstOffset;
2026
2027    offset += 12;
2028    size -= 12;
2029
2030    if (version == 0) {
2031        if (size < 8) {
2032            return -EINVAL;
2033        }
2034        uint32_t tmp;
2035        if (!mDataSource->getUInt32(offset, &tmp)) {
2036            return ERROR_MALFORMED;
2037        }
2038        earliestPresentationTime = tmp;
2039        if (!mDataSource->getUInt32(offset + 4, &tmp)) {
2040            return ERROR_MALFORMED;
2041        }
2042        firstOffset = tmp;
2043        offset += 8;
2044        size -= 8;
2045    } else {
2046        if (size < 16) {
2047            return -EINVAL;
2048        }
2049        if (!mDataSource->getUInt64(offset, &earliestPresentationTime)) {
2050            return ERROR_MALFORMED;
2051        }
2052        if (!mDataSource->getUInt64(offset + 8, &firstOffset)) {
2053            return ERROR_MALFORMED;
2054        }
2055        offset += 16;
2056        size -= 16;
2057    }
2058    ALOGV("sidx pres/off: %" PRIu64 "/%" PRIu64, earliestPresentationTime, firstOffset);
2059
2060    if (size < 4) {
2061        return -EINVAL;
2062    }
2063
2064    uint16_t referenceCount;
2065    if (!mDataSource->getUInt16(offset + 2, &referenceCount)) {
2066        return ERROR_MALFORMED;
2067    }
2068    offset += 4;
2069    size -= 4;
2070    ALOGV("refcount: %d", referenceCount);
2071
2072    if (size < referenceCount * 12) {
2073        return -EINVAL;
2074    }
2075
2076    uint64_t total_duration = 0;
2077    for (unsigned int i = 0; i < referenceCount; i++) {
2078        uint32_t d1, d2, d3;
2079
2080        if (!mDataSource->getUInt32(offset, &d1) ||     // size
2081            !mDataSource->getUInt32(offset + 4, &d2) || // duration
2082            !mDataSource->getUInt32(offset + 8, &d3)) { // flags
2083            return ERROR_MALFORMED;
2084        }
2085
2086        if (d1 & 0x80000000) {
2087            ALOGW("sub-sidx boxes not supported yet");
2088        }
2089        bool sap = d3 & 0x80000000;
2090        uint32_t saptype = (d3 >> 28) & 7;
2091        if (!sap || (saptype != 1 && saptype != 2)) {
2092            // type 1 and 2 are sync samples
2093            ALOGW("not a stream access point, or unsupported type: %08x", d3);
2094        }
2095        total_duration += d2;
2096        offset += 12;
2097        ALOGV(" item %d, %08x %08x %08x", i, d1, d2, d3);
2098        SidxEntry se;
2099        se.mSize = d1 & 0x7fffffff;
2100        se.mDurationUs = 1000000LL * d2 / timeScale;
2101        mSidxEntries.add(se);
2102    }
2103
2104    uint64_t sidxDuration = total_duration * 1000000 / timeScale;
2105
2106    int64_t metaDuration;
2107    if (!mLastTrack->meta->findInt64(kKeyDuration, &metaDuration) || metaDuration == 0) {
2108        mLastTrack->meta->setInt64(kKeyDuration, sidxDuration);
2109    }
2110    return OK;
2111}
2112
2113
2114
2115status_t MPEG4Extractor::parseTrackHeader(
2116        off64_t data_offset, off64_t data_size) {
2117    if (data_size < 4) {
2118        return ERROR_MALFORMED;
2119    }
2120
2121    uint8_t version;
2122    if (mDataSource->readAt(data_offset, &version, 1) < 1) {
2123        return ERROR_IO;
2124    }
2125
2126    size_t dynSize = (version == 1) ? 36 : 24;
2127
2128    uint8_t buffer[36 + 60];
2129
2130    if (data_size != (off64_t)dynSize + 60) {
2131        return ERROR_MALFORMED;
2132    }
2133
2134    if (mDataSource->readAt(
2135                data_offset, buffer, data_size) < (ssize_t)data_size) {
2136        return ERROR_IO;
2137    }
2138
2139    uint64_t ctime, mtime, duration;
2140    int32_t id;
2141
2142    if (version == 1) {
2143        ctime = U64_AT(&buffer[4]);
2144        mtime = U64_AT(&buffer[12]);
2145        id = U32_AT(&buffer[20]);
2146        duration = U64_AT(&buffer[28]);
2147    } else if (version == 0) {
2148        ctime = U32_AT(&buffer[4]);
2149        mtime = U32_AT(&buffer[8]);
2150        id = U32_AT(&buffer[12]);
2151        duration = U32_AT(&buffer[20]);
2152    } else {
2153        return ERROR_UNSUPPORTED;
2154    }
2155
2156    mLastTrack->meta->setInt32(kKeyTrackID, id);
2157
2158    size_t matrixOffset = dynSize + 16;
2159    int32_t a00 = U32_AT(&buffer[matrixOffset]);
2160    int32_t a01 = U32_AT(&buffer[matrixOffset + 4]);
2161    int32_t dx = U32_AT(&buffer[matrixOffset + 8]);
2162    int32_t a10 = U32_AT(&buffer[matrixOffset + 12]);
2163    int32_t a11 = U32_AT(&buffer[matrixOffset + 16]);
2164    int32_t dy = U32_AT(&buffer[matrixOffset + 20]);
2165
2166#if 0
2167    ALOGI("x' = %.2f * x + %.2f * y + %.2f",
2168         a00 / 65536.0f, a01 / 65536.0f, dx / 65536.0f);
2169    ALOGI("y' = %.2f * x + %.2f * y + %.2f",
2170         a10 / 65536.0f, a11 / 65536.0f, dy / 65536.0f);
2171#endif
2172
2173    uint32_t rotationDegrees;
2174
2175    static const int32_t kFixedOne = 0x10000;
2176    if (a00 == kFixedOne && a01 == 0 && a10 == 0 && a11 == kFixedOne) {
2177        // Identity, no rotation
2178        rotationDegrees = 0;
2179    } else if (a00 == 0 && a01 == kFixedOne && a10 == -kFixedOne && a11 == 0) {
2180        rotationDegrees = 90;
2181    } else if (a00 == 0 && a01 == -kFixedOne && a10 == kFixedOne && a11 == 0) {
2182        rotationDegrees = 270;
2183    } else if (a00 == -kFixedOne && a01 == 0 && a10 == 0 && a11 == -kFixedOne) {
2184        rotationDegrees = 180;
2185    } else {
2186        ALOGW("We only support 0,90,180,270 degree rotation matrices");
2187        rotationDegrees = 0;
2188    }
2189
2190    if (rotationDegrees != 0) {
2191        mLastTrack->meta->setInt32(kKeyRotation, rotationDegrees);
2192    }
2193
2194    // Handle presentation display size, which could be different
2195    // from the image size indicated by kKeyWidth and kKeyHeight.
2196    uint32_t width = U32_AT(&buffer[dynSize + 52]);
2197    uint32_t height = U32_AT(&buffer[dynSize + 56]);
2198    mLastTrack->meta->setInt32(kKeyDisplayWidth, width >> 16);
2199    mLastTrack->meta->setInt32(kKeyDisplayHeight, height >> 16);
2200
2201    return OK;
2202}
2203
2204status_t MPEG4Extractor::parseITunesMetaData(off64_t offset, size_t size) {
2205    if (size < 4) {
2206        return ERROR_MALFORMED;
2207    }
2208
2209    uint8_t *buffer = new (std::nothrow) uint8_t[size + 1];
2210    if (buffer == NULL) {
2211        return ERROR_MALFORMED;
2212    }
2213    if (mDataSource->readAt(
2214                offset, buffer, size) != (ssize_t)size) {
2215        delete[] buffer;
2216        buffer = NULL;
2217
2218        return ERROR_IO;
2219    }
2220
2221    uint32_t flags = U32_AT(buffer);
2222
2223    uint32_t metadataKey = 0;
2224    char chunk[5];
2225    MakeFourCCString(mPath[4], chunk);
2226    ALOGV("meta: %s @ %lld", chunk, offset);
2227    switch (mPath[4]) {
2228        case FOURCC(0xa9, 'a', 'l', 'b'):
2229        {
2230            metadataKey = kKeyAlbum;
2231            break;
2232        }
2233        case FOURCC(0xa9, 'A', 'R', 'T'):
2234        {
2235            metadataKey = kKeyArtist;
2236            break;
2237        }
2238        case FOURCC('a', 'A', 'R', 'T'):
2239        {
2240            metadataKey = kKeyAlbumArtist;
2241            break;
2242        }
2243        case FOURCC(0xa9, 'd', 'a', 'y'):
2244        {
2245            metadataKey = kKeyYear;
2246            break;
2247        }
2248        case FOURCC(0xa9, 'n', 'a', 'm'):
2249        {
2250            metadataKey = kKeyTitle;
2251            break;
2252        }
2253        case FOURCC(0xa9, 'w', 'r', 't'):
2254        {
2255            metadataKey = kKeyWriter;
2256            break;
2257        }
2258        case FOURCC('c', 'o', 'v', 'r'):
2259        {
2260            metadataKey = kKeyAlbumArt;
2261            break;
2262        }
2263        case FOURCC('g', 'n', 'r', 'e'):
2264        {
2265            metadataKey = kKeyGenre;
2266            break;
2267        }
2268        case FOURCC(0xa9, 'g', 'e', 'n'):
2269        {
2270            metadataKey = kKeyGenre;
2271            break;
2272        }
2273        case FOURCC('c', 'p', 'i', 'l'):
2274        {
2275            if (size == 9 && flags == 21) {
2276                char tmp[16];
2277                sprintf(tmp, "%d",
2278                        (int)buffer[size - 1]);
2279
2280                mFileMetaData->setCString(kKeyCompilation, tmp);
2281            }
2282            break;
2283        }
2284        case FOURCC('t', 'r', 'k', 'n'):
2285        {
2286            if (size == 16 && flags == 0) {
2287                char tmp[16];
2288                uint16_t* pTrack = (uint16_t*)&buffer[10];
2289                uint16_t* pTotalTracks = (uint16_t*)&buffer[12];
2290                sprintf(tmp, "%d/%d", ntohs(*pTrack), ntohs(*pTotalTracks));
2291
2292                mFileMetaData->setCString(kKeyCDTrackNumber, tmp);
2293            }
2294            break;
2295        }
2296        case FOURCC('d', 'i', 's', 'k'):
2297        {
2298            if ((size == 14 || size == 16) && flags == 0) {
2299                char tmp[16];
2300                uint16_t* pDisc = (uint16_t*)&buffer[10];
2301                uint16_t* pTotalDiscs = (uint16_t*)&buffer[12];
2302                sprintf(tmp, "%d/%d", ntohs(*pDisc), ntohs(*pTotalDiscs));
2303
2304                mFileMetaData->setCString(kKeyDiscNumber, tmp);
2305            }
2306            break;
2307        }
2308        case FOURCC('-', '-', '-', '-'):
2309        {
2310            buffer[size] = '\0';
2311            switch (mPath[5]) {
2312                case FOURCC('m', 'e', 'a', 'n'):
2313                    mLastCommentMean.setTo((const char *)buffer + 4);
2314                    break;
2315                case FOURCC('n', 'a', 'm', 'e'):
2316                    mLastCommentName.setTo((const char *)buffer + 4);
2317                    break;
2318                case FOURCC('d', 'a', 't', 'a'):
2319                    mLastCommentData.setTo((const char *)buffer + 8);
2320                    break;
2321            }
2322
2323            // Once we have a set of mean/name/data info, go ahead and process
2324            // it to see if its something we are interested in.  Whether or not
2325            // were are interested in the specific tag, make sure to clear out
2326            // the set so we can be ready to process another tuple should one
2327            // show up later in the file.
2328            if ((mLastCommentMean.length() != 0) &&
2329                (mLastCommentName.length() != 0) &&
2330                (mLastCommentData.length() != 0)) {
2331
2332                if (mLastCommentMean == "com.apple.iTunes"
2333                        && mLastCommentName == "iTunSMPB") {
2334                    int32_t delay, padding;
2335                    if (sscanf(mLastCommentData,
2336                               " %*x %x %x %*x", &delay, &padding) == 2) {
2337                        mLastTrack->meta->setInt32(kKeyEncoderDelay, delay);
2338                        mLastTrack->meta->setInt32(kKeyEncoderPadding, padding);
2339                    }
2340                }
2341
2342                mLastCommentMean.clear();
2343                mLastCommentName.clear();
2344                mLastCommentData.clear();
2345            }
2346            break;
2347        }
2348
2349        default:
2350            break;
2351    }
2352
2353    if (size >= 8 && metadataKey && !mFileMetaData->hasData(metadataKey)) {
2354        if (metadataKey == kKeyAlbumArt) {
2355            mFileMetaData->setData(
2356                    kKeyAlbumArt, MetaData::TYPE_NONE,
2357                    buffer + 8, size - 8);
2358        } else if (metadataKey == kKeyGenre) {
2359            if (flags == 0) {
2360                // uint8_t genre code, iTunes genre codes are
2361                // the standard id3 codes, except they start
2362                // at 1 instead of 0 (e.g. Pop is 14, not 13)
2363                // We use standard id3 numbering, so subtract 1.
2364                int genrecode = (int)buffer[size - 1];
2365                genrecode--;
2366                if (genrecode < 0) {
2367                    genrecode = 255; // reserved for 'unknown genre'
2368                }
2369                char genre[10];
2370                sprintf(genre, "%d", genrecode);
2371
2372                mFileMetaData->setCString(metadataKey, genre);
2373            } else if (flags == 1) {
2374                // custom genre string
2375                buffer[size] = '\0';
2376
2377                mFileMetaData->setCString(
2378                        metadataKey, (const char *)buffer + 8);
2379            }
2380        } else {
2381            buffer[size] = '\0';
2382
2383            mFileMetaData->setCString(
2384                    metadataKey, (const char *)buffer + 8);
2385        }
2386    }
2387
2388    delete[] buffer;
2389    buffer = NULL;
2390
2391    return OK;
2392}
2393
2394status_t MPEG4Extractor::parse3GPPMetaData(off64_t offset, size_t size, int depth) {
2395    if (size < 4) {
2396        return ERROR_MALFORMED;
2397    }
2398
2399    uint8_t *buffer = new (std::nothrow) uint8_t[size];
2400    if (buffer == NULL) {
2401        return ERROR_MALFORMED;
2402    }
2403    if (mDataSource->readAt(
2404                offset, buffer, size) != (ssize_t)size) {
2405        delete[] buffer;
2406        buffer = NULL;
2407
2408        return ERROR_IO;
2409    }
2410
2411    uint32_t metadataKey = 0;
2412    switch (mPath[depth]) {
2413        case FOURCC('t', 'i', 't', 'l'):
2414        {
2415            metadataKey = kKeyTitle;
2416            break;
2417        }
2418        case FOURCC('p', 'e', 'r', 'f'):
2419        {
2420            metadataKey = kKeyArtist;
2421            break;
2422        }
2423        case FOURCC('a', 'u', 't', 'h'):
2424        {
2425            metadataKey = kKeyWriter;
2426            break;
2427        }
2428        case FOURCC('g', 'n', 'r', 'e'):
2429        {
2430            metadataKey = kKeyGenre;
2431            break;
2432        }
2433        case FOURCC('a', 'l', 'b', 'm'):
2434        {
2435            if (buffer[size - 1] != '\0') {
2436              char tmp[4];
2437              sprintf(tmp, "%u", buffer[size - 1]);
2438
2439              mFileMetaData->setCString(kKeyCDTrackNumber, tmp);
2440            }
2441
2442            metadataKey = kKeyAlbum;
2443            break;
2444        }
2445        case FOURCC('y', 'r', 'r', 'c'):
2446        {
2447            char tmp[5];
2448            uint16_t year = U16_AT(&buffer[4]);
2449
2450            if (year < 10000) {
2451                sprintf(tmp, "%u", year);
2452
2453                mFileMetaData->setCString(kKeyYear, tmp);
2454            }
2455            break;
2456        }
2457
2458        default:
2459            break;
2460    }
2461
2462    if (metadataKey > 0) {
2463        bool isUTF8 = true; // Common case
2464        char16_t *framedata = NULL;
2465        int len16 = 0; // Number of UTF-16 characters
2466
2467        // smallest possible valid UTF-16 string w BOM: 0xfe 0xff 0x00 0x00
2468        if (size - 6 >= 4) {
2469            len16 = ((size - 6) / 2) - 1; // don't include 0x0000 terminator
2470            framedata = (char16_t *)(buffer + 6);
2471            if (0xfffe == *framedata) {
2472                // endianness marker (BOM) doesn't match host endianness
2473                for (int i = 0; i < len16; i++) {
2474                    framedata[i] = bswap_16(framedata[i]);
2475                }
2476                // BOM is now swapped to 0xfeff, we will execute next block too
2477            }
2478
2479            if (0xfeff == *framedata) {
2480                // Remove the BOM
2481                framedata++;
2482                len16--;
2483                isUTF8 = false;
2484            }
2485            // else normal non-zero-length UTF-8 string
2486            // we can't handle UTF-16 without BOM as there is no other
2487            // indication of encoding.
2488        }
2489
2490        if (isUTF8) {
2491            mFileMetaData->setCString(metadataKey, (const char *)buffer + 6);
2492        } else {
2493            // Convert from UTF-16 string to UTF-8 string.
2494            String8 tmpUTF8str(framedata, len16);
2495            mFileMetaData->setCString(metadataKey, tmpUTF8str.string());
2496        }
2497    }
2498
2499    delete[] buffer;
2500    buffer = NULL;
2501
2502    return OK;
2503}
2504
2505void MPEG4Extractor::parseID3v2MetaData(off64_t offset) {
2506    ID3 id3(mDataSource, true /* ignorev1 */, offset);
2507
2508    if (id3.isValid()) {
2509        struct Map {
2510            int key;
2511            const char *tag1;
2512            const char *tag2;
2513        };
2514        static const Map kMap[] = {
2515            { kKeyAlbum, "TALB", "TAL" },
2516            { kKeyArtist, "TPE1", "TP1" },
2517            { kKeyAlbumArtist, "TPE2", "TP2" },
2518            { kKeyComposer, "TCOM", "TCM" },
2519            { kKeyGenre, "TCON", "TCO" },
2520            { kKeyTitle, "TIT2", "TT2" },
2521            { kKeyYear, "TYE", "TYER" },
2522            { kKeyAuthor, "TXT", "TEXT" },
2523            { kKeyCDTrackNumber, "TRK", "TRCK" },
2524            { kKeyDiscNumber, "TPA", "TPOS" },
2525            { kKeyCompilation, "TCP", "TCMP" },
2526        };
2527        static const size_t kNumMapEntries = sizeof(kMap) / sizeof(kMap[0]);
2528
2529        for (size_t i = 0; i < kNumMapEntries; ++i) {
2530            if (!mFileMetaData->hasData(kMap[i].key)) {
2531                ID3::Iterator *it = new ID3::Iterator(id3, kMap[i].tag1);
2532                if (it->done()) {
2533                    delete it;
2534                    it = new ID3::Iterator(id3, kMap[i].tag2);
2535                }
2536
2537                if (it->done()) {
2538                    delete it;
2539                    continue;
2540                }
2541
2542                String8 s;
2543                it->getString(&s);
2544                delete it;
2545
2546                mFileMetaData->setCString(kMap[i].key, s);
2547            }
2548        }
2549
2550        size_t dataSize;
2551        String8 mime;
2552        const void *data = id3.getAlbumArt(&dataSize, &mime);
2553
2554        if (data) {
2555            mFileMetaData->setData(kKeyAlbumArt, MetaData::TYPE_NONE, data, dataSize);
2556            mFileMetaData->setCString(kKeyAlbumArtMIME, mime.string());
2557        }
2558    }
2559}
2560
2561sp<MediaSource> MPEG4Extractor::getTrack(size_t index) {
2562    status_t err;
2563    if ((err = readMetaData()) != OK) {
2564        return NULL;
2565    }
2566
2567    Track *track = mFirstTrack;
2568    while (index > 0) {
2569        if (track == NULL) {
2570            return NULL;
2571        }
2572
2573        track = track->next;
2574        --index;
2575    }
2576
2577    if (track == NULL) {
2578        return NULL;
2579    }
2580
2581
2582    Trex *trex = NULL;
2583    int32_t trackId;
2584    if (track->meta->findInt32(kKeyTrackID, &trackId)) {
2585        for (size_t i = 0; i < mTrex.size(); i++) {
2586            Trex *t = &mTrex.editItemAt(index);
2587            if (t->track_ID == (uint32_t) trackId) {
2588                trex = t;
2589                break;
2590            }
2591        }
2592    }
2593
2594    ALOGV("getTrack called, pssh: %zu", mPssh.size());
2595
2596    return new MPEG4Source(
2597            track->meta, mDataSource, track->timescale, track->sampleTable,
2598            mSidxEntries, trex, mMoofOffset);
2599}
2600
2601// static
2602status_t MPEG4Extractor::verifyTrack(Track *track) {
2603    const char *mime;
2604    CHECK(track->meta->findCString(kKeyMIMEType, &mime));
2605
2606    uint32_t type;
2607    const void *data;
2608    size_t size;
2609    if (!strcasecmp(mime, MEDIA_MIMETYPE_VIDEO_AVC)) {
2610        if (!track->meta->findData(kKeyAVCC, &type, &data, &size)
2611                || type != kTypeAVCC) {
2612            return ERROR_MALFORMED;
2613        }
2614    } else if (!strcasecmp(mime, MEDIA_MIMETYPE_VIDEO_HEVC)) {
2615        if (!track->meta->findData(kKeyHVCC, &type, &data, &size)
2616                    || type != kTypeHVCC) {
2617            return ERROR_MALFORMED;
2618        }
2619    } else if (!strcasecmp(mime, MEDIA_MIMETYPE_VIDEO_MPEG4)
2620            || !strcasecmp(mime, MEDIA_MIMETYPE_AUDIO_AAC)) {
2621        if (!track->meta->findData(kKeyESDS, &type, &data, &size)
2622                || type != kTypeESDS) {
2623            return ERROR_MALFORMED;
2624        }
2625    }
2626
2627    if (track->sampleTable == NULL || !track->sampleTable->isValid()) {
2628        // Make sure we have all the metadata we need.
2629        ALOGE("stbl atom missing/invalid.");
2630        return ERROR_MALFORMED;
2631    }
2632
2633    return OK;
2634}
2635
2636typedef enum {
2637    //AOT_NONE             = -1,
2638    //AOT_NULL_OBJECT      = 0,
2639    //AOT_AAC_MAIN         = 1, /**< Main profile                              */
2640    AOT_AAC_LC           = 2,   /**< Low Complexity object                     */
2641    //AOT_AAC_SSR          = 3,
2642    //AOT_AAC_LTP          = 4,
2643    AOT_SBR              = 5,
2644    //AOT_AAC_SCAL         = 6,
2645    //AOT_TWIN_VQ          = 7,
2646    //AOT_CELP             = 8,
2647    //AOT_HVXC             = 9,
2648    //AOT_RSVD_10          = 10, /**< (reserved)                                */
2649    //AOT_RSVD_11          = 11, /**< (reserved)                                */
2650    //AOT_TTSI             = 12, /**< TTSI Object                               */
2651    //AOT_MAIN_SYNTH       = 13, /**< Main Synthetic object                     */
2652    //AOT_WAV_TAB_SYNTH    = 14, /**< Wavetable Synthesis object                */
2653    //AOT_GEN_MIDI         = 15, /**< General MIDI object                       */
2654    //AOT_ALG_SYNTH_AUD_FX = 16, /**< Algorithmic Synthesis and Audio FX object */
2655    AOT_ER_AAC_LC        = 17,   /**< Error Resilient(ER) AAC Low Complexity    */
2656    //AOT_RSVD_18          = 18, /**< (reserved)                                */
2657    //AOT_ER_AAC_LTP       = 19, /**< Error Resilient(ER) AAC LTP object        */
2658    AOT_ER_AAC_SCAL      = 20,   /**< Error Resilient(ER) AAC Scalable object   */
2659    //AOT_ER_TWIN_VQ       = 21, /**< Error Resilient(ER) TwinVQ object         */
2660    AOT_ER_BSAC          = 22,   /**< Error Resilient(ER) BSAC object           */
2661    AOT_ER_AAC_LD        = 23,   /**< Error Resilient(ER) AAC LowDelay object   */
2662    //AOT_ER_CELP          = 24, /**< Error Resilient(ER) CELP object           */
2663    //AOT_ER_HVXC          = 25, /**< Error Resilient(ER) HVXC object           */
2664    //AOT_ER_HILN          = 26, /**< Error Resilient(ER) HILN object           */
2665    //AOT_ER_PARA          = 27, /**< Error Resilient(ER) Parametric object     */
2666    //AOT_RSVD_28          = 28, /**< might become SSC                          */
2667    AOT_PS               = 29,   /**< PS, Parametric Stereo (includes SBR)      */
2668    //AOT_MPEGS            = 30, /**< MPEG Surround                             */
2669
2670    AOT_ESCAPE           = 31,   /**< Signal AOT uses more than 5 bits          */
2671
2672    //AOT_MP3ONMP4_L1      = 32, /**< MPEG-Layer1 in mp4                        */
2673    //AOT_MP3ONMP4_L2      = 33, /**< MPEG-Layer2 in mp4                        */
2674    //AOT_MP3ONMP4_L3      = 34, /**< MPEG-Layer3 in mp4                        */
2675    //AOT_RSVD_35          = 35, /**< might become DST                          */
2676    //AOT_RSVD_36          = 36, /**< might become ALS                          */
2677    //AOT_AAC_SLS          = 37, /**< AAC + SLS                                 */
2678    //AOT_SLS              = 38, /**< SLS                                       */
2679    //AOT_ER_AAC_ELD       = 39, /**< AAC Enhanced Low Delay                    */
2680
2681    //AOT_USAC             = 42, /**< USAC                                      */
2682    //AOT_SAOC             = 43, /**< SAOC                                      */
2683    //AOT_LD_MPEGS         = 44, /**< Low Delay MPEG Surround                   */
2684
2685    //AOT_RSVD50           = 50,  /**< Interim AOT for Rsvd50                   */
2686} AUDIO_OBJECT_TYPE;
2687
2688status_t MPEG4Extractor::updateAudioTrackInfoFromESDS_MPEG4Audio(
2689        const void *esds_data, size_t esds_size) {
2690    ESDS esds(esds_data, esds_size);
2691
2692    uint8_t objectTypeIndication;
2693    if (esds.getObjectTypeIndication(&objectTypeIndication) != OK) {
2694        return ERROR_MALFORMED;
2695    }
2696
2697    if (objectTypeIndication == 0xe1) {
2698        // This isn't MPEG4 audio at all, it's QCELP 14k...
2699        mLastTrack->meta->setCString(kKeyMIMEType, MEDIA_MIMETYPE_AUDIO_QCELP);
2700        return OK;
2701    }
2702
2703    if (objectTypeIndication  == 0x6b) {
2704        // The media subtype is MP3 audio
2705        // Our software MP3 audio decoder may not be able to handle
2706        // packetized MP3 audio; for now, lets just return ERROR_UNSUPPORTED
2707        ALOGE("MP3 track in MP4/3GPP file is not supported");
2708        return ERROR_UNSUPPORTED;
2709    }
2710
2711    const uint8_t *csd;
2712    size_t csd_size;
2713    if (esds.getCodecSpecificInfo(
2714                (const void **)&csd, &csd_size) != OK) {
2715        return ERROR_MALFORMED;
2716    }
2717
2718#if 0
2719    printf("ESD of size %d\n", csd_size);
2720    hexdump(csd, csd_size);
2721#endif
2722
2723    if (csd_size == 0) {
2724        // There's no further information, i.e. no codec specific data
2725        // Let's assume that the information provided in the mpeg4 headers
2726        // is accurate and hope for the best.
2727
2728        return OK;
2729    }
2730
2731    if (csd_size < 2) {
2732        return ERROR_MALFORMED;
2733    }
2734
2735    static uint32_t kSamplingRate[] = {
2736        96000, 88200, 64000, 48000, 44100, 32000, 24000, 22050,
2737        16000, 12000, 11025, 8000, 7350
2738    };
2739
2740    ABitReader br(csd, csd_size);
2741    uint32_t objectType = br.getBits(5);
2742
2743    if (objectType == 31) {  // AAC-ELD => additional 6 bits
2744        objectType = 32 + br.getBits(6);
2745    }
2746
2747    //keep AOT type
2748    mLastTrack->meta->setInt32(kKeyAACAOT, objectType);
2749
2750    uint32_t freqIndex = br.getBits(4);
2751
2752    int32_t sampleRate = 0;
2753    int32_t numChannels = 0;
2754    if (freqIndex == 15) {
2755        if (csd_size < 5) {
2756            return ERROR_MALFORMED;
2757        }
2758        sampleRate = br.getBits(24);
2759        numChannels = br.getBits(4);
2760    } else {
2761        numChannels = br.getBits(4);
2762
2763        if (freqIndex == 13 || freqIndex == 14) {
2764            return ERROR_MALFORMED;
2765        }
2766
2767        sampleRate = kSamplingRate[freqIndex];
2768    }
2769
2770    if (objectType == AOT_SBR || objectType == AOT_PS) {//SBR specific config per 14496-3 table 1.13
2771        uint32_t extFreqIndex = br.getBits(4);
2772        int32_t extSampleRate;
2773        if (extFreqIndex == 15) {
2774            if (csd_size < 8) {
2775                return ERROR_MALFORMED;
2776            }
2777            extSampleRate = br.getBits(24);
2778        } else {
2779            if (extFreqIndex == 13 || extFreqIndex == 14) {
2780                return ERROR_MALFORMED;
2781            }
2782            extSampleRate = kSamplingRate[extFreqIndex];
2783        }
2784        //TODO: save the extension sampling rate value in meta data =>
2785        //      mLastTrack->meta->setInt32(kKeyExtSampleRate, extSampleRate);
2786    }
2787
2788    switch (numChannels) {
2789        // values defined in 14496-3_2009 amendment-4 Table 1.19 - Channel Configuration
2790        case 0:
2791        case 1:// FC
2792        case 2:// FL FR
2793        case 3:// FC, FL FR
2794        case 4:// FC, FL FR, RC
2795        case 5:// FC, FL FR, SL SR
2796        case 6:// FC, FL FR, SL SR, LFE
2797            //numChannels already contains the right value
2798            break;
2799        case 11:// FC, FL FR, SL SR, RC, LFE
2800            numChannels = 7;
2801            break;
2802        case 7: // FC, FCL FCR, FL FR, SL SR, LFE
2803        case 12:// FC, FL  FR,  SL SR, RL RR, LFE
2804        case 14:// FC, FL  FR,  SL SR, LFE, FHL FHR
2805            numChannels = 8;
2806            break;
2807        default:
2808            return ERROR_UNSUPPORTED;
2809    }
2810
2811    {
2812        if (objectType == AOT_SBR || objectType == AOT_PS) {
2813            const int32_t extensionSamplingFrequency = br.getBits(4);
2814            objectType = br.getBits(5);
2815
2816            if (objectType == AOT_ESCAPE) {
2817                objectType = 32 + br.getBits(6);
2818            }
2819        }
2820        if (objectType == AOT_AAC_LC || objectType == AOT_ER_AAC_LC ||
2821                objectType == AOT_ER_AAC_LD || objectType == AOT_ER_AAC_SCAL ||
2822                objectType == AOT_ER_BSAC) {
2823            const int32_t frameLengthFlag = br.getBits(1);
2824
2825            const int32_t dependsOnCoreCoder = br.getBits(1);
2826
2827            if (dependsOnCoreCoder ) {
2828                const int32_t coreCoderDelay = br.getBits(14);
2829            }
2830
2831            const int32_t extensionFlag = br.getBits(1);
2832
2833            if (numChannels == 0 ) {
2834                int32_t channelsEffectiveNum = 0;
2835                int32_t channelsNum = 0;
2836                const int32_t ElementInstanceTag = br.getBits(4);
2837                const int32_t Profile = br.getBits(2);
2838                const int32_t SamplingFrequencyIndex = br.getBits(4);
2839                const int32_t NumFrontChannelElements = br.getBits(4);
2840                const int32_t NumSideChannelElements = br.getBits(4);
2841                const int32_t NumBackChannelElements = br.getBits(4);
2842                const int32_t NumLfeChannelElements = br.getBits(2);
2843                const int32_t NumAssocDataElements = br.getBits(3);
2844                const int32_t NumValidCcElements = br.getBits(4);
2845
2846                const int32_t MonoMixdownPresent = br.getBits(1);
2847                if (MonoMixdownPresent != 0) {
2848                    const int32_t MonoMixdownElementNumber = br.getBits(4);
2849                }
2850
2851                const int32_t StereoMixdownPresent = br.getBits(1);
2852                if (StereoMixdownPresent != 0) {
2853                    const int32_t StereoMixdownElementNumber = br.getBits(4);
2854                }
2855
2856                const int32_t MatrixMixdownIndexPresent = br.getBits(1);
2857                if (MatrixMixdownIndexPresent != 0) {
2858                    const int32_t MatrixMixdownIndex = br.getBits(2);
2859                    const int32_t PseudoSurroundEnable = br.getBits(1);
2860                }
2861
2862                int i;
2863                for (i=0; i < NumFrontChannelElements; i++) {
2864                    const int32_t FrontElementIsCpe = br.getBits(1);
2865                    const int32_t FrontElementTagSelect = br.getBits(4);
2866                    channelsNum += FrontElementIsCpe ? 2 : 1;
2867                }
2868
2869                for (i=0; i < NumSideChannelElements; i++) {
2870                    const int32_t SideElementIsCpe = br.getBits(1);
2871                    const int32_t SideElementTagSelect = br.getBits(4);
2872                    channelsNum += SideElementIsCpe ? 2 : 1;
2873                }
2874
2875                for (i=0; i < NumBackChannelElements; i++) {
2876                    const int32_t BackElementIsCpe = br.getBits(1);
2877                    const int32_t BackElementTagSelect = br.getBits(4);
2878                    channelsNum += BackElementIsCpe ? 2 : 1;
2879                }
2880                channelsEffectiveNum = channelsNum;
2881
2882                for (i=0; i < NumLfeChannelElements; i++) {
2883                    const int32_t LfeElementTagSelect = br.getBits(4);
2884                    channelsNum += 1;
2885                }
2886                ALOGV("mpeg4 audio channelsNum = %d", channelsNum);
2887                ALOGV("mpeg4 audio channelsEffectiveNum = %d", channelsEffectiveNum);
2888                numChannels = channelsNum;
2889            }
2890        }
2891    }
2892
2893    if (numChannels == 0) {
2894        return ERROR_UNSUPPORTED;
2895    }
2896
2897    int32_t prevSampleRate;
2898    CHECK(mLastTrack->meta->findInt32(kKeySampleRate, &prevSampleRate));
2899
2900    if (prevSampleRate != sampleRate) {
2901        ALOGV("mpeg4 audio sample rate different from previous setting. "
2902             "was: %d, now: %d", prevSampleRate, sampleRate);
2903    }
2904
2905    mLastTrack->meta->setInt32(kKeySampleRate, sampleRate);
2906
2907    int32_t prevChannelCount;
2908    CHECK(mLastTrack->meta->findInt32(kKeyChannelCount, &prevChannelCount));
2909
2910    if (prevChannelCount != numChannels) {
2911        ALOGV("mpeg4 audio channel count different from previous setting. "
2912             "was: %d, now: %d", prevChannelCount, numChannels);
2913    }
2914
2915    mLastTrack->meta->setInt32(kKeyChannelCount, numChannels);
2916
2917    return OK;
2918}
2919
2920////////////////////////////////////////////////////////////////////////////////
2921
2922MPEG4Source::MPEG4Source(
2923        const sp<MetaData> &format,
2924        const sp<DataSource> &dataSource,
2925        int32_t timeScale,
2926        const sp<SampleTable> &sampleTable,
2927        Vector<SidxEntry> &sidx,
2928        const Trex *trex,
2929        off64_t firstMoofOffset)
2930    : mFormat(format),
2931      mDataSource(dataSource),
2932      mTimescale(timeScale),
2933      mSampleTable(sampleTable),
2934      mCurrentSampleIndex(0),
2935      mCurrentFragmentIndex(0),
2936      mSegments(sidx),
2937      mTrex(trex),
2938      mFirstMoofOffset(firstMoofOffset),
2939      mCurrentMoofOffset(firstMoofOffset),
2940      mCurrentTime(0),
2941      mCurrentSampleInfoAllocSize(0),
2942      mCurrentSampleInfoSizes(NULL),
2943      mCurrentSampleInfoOffsetsAllocSize(0),
2944      mCurrentSampleInfoOffsets(NULL),
2945      mIsAVC(false),
2946      mIsHEVC(false),
2947      mNALLengthSize(0),
2948      mStarted(false),
2949      mGroup(NULL),
2950      mBuffer(NULL),
2951      mWantsNALFragments(false),
2952      mSrcBuffer(NULL) {
2953
2954    memset(&mTrackFragmentHeaderInfo, 0, sizeof(mTrackFragmentHeaderInfo));
2955
2956    mFormat->findInt32(kKeyCryptoMode, &mCryptoMode);
2957    mDefaultIVSize = 0;
2958    mFormat->findInt32(kKeyCryptoDefaultIVSize, &mDefaultIVSize);
2959    uint32_t keytype;
2960    const void *key;
2961    size_t keysize;
2962    if (mFormat->findData(kKeyCryptoKey, &keytype, &key, &keysize)) {
2963        CHECK(keysize <= 16);
2964        memset(mCryptoKey, 0, 16);
2965        memcpy(mCryptoKey, key, keysize);
2966    }
2967
2968    const char *mime;
2969    bool success = mFormat->findCString(kKeyMIMEType, &mime);
2970    CHECK(success);
2971
2972    mIsAVC = !strcasecmp(mime, MEDIA_MIMETYPE_VIDEO_AVC);
2973    mIsHEVC = !strcasecmp(mime, MEDIA_MIMETYPE_VIDEO_HEVC);
2974
2975    if (mIsAVC) {
2976        uint32_t type;
2977        const void *data;
2978        size_t size;
2979        CHECK(format->findData(kKeyAVCC, &type, &data, &size));
2980
2981        const uint8_t *ptr = (const uint8_t *)data;
2982
2983        CHECK(size >= 7);
2984        CHECK_EQ((unsigned)ptr[0], 1u);  // configurationVersion == 1
2985
2986        // The number of bytes used to encode the length of a NAL unit.
2987        mNALLengthSize = 1 + (ptr[4] & 3);
2988    } else if (mIsHEVC) {
2989        uint32_t type;
2990        const void *data;
2991        size_t size;
2992        CHECK(format->findData(kKeyHVCC, &type, &data, &size));
2993
2994        const uint8_t *ptr = (const uint8_t *)data;
2995
2996        CHECK(size >= 7);
2997        CHECK_EQ((unsigned)ptr[0], 1u);  // configurationVersion == 1
2998
2999        mNALLengthSize = 1 + (ptr[14 + 7] & 3);
3000    }
3001
3002    CHECK(format->findInt32(kKeyTrackID, &mTrackId));
3003
3004    if (mFirstMoofOffset != 0) {
3005        off64_t offset = mFirstMoofOffset;
3006        parseChunk(&offset);
3007    }
3008}
3009
3010MPEG4Source::~MPEG4Source() {
3011    if (mStarted) {
3012        stop();
3013    }
3014    free(mCurrentSampleInfoSizes);
3015    free(mCurrentSampleInfoOffsets);
3016}
3017
3018status_t MPEG4Source::start(MetaData *params) {
3019    Mutex::Autolock autoLock(mLock);
3020
3021    CHECK(!mStarted);
3022
3023    int32_t val;
3024    if (params && params->findInt32(kKeyWantsNALFragments, &val)
3025        && val != 0) {
3026        mWantsNALFragments = true;
3027    } else {
3028        mWantsNALFragments = false;
3029    }
3030
3031    mGroup = new MediaBufferGroup;
3032
3033    int32_t max_size;
3034    CHECK(mFormat->findInt32(kKeyMaxInputSize, &max_size));
3035
3036    mGroup->add_buffer(new MediaBuffer(max_size));
3037
3038    mSrcBuffer = new (std::nothrow) uint8_t[max_size];
3039    if (mSrcBuffer == NULL) {
3040        // file probably specified a bad max size
3041        return ERROR_MALFORMED;
3042    }
3043
3044    mStarted = true;
3045
3046    return OK;
3047}
3048
3049status_t MPEG4Source::stop() {
3050    Mutex::Autolock autoLock(mLock);
3051
3052    CHECK(mStarted);
3053
3054    if (mBuffer != NULL) {
3055        mBuffer->release();
3056        mBuffer = NULL;
3057    }
3058
3059    delete[] mSrcBuffer;
3060    mSrcBuffer = NULL;
3061
3062    delete mGroup;
3063    mGroup = NULL;
3064
3065    mStarted = false;
3066    mCurrentSampleIndex = 0;
3067
3068    return OK;
3069}
3070
3071status_t MPEG4Source::parseChunk(off64_t *offset) {
3072    uint32_t hdr[2];
3073    if (mDataSource->readAt(*offset, hdr, 8) < 8) {
3074        return ERROR_IO;
3075    }
3076    uint64_t chunk_size = ntohl(hdr[0]);
3077    uint32_t chunk_type = ntohl(hdr[1]);
3078    off64_t data_offset = *offset + 8;
3079
3080    if (chunk_size == 1) {
3081        if (mDataSource->readAt(*offset + 8, &chunk_size, 8) < 8) {
3082            return ERROR_IO;
3083        }
3084        chunk_size = ntoh64(chunk_size);
3085        data_offset += 8;
3086
3087        if (chunk_size < 16) {
3088            // The smallest valid chunk is 16 bytes long in this case.
3089            return ERROR_MALFORMED;
3090        }
3091    } else if (chunk_size < 8) {
3092        // The smallest valid chunk is 8 bytes long.
3093        return ERROR_MALFORMED;
3094    }
3095
3096    char chunk[5];
3097    MakeFourCCString(chunk_type, chunk);
3098    ALOGV("MPEG4Source chunk %s @ %llx", chunk, *offset);
3099
3100    off64_t chunk_data_size = *offset + chunk_size - data_offset;
3101
3102    switch(chunk_type) {
3103
3104        case FOURCC('t', 'r', 'a', 'f'):
3105        case FOURCC('m', 'o', 'o', 'f'): {
3106            off64_t stop_offset = *offset + chunk_size;
3107            *offset = data_offset;
3108            while (*offset < stop_offset) {
3109                status_t err = parseChunk(offset);
3110                if (err != OK) {
3111                    return err;
3112                }
3113            }
3114            if (chunk_type == FOURCC('m', 'o', 'o', 'f')) {
3115                // *offset points to the box following this moof. Find the next moof from there.
3116
3117                while (true) {
3118                    if (mDataSource->readAt(*offset, hdr, 8) < 8) {
3119                        return ERROR_END_OF_STREAM;
3120                    }
3121                    chunk_size = ntohl(hdr[0]);
3122                    chunk_type = ntohl(hdr[1]);
3123                    if (chunk_type == FOURCC('m', 'o', 'o', 'f')) {
3124                        mNextMoofOffset = *offset;
3125                        break;
3126                    }
3127                    *offset += chunk_size;
3128                }
3129            }
3130            break;
3131        }
3132
3133        case FOURCC('t', 'f', 'h', 'd'): {
3134                status_t err;
3135                if ((err = parseTrackFragmentHeader(data_offset, chunk_data_size)) != OK) {
3136                    return err;
3137                }
3138                *offset += chunk_size;
3139                break;
3140        }
3141
3142        case FOURCC('t', 'r', 'u', 'n'): {
3143                status_t err;
3144                if (mLastParsedTrackId == mTrackId) {
3145                    if ((err = parseTrackFragmentRun(data_offset, chunk_data_size)) != OK) {
3146                        return err;
3147                    }
3148                }
3149
3150                *offset += chunk_size;
3151                break;
3152        }
3153
3154        case FOURCC('s', 'a', 'i', 'z'): {
3155            status_t err;
3156            if ((err = parseSampleAuxiliaryInformationSizes(data_offset, chunk_data_size)) != OK) {
3157                return err;
3158            }
3159            *offset += chunk_size;
3160            break;
3161        }
3162        case FOURCC('s', 'a', 'i', 'o'): {
3163            status_t err;
3164            if ((err = parseSampleAuxiliaryInformationOffsets(data_offset, chunk_data_size)) != OK) {
3165                return err;
3166            }
3167            *offset += chunk_size;
3168            break;
3169        }
3170
3171        case FOURCC('m', 'd', 'a', 't'): {
3172            // parse DRM info if present
3173            ALOGV("MPEG4Source::parseChunk mdat");
3174            // if saiz/saoi was previously observed, do something with the sampleinfos
3175            *offset += chunk_size;
3176            break;
3177        }
3178
3179        default: {
3180            *offset += chunk_size;
3181            break;
3182        }
3183    }
3184    return OK;
3185}
3186
3187status_t MPEG4Source::parseSampleAuxiliaryInformationSizes(
3188        off64_t offset, off64_t /* size */) {
3189    ALOGV("parseSampleAuxiliaryInformationSizes");
3190    // 14496-12 8.7.12
3191    uint8_t version;
3192    if (mDataSource->readAt(
3193            offset, &version, sizeof(version))
3194            < (ssize_t)sizeof(version)) {
3195        return ERROR_IO;
3196    }
3197
3198    if (version != 0) {
3199        return ERROR_UNSUPPORTED;
3200    }
3201    offset++;
3202
3203    uint32_t flags;
3204    if (!mDataSource->getUInt24(offset, &flags)) {
3205        return ERROR_IO;
3206    }
3207    offset += 3;
3208
3209    if (flags & 1) {
3210        uint32_t tmp;
3211        if (!mDataSource->getUInt32(offset, &tmp)) {
3212            return ERROR_MALFORMED;
3213        }
3214        mCurrentAuxInfoType = tmp;
3215        offset += 4;
3216        if (!mDataSource->getUInt32(offset, &tmp)) {
3217            return ERROR_MALFORMED;
3218        }
3219        mCurrentAuxInfoTypeParameter = tmp;
3220        offset += 4;
3221    }
3222
3223    uint8_t defsize;
3224    if (mDataSource->readAt(offset, &defsize, 1) != 1) {
3225        return ERROR_MALFORMED;
3226    }
3227    mCurrentDefaultSampleInfoSize = defsize;
3228    offset++;
3229
3230    uint32_t smplcnt;
3231    if (!mDataSource->getUInt32(offset, &smplcnt)) {
3232        return ERROR_MALFORMED;
3233    }
3234    mCurrentSampleInfoCount = smplcnt;
3235    offset += 4;
3236
3237    if (mCurrentDefaultSampleInfoSize != 0) {
3238        ALOGV("@@@@ using default sample info size of %d", mCurrentDefaultSampleInfoSize);
3239        return OK;
3240    }
3241    if (smplcnt > mCurrentSampleInfoAllocSize) {
3242        mCurrentSampleInfoSizes = (uint8_t*) realloc(mCurrentSampleInfoSizes, smplcnt);
3243        mCurrentSampleInfoAllocSize = smplcnt;
3244    }
3245
3246    mDataSource->readAt(offset, mCurrentSampleInfoSizes, smplcnt);
3247    return OK;
3248}
3249
3250status_t MPEG4Source::parseSampleAuxiliaryInformationOffsets(
3251        off64_t offset, off64_t /* size */) {
3252    ALOGV("parseSampleAuxiliaryInformationOffsets");
3253    // 14496-12 8.7.13
3254    uint8_t version;
3255    if (mDataSource->readAt(offset, &version, sizeof(version)) != 1) {
3256        return ERROR_IO;
3257    }
3258    offset++;
3259
3260    uint32_t flags;
3261    if (!mDataSource->getUInt24(offset, &flags)) {
3262        return ERROR_IO;
3263    }
3264    offset += 3;
3265
3266    uint32_t entrycount;
3267    if (!mDataSource->getUInt32(offset, &entrycount)) {
3268        return ERROR_IO;
3269    }
3270    offset += 4;
3271
3272    if (entrycount > mCurrentSampleInfoOffsetsAllocSize) {
3273        mCurrentSampleInfoOffsets = (uint64_t*) realloc(mCurrentSampleInfoOffsets, entrycount * 8);
3274        mCurrentSampleInfoOffsetsAllocSize = entrycount;
3275    }
3276    mCurrentSampleInfoOffsetCount = entrycount;
3277
3278    for (size_t i = 0; i < entrycount; i++) {
3279        if (version == 0) {
3280            uint32_t tmp;
3281            if (!mDataSource->getUInt32(offset, &tmp)) {
3282                return ERROR_IO;
3283            }
3284            mCurrentSampleInfoOffsets[i] = tmp;
3285            offset += 4;
3286        } else {
3287            uint64_t tmp;
3288            if (!mDataSource->getUInt64(offset, &tmp)) {
3289                return ERROR_IO;
3290            }
3291            mCurrentSampleInfoOffsets[i] = tmp;
3292            offset += 8;
3293        }
3294    }
3295
3296    // parse clear/encrypted data
3297
3298    off64_t drmoffset = mCurrentSampleInfoOffsets[0]; // from moof
3299
3300    drmoffset += mCurrentMoofOffset;
3301    int ivlength;
3302    CHECK(mFormat->findInt32(kKeyCryptoDefaultIVSize, &ivlength));
3303
3304    // read CencSampleAuxiliaryDataFormats
3305    for (size_t i = 0; i < mCurrentSampleInfoCount; i++) {
3306        Sample *smpl = &mCurrentSamples.editItemAt(i);
3307
3308        memset(smpl->iv, 0, 16);
3309        if (mDataSource->readAt(drmoffset, smpl->iv, ivlength) != ivlength) {
3310            return ERROR_IO;
3311        }
3312
3313        drmoffset += ivlength;
3314
3315        int32_t smplinfosize = mCurrentDefaultSampleInfoSize;
3316        if (smplinfosize == 0) {
3317            smplinfosize = mCurrentSampleInfoSizes[i];
3318        }
3319        if (smplinfosize > ivlength) {
3320            uint16_t numsubsamples;
3321            if (!mDataSource->getUInt16(drmoffset, &numsubsamples)) {
3322                return ERROR_IO;
3323            }
3324            drmoffset += 2;
3325            for (size_t j = 0; j < numsubsamples; j++) {
3326                uint16_t numclear;
3327                uint32_t numencrypted;
3328                if (!mDataSource->getUInt16(drmoffset, &numclear)) {
3329                    return ERROR_IO;
3330                }
3331                drmoffset += 2;
3332                if (!mDataSource->getUInt32(drmoffset, &numencrypted)) {
3333                    return ERROR_IO;
3334                }
3335                drmoffset += 4;
3336                smpl->clearsizes.add(numclear);
3337                smpl->encryptedsizes.add(numencrypted);
3338            }
3339        } else {
3340            smpl->clearsizes.add(0);
3341            smpl->encryptedsizes.add(smpl->size);
3342        }
3343    }
3344
3345
3346    return OK;
3347}
3348
3349status_t MPEG4Source::parseTrackFragmentHeader(off64_t offset, off64_t size) {
3350
3351    if (size < 8) {
3352        return -EINVAL;
3353    }
3354
3355    uint32_t flags;
3356    if (!mDataSource->getUInt32(offset, &flags)) { // actually version + flags
3357        return ERROR_MALFORMED;
3358    }
3359
3360    if (flags & 0xff000000) {
3361        return -EINVAL;
3362    }
3363
3364    if (!mDataSource->getUInt32(offset + 4, (uint32_t*)&mLastParsedTrackId)) {
3365        return ERROR_MALFORMED;
3366    }
3367
3368    if (mLastParsedTrackId != mTrackId) {
3369        // this is not the right track, skip it
3370        return OK;
3371    }
3372
3373    mTrackFragmentHeaderInfo.mFlags = flags;
3374    mTrackFragmentHeaderInfo.mTrackID = mLastParsedTrackId;
3375    offset += 8;
3376    size -= 8;
3377
3378    ALOGV("fragment header: %08x %08x", flags, mTrackFragmentHeaderInfo.mTrackID);
3379
3380    if (flags & TrackFragmentHeaderInfo::kBaseDataOffsetPresent) {
3381        if (size < 8) {
3382            return -EINVAL;
3383        }
3384
3385        if (!mDataSource->getUInt64(offset, &mTrackFragmentHeaderInfo.mBaseDataOffset)) {
3386            return ERROR_MALFORMED;
3387        }
3388        offset += 8;
3389        size -= 8;
3390    }
3391
3392    if (flags & TrackFragmentHeaderInfo::kSampleDescriptionIndexPresent) {
3393        if (size < 4) {
3394            return -EINVAL;
3395        }
3396
3397        if (!mDataSource->getUInt32(offset, &mTrackFragmentHeaderInfo.mSampleDescriptionIndex)) {
3398            return ERROR_MALFORMED;
3399        }
3400        offset += 4;
3401        size -= 4;
3402    }
3403
3404    if (flags & TrackFragmentHeaderInfo::kDefaultSampleDurationPresent) {
3405        if (size < 4) {
3406            return -EINVAL;
3407        }
3408
3409        if (!mDataSource->getUInt32(offset, &mTrackFragmentHeaderInfo.mDefaultSampleDuration)) {
3410            return ERROR_MALFORMED;
3411        }
3412        offset += 4;
3413        size -= 4;
3414    }
3415
3416    if (flags & TrackFragmentHeaderInfo::kDefaultSampleSizePresent) {
3417        if (size < 4) {
3418            return -EINVAL;
3419        }
3420
3421        if (!mDataSource->getUInt32(offset, &mTrackFragmentHeaderInfo.mDefaultSampleSize)) {
3422            return ERROR_MALFORMED;
3423        }
3424        offset += 4;
3425        size -= 4;
3426    }
3427
3428    if (flags & TrackFragmentHeaderInfo::kDefaultSampleFlagsPresent) {
3429        if (size < 4) {
3430            return -EINVAL;
3431        }
3432
3433        if (!mDataSource->getUInt32(offset, &mTrackFragmentHeaderInfo.mDefaultSampleFlags)) {
3434            return ERROR_MALFORMED;
3435        }
3436        offset += 4;
3437        size -= 4;
3438    }
3439
3440    if (!(flags & TrackFragmentHeaderInfo::kBaseDataOffsetPresent)) {
3441        mTrackFragmentHeaderInfo.mBaseDataOffset = mCurrentMoofOffset;
3442    }
3443
3444    mTrackFragmentHeaderInfo.mDataOffset = 0;
3445    return OK;
3446}
3447
3448status_t MPEG4Source::parseTrackFragmentRun(off64_t offset, off64_t size) {
3449
3450    ALOGV("MPEG4Extractor::parseTrackFragmentRun");
3451    if (size < 8) {
3452        return -EINVAL;
3453    }
3454
3455    enum {
3456        kDataOffsetPresent                  = 0x01,
3457        kFirstSampleFlagsPresent            = 0x04,
3458        kSampleDurationPresent              = 0x100,
3459        kSampleSizePresent                  = 0x200,
3460        kSampleFlagsPresent                 = 0x400,
3461        kSampleCompositionTimeOffsetPresent = 0x800,
3462    };
3463
3464    uint32_t flags;
3465    if (!mDataSource->getUInt32(offset, &flags)) {
3466        return ERROR_MALFORMED;
3467    }
3468    ALOGV("fragment run flags: %08x", flags);
3469
3470    if (flags & 0xff000000) {
3471        return -EINVAL;
3472    }
3473
3474    if ((flags & kFirstSampleFlagsPresent) && (flags & kSampleFlagsPresent)) {
3475        // These two shall not be used together.
3476        return -EINVAL;
3477    }
3478
3479    uint32_t sampleCount;
3480    if (!mDataSource->getUInt32(offset + 4, &sampleCount)) {
3481        return ERROR_MALFORMED;
3482    }
3483    offset += 8;
3484    size -= 8;
3485
3486    uint64_t dataOffset = mTrackFragmentHeaderInfo.mDataOffset;
3487
3488    uint32_t firstSampleFlags = 0;
3489
3490    if (flags & kDataOffsetPresent) {
3491        if (size < 4) {
3492            return -EINVAL;
3493        }
3494
3495        int32_t dataOffsetDelta;
3496        if (!mDataSource->getUInt32(offset, (uint32_t*)&dataOffsetDelta)) {
3497            return ERROR_MALFORMED;
3498        }
3499
3500        dataOffset = mTrackFragmentHeaderInfo.mBaseDataOffset + dataOffsetDelta;
3501
3502        offset += 4;
3503        size -= 4;
3504    }
3505
3506    if (flags & kFirstSampleFlagsPresent) {
3507        if (size < 4) {
3508            return -EINVAL;
3509        }
3510
3511        if (!mDataSource->getUInt32(offset, &firstSampleFlags)) {
3512            return ERROR_MALFORMED;
3513        }
3514        offset += 4;
3515        size -= 4;
3516    }
3517
3518    uint32_t sampleDuration = 0, sampleSize = 0, sampleFlags = 0,
3519             sampleCtsOffset = 0;
3520
3521    size_t bytesPerSample = 0;
3522    if (flags & kSampleDurationPresent) {
3523        bytesPerSample += 4;
3524    } else if (mTrackFragmentHeaderInfo.mFlags
3525            & TrackFragmentHeaderInfo::kDefaultSampleDurationPresent) {
3526        sampleDuration = mTrackFragmentHeaderInfo.mDefaultSampleDuration;
3527    } else if (mTrex) {
3528        sampleDuration = mTrex->default_sample_duration;
3529    }
3530
3531    if (flags & kSampleSizePresent) {
3532        bytesPerSample += 4;
3533    } else if (mTrackFragmentHeaderInfo.mFlags
3534            & TrackFragmentHeaderInfo::kDefaultSampleSizePresent) {
3535        sampleSize = mTrackFragmentHeaderInfo.mDefaultSampleSize;
3536    } else {
3537        sampleSize = mTrackFragmentHeaderInfo.mDefaultSampleSize;
3538    }
3539
3540    if (flags & kSampleFlagsPresent) {
3541        bytesPerSample += 4;
3542    } else if (mTrackFragmentHeaderInfo.mFlags
3543            & TrackFragmentHeaderInfo::kDefaultSampleFlagsPresent) {
3544        sampleFlags = mTrackFragmentHeaderInfo.mDefaultSampleFlags;
3545    } else {
3546        sampleFlags = mTrackFragmentHeaderInfo.mDefaultSampleFlags;
3547    }
3548
3549    if (flags & kSampleCompositionTimeOffsetPresent) {
3550        bytesPerSample += 4;
3551    } else {
3552        sampleCtsOffset = 0;
3553    }
3554
3555    if (size < (off64_t)sampleCount * bytesPerSample) {
3556        return -EINVAL;
3557    }
3558
3559    Sample tmp;
3560    for (uint32_t i = 0; i < sampleCount; ++i) {
3561        if (flags & kSampleDurationPresent) {
3562            if (!mDataSource->getUInt32(offset, &sampleDuration)) {
3563                return ERROR_MALFORMED;
3564            }
3565            offset += 4;
3566        }
3567
3568        if (flags & kSampleSizePresent) {
3569            if (!mDataSource->getUInt32(offset, &sampleSize)) {
3570                return ERROR_MALFORMED;
3571            }
3572            offset += 4;
3573        }
3574
3575        if (flags & kSampleFlagsPresent) {
3576            if (!mDataSource->getUInt32(offset, &sampleFlags)) {
3577                return ERROR_MALFORMED;
3578            }
3579            offset += 4;
3580        }
3581
3582        if (flags & kSampleCompositionTimeOffsetPresent) {
3583            if (!mDataSource->getUInt32(offset, &sampleCtsOffset)) {
3584                return ERROR_MALFORMED;
3585            }
3586            offset += 4;
3587        }
3588
3589        ALOGV("adding sample %d at offset 0x%08" PRIx64 ", size %u, duration %u, "
3590              " flags 0x%08x", i + 1,
3591                dataOffset, sampleSize, sampleDuration,
3592                (flags & kFirstSampleFlagsPresent) && i == 0
3593                    ? firstSampleFlags : sampleFlags);
3594        tmp.offset = dataOffset;
3595        tmp.size = sampleSize;
3596        tmp.duration = sampleDuration;
3597        tmp.compositionOffset = sampleCtsOffset;
3598        mCurrentSamples.add(tmp);
3599
3600        dataOffset += sampleSize;
3601    }
3602
3603    mTrackFragmentHeaderInfo.mDataOffset = dataOffset;
3604
3605    return OK;
3606}
3607
3608sp<MetaData> MPEG4Source::getFormat() {
3609    Mutex::Autolock autoLock(mLock);
3610
3611    return mFormat;
3612}
3613
3614size_t MPEG4Source::parseNALSize(const uint8_t *data) const {
3615    switch (mNALLengthSize) {
3616        case 1:
3617            return *data;
3618        case 2:
3619            return U16_AT(data);
3620        case 3:
3621            return ((size_t)data[0] << 16) | U16_AT(&data[1]);
3622        case 4:
3623            return U32_AT(data);
3624    }
3625
3626    // This cannot happen, mNALLengthSize springs to life by adding 1 to
3627    // a 2-bit integer.
3628    CHECK(!"Should not be here.");
3629
3630    return 0;
3631}
3632
3633status_t MPEG4Source::read(
3634        MediaBuffer **out, const ReadOptions *options) {
3635    Mutex::Autolock autoLock(mLock);
3636
3637    CHECK(mStarted);
3638
3639    if (mFirstMoofOffset > 0) {
3640        return fragmentedRead(out, options);
3641    }
3642
3643    *out = NULL;
3644
3645    int64_t targetSampleTimeUs = -1;
3646
3647    int64_t seekTimeUs;
3648    ReadOptions::SeekMode mode;
3649    if (options && options->getSeekTo(&seekTimeUs, &mode)) {
3650        uint32_t findFlags = 0;
3651        switch (mode) {
3652            case ReadOptions::SEEK_PREVIOUS_SYNC:
3653                findFlags = SampleTable::kFlagBefore;
3654                break;
3655            case ReadOptions::SEEK_NEXT_SYNC:
3656                findFlags = SampleTable::kFlagAfter;
3657                break;
3658            case ReadOptions::SEEK_CLOSEST_SYNC:
3659            case ReadOptions::SEEK_CLOSEST:
3660                findFlags = SampleTable::kFlagClosest;
3661                break;
3662            default:
3663                CHECK(!"Should not be here.");
3664                break;
3665        }
3666
3667        uint32_t sampleIndex;
3668        status_t err = mSampleTable->findSampleAtTime(
3669                seekTimeUs, 1000000, mTimescale,
3670                &sampleIndex, findFlags);
3671
3672        if (mode == ReadOptions::SEEK_CLOSEST) {
3673            // We found the closest sample already, now we want the sync
3674            // sample preceding it (or the sample itself of course), even
3675            // if the subsequent sync sample is closer.
3676            findFlags = SampleTable::kFlagBefore;
3677        }
3678
3679        uint32_t syncSampleIndex;
3680        if (err == OK) {
3681            err = mSampleTable->findSyncSampleNear(
3682                    sampleIndex, &syncSampleIndex, findFlags);
3683        }
3684
3685        uint32_t sampleTime;
3686        if (err == OK) {
3687            err = mSampleTable->getMetaDataForSample(
3688                    sampleIndex, NULL, NULL, &sampleTime);
3689        }
3690
3691        if (err != OK) {
3692            if (err == ERROR_OUT_OF_RANGE) {
3693                // An attempt to seek past the end of the stream would
3694                // normally cause this ERROR_OUT_OF_RANGE error. Propagating
3695                // this all the way to the MediaPlayer would cause abnormal
3696                // termination. Legacy behaviour appears to be to behave as if
3697                // we had seeked to the end of stream, ending normally.
3698                err = ERROR_END_OF_STREAM;
3699            }
3700            ALOGV("end of stream");
3701            return err;
3702        }
3703
3704        if (mode == ReadOptions::SEEK_CLOSEST) {
3705            targetSampleTimeUs = (sampleTime * 1000000ll) / mTimescale;
3706        }
3707
3708#if 0
3709        uint32_t syncSampleTime;
3710        CHECK_EQ(OK, mSampleTable->getMetaDataForSample(
3711                    syncSampleIndex, NULL, NULL, &syncSampleTime));
3712
3713        ALOGI("seek to time %lld us => sample at time %lld us, "
3714             "sync sample at time %lld us",
3715             seekTimeUs,
3716             sampleTime * 1000000ll / mTimescale,
3717             syncSampleTime * 1000000ll / mTimescale);
3718#endif
3719
3720        mCurrentSampleIndex = syncSampleIndex;
3721        if (mBuffer != NULL) {
3722            mBuffer->release();
3723            mBuffer = NULL;
3724        }
3725
3726        // fall through
3727    }
3728
3729    off64_t offset;
3730    size_t size;
3731    uint32_t cts, stts;
3732    bool isSyncSample;
3733    bool newBuffer = false;
3734    if (mBuffer == NULL) {
3735        newBuffer = true;
3736
3737        status_t err =
3738            mSampleTable->getMetaDataForSample(
3739                    mCurrentSampleIndex, &offset, &size, &cts, &isSyncSample, &stts);
3740
3741        if (err != OK) {
3742            return err;
3743        }
3744
3745        err = mGroup->acquire_buffer(&mBuffer);
3746
3747        if (err != OK) {
3748            CHECK(mBuffer == NULL);
3749            return err;
3750        }
3751    }
3752
3753    if ((!mIsAVC && !mIsHEVC) || mWantsNALFragments) {
3754        if (newBuffer) {
3755            ssize_t num_bytes_read =
3756                mDataSource->readAt(offset, (uint8_t *)mBuffer->data(), size);
3757
3758            if (num_bytes_read < (ssize_t)size) {
3759                mBuffer->release();
3760                mBuffer = NULL;
3761
3762                return ERROR_IO;
3763            }
3764
3765            CHECK(mBuffer != NULL);
3766            mBuffer->set_range(0, size);
3767            mBuffer->meta_data()->clear();
3768            mBuffer->meta_data()->setInt64(
3769                    kKeyTime, ((int64_t)cts * 1000000) / mTimescale);
3770            mBuffer->meta_data()->setInt64(
3771                    kKeyDuration, ((int64_t)stts * 1000000) / mTimescale);
3772
3773            if (targetSampleTimeUs >= 0) {
3774                mBuffer->meta_data()->setInt64(
3775                        kKeyTargetTime, targetSampleTimeUs);
3776            }
3777
3778            if (isSyncSample) {
3779                mBuffer->meta_data()->setInt32(kKeyIsSyncFrame, 1);
3780            }
3781
3782            ++mCurrentSampleIndex;
3783        }
3784
3785        if (!mIsAVC && !mIsHEVC) {
3786            *out = mBuffer;
3787            mBuffer = NULL;
3788
3789            return OK;
3790        }
3791
3792        // Each NAL unit is split up into its constituent fragments and
3793        // each one of them returned in its own buffer.
3794
3795        CHECK(mBuffer->range_length() >= mNALLengthSize);
3796
3797        const uint8_t *src =
3798            (const uint8_t *)mBuffer->data() + mBuffer->range_offset();
3799
3800        size_t nal_size = parseNALSize(src);
3801        if (mBuffer->range_length() < mNALLengthSize + nal_size) {
3802            ALOGE("incomplete NAL unit.");
3803
3804            mBuffer->release();
3805            mBuffer = NULL;
3806
3807            return ERROR_MALFORMED;
3808        }
3809
3810        MediaBuffer *clone = mBuffer->clone();
3811        CHECK(clone != NULL);
3812        clone->set_range(mBuffer->range_offset() + mNALLengthSize, nal_size);
3813
3814        CHECK(mBuffer != NULL);
3815        mBuffer->set_range(
3816                mBuffer->range_offset() + mNALLengthSize + nal_size,
3817                mBuffer->range_length() - mNALLengthSize - nal_size);
3818
3819        if (mBuffer->range_length() == 0) {
3820            mBuffer->release();
3821            mBuffer = NULL;
3822        }
3823
3824        *out = clone;
3825
3826        return OK;
3827    } else {
3828        // Whole NAL units are returned but each fragment is prefixed by
3829        // the start code (0x00 00 00 01).
3830        ssize_t num_bytes_read = 0;
3831        int32_t drm = 0;
3832        bool usesDRM = (mFormat->findInt32(kKeyIsDRM, &drm) && drm != 0);
3833        if (usesDRM) {
3834            num_bytes_read =
3835                mDataSource->readAt(offset, (uint8_t*)mBuffer->data(), size);
3836        } else {
3837            num_bytes_read = mDataSource->readAt(offset, mSrcBuffer, size);
3838        }
3839
3840        if (num_bytes_read < (ssize_t)size) {
3841            mBuffer->release();
3842            mBuffer = NULL;
3843
3844            return ERROR_IO;
3845        }
3846
3847        if (usesDRM) {
3848            CHECK(mBuffer != NULL);
3849            mBuffer->set_range(0, size);
3850
3851        } else {
3852            uint8_t *dstData = (uint8_t *)mBuffer->data();
3853            size_t srcOffset = 0;
3854            size_t dstOffset = 0;
3855
3856            while (srcOffset < size) {
3857                bool isMalFormed = (srcOffset + mNALLengthSize > size);
3858                size_t nalLength = 0;
3859                if (!isMalFormed) {
3860                    nalLength = parseNALSize(&mSrcBuffer[srcOffset]);
3861                    srcOffset += mNALLengthSize;
3862                    isMalFormed = srcOffset + nalLength > size;
3863                }
3864
3865                if (isMalFormed) {
3866                    ALOGE("Video is malformed");
3867                    mBuffer->release();
3868                    mBuffer = NULL;
3869                    return ERROR_MALFORMED;
3870                }
3871
3872                if (nalLength == 0) {
3873                    continue;
3874                }
3875
3876                CHECK(dstOffset + 4 <= mBuffer->size());
3877
3878                dstData[dstOffset++] = 0;
3879                dstData[dstOffset++] = 0;
3880                dstData[dstOffset++] = 0;
3881                dstData[dstOffset++] = 1;
3882                memcpy(&dstData[dstOffset], &mSrcBuffer[srcOffset], nalLength);
3883                srcOffset += nalLength;
3884                dstOffset += nalLength;
3885            }
3886            CHECK_EQ(srcOffset, size);
3887            CHECK(mBuffer != NULL);
3888            mBuffer->set_range(0, dstOffset);
3889        }
3890
3891        mBuffer->meta_data()->clear();
3892        mBuffer->meta_data()->setInt64(
3893                kKeyTime, ((int64_t)cts * 1000000) / mTimescale);
3894        mBuffer->meta_data()->setInt64(
3895                kKeyDuration, ((int64_t)stts * 1000000) / mTimescale);
3896
3897        if (targetSampleTimeUs >= 0) {
3898            mBuffer->meta_data()->setInt64(
3899                    kKeyTargetTime, targetSampleTimeUs);
3900        }
3901
3902        if (isSyncSample) {
3903            mBuffer->meta_data()->setInt32(kKeyIsSyncFrame, 1);
3904        }
3905
3906        ++mCurrentSampleIndex;
3907
3908        *out = mBuffer;
3909        mBuffer = NULL;
3910
3911        return OK;
3912    }
3913}
3914
3915status_t MPEG4Source::fragmentedRead(
3916        MediaBuffer **out, const ReadOptions *options) {
3917
3918    ALOGV("MPEG4Source::fragmentedRead");
3919
3920    CHECK(mStarted);
3921
3922    *out = NULL;
3923
3924    int64_t targetSampleTimeUs = -1;
3925
3926    int64_t seekTimeUs;
3927    ReadOptions::SeekMode mode;
3928    if (options && options->getSeekTo(&seekTimeUs, &mode)) {
3929
3930        int numSidxEntries = mSegments.size();
3931        if (numSidxEntries != 0) {
3932            int64_t totalTime = 0;
3933            off64_t totalOffset = mFirstMoofOffset;
3934            for (int i = 0; i < numSidxEntries; i++) {
3935                const SidxEntry *se = &mSegments[i];
3936                if (totalTime + se->mDurationUs > seekTimeUs) {
3937                    // The requested time is somewhere in this segment
3938                    if ((mode == ReadOptions::SEEK_NEXT_SYNC && seekTimeUs > totalTime) ||
3939                        (mode == ReadOptions::SEEK_CLOSEST_SYNC &&
3940                        (seekTimeUs - totalTime) > (totalTime + se->mDurationUs - seekTimeUs))) {
3941                        // requested next sync, or closest sync and it was closer to the end of
3942                        // this segment
3943                        totalTime += se->mDurationUs;
3944                        totalOffset += se->mSize;
3945                    }
3946                    break;
3947                }
3948                totalTime += se->mDurationUs;
3949                totalOffset += se->mSize;
3950            }
3951            mCurrentMoofOffset = totalOffset;
3952            mCurrentSamples.clear();
3953            mCurrentSampleIndex = 0;
3954            parseChunk(&totalOffset);
3955            mCurrentTime = totalTime * mTimescale / 1000000ll;
3956        } else {
3957            // without sidx boxes, we can only seek to 0
3958            mCurrentMoofOffset = mFirstMoofOffset;
3959            mCurrentSamples.clear();
3960            mCurrentSampleIndex = 0;
3961            off64_t tmp = mCurrentMoofOffset;
3962            parseChunk(&tmp);
3963            mCurrentTime = 0;
3964        }
3965
3966        if (mBuffer != NULL) {
3967            mBuffer->release();
3968            mBuffer = NULL;
3969        }
3970
3971        // fall through
3972    }
3973
3974    off64_t offset = 0;
3975    size_t size = 0;
3976    uint32_t cts = 0;
3977    bool isSyncSample = false;
3978    bool newBuffer = false;
3979    if (mBuffer == NULL) {
3980        newBuffer = true;
3981
3982        if (mCurrentSampleIndex >= mCurrentSamples.size()) {
3983            // move to next fragment if there is one
3984            if (mNextMoofOffset <= mCurrentMoofOffset) {
3985                return ERROR_END_OF_STREAM;
3986            }
3987            off64_t nextMoof = mNextMoofOffset;
3988            mCurrentMoofOffset = nextMoof;
3989            mCurrentSamples.clear();
3990            mCurrentSampleIndex = 0;
3991            parseChunk(&nextMoof);
3992            if (mCurrentSampleIndex >= mCurrentSamples.size()) {
3993                return ERROR_END_OF_STREAM;
3994            }
3995        }
3996
3997        const Sample *smpl = &mCurrentSamples[mCurrentSampleIndex];
3998        offset = smpl->offset;
3999        size = smpl->size;
4000        cts = mCurrentTime + smpl->compositionOffset;
4001        mCurrentTime += smpl->duration;
4002        isSyncSample = (mCurrentSampleIndex == 0); // XXX
4003
4004        status_t err = mGroup->acquire_buffer(&mBuffer);
4005
4006        if (err != OK) {
4007            CHECK(mBuffer == NULL);
4008            ALOGV("acquire_buffer returned %d", err);
4009            return err;
4010        }
4011    }
4012
4013    const Sample *smpl = &mCurrentSamples[mCurrentSampleIndex];
4014    const sp<MetaData> bufmeta = mBuffer->meta_data();
4015    bufmeta->clear();
4016    if (smpl->encryptedsizes.size()) {
4017        // store clear/encrypted lengths in metadata
4018        bufmeta->setData(kKeyPlainSizes, 0,
4019                smpl->clearsizes.array(), smpl->clearsizes.size() * 4);
4020        bufmeta->setData(kKeyEncryptedSizes, 0,
4021                smpl->encryptedsizes.array(), smpl->encryptedsizes.size() * 4);
4022        bufmeta->setData(kKeyCryptoIV, 0, smpl->iv, 16); // use 16 or the actual size?
4023        bufmeta->setInt32(kKeyCryptoDefaultIVSize, mDefaultIVSize);
4024        bufmeta->setInt32(kKeyCryptoMode, mCryptoMode);
4025        bufmeta->setData(kKeyCryptoKey, 0, mCryptoKey, 16);
4026    }
4027
4028    if ((!mIsAVC && !mIsHEVC)|| mWantsNALFragments) {
4029        if (newBuffer) {
4030            ssize_t num_bytes_read =
4031                mDataSource->readAt(offset, (uint8_t *)mBuffer->data(), size);
4032
4033            if (num_bytes_read < (ssize_t)size) {
4034                mBuffer->release();
4035                mBuffer = NULL;
4036
4037                ALOGV("i/o error");
4038                return ERROR_IO;
4039            }
4040
4041            CHECK(mBuffer != NULL);
4042            mBuffer->set_range(0, size);
4043            mBuffer->meta_data()->setInt64(
4044                    kKeyTime, ((int64_t)cts * 1000000) / mTimescale);
4045            mBuffer->meta_data()->setInt64(
4046                    kKeyDuration, ((int64_t)smpl->duration * 1000000) / mTimescale);
4047
4048            if (targetSampleTimeUs >= 0) {
4049                mBuffer->meta_data()->setInt64(
4050                        kKeyTargetTime, targetSampleTimeUs);
4051            }
4052
4053            if (isSyncSample) {
4054                mBuffer->meta_data()->setInt32(kKeyIsSyncFrame, 1);
4055            }
4056
4057            ++mCurrentSampleIndex;
4058        }
4059
4060        if (!mIsAVC && !mIsHEVC) {
4061            *out = mBuffer;
4062            mBuffer = NULL;
4063
4064            return OK;
4065        }
4066
4067        // Each NAL unit is split up into its constituent fragments and
4068        // each one of them returned in its own buffer.
4069
4070        CHECK(mBuffer->range_length() >= mNALLengthSize);
4071
4072        const uint8_t *src =
4073            (const uint8_t *)mBuffer->data() + mBuffer->range_offset();
4074
4075        size_t nal_size = parseNALSize(src);
4076        if (mBuffer->range_length() < mNALLengthSize + nal_size) {
4077            ALOGE("incomplete NAL unit.");
4078
4079            mBuffer->release();
4080            mBuffer = NULL;
4081
4082            return ERROR_MALFORMED;
4083        }
4084
4085        MediaBuffer *clone = mBuffer->clone();
4086        CHECK(clone != NULL);
4087        clone->set_range(mBuffer->range_offset() + mNALLengthSize, nal_size);
4088
4089        CHECK(mBuffer != NULL);
4090        mBuffer->set_range(
4091                mBuffer->range_offset() + mNALLengthSize + nal_size,
4092                mBuffer->range_length() - mNALLengthSize - nal_size);
4093
4094        if (mBuffer->range_length() == 0) {
4095            mBuffer->release();
4096            mBuffer = NULL;
4097        }
4098
4099        *out = clone;
4100
4101        return OK;
4102    } else {
4103        ALOGV("whole NAL");
4104        // Whole NAL units are returned but each fragment is prefixed by
4105        // the start code (0x00 00 00 01).
4106        ssize_t num_bytes_read = 0;
4107        int32_t drm = 0;
4108        bool usesDRM = (mFormat->findInt32(kKeyIsDRM, &drm) && drm != 0);
4109        if (usesDRM) {
4110            num_bytes_read =
4111                mDataSource->readAt(offset, (uint8_t*)mBuffer->data(), size);
4112        } else {
4113            num_bytes_read = mDataSource->readAt(offset, mSrcBuffer, size);
4114        }
4115
4116        if (num_bytes_read < (ssize_t)size) {
4117            mBuffer->release();
4118            mBuffer = NULL;
4119
4120            ALOGV("i/o error");
4121            return ERROR_IO;
4122        }
4123
4124        if (usesDRM) {
4125            CHECK(mBuffer != NULL);
4126            mBuffer->set_range(0, size);
4127
4128        } else {
4129            uint8_t *dstData = (uint8_t *)mBuffer->data();
4130            size_t srcOffset = 0;
4131            size_t dstOffset = 0;
4132
4133            while (srcOffset < size) {
4134                bool isMalFormed = (srcOffset + mNALLengthSize > size);
4135                size_t nalLength = 0;
4136                if (!isMalFormed) {
4137                    nalLength = parseNALSize(&mSrcBuffer[srcOffset]);
4138                    srcOffset += mNALLengthSize;
4139                    isMalFormed = srcOffset + nalLength > size;
4140                }
4141
4142                if (isMalFormed) {
4143                    ALOGE("Video is malformed");
4144                    mBuffer->release();
4145                    mBuffer = NULL;
4146                    return ERROR_MALFORMED;
4147                }
4148
4149                if (nalLength == 0) {
4150                    continue;
4151                }
4152
4153                CHECK(dstOffset + 4 <= mBuffer->size());
4154
4155                dstData[dstOffset++] = 0;
4156                dstData[dstOffset++] = 0;
4157                dstData[dstOffset++] = 0;
4158                dstData[dstOffset++] = 1;
4159                memcpy(&dstData[dstOffset], &mSrcBuffer[srcOffset], nalLength);
4160                srcOffset += nalLength;
4161                dstOffset += nalLength;
4162            }
4163            CHECK_EQ(srcOffset, size);
4164            CHECK(mBuffer != NULL);
4165            mBuffer->set_range(0, dstOffset);
4166        }
4167
4168        mBuffer->meta_data()->setInt64(
4169                kKeyTime, ((int64_t)cts * 1000000) / mTimescale);
4170        mBuffer->meta_data()->setInt64(
4171                kKeyDuration, ((int64_t)smpl->duration * 1000000) / mTimescale);
4172
4173        if (targetSampleTimeUs >= 0) {
4174            mBuffer->meta_data()->setInt64(
4175                    kKeyTargetTime, targetSampleTimeUs);
4176        }
4177
4178        if (isSyncSample) {
4179            mBuffer->meta_data()->setInt32(kKeyIsSyncFrame, 1);
4180        }
4181
4182        ++mCurrentSampleIndex;
4183
4184        *out = mBuffer;
4185        mBuffer = NULL;
4186
4187        return OK;
4188    }
4189}
4190
4191MPEG4Extractor::Track *MPEG4Extractor::findTrackByMimePrefix(
4192        const char *mimePrefix) {
4193    for (Track *track = mFirstTrack; track != NULL; track = track->next) {
4194        const char *mime;
4195        if (track->meta != NULL
4196                && track->meta->findCString(kKeyMIMEType, &mime)
4197                && !strncasecmp(mime, mimePrefix, strlen(mimePrefix))) {
4198            return track;
4199        }
4200    }
4201
4202    return NULL;
4203}
4204
4205static bool LegacySniffMPEG4(
4206        const sp<DataSource> &source, String8 *mimeType, float *confidence) {
4207    uint8_t header[8];
4208
4209    ssize_t n = source->readAt(4, header, sizeof(header));
4210    if (n < (ssize_t)sizeof(header)) {
4211        return false;
4212    }
4213
4214    if (!memcmp(header, "ftyp3gp", 7) || !memcmp(header, "ftypmp42", 8)
4215        || !memcmp(header, "ftyp3gr6", 8) || !memcmp(header, "ftyp3gs6", 8)
4216        || !memcmp(header, "ftyp3ge6", 8) || !memcmp(header, "ftyp3gg6", 8)
4217        || !memcmp(header, "ftypisom", 8) || !memcmp(header, "ftypM4V ", 8)
4218        || !memcmp(header, "ftypM4A ", 8) || !memcmp(header, "ftypf4v ", 8)
4219        || !memcmp(header, "ftypkddi", 8) || !memcmp(header, "ftypM4VP", 8)) {
4220        *mimeType = MEDIA_MIMETYPE_CONTAINER_MPEG4;
4221        *confidence = 0.4;
4222
4223        return true;
4224    }
4225
4226    return false;
4227}
4228
4229static bool isCompatibleBrand(uint32_t fourcc) {
4230    static const uint32_t kCompatibleBrands[] = {
4231        FOURCC('i', 's', 'o', 'm'),
4232        FOURCC('i', 's', 'o', '2'),
4233        FOURCC('a', 'v', 'c', '1'),
4234        FOURCC('h', 'v', 'c', '1'),
4235        FOURCC('h', 'e', 'v', '1'),
4236        FOURCC('3', 'g', 'p', '4'),
4237        FOURCC('m', 'p', '4', '1'),
4238        FOURCC('m', 'p', '4', '2'),
4239
4240        // Won't promise that the following file types can be played.
4241        // Just give these file types a chance.
4242        FOURCC('q', 't', ' ', ' '),  // Apple's QuickTime
4243        FOURCC('M', 'S', 'N', 'V'),  // Sony's PSP
4244
4245        FOURCC('3', 'g', '2', 'a'),  // 3GPP2
4246        FOURCC('3', 'g', '2', 'b'),
4247    };
4248
4249    for (size_t i = 0;
4250         i < sizeof(kCompatibleBrands) / sizeof(kCompatibleBrands[0]);
4251         ++i) {
4252        if (kCompatibleBrands[i] == fourcc) {
4253            return true;
4254        }
4255    }
4256
4257    return false;
4258}
4259
4260// Attempt to actually parse the 'ftyp' atom and determine if a suitable
4261// compatible brand is present.
4262// Also try to identify where this file's metadata ends
4263// (end of the 'moov' atom) and report it to the caller as part of
4264// the metadata.
4265static bool BetterSniffMPEG4(
4266        const sp<DataSource> &source, String8 *mimeType, float *confidence,
4267        sp<AMessage> *meta) {
4268    // We scan up to 128 bytes to identify this file as an MP4.
4269    static const off64_t kMaxScanOffset = 128ll;
4270
4271    off64_t offset = 0ll;
4272    bool foundGoodFileType = false;
4273    off64_t moovAtomEndOffset = -1ll;
4274    bool done = false;
4275
4276    while (!done && offset < kMaxScanOffset) {
4277        uint32_t hdr[2];
4278        if (source->readAt(offset, hdr, 8) < 8) {
4279            return false;
4280        }
4281
4282        uint64_t chunkSize = ntohl(hdr[0]);
4283        uint32_t chunkType = ntohl(hdr[1]);
4284        off64_t chunkDataOffset = offset + 8;
4285
4286        if (chunkSize == 1) {
4287            if (source->readAt(offset + 8, &chunkSize, 8) < 8) {
4288                return false;
4289            }
4290
4291            chunkSize = ntoh64(chunkSize);
4292            chunkDataOffset += 8;
4293
4294            if (chunkSize < 16) {
4295                // The smallest valid chunk is 16 bytes long in this case.
4296                return false;
4297            }
4298        } else if (chunkSize < 8) {
4299            // The smallest valid chunk is 8 bytes long.
4300            return false;
4301        }
4302
4303        off64_t chunkDataSize = offset + chunkSize - chunkDataOffset;
4304
4305        char chunkstring[5];
4306        MakeFourCCString(chunkType, chunkstring);
4307        ALOGV("saw chunk type %s, size %" PRIu64 " @ %lld", chunkstring, chunkSize, offset);
4308        switch (chunkType) {
4309            case FOURCC('f', 't', 'y', 'p'):
4310            {
4311                if (chunkDataSize < 8) {
4312                    return false;
4313                }
4314
4315                uint32_t numCompatibleBrands = (chunkDataSize - 8) / 4;
4316                for (size_t i = 0; i < numCompatibleBrands + 2; ++i) {
4317                    if (i == 1) {
4318                        // Skip this index, it refers to the minorVersion,
4319                        // not a brand.
4320                        continue;
4321                    }
4322
4323                    uint32_t brand;
4324                    if (source->readAt(
4325                                chunkDataOffset + 4 * i, &brand, 4) < 4) {
4326                        return false;
4327                    }
4328
4329                    brand = ntohl(brand);
4330
4331                    if (isCompatibleBrand(brand)) {
4332                        foundGoodFileType = true;
4333                        break;
4334                    }
4335                }
4336
4337                if (!foundGoodFileType) {
4338                    return false;
4339                }
4340
4341                break;
4342            }
4343
4344            case FOURCC('m', 'o', 'o', 'v'):
4345            {
4346                moovAtomEndOffset = offset + chunkSize;
4347
4348                done = true;
4349                break;
4350            }
4351
4352            default:
4353                break;
4354        }
4355
4356        offset += chunkSize;
4357    }
4358
4359    if (!foundGoodFileType) {
4360        return false;
4361    }
4362
4363    *mimeType = MEDIA_MIMETYPE_CONTAINER_MPEG4;
4364    *confidence = 0.4f;
4365
4366    if (moovAtomEndOffset >= 0) {
4367        *meta = new AMessage;
4368        (*meta)->setInt64("meta-data-size", moovAtomEndOffset);
4369
4370        ALOGV("found metadata size: %lld", moovAtomEndOffset);
4371    }
4372
4373    return true;
4374}
4375
4376bool SniffMPEG4(
4377        const sp<DataSource> &source, String8 *mimeType, float *confidence,
4378        sp<AMessage> *meta) {
4379    if (BetterSniffMPEG4(source, mimeType, confidence, meta)) {
4380        return true;
4381    }
4382
4383    if (LegacySniffMPEG4(source, mimeType, confidence)) {
4384        ALOGW("Identified supported mpeg4 through LegacySniffMPEG4.");
4385        return true;
4386    }
4387
4388    return false;
4389}
4390
4391}  // namespace android
4392