OMX.cpp revision 979d233237271c2acc0c3902508e208fce16a1c9
1e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard/*
2e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard * Copyright (C) 2009 The Android Open Source Project
3e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard *
4e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard * Licensed under the Apache License, Version 2.0 (the "License");
5e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard * you may not use this file except in compliance with the License.
6e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard * You may obtain a copy of the License at
7e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard *
8e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard *      http://www.apache.org/licenses/LICENSE-2.0
9e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard *
10e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard * Unless required by applicable law or agreed to in writing, software
11e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard * distributed under the License is distributed on an "AS IS" BASIS,
12e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard * See the License for the specific language governing permissions and
14e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard * limitations under the License.
15e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard */
16e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
17e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard//#define LOG_NDEBUG 0
18e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#define LOG_TAG "OMX"
19e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#include <utils/Log.h>
20e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
21e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#include <dlfcn.h>
22e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
23e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#include <sys/prctl.h>
24e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#include <sys/resource.h>
25e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
26e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#include "../include/OMX.h"
27e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#include "OMXRenderer.h"
28e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
29e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#include "../include/OMXNodeInstance.h"
30e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#include "../include/SoftwareRenderer.h"
31e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
32e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#include <binder/IMemory.h>
33e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#include <media/stagefright/MediaDebug.h>
34e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#include <media/stagefright/VideoRenderer.h>
35e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#include <utils/threads.h>
36e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
37e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#include "OMXMaster.h"
38e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
39e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#include <OMX_Component.h>
40e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
41e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardnamespace android {
42e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
43e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard////////////////////////////////////////////////////////////////////////////////
44e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
45e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstruct OMX::CallbackDispatcher : public RefBase {
46e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    CallbackDispatcher(OMXNodeInstance *owner);
47e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
48e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    void post(const omx_message &msg);
49e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
50e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardprotected:
51e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    virtual ~CallbackDispatcher();
52e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
53e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardprivate:
54e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    Mutex mLock;
55e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
56e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    OMXNodeInstance *mOwner;
57e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    bool mDone;
58e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    Condition mQueueChanged;
59e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    List<omx_message> mQueue;
60e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
61e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    pthread_t mThread;
62e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
63e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    void dispatch(const omx_message &msg);
64e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
65e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    static void *ThreadWrapper(void *me);
66e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    void threadEntry();
67e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
68e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    CallbackDispatcher(const CallbackDispatcher &);
69e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    CallbackDispatcher &operator=(const CallbackDispatcher &);
70e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard};
71e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
72e2e838afcf03e603a41a0455846eaf9614537c16Mans RullgardOMX::CallbackDispatcher::CallbackDispatcher(OMXNodeInstance *owner)
73e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    : mOwner(owner),
74e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard      mDone(false) {
75e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    pthread_attr_t attr;
76e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    pthread_attr_init(&attr);
77e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_JOINABLE);
78e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
79e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    pthread_create(&mThread, &attr, ThreadWrapper, this);
80e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
81e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    pthread_attr_destroy(&attr);
82e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
83e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
84e2e838afcf03e603a41a0455846eaf9614537c16Mans RullgardOMX::CallbackDispatcher::~CallbackDispatcher() {
85e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    {
86b676a05348e4c516fa8b57e33b10548e6142c3f8Mans Rullgard        Mutex::Autolock autoLock(mLock);
87e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
88e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        mDone = true;
89e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        mQueueChanged.signal();
90e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    }
91e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
92e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    void *dummy;
93e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    pthread_join(mThread, &dummy);
94e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
95e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
96e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardvoid OMX::CallbackDispatcher::post(const omx_message &msg) {
97e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    Mutex::Autolock autoLock(mLock);
98e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
99e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    mQueue.push_back(msg);
100e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    mQueueChanged.signal();
101e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
102e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
103e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardvoid OMX::CallbackDispatcher::dispatch(const omx_message &msg) {
104e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    if (mOwner == NULL) {
105e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        LOGV("Would have dispatched a message to a node that's already gone.");
106e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        return;
107e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    }
108e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    mOwner->onMessage(msg);
109e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
110e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
111e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard// static
112e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardvoid *OMX::CallbackDispatcher::ThreadWrapper(void *me) {
113e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    static_cast<CallbackDispatcher *>(me)->threadEntry();
114e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
115e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return NULL;
116e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
117e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
118e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardvoid OMX::CallbackDispatcher::threadEntry() {
119e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    setpriority(PRIO_PROCESS, 0, ANDROID_PRIORITY_AUDIO);
120e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    prctl(PR_SET_NAME, (unsigned long)"OMXCallbackDisp", 0, 0, 0);
121e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
122e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    for (;;) {
123e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        omx_message msg;
124e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
125e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        {
126e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            Mutex::Autolock autoLock(mLock);
127e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            while (!mDone && mQueue.empty()) {
128e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                mQueueChanged.wait(mLock);
129e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            }
130e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
131e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            if (mDone) {
132e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                break;
133e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            }
134e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
135e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            msg = *mQueue.begin();
136e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            mQueue.erase(mQueue.begin());
137e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        }
138e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
139e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        dispatch(msg);
140e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    }
141e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
142e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
143e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard////////////////////////////////////////////////////////////////////////////////
144e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
145e2e838afcf03e603a41a0455846eaf9614537c16Mans RullgardOMX::OMX()
146e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    : mMaster(new OMXMaster),
147e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard      mNodeCounter(0) {
148e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
149e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
150e2e838afcf03e603a41a0455846eaf9614537c16Mans RullgardOMX::~OMX() {
151e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    delete mMaster;
152e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    mMaster = NULL;
153e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
154e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
155e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardvoid OMX::binderDied(const wp<IBinder> &the_late_who) {
156e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    OMXNodeInstance *instance;
157e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
158e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    {
159e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        Mutex::Autolock autoLock(mLock);
160e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
161e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        ssize_t index = mLiveNodes.indexOfKey(the_late_who);
162e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        CHECK(index >= 0);
163e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
164e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        instance = mLiveNodes.editValueAt(index);
165e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        mLiveNodes.removeItemsAt(index);
166e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
167e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        index = mDispatchers.indexOfKey(instance->nodeID());
168e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        CHECK(index >= 0);
169e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        mDispatchers.removeItemsAt(index);
170e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
171e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        invalidateNodeID_l(instance->nodeID());
172e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    }
173e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
174e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    instance->onObserverDied(mMaster);
175e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
176e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
177e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardbool OMX::livesLocally(pid_t pid) {
178e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return pid == getpid();
179e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
180e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
181e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstatus_t OMX::listNodes(List<ComponentInfo> *list) {
182e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    list->clear();
183e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
184e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    OMX_U32 index = 0;
185e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    char componentName[256];
186e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    while (mMaster->enumerateComponents(
187e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                componentName, sizeof(componentName), index) == OMX_ErrorNone) {
188e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        list->push_back(ComponentInfo());
189e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        ComponentInfo &info = *--list->end();
190e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
191e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        info.mName = componentName;
192e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
193e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        Vector<String8> roles;
194e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        OMX_ERRORTYPE err =
195e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            mMaster->getRolesOfComponent(componentName, &roles);
196e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
197e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        if (err == OMX_ErrorNone) {
198e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            for (OMX_U32 i = 0; i < roles.size(); ++i) {
199e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                info.mRoles.push_back(roles[i]);
200e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            }
201e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        }
202e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
203e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        ++index;
204e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    }
205e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
206e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return OK;
207e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
208e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
209e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstatus_t OMX::allocateNode(
210e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        const char *name, const sp<IOMXObserver> &observer, node_id *node) {
211e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    Mutex::Autolock autoLock(mLock);
212e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
213e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    *node = 0;
214e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
215e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    OMXNodeInstance *instance = new OMXNodeInstance(this, observer);
216e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
217e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    OMX_COMPONENTTYPE *handle;
218e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    OMX_ERRORTYPE err = mMaster->makeComponentInstance(
219e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            name, &OMXNodeInstance::kCallbacks,
220e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            instance, &handle);
221e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
222e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    if (err != OMX_ErrorNone) {
223e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        LOGV("FAILED to allocate omx component '%s'", name);
224e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
225e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        instance->onGetHandleFailed();
226e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
227e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        return UNKNOWN_ERROR;
228e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    }
229e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
230e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    *node = makeNodeID(instance);
231e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    mDispatchers.add(*node, new CallbackDispatcher(instance));
232e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
233e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    instance->setHandle(*node, handle);
234e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
235e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    mLiveNodes.add(observer->asBinder(), instance);
236e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    observer->asBinder()->linkToDeath(this);
237e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
238e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return OK;
239e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
240e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
241e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstatus_t OMX::freeNode(node_id node) {
242e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    OMXNodeInstance *instance = findInstance(node);
243e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
244e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    ssize_t index = mLiveNodes.indexOfKey(instance->observer()->asBinder());
245e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    CHECK(index >= 0);
246e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    mLiveNodes.removeItemsAt(index);
247e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
248e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    instance->observer()->asBinder()->unlinkToDeath(this);
249e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
250e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    status_t err = instance->freeNode(mMaster);
251e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
252e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    index = mDispatchers.indexOfKey(node);
253e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    CHECK(index >= 0);
254e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    mDispatchers.removeItemsAt(index);
255e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
256e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return err;
257e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
258e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
259e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstatus_t OMX::sendCommand(
260e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        node_id node, OMX_COMMANDTYPE cmd, OMX_S32 param) {
261e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return findInstance(node)->sendCommand(cmd, param);
262e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
263e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
264e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstatus_t OMX::getParameter(
265e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        node_id node, OMX_INDEXTYPE index,
266e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        void *params, size_t size) {
267e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return findInstance(node)->getParameter(
268e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            index, params, size);
269e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
270e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
271e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstatus_t OMX::setParameter(
272e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        node_id node, OMX_INDEXTYPE index,
273e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        const void *params, size_t size) {
274e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return findInstance(node)->setParameter(
275e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            index, params, size);
276e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
277e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
278e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstatus_t OMX::getConfig(
279e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        node_id node, OMX_INDEXTYPE index,
280e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        void *params, size_t size) {
281e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return findInstance(node)->getConfig(
282e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            index, params, size);
283e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
284e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
285e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstatus_t OMX::setConfig(
286e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        node_id node, OMX_INDEXTYPE index,
287e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        const void *params, size_t size) {
288e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return findInstance(node)->setConfig(
289e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            index, params, size);
290e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
291e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
292e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstatus_t OMX::enableGraphicBuffers(
293e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        node_id node, OMX_U32 port_index, OMX_BOOL enable) {
294e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return findInstance(node)->enableGraphicBuffers(port_index, enable);
295e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
296e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
297e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstatus_t OMX::useBuffer(
298e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        node_id node, OMX_U32 port_index, const sp<IMemory> &params,
299e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        buffer_id *buffer) {
300e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return findInstance(node)->useBuffer(
301e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            port_index, params, buffer);
302e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
303e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
304e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstatus_t OMX::useGraphicBuffer(
305e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        node_id node, OMX_U32 port_index,
306e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        const sp<GraphicBuffer> &graphicBuffer, buffer_id *buffer) {
307e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return findInstance(node)->useGraphicBuffer(
308e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            port_index, graphicBuffer, buffer);
309e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
310e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
311e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstatus_t OMX::allocateBuffer(
312e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        node_id node, OMX_U32 port_index, size_t size,
313e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        buffer_id *buffer, void **buffer_data) {
314e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return findInstance(node)->allocateBuffer(
315e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            port_index, size, buffer, buffer_data);
316e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
317e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
318e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstatus_t OMX::allocateBufferWithBackup(
319e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        node_id node, OMX_U32 port_index, const sp<IMemory> &params,
320e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        buffer_id *buffer) {
321e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return findInstance(node)->allocateBufferWithBackup(
322e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            port_index, params, buffer);
323e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
324e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
325e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstatus_t OMX::freeBuffer(node_id node, OMX_U32 port_index, buffer_id buffer) {
326e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return findInstance(node)->freeBuffer(
327e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            port_index, buffer);
328e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
329e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
330e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstatus_t OMX::fillBuffer(node_id node, buffer_id buffer) {
331e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return findInstance(node)->fillBuffer(buffer);
332e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
333e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
334e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstatus_t OMX::emptyBuffer(
335e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        node_id node,
336e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        buffer_id buffer,
337e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        OMX_U32 range_offset, OMX_U32 range_length,
338e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        OMX_U32 flags, OMX_TICKS timestamp) {
339e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return findInstance(node)->emptyBuffer(
340e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            buffer, range_offset, range_length, flags, timestamp);
341e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
342e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
343e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstatus_t OMX::getExtensionIndex(
344e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        node_id node,
345e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        const char *parameter_name,
346e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        OMX_INDEXTYPE *index) {
347e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return findInstance(node)->getExtensionIndex(
348e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            parameter_name, index);
349e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
350e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
351e2e838afcf03e603a41a0455846eaf9614537c16Mans RullgardOMX_ERRORTYPE OMX::OnEvent(
352e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        node_id node,
353e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        OMX_IN OMX_EVENTTYPE eEvent,
354e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        OMX_IN OMX_U32 nData1,
355e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        OMX_IN OMX_U32 nData2,
356e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        OMX_IN OMX_PTR pEventData) {
357e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    LOGV("OnEvent(%d, %ld, %ld)", eEvent, nData1, nData2);
358e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
359e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    omx_message msg;
360e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    msg.type = omx_message::EVENT;
361e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    msg.node = node;
362e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    msg.u.event_data.event = eEvent;
363e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    msg.u.event_data.data1 = nData1;
364e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    msg.u.event_data.data2 = nData2;
365e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
366e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    findDispatcher(node)->post(msg);
367e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
368e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return OMX_ErrorNone;
369e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
370e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
371e2e838afcf03e603a41a0455846eaf9614537c16Mans RullgardOMX_ERRORTYPE OMX::OnEmptyBufferDone(
372e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        node_id node, OMX_IN OMX_BUFFERHEADERTYPE *pBuffer) {
373e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    LOGV("OnEmptyBufferDone buffer=%p", pBuffer);
374e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
375e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    omx_message msg;
376e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    msg.type = omx_message::EMPTY_BUFFER_DONE;
377e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    msg.node = node;
378e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    msg.u.buffer_data.buffer = pBuffer;
379e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
380e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    findDispatcher(node)->post(msg);
381e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
382e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return OMX_ErrorNone;
383e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
384e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
385e2e838afcf03e603a41a0455846eaf9614537c16Mans RullgardOMX_ERRORTYPE OMX::OnFillBufferDone(
386e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        node_id node, OMX_IN OMX_BUFFERHEADERTYPE *pBuffer) {
387e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    LOGV("OnFillBufferDone buffer=%p", pBuffer);
388e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
389e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    omx_message msg;
390e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    msg.type = omx_message::FILL_BUFFER_DONE;
391e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    msg.node = node;
392e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    msg.u.extended_buffer_data.buffer = pBuffer;
393e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    msg.u.extended_buffer_data.range_offset = pBuffer->nOffset;
394e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    msg.u.extended_buffer_data.range_length = pBuffer->nFilledLen;
395e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    msg.u.extended_buffer_data.flags = pBuffer->nFlags;
396e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    msg.u.extended_buffer_data.timestamp = pBuffer->nTimeStamp;
397e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    msg.u.extended_buffer_data.platform_private = pBuffer->pPlatformPrivate;
398e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    msg.u.extended_buffer_data.data_ptr = pBuffer->pBuffer;
399e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
400e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    findDispatcher(node)->post(msg);
401e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
402e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return OMX_ErrorNone;
403e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
404e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
405e2e838afcf03e603a41a0455846eaf9614537c16Mans RullgardOMX::node_id OMX::makeNodeID(OMXNodeInstance *instance) {
406e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    // mLock is already held.
407e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
408e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    node_id node = (node_id)++mNodeCounter;
409e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    mNodeIDToInstance.add(node, instance);
410e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
411e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return node;
412e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
413e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
414e2e838afcf03e603a41a0455846eaf9614537c16Mans RullgardOMXNodeInstance *OMX::findInstance(node_id node) {
415e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    Mutex::Autolock autoLock(mLock);
416e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
417e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    ssize_t index = mNodeIDToInstance.indexOfKey(node);
418e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
419e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return index < 0 ? NULL : mNodeIDToInstance.valueAt(index);
420e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
421e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
422e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardsp<OMX::CallbackDispatcher> OMX::findDispatcher(node_id node) {
423e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    Mutex::Autolock autoLock(mLock);
424e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
425e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    ssize_t index = mDispatchers.indexOfKey(node);
426e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
427e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return index < 0 ? NULL : mDispatchers.valueAt(index);
428e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
429e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
430e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardvoid OMX::invalidateNodeID(node_id node) {
431e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    Mutex::Autolock autoLock(mLock);
432e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    invalidateNodeID_l(node);
433e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
434e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
435e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardvoid OMX::invalidateNodeID_l(node_id node) {
436e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    // mLock is held.
437e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    mNodeIDToInstance.removeItem(node);
438e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
439e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
440e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard////////////////////////////////////////////////////////////////////////////////
441e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
442e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardstruct SharedVideoRenderer : public VideoRenderer {
443e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    SharedVideoRenderer(void *libHandle, VideoRenderer *obj)
444e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        : mLibHandle(libHandle),
445e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard          mObj(obj) {
446e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    }
447e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
448e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    virtual ~SharedVideoRenderer() {
449e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        delete mObj;
450e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        mObj = NULL;
451e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
452e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        dlclose(mLibHandle);
453e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        mLibHandle = NULL;
454e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    }
455e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
456e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    virtual void render(
457e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            const void *data, size_t size, void *platformPrivate) {
458e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        return mObj->render(data, size, platformPrivate);
459e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    }
460e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
461e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardprivate:
462e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    void *mLibHandle;
463e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    VideoRenderer *mObj;
464e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
465e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    SharedVideoRenderer(const SharedVideoRenderer &);
466e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    SharedVideoRenderer &operator=(const SharedVideoRenderer &);
467e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard};
468e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
469e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardsp<IOMXRenderer> OMX::createRenderer(
470e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        const sp<ISurface> &surface,
471e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        const char *componentName,
472e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        OMX_COLOR_FORMATTYPE colorFormat,
473e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        size_t encodedWidth, size_t encodedHeight,
474e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        size_t displayWidth, size_t displayHeight) {
475e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    Mutex::Autolock autoLock(mLock);
476e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
477e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    VideoRenderer *impl = NULL;
478e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
479e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    void *libHandle = dlopen("libstagefrighthw.so", RTLD_NOW);
480e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
481e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    if (libHandle) {
482e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        typedef VideoRenderer *(*CreateRendererFunc)(
483e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                const sp<ISurface> &surface,
484e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                const char *componentName,
485e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                OMX_COLOR_FORMATTYPE colorFormat,
486e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                size_t displayWidth, size_t displayHeight,
487e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                size_t decodedWidth, size_t decodedHeight);
488e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
489e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        CreateRendererFunc func =
490e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            (CreateRendererFunc)dlsym(
491e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                    libHandle,
492e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                    "_Z14createRendererRKN7android2spINS_8ISurfaceEEEPKc20"
493e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                    "OMX_COLOR_FORMATTYPEjjjj");
494e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
495e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        if (func) {
496e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            impl = (*func)(surface, componentName, colorFormat,
497e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                    displayWidth, displayHeight, encodedWidth, encodedHeight);
498e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
499e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            if (impl) {
500e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                impl = new SharedVideoRenderer(libHandle, impl);
501e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                libHandle = NULL;
502e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            }
503e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        }
504e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
505e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        if (libHandle) {
506e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            dlclose(libHandle);
507e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            libHandle = NULL;
508e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        }
509e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    }
510e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
511e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    if (!impl) {
512e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#if 0
513e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        LOGW("Using software renderer.");
514e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        impl = new SoftwareRenderer(
515e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                colorFormat,
516e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                surface,
517e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                displayWidth, displayHeight,
518e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard                encodedWidth, encodedHeight);
519e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#else
520e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        CHECK(!"Should not be here.");
521e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard        return NULL;
522e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard#endif
523e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    }
524e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
525e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    return new OMXRenderer(impl);
526e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
527e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
528e2e838afcf03e603a41a0455846eaf9614537c16Mans RullgardOMXRenderer::OMXRenderer(VideoRenderer *impl)
529e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    : mImpl(impl) {
530e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
531e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
532e2e838afcf03e603a41a0455846eaf9614537c16Mans RullgardOMXRenderer::~OMXRenderer() {
533e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    delete mImpl;
534e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    mImpl = NULL;
535e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
536e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
537e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgardvoid OMXRenderer::render(IOMX::buffer_id buffer) {
538e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    OMX_BUFFERHEADERTYPE *header = (OMX_BUFFERHEADERTYPE *)buffer;
539e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
540e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard    mImpl->render(
541e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            header->pBuffer + header->nOffset,
542e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            header->nFilledLen,
543e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard            header->pPlatformPrivate);
544e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}
545e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard
546e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard}  // namespace android
547e2e838afcf03e603a41a0455846eaf9614537c16Mans Rullgard