Convert MPEG2 extractor to V3 format

and move it to the media APEX.

Bug: 111407253
Test: manual, CTS
Change-Id: Ibcbdd0e901e9d79b5a857b5d0a65bd6b1ec675a6
diff --git a/media/extractors/mpeg2/Android.bp b/media/extractors/mpeg2/Android.bp
index e5cdfe4..b816093 100644
--- a/media/extractors/mpeg2/Android.bp
+++ b/media/extractors/mpeg2/Android.bp
@@ -17,12 +17,9 @@
         "android.hidl.token@1.0-utils",
         "android.hidl.allocator@1.0",
         "libhidlmemory",
-        "libcrypto",
-        "libcutils",
         "libhidlbase",
         "liblog",
-        "libmediaextractor",
-        "libstagefright_foundation",
+        "libmediandk",
     ],
 
     header_libs: [
@@ -30,8 +27,13 @@
     ],
 
     static_libs: [
+        "libcrypto",
+        "libstagefright_foundation",
         "libstagefright_mpeg2support",
+        "libmediaextractor",
         "libutils",
+        "libstagefright",
+        "libstagefright_esds",
     ],
 
     name: "libmpeg2extractor",
diff --git a/media/extractors/mpeg2/ExtractorBundle.cpp b/media/extractors/mpeg2/ExtractorBundle.cpp
index 366aa59..c10a797 100644
--- a/media/extractors/mpeg2/ExtractorBundle.cpp
+++ b/media/extractors/mpeg2/ExtractorBundle.cpp
@@ -31,27 +31,27 @@
 __attribute__ ((visibility ("default")))
 ExtractorDef GETEXTRACTORDEF() {
     return {
-        EXTRACTORDEF_VERSION,
+        EXTRACTORDEF_VERSION_CURRENT + 1,
         UUID("3d1dcfeb-e40a-436d-a574-c2438a555e5f"),
         1,
         "MPEG2-PS/TS Extractor",
         {
-            [](
+            .v3 = [](
                     CDataSource *source,
                     float *confidence,
                     void **,
-                    FreeMetaFunc *) -> CreatorFunc {
+                    FreeMetaFunc *) -> CreatorFuncV3 {
                 DataSourceHelper helper(source);
                 if (SniffMPEG2TS(&helper, confidence)) {
                     return [](
                             CDataSource *source,
-                            void *) -> CMediaExtractor* {
-                        return wrap(new MPEG2TSExtractor(new DataSourceHelper(source)));};
+                            void *) -> CMediaExtractorV3* {
+                        return wrapV3(new MPEG2TSExtractor(new DataSourceHelper(source)));};
                 } else if (SniffMPEG2PS(&helper, confidence)) {
                             return [](
                                     CDataSource *source,
-                                    void *) -> CMediaExtractor* {
-                                return wrap(new MPEG2PSExtractor(new DataSourceHelper(source)));};
+                                    void *) -> CMediaExtractorV3* {
+                                return wrapV3(new MPEG2PSExtractor(new DataSourceHelper(source)));};
                 }
                 return NULL;
             }
diff --git a/media/extractors/mpeg2/MPEG2PSExtractor.cpp b/media/extractors/mpeg2/MPEG2PSExtractor.cpp
index fc13d2c..b60fc4e 100644
--- a/media/extractors/mpeg2/MPEG2PSExtractor.cpp
+++ b/media/extractors/mpeg2/MPEG2PSExtractor.cpp
@@ -33,22 +33,23 @@
 #include <media/stagefright/MediaDefs.h>
 #include <media/stagefright/MediaErrors.h>
 #include <media/stagefright/MetaData.h>
+#include <media/stagefright/Utils.h>
 #include <utils/String8.h>
 
 #include <inttypes.h>
 
 namespace android {
 
-struct MPEG2PSExtractor::Track : public MediaTrackHelper, public RefBase {
+struct MPEG2PSExtractor::Track : public MediaTrackHelperV3 {
     Track(MPEG2PSExtractor *extractor,
           unsigned stream_id, unsigned stream_type);
 
-    virtual status_t start();
-    virtual status_t stop();
-    virtual status_t getFormat(MetaDataBase &);
+    virtual media_status_t start();
+    virtual media_status_t stop();
+    virtual media_status_t getFormat(AMediaFormat *);
 
-    virtual status_t read(
-            MediaBufferBase **buffer, const ReadOptions *options);
+    virtual media_status_t read(
+            MediaBufferHelperV3 **buffer, const ReadOptions *options);
 
 protected:
     virtual ~Track();
@@ -71,22 +72,22 @@
     DISALLOW_EVIL_CONSTRUCTORS(Track);
 };
 
-struct MPEG2PSExtractor::WrappedTrack : public MediaTrackHelper {
-    WrappedTrack(MPEG2PSExtractor *extractor, const sp<Track> &track);
+struct MPEG2PSExtractor::WrappedTrack : public MediaTrackHelperV3 {
+    WrappedTrack(MPEG2PSExtractor *extractor, Track *track);
 
-    virtual status_t start();
-    virtual status_t stop();
-    virtual status_t getFormat(MetaDataBase &);
+    virtual media_status_t start();
+    virtual media_status_t stop();
+    virtual media_status_t getFormat(AMediaFormat *);
 
-    virtual status_t read(
-            MediaBufferBase **buffer, const ReadOptions *options);
+    virtual media_status_t read(
+            MediaBufferHelperV3 **buffer, const ReadOptions *options);
 
 protected:
     virtual ~WrappedTrack();
 
 private:
     MPEG2PSExtractor *mExtractor;
-    sp<MPEG2PSExtractor::Track> mTrack;
+    MPEG2PSExtractor::Track *mTrack;
 
     DISALLOW_EVIL_CONSTRUCTORS(WrappedTrack);
 };
@@ -107,13 +108,14 @@
     }
 
     // Remove all tracks that were unable to determine their format.
-    MetaDataBase meta;
+    AMediaFormat *meta = AMediaFormat_new();
     for (size_t i = mTracks.size(); i > 0;) {
         i--;
-        if (mTracks.valueAt(i)->getFormat(meta) != OK) {
+        if (mTracks.valueAt(i)->getFormat(meta) != AMEDIA_OK) {
             mTracks.removeItemsAt(i);
         }
     }
+    AMediaFormat_delete(meta);
 
     mScanning = false;
 }
@@ -126,7 +128,7 @@
     return mTracks.size();
 }
 
-MediaTrackHelper *MPEG2PSExtractor::getTrack(size_t index) {
+MediaTrackHelperV3 *MPEG2PSExtractor::getTrack(size_t index) {
     if (index >= mTracks.size()) {
         return NULL;
     }
@@ -134,20 +136,20 @@
     return new WrappedTrack(this, mTracks.valueAt(index));
 }
 
-status_t MPEG2PSExtractor::getTrackMetaData(
-        MetaDataBase &meta,
+media_status_t MPEG2PSExtractor::getTrackMetaData(
+        AMediaFormat *meta,
         size_t index, uint32_t /* flags */) {
     if (index >= mTracks.size()) {
-        return UNKNOWN_ERROR;
+        return AMEDIA_ERROR_UNKNOWN;
     }
 
     return mTracks.valueAt(index)->getFormat(meta);
 }
 
-status_t MPEG2PSExtractor::getMetaData(MetaDataBase &meta) {
-    meta.setCString(kKeyMIMEType, MEDIA_MIMETYPE_CONTAINER_MPEG2PS);
+media_status_t MPEG2PSExtractor::getMetaData(AMediaFormat *meta) {
+    AMediaFormat_setString(meta, AMEDIAFORMAT_KEY_MIME, MEDIA_MIMETYPE_CONTAINER_MPEG2PS);
 
-    return OK;
+    return AMEDIA_OK;
 }
 
 uint32_t MPEG2PSExtractor::flags() const {
@@ -635,42 +637,55 @@
     mQueue = NULL;
 }
 
-status_t MPEG2PSExtractor::Track::start() {
+media_status_t MPEG2PSExtractor::Track::start() {
     if (mSource == NULL) {
-        return NO_INIT;
+        return AMEDIA_ERROR_UNKNOWN;
     }
 
-    return mSource->start(NULL); // AnotherPacketSource::start doesn't use its argument
+    // initialize with one small buffer, but allow growth
+    mBufferGroup->init(1 /* one buffer */, 256 /* buffer size */, 64 /* max number of buffers */);
+
+    if (mSource->start(NULL) == OK) { // AnotherPacketSource::start doesn't use its argument
+        return AMEDIA_OK;
+    }
+    return AMEDIA_ERROR_UNKNOWN;
 }
 
-status_t MPEG2PSExtractor::Track::stop() {
+media_status_t MPEG2PSExtractor::Track::stop() {
     if (mSource == NULL) {
-        return NO_INIT;
+        return AMEDIA_ERROR_UNKNOWN;
     }
 
-    return mSource->stop();
+    if (mSource->stop() == OK) {
+        return AMEDIA_OK;
+    }
+    return AMEDIA_ERROR_UNKNOWN;
 }
 
-status_t MPEG2PSExtractor::Track::getFormat(MetaDataBase &meta) {
+void copyAMessageToAMediaFormat(AMediaFormat *format, sp<AMessage> msg);
+
+media_status_t MPEG2PSExtractor::Track::getFormat(AMediaFormat *meta) {
     if (mSource == NULL) {
-        return NO_INIT;
+        return AMEDIA_ERROR_UNKNOWN;
     }
 
     sp<MetaData> sourceMeta = mSource->getFormat();
-    meta = *sourceMeta;
-    return OK;
+    sp<AMessage> msg;
+    convertMetaDataToMessage(sourceMeta, &msg);
+    copyAMessageToAMediaFormat(meta, msg);
+    return AMEDIA_OK;
 }
 
-status_t MPEG2PSExtractor::Track::read(
-        MediaBufferBase **buffer, const ReadOptions *options) {
+media_status_t MPEG2PSExtractor::Track::read(
+        MediaBufferHelperV3 **buffer, const ReadOptions *options) {
     if (mSource == NULL) {
-        return NO_INIT;
+        return AMEDIA_ERROR_UNKNOWN;
     }
 
     status_t finalResult;
     while (!mSource->hasBufferAvailable(&finalResult)) {
         if (finalResult != OK) {
-            return ERROR_END_OF_STREAM;
+            return AMEDIA_ERROR_END_OF_STREAM;
         }
 
         status_t err = mExtractor->feedMore();
@@ -680,7 +695,46 @@
         }
     }
 
-    return mSource->read(buffer, (MediaSource::ReadOptions*)options);
+    MediaBufferBase *mbuf;
+    mSource->read(&mbuf, (MediaTrack::ReadOptions*) options);
+    size_t length = mbuf->range_length();
+    MediaBufferHelperV3 *outbuf;
+    mBufferGroup->acquire_buffer(&outbuf, false, length);
+    memcpy(outbuf->data(), mbuf->data(), length);
+    outbuf->set_range(0, length);
+    *buffer = outbuf;
+    MetaDataBase &inMeta = mbuf->meta_data();
+    AMediaFormat *outMeta = outbuf->meta_data();
+    int64_t val64;
+    if (inMeta.findInt64(kKeyTime, &val64)) {
+        AMediaFormat_setInt64(outMeta, AMEDIAFORMAT_KEY_TIME_US, val64);
+    }
+    int32_t val32;
+    if (inMeta.findInt32(kKeyIsSyncFrame, &val32)) {
+        AMediaFormat_setInt32(outMeta, AMEDIAFORMAT_KEY_IS_SYNC_FRAME, val32);
+    }
+    if (inMeta.findInt32(kKeyCryptoMode, &val32)) {
+        AMediaFormat_setInt32(outMeta, AMEDIAFORMAT_KEY_CRYPTO_MODE, val32);
+    }
+    uint32_t bufType;
+    const void *bufData;
+    size_t bufSize;
+    if (inMeta.findData(kKeyCryptoIV, &bufType, &bufData, &bufSize)) {
+        AMediaFormat_setBuffer(outMeta, AMEDIAFORMAT_KEY_CRYPTO_IV, bufData, bufSize);
+    }
+    if (inMeta.findData(kKeyCryptoKey, &bufType, &bufData, &bufSize)) {
+        AMediaFormat_setBuffer(outMeta, AMEDIAFORMAT_KEY_CRYPTO_KEY, bufData, bufSize);
+    }
+    if (inMeta.findData(kKeyPlainSizes, &bufType, &bufData, &bufSize)) {
+        AMediaFormat_setBuffer(outMeta, AMEDIAFORMAT_KEY_CRYPTO_PLAIN_SIZES, bufData, bufSize);
+    }
+    if (inMeta.findData(kKeyEncryptedSizes, &bufType, &bufData, &bufSize)) {
+        AMediaFormat_setBuffer(outMeta, AMEDIAFORMAT_KEY_CRYPTO_ENCRYPTED_SIZES, bufData, bufSize);
+    }
+    if (inMeta.findData(kKeySEI, &bufType, &bufData, &bufSize)) {
+        AMediaFormat_setBuffer(outMeta, AMEDIAFORMAT_KEY_SEI, bufData, bufSize);
+    }
+    return AMEDIA_OK;
 }
 
 status_t MPEG2PSExtractor::Track::appendPESData(
@@ -726,7 +780,7 @@
 ////////////////////////////////////////////////////////////////////////////////
 
 MPEG2PSExtractor::WrappedTrack::WrappedTrack(
-        MPEG2PSExtractor *extractor, const sp<Track> &track)
+        MPEG2PSExtractor *extractor, Track *track)
     : mExtractor(extractor),
       mTrack(track) {
 }
@@ -734,20 +788,20 @@
 MPEG2PSExtractor::WrappedTrack::~WrappedTrack() {
 }
 
-status_t MPEG2PSExtractor::WrappedTrack::start() {
+media_status_t MPEG2PSExtractor::WrappedTrack::start() {
     return mTrack->start();
 }
 
-status_t MPEG2PSExtractor::WrappedTrack::stop() {
+media_status_t MPEG2PSExtractor::WrappedTrack::stop() {
     return mTrack->stop();
 }
 
-status_t MPEG2PSExtractor::WrappedTrack::getFormat(MetaDataBase &meta) {
+media_status_t MPEG2PSExtractor::WrappedTrack::getFormat(AMediaFormat *meta) {
     return mTrack->getFormat(meta);
 }
 
-status_t MPEG2PSExtractor::WrappedTrack::read(
-        MediaBufferBase **buffer, const ReadOptions *options) {
+media_status_t MPEG2PSExtractor::WrappedTrack::read(
+        MediaBufferHelperV3 **buffer, const ReadOptions *options) {
     return mTrack->read(buffer, options);
 }
 
diff --git a/media/extractors/mpeg2/MPEG2PSExtractor.h b/media/extractors/mpeg2/MPEG2PSExtractor.h
index c4082ef..d251688 100644
--- a/media/extractors/mpeg2/MPEG2PSExtractor.h
+++ b/media/extractors/mpeg2/MPEG2PSExtractor.h
@@ -32,14 +32,14 @@
 struct Track;
 class String8;
 
-struct MPEG2PSExtractor : public MediaExtractorPluginHelper {
+struct MPEG2PSExtractor : public MediaExtractorPluginHelperV3 {
     explicit MPEG2PSExtractor(DataSourceHelper *source);
 
     virtual size_t countTracks();
-    virtual MediaTrackHelper *getTrack(size_t index);
-    virtual status_t getTrackMetaData(MetaDataBase& meta, size_t index, uint32_t flags);
+    virtual MediaTrackHelperV3 *getTrack(size_t index);
+    virtual media_status_t getTrackMetaData(AMediaFormat *meta, size_t index, uint32_t flags);
 
-    virtual status_t getMetaData(MetaDataBase& meta);
+    virtual media_status_t getMetaData(AMediaFormat *meta);
 
     virtual uint32_t flags() const;
     virtual const char * name() { return "MPEG2PSExtractor"; }
@@ -57,7 +57,7 @@
     off64_t mOffset;
     status_t mFinalResult;
     sp<ABuffer> mBuffer;
-    KeyedVector<unsigned, sp<Track> > mTracks;
+    KeyedVector<unsigned, Track* > mTracks;
     bool mScanning;
 
     bool mProgramStreamMapValid;
diff --git a/media/extractors/mpeg2/MPEG2TSExtractor.cpp b/media/extractors/mpeg2/MPEG2TSExtractor.cpp
index 605b13a..fc066ee 100644
--- a/media/extractors/mpeg2/MPEG2TSExtractor.cpp
+++ b/media/extractors/mpeg2/MPEG2TSExtractor.cpp
@@ -34,6 +34,7 @@
 #include <media/stagefright/MediaDefs.h>
 #include <media/stagefright/MediaErrors.h>
 #include <media/stagefright/MetaData.h>
+#include <media/stagefright/Utils.h>
 #include <utils/String8.h>
 
 #include "mpeg2ts/AnotherPacketSource.h"
@@ -50,19 +51,19 @@
 static const int kMaxDurationReadSize = 250000LL;
 static const int kMaxDurationRetry = 6;
 
-struct MPEG2TSSource : public MediaTrackHelper {
+struct MPEG2TSSource : public MediaTrackHelperV3 {
     MPEG2TSSource(
             MPEG2TSExtractor *extractor,
             const sp<AnotherPacketSource> &impl,
             bool doesSeek);
     virtual ~MPEG2TSSource();
 
-    virtual status_t start();
-    virtual status_t stop();
-    virtual status_t getFormat(MetaDataBase &);
+    virtual media_status_t start();
+    virtual media_status_t stop();
+    virtual media_status_t getFormat(AMediaFormat *);
 
-    virtual status_t read(
-            MediaBufferBase **buffer, const ReadOptions *options = NULL);
+    virtual media_status_t read(
+            MediaBufferHelperV3 **buffer, const ReadOptions *options = NULL);
 
 private:
     MPEG2TSExtractor *mExtractor;
@@ -87,22 +88,84 @@
 MPEG2TSSource::~MPEG2TSSource() {
 }
 
-status_t MPEG2TSSource::start() {
-    return mImpl->start(NULL); // AnotherPacketSource::start() doesn't use its argument
+media_status_t MPEG2TSSource::start() {
+    // initialize with one small buffer, but allow growth
+    mBufferGroup->init(1 /* one buffer */, 256 /* buffer size */, 64 /* max number of buffers */);
+
+    if (!mImpl->start(NULL)) { // AnotherPacketSource::start() doesn't use its argument
+        return AMEDIA_OK;
+    }
+    return AMEDIA_ERROR_UNKNOWN;
 }
 
-status_t MPEG2TSSource::stop() {
-    return mImpl->stop();
+media_status_t MPEG2TSSource::stop() {
+    if (!mImpl->stop()) {
+        return AMEDIA_OK;
+    }
+    return AMEDIA_ERROR_UNKNOWN;
 }
 
-status_t MPEG2TSSource::getFormat(MetaDataBase &meta) {
+void copyAMessageToAMediaFormat(AMediaFormat *format, sp<AMessage> msg) {
+    size_t numEntries = msg->countEntries();
+    for (size_t i = 0; i < numEntries; i++) {
+        AMessage::Type type;
+        const char *name = msg->getEntryNameAt(i, &type);
+        AMessage::ItemData id = msg->getEntryAt(i);
+
+        switch (type) {
+            case AMessage::kTypeInt32:
+                int32_t val32;
+                if (id.find(&val32)) {
+                    AMediaFormat_setInt32(format, name, val32);
+                }
+                break;
+            case AMessage::kTypeInt64:
+                int64_t val64;
+                if (id.find(&val64)) {
+                    AMediaFormat_setInt64(format, name, val64);
+                }
+                break;
+            case AMessage::kTypeFloat:
+                float valfloat;
+                if (id.find(&valfloat)) {
+                    AMediaFormat_setFloat(format, name, valfloat);
+                }
+                break;
+            case AMessage::kTypeDouble:
+                double valdouble;
+                if (id.find(&valdouble)) {
+                    AMediaFormat_setDouble(format, name, valdouble);
+                }
+                break;
+            case AMessage::kTypeString:
+                if (AString s; id.find(&s)) {
+                    AMediaFormat_setString(format, name, s.c_str());
+                }
+                break;
+            case AMessage::kTypeBuffer:
+            {
+                sp<ABuffer> buffer;
+                if (id.find(&buffer)) {
+                    AMediaFormat_setBuffer(format, name, buffer->data(), buffer->size());
+                }
+                break;
+            }
+            default:
+                ALOGW("ignoring unsupported type %d '%s'", type, name);
+        }
+    }
+}
+
+media_status_t MPEG2TSSource::getFormat(AMediaFormat *meta) {
     sp<MetaData> implMeta = mImpl->getFormat();
-    meta = *implMeta;
-    return OK;
+    sp<AMessage> msg;
+    convertMetaDataToMessage(implMeta, &msg);
+    copyAMessageToAMediaFormat(meta, msg);
+    return AMEDIA_OK;
 }
 
-status_t MPEG2TSSource::read(
-        MediaBufferBase **out, const ReadOptions *options) {
+media_status_t MPEG2TSSource::read(
+        MediaBufferHelperV3 **out, const ReadOptions *options) {
     *out = NULL;
 
     int64_t seekTimeUs;
@@ -110,16 +173,59 @@
     if (mDoesSeek && options && options->getSeekTo(&seekTimeUs, &seekMode)) {
         // seek is needed
         status_t err = mExtractor->seek(seekTimeUs, (ReadOptions::SeekMode)seekMode);
-        if (err != OK) {
-            return err;
+        if (err == ERROR_END_OF_STREAM) {
+            return AMEDIA_ERROR_END_OF_STREAM;
+        } else if (err != OK) {
+            return AMEDIA_ERROR_UNKNOWN;
         }
     }
 
     if (mExtractor->feedUntilBufferAvailable(mImpl) != OK) {
-        return ERROR_END_OF_STREAM;
+        return AMEDIA_ERROR_END_OF_STREAM;
     }
 
-    return mImpl->read(out, (MediaSource::ReadOptions*) options);
+    MediaBufferBase *mbuf;
+    mImpl->read(&mbuf, (MediaTrack::ReadOptions*) options);
+    size_t length = mbuf->range_length();
+    MediaBufferHelperV3 *outbuf;
+    mBufferGroup->acquire_buffer(&outbuf, false, length);
+    memcpy(outbuf->data(), mbuf->data(), length);
+    outbuf->set_range(0, length);
+    *out = outbuf;
+    MetaDataBase &inMeta = mbuf->meta_data();
+    AMediaFormat *outMeta = outbuf->meta_data();
+    AMediaFormat_clear(outMeta);
+    int64_t val64;
+    if (inMeta.findInt64(kKeyTime, &val64)) {
+        AMediaFormat_setInt64(outMeta, AMEDIAFORMAT_KEY_TIME_US, val64);
+    }
+    int32_t val32;
+    if (inMeta.findInt32(kKeyIsSyncFrame, &val32)) {
+        AMediaFormat_setInt32(outMeta, AMEDIAFORMAT_KEY_IS_SYNC_FRAME, val32);
+    }
+    if (inMeta.findInt32(kKeyCryptoMode, &val32)) {
+        AMediaFormat_setInt32(outMeta, AMEDIAFORMAT_KEY_CRYPTO_MODE, val32);
+    }
+    uint32_t bufType;
+    const void *bufData;
+    size_t bufSize;
+    if (inMeta.findData(kKeyCryptoIV, &bufType, &bufData, &bufSize)) {
+        AMediaFormat_setBuffer(outMeta, AMEDIAFORMAT_KEY_CRYPTO_IV, bufData, bufSize);
+    }
+    if (inMeta.findData(kKeyCryptoKey, &bufType, &bufData, &bufSize)) {
+        AMediaFormat_setBuffer(outMeta, AMEDIAFORMAT_KEY_CRYPTO_KEY, bufData, bufSize);
+    }
+    if (inMeta.findData(kKeyPlainSizes, &bufType, &bufData, &bufSize)) {
+        AMediaFormat_setBuffer(outMeta, AMEDIAFORMAT_KEY_CRYPTO_PLAIN_SIZES, bufData, bufSize);
+    }
+    if (inMeta.findData(kKeyEncryptedSizes, &bufType, &bufData, &bufSize)) {
+        AMediaFormat_setBuffer(outMeta, AMEDIAFORMAT_KEY_CRYPTO_ENCRYPTED_SIZES, bufData, bufSize);
+    }
+    if (inMeta.findData(kKeySEI, &bufType, &bufData, &bufSize)) {
+        AMediaFormat_setBuffer(outMeta, AMEDIAFORMAT_KEY_SEI, bufData, bufSize);
+    }
+
+    return AMEDIA_OK;
 }
 
 ////////////////////////////////////////////////////////////////////////////////
@@ -140,7 +246,7 @@
     return mSourceImpls.size();
 }
 
-MediaTrackHelper *MPEG2TSExtractor::getTrack(size_t index) {
+MediaTrackHelperV3 *MPEG2TSExtractor::getTrack(size_t index) {
     if (index >= mSourceImpls.size()) {
         return NULL;
     }
@@ -151,22 +257,23 @@
             (mSeekSyncPoints == &mSyncPoints.editItemAt(index)));
 }
 
-status_t MPEG2TSExtractor::getTrackMetaData(
-        MetaDataBase &meta,
+media_status_t MPEG2TSExtractor::getTrackMetaData(
+        AMediaFormat *meta,
         size_t index, uint32_t /* flags */) {
     sp<MetaData> implMeta = index < mSourceImpls.size()
         ? mSourceImpls.editItemAt(index)->getFormat() : NULL;
     if (implMeta == NULL) {
-        return UNKNOWN_ERROR;
+        return AMEDIA_ERROR_UNKNOWN;
     }
-    meta = *implMeta;
-    return OK;
+    sp<AMessage> msg = new AMessage;
+    convertMetaDataToMessage(implMeta, &msg);
+    copyAMessageToAMediaFormat(meta, msg);
+    return AMEDIA_OK;
 }
 
-status_t MPEG2TSExtractor::getMetaData(MetaDataBase &meta) {
-    meta.setCString(kKeyMIMEType, MEDIA_MIMETYPE_CONTAINER_MPEG2TS);
-
-    return OK;
+media_status_t MPEG2TSExtractor::getMetaData(AMediaFormat *meta) {
+    AMediaFormat_setString(meta, AMEDIAFORMAT_KEY_MIME, MEDIA_MIMETYPE_CONTAINER_MPEG2TS);
+    return AMEDIA_OK;
 }
 
 //static
@@ -177,7 +284,7 @@
                     || !strcasecmp(MEDIA_MIMETYPE_AUDIO_SCRAMBLED, mime));
 }
 
-status_t MPEG2TSExtractor::setMediaCas(const uint8_t* casToken, size_t size) {
+media_status_t MPEG2TSExtractor::setMediaCas(const uint8_t* casToken, size_t size) {
     HalToken halToken;
     halToken.setToExternal((uint8_t*)casToken, size);
     sp<ICas> cas = ICas::castFrom(retrieveHalInterface(halToken));
@@ -187,8 +294,9 @@
     if (err == OK) {
         ALOGI("All tracks now have descramblers");
         init();
+        return AMEDIA_OK;
     }
-    return err;
+    return AMEDIA_ERROR_UNKNOWN;
 }
 
 void MPEG2TSExtractor::addSource(const sp<AnotherPacketSource> &impl) {
@@ -494,7 +602,7 @@
 }
 
 status_t MPEG2TSExtractor::seek(int64_t seekTimeUs,
-        const MediaTrackHelper::ReadOptions::SeekMode &seekMode) {
+        const MediaTrackHelperV3::ReadOptions::SeekMode &seekMode) {
     if (mSeekSyncPoints == NULL || mSeekSyncPoints->isEmpty()) {
         ALOGW("No sync point to seek to.");
         // ... and therefore we have nothing useful to do here.
@@ -515,18 +623,18 @@
     }
 
     switch (seekMode) {
-        case MediaTrackHelper::ReadOptions::SEEK_NEXT_SYNC:
+        case MediaTrackHelperV3::ReadOptions::SEEK_NEXT_SYNC:
             if (index == mSeekSyncPoints->size()) {
                 ALOGW("Next sync not found; starting from the latest sync.");
                 --index;
             }
             break;
-        case MediaTrackHelper::ReadOptions::SEEK_CLOSEST_SYNC:
-        case MediaTrackHelper::ReadOptions::SEEK_CLOSEST:
+        case MediaTrackHelperV3::ReadOptions::SEEK_CLOSEST_SYNC:
+        case MediaTrackHelperV3::ReadOptions::SEEK_CLOSEST:
             ALOGW("seekMode not supported: %d; falling back to PREVIOUS_SYNC",
                     seekMode);
             FALLTHROUGH_INTENDED;
-        case MediaTrackHelper::ReadOptions::SEEK_PREVIOUS_SYNC:
+        case MediaTrackHelperV3::ReadOptions::SEEK_PREVIOUS_SYNC:
             if (index == 0) {
                 ALOGW("Previous sync not found; starting from the earliest "
                         "sync.");
diff --git a/media/extractors/mpeg2/MPEG2TSExtractor.h b/media/extractors/mpeg2/MPEG2TSExtractor.h
index 4013442..aed17bb 100644
--- a/media/extractors/mpeg2/MPEG2TSExtractor.h
+++ b/media/extractors/mpeg2/MPEG2TSExtractor.h
@@ -38,16 +38,16 @@
 struct MPEG2TSSource;
 class String8;
 
-struct MPEG2TSExtractor : public MediaExtractorPluginHelper {
+struct MPEG2TSExtractor : public MediaExtractorPluginHelperV3 {
     explicit MPEG2TSExtractor(DataSourceHelper *source);
 
     virtual size_t countTracks();
-    virtual MediaTrackHelper *getTrack(size_t index);
-    virtual status_t getTrackMetaData(MetaDataBase &meta, size_t index, uint32_t flags);
+    virtual MediaTrackHelperV3 *getTrack(size_t index);
+    virtual media_status_t getTrackMetaData(AMediaFormat *meta, size_t index, uint32_t flags);
 
-    virtual status_t getMetaData(MetaDataBase& meta);
+    virtual media_status_t getMetaData(AMediaFormat *meta);
 
-    virtual status_t setMediaCas(const uint8_t* /*casToken*/, size_t /*size*/) override;
+    virtual media_status_t setMediaCas(const uint8_t* /*casToken*/, size_t /*size*/) override;
 
     virtual uint32_t flags() const;
     virtual const char * name() { return "MPEG2TSExtractor"; }
@@ -90,7 +90,7 @@
     // the data has syntax error during parsing, etc.
     status_t feedMore(bool isInit = false);
     status_t seek(int64_t seekTimeUs,
-            const MediaTrackHelper::ReadOptions::SeekMode& seekMode);
+            const MediaTrackHelperV3::ReadOptions::SeekMode& seekMode);
     status_t queueDiscontinuityForSeek(int64_t actualSeekTimeUs);
     status_t seekBeyond(int64_t seekTimeUs);