SoftVPX.cpp revision 50f939d655a5156157564cb91434f1cce424b2dd
1bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber/*
2bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber * Copyright (C) 2011 The Android Open Source Project
3bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber *
4bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber * Licensed under the Apache License, Version 2.0 (the "License");
5bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber * you may not use this file except in compliance with the License.
6bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber * You may obtain a copy of the License at
7bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber *
8bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber *      http://www.apache.org/licenses/LICENSE-2.0
9bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber *
10bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber * Unless required by applicable law or agreed to in writing, software
11bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber * distributed under the License is distributed on an "AS IS" BASIS,
12bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber * See the License for the specific language governing permissions and
14bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber * limitations under the License.
15bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber */
16bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
17bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber//#define LOG_NDEBUG 0
18bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber#define LOG_TAG "SoftVPX"
19bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber#include <utils/Log.h>
20bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
21bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber#include "SoftVPX.h"
22bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
23bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber#include <media/stagefright/foundation/ADebug.h>
24bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber#include <media/stagefright/MediaDefs.h>
25bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
26bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
27bbba88cb1bdc34705d1477208990a06904c022e7Andreas Hubernamespace android {
28bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
29bbba88cb1bdc34705d1477208990a06904c022e7Andreas HuberSoftVPX::SoftVPX(
30bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        const char *name,
3194705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang        const char *componentRole,
3294705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang        OMX_VIDEO_CODINGTYPE codingType,
33bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        const OMX_CALLBACKTYPE *callbacks,
34bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        OMX_PTR appData,
35bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        OMX_COMPONENTTYPE **component)
367f616d3cc5366a4b8af20d3d0c768e3de1df0666Lajos Molnar    : SoftVideoDecoderOMXComponent(
3794705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang            name, componentRole, codingType,
387f616d3cc5366a4b8af20d3d0c768e3de1df0666Lajos Molnar            NULL /* profileLevels */, 0 /* numProfileLevels */,
397f616d3cc5366a4b8af20d3d0c768e3de1df0666Lajos Molnar            320 /* width */, 240 /* height */, callbacks, appData, component),
4094705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang      mMode(codingType == OMX_VIDEO_CodingVP8 ? MODE_VP8 : MODE_VP9),
4150f939d655a5156157564cb91434f1cce424b2ddhkuang      mCtx(NULL),
4250f939d655a5156157564cb91434f1cce424b2ddhkuang      mImg(NULL) {
437f616d3cc5366a4b8af20d3d0c768e3de1df0666Lajos Molnar    initPorts(kNumBuffers, 768 * 1024 /* inputBufferSize */,
4494705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang            kNumBuffers,
4594705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang            codingType == OMX_VIDEO_CodingVP8 ? MEDIA_MIMETYPE_VIDEO_VP8 : MEDIA_MIMETYPE_VIDEO_VP9);
467f616d3cc5366a4b8af20d3d0c768e3de1df0666Lajos Molnar
47bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber    CHECK_EQ(initDecoder(), (status_t)OK);
48bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber}
49bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
50bbba88cb1bdc34705d1477208990a06904c022e7Andreas HuberSoftVPX::~SoftVPX() {
51bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber    vpx_codec_destroy((vpx_codec_ctx_t *)mCtx);
52bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber    delete (vpx_codec_ctx_t *)mCtx;
53bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber    mCtx = NULL;
54bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber}
55bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
56f3ac3e3c94c14dbf1cdf6a4577f0b3aa8edfad06James Dongstatic int GetCPUCoreCount() {
57f3ac3e3c94c14dbf1cdf6a4577f0b3aa8edfad06James Dong    int cpuCoreCount = 1;
58f3ac3e3c94c14dbf1cdf6a4577f0b3aa8edfad06James Dong#if defined(_SC_NPROCESSORS_ONLN)
59f3ac3e3c94c14dbf1cdf6a4577f0b3aa8edfad06James Dong    cpuCoreCount = sysconf(_SC_NPROCESSORS_ONLN);
60f3ac3e3c94c14dbf1cdf6a4577f0b3aa8edfad06James Dong#else
61f3ac3e3c94c14dbf1cdf6a4577f0b3aa8edfad06James Dong    // _SC_NPROC_ONLN must be defined...
62f3ac3e3c94c14dbf1cdf6a4577f0b3aa8edfad06James Dong    cpuCoreCount = sysconf(_SC_NPROC_ONLN);
63f3ac3e3c94c14dbf1cdf6a4577f0b3aa8edfad06James Dong#endif
64f3ac3e3c94c14dbf1cdf6a4577f0b3aa8edfad06James Dong    CHECK(cpuCoreCount >= 1);
653856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("Number of CPU cores: %d", cpuCoreCount);
66f3ac3e3c94c14dbf1cdf6a4577f0b3aa8edfad06James Dong    return cpuCoreCount;
67f3ac3e3c94c14dbf1cdf6a4577f0b3aa8edfad06James Dong}
68f3ac3e3c94c14dbf1cdf6a4577f0b3aa8edfad06James Dong
69bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huberstatus_t SoftVPX::initDecoder() {
70bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber    mCtx = new vpx_codec_ctx_t;
71bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber    vpx_codec_err_t vpx_err;
72f3ac3e3c94c14dbf1cdf6a4577f0b3aa8edfad06James Dong    vpx_codec_dec_cfg_t cfg;
73f3ac3e3c94c14dbf1cdf6a4577f0b3aa8edfad06James Dong    memset(&cfg, 0, sizeof(vpx_codec_dec_cfg_t));
74f3ac3e3c94c14dbf1cdf6a4577f0b3aa8edfad06James Dong    cfg.threads = GetCPUCoreCount();
75bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber    if ((vpx_err = vpx_codec_dec_init(
7694705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang                (vpx_codec_ctx_t *)mCtx,
7794705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang                 mMode == MODE_VP8 ? &vpx_codec_vp8_dx_algo : &vpx_codec_vp9_dx_algo,
7894705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang                 &cfg, 0))) {
7929357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block        ALOGE("on2 decoder failed to initialize. (%d)", vpx_err);
80bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        return UNKNOWN_ERROR;
81bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber    }
82bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
83bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber    return OK;
84bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber}
85bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
8684333e0475bc911adc16417f4ca327c975cf6c36Andreas Hubervoid SoftVPX::onQueueFilled(OMX_U32 /* portIndex */) {
87bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber    if (mOutputPortSettingsChange != NONE) {
88bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        return;
89bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber    }
90bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
91bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber    List<BufferInfo *> &inQueue = getPortQueue(0);
92bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber    List<BufferInfo *> &outQueue = getPortQueue(1);
93a02eae5e911f3bdc3f84f39c0ef223261b646128Lajos Molnar    bool EOSseen = false;
94bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
95bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber    while (!inQueue.empty() && !outQueue.empty()) {
96bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        BufferInfo *inInfo = *inQueue.begin();
97bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        OMX_BUFFERHEADERTYPE *inHeader = inInfo->mHeader;
98bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
99bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        BufferInfo *outInfo = *outQueue.begin();
100bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        OMX_BUFFERHEADERTYPE *outHeader = outInfo->mHeader;
101bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
102bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        if (inHeader->nFlags & OMX_BUFFERFLAG_EOS) {
103a02eae5e911f3bdc3f84f39c0ef223261b646128Lajos Molnar            EOSseen = true;
104a02eae5e911f3bdc3f84f39c0ef223261b646128Lajos Molnar            if (inHeader->nFilledLen == 0) {
105a02eae5e911f3bdc3f84f39c0ef223261b646128Lajos Molnar                inQueue.erase(inQueue.begin());
106a02eae5e911f3bdc3f84f39c0ef223261b646128Lajos Molnar                inInfo->mOwnedByUs = false;
107a02eae5e911f3bdc3f84f39c0ef223261b646128Lajos Molnar                notifyEmptyBufferDone(inHeader);
108a02eae5e911f3bdc3f84f39c0ef223261b646128Lajos Molnar
109a02eae5e911f3bdc3f84f39c0ef223261b646128Lajos Molnar                outHeader->nFilledLen = 0;
110a02eae5e911f3bdc3f84f39c0ef223261b646128Lajos Molnar                outHeader->nFlags = OMX_BUFFERFLAG_EOS;
111a02eae5e911f3bdc3f84f39c0ef223261b646128Lajos Molnar
112a02eae5e911f3bdc3f84f39c0ef223261b646128Lajos Molnar                outQueue.erase(outQueue.begin());
113a02eae5e911f3bdc3f84f39c0ef223261b646128Lajos Molnar                outInfo->mOwnedByUs = false;
114a02eae5e911f3bdc3f84f39c0ef223261b646128Lajos Molnar                notifyFillBufferDone(outHeader);
115a02eae5e911f3bdc3f84f39c0ef223261b646128Lajos Molnar                return;
116a02eae5e911f3bdc3f84f39c0ef223261b646128Lajos Molnar            }
117bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        }
118bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
11950f939d655a5156157564cb91434f1cce424b2ddhkuang        if (mImg == NULL) {
12050f939d655a5156157564cb91434f1cce424b2ddhkuang            if (vpx_codec_decode(
12150f939d655a5156157564cb91434f1cce424b2ddhkuang                        (vpx_codec_ctx_t *)mCtx,
12250f939d655a5156157564cb91434f1cce424b2ddhkuang                        inHeader->pBuffer + inHeader->nOffset,
12350f939d655a5156157564cb91434f1cce424b2ddhkuang                        inHeader->nFilledLen,
12450f939d655a5156157564cb91434f1cce424b2ddhkuang                        NULL,
12550f939d655a5156157564cb91434f1cce424b2ddhkuang                        0)) {
12650f939d655a5156157564cb91434f1cce424b2ddhkuang                ALOGE("on2 decoder failed to decode frame.");
127bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
12850f939d655a5156157564cb91434f1cce424b2ddhkuang                notify(OMX_EventError, OMX_ErrorUndefined, 0, NULL);
12950f939d655a5156157564cb91434f1cce424b2ddhkuang                return;
13050f939d655a5156157564cb91434f1cce424b2ddhkuang            }
13150f939d655a5156157564cb91434f1cce424b2ddhkuang            vpx_codec_iter_t iter = NULL;
13250f939d655a5156157564cb91434f1cce424b2ddhkuang            mImg = vpx_codec_get_frame((vpx_codec_ctx_t *)mCtx, &iter);
133bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        }
134bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
13550f939d655a5156157564cb91434f1cce424b2ddhkuang        if (mImg != NULL) {
13650f939d655a5156157564cb91434f1cce424b2ddhkuang            CHECK_EQ(mImg->fmt, IMG_FMT_I420);
137bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
13850f939d655a5156157564cb91434f1cce424b2ddhkuang            uint32_t width = mImg->d_w;
13950f939d655a5156157564cb91434f1cce424b2ddhkuang            uint32_t height = mImg->d_h;
140bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
141bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber            if (width != mWidth || height != mHeight) {
142bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber                mWidth = width;
143bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber                mHeight = height;
144bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
145031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                if (!mIsAdaptive || width > mAdaptiveMaxWidth || height > mAdaptiveMaxHeight) {
146031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                    if (mIsAdaptive) {
147031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                        if (width > mAdaptiveMaxWidth) {
148031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                            mAdaptiveMaxWidth = width;
149031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                        }
150031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                        if (height > mAdaptiveMaxHeight) {
151031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                            mAdaptiveMaxHeight = height;
152031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                        }
153031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                    }
154031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                    updatePortDefinitions();
155031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                    notify(OMX_EventPortSettingsChanged, kOutputPortIndex, 0, NULL);
156031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                    mOutputPortSettingsChange = AWAITING_DISABLED;
157031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                    return;
158031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                } else {
159031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                    updatePortDefinitions();
160031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                    notify(OMX_EventPortSettingsChanged, kOutputPortIndex,
161031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                           OMX_IndexConfigCommonOutputCrop, NULL);
162031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                }
163bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber            }
164bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
165bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber            outHeader->nOffset = 0;
166bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber            outHeader->nFilledLen = (width * height * 3) / 2;
167a02eae5e911f3bdc3f84f39c0ef223261b646128Lajos Molnar            outHeader->nFlags = EOSseen ? OMX_BUFFERFLAG_EOS : 0;
168bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber            outHeader->nTimeStamp = inHeader->nTimeStamp;
169bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
170031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu            uint32_t buffer_stride = mIsAdaptive ? mAdaptiveMaxWidth : mWidth;
171031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu            uint32_t buffer_height = mIsAdaptive ? mAdaptiveMaxHeight : mHeight;
172031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu
17350f939d655a5156157564cb91434f1cce424b2ddhkuang            const uint8_t *srcLine = (const uint8_t *)mImg->planes[PLANE_Y];
174bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber            uint8_t *dst = outHeader->pBuffer;
175031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu            for (size_t i = 0; i < buffer_height; ++i) {
17650f939d655a5156157564cb91434f1cce424b2ddhkuang                if (i < mImg->d_h) {
17750f939d655a5156157564cb91434f1cce424b2ddhkuang                    memcpy(dst, srcLine, mImg->d_w);
17850f939d655a5156157564cb91434f1cce424b2ddhkuang                    srcLine += mImg->stride[PLANE_Y];
179031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                }
180031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                dst += buffer_stride;
181bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber            }
182bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
18350f939d655a5156157564cb91434f1cce424b2ddhkuang            srcLine = (const uint8_t *)mImg->planes[PLANE_U];
184031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu            for (size_t i = 0; i < buffer_height / 2; ++i) {
18550f939d655a5156157564cb91434f1cce424b2ddhkuang                if (i < mImg->d_h / 2) {
18650f939d655a5156157564cb91434f1cce424b2ddhkuang                    memcpy(dst, srcLine, mImg->d_w / 2);
18750f939d655a5156157564cb91434f1cce424b2ddhkuang                    srcLine += mImg->stride[PLANE_U];
188031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                }
189031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                dst += buffer_stride / 2;
190bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber            }
191bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
19250f939d655a5156157564cb91434f1cce424b2ddhkuang            srcLine = (const uint8_t *)mImg->planes[PLANE_V];
193031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu            for (size_t i = 0; i < buffer_height / 2; ++i) {
19450f939d655a5156157564cb91434f1cce424b2ddhkuang                if (i < mImg->d_h / 2) {
19550f939d655a5156157564cb91434f1cce424b2ddhkuang                    memcpy(dst, srcLine, mImg->d_w / 2);
19650f939d655a5156157564cb91434f1cce424b2ddhkuang                    srcLine += mImg->stride[PLANE_V];
197031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                }
198031be0f358b07732092a4d1bf02fc99f109a63c4Ronghua Wu                dst += buffer_stride / 2;
199bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber            }
200bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
20150f939d655a5156157564cb91434f1cce424b2ddhkuang            mImg = NULL;
202bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber            outInfo->mOwnedByUs = false;
203bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber            outQueue.erase(outQueue.begin());
204bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber            outInfo = NULL;
205bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber            notifyFillBufferDone(outHeader);
206bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber            outHeader = NULL;
207bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        }
208bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
209bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        inInfo->mOwnedByUs = false;
210bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        inQueue.erase(inQueue.begin());
211bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        inInfo = NULL;
212bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        notifyEmptyBufferDone(inHeader);
213bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        inHeader = NULL;
214bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber    }
215bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber}
216bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
217bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber}  // namespace android
218bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber
219bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huberandroid::SoftOMXComponent *createSoftOMXComponent(
220bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        const char *name, const OMX_CALLBACKTYPE *callbacks,
221bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber        OMX_PTR appData, OMX_COMPONENTTYPE **component) {
22294705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang    if (!strcmp(name, "OMX.google.vp8.decoder")) {
22394705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang        return new android::SoftVPX(
22494705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang                name, "video_decoder.vp8", OMX_VIDEO_CodingVP8,
22594705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang                callbacks, appData, component);
22694705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang    } else if (!strcmp(name, "OMX.google.vp9.decoder")) {
22794705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang        return new android::SoftVPX(
22894705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang                name, "video_decoder.vp9", OMX_VIDEO_CodingVP9,
22994705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang                callbacks, appData, component);
23094705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang    } else {
23194705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang        CHECK(!"Unknown component");
23294705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang    }
233bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber}
234