Merge "Avoid deadlock in OMX::freeNode by making sure OMXCodecObserver does not hold the last reference of OMXCodec object - do not merge" into gingerbread

This commit is contained in:
James Dong
2011-01-10 12:04:50 -08:00
committed by Android (Google) Code Review
3 changed files with 18 additions and 7 deletions

View File

@@ -60,8 +60,6 @@ struct OMXCodec : public MediaSource,
virtual status_t pause(); virtual status_t pause();
void on_message(const omx_message &msg);
// from MediaBufferObserver // from MediaBufferObserver
virtual void signalBufferReturned(MediaBuffer *buffer); virtual void signalBufferReturned(MediaBuffer *buffer);
@@ -69,6 +67,13 @@ protected:
virtual ~OMXCodec(); virtual ~OMXCodec();
private: private:
// Make sure mLock is accessible to OMXCodecObserver
friend class OMXCodecObserver;
// Call this with mLock hold
void on_message(const omx_message &msg);
enum State { enum State {
DEAD, DEAD,
LOADED, LOADED,

View File

@@ -234,7 +234,9 @@ struct OMXCodecObserver : public BnOMXObserver {
sp<OMXCodec> codec = mTarget.promote(); sp<OMXCodec> codec = mTarget.promote();
if (codec.get() != NULL) { if (codec.get() != NULL) {
Mutex::Autolock autoLock(codec->mLock);
codec->on_message(msg); codec->on_message(msg);
codec.clear();
} }
} }
@@ -1672,8 +1674,6 @@ status_t OMXCodec::allocateBuffersOnPort(OMX_U32 portIndex) {
} }
void OMXCodec::on_message(const omx_message &msg) { void OMXCodec::on_message(const omx_message &msg) {
Mutex::Autolock autoLock(mLock);
switch (msg.type) { switch (msg.type) {
case omx_message::EVENT: case omx_message::EVENT:
{ {

View File

@@ -89,6 +89,9 @@ OMX::CallbackDispatcher::~CallbackDispatcher() {
mQueueChanged.signal(); mQueueChanged.signal();
} }
// Don't call join on myself
CHECK(mThread != pthread_self());
void *dummy; void *dummy;
pthread_join(mThread, &dummy); pthread_join(mThread, &dummy);
} }
@@ -249,9 +252,12 @@ status_t OMX::freeNode(node_id node) {
status_t err = instance->freeNode(mMaster); status_t err = instance->freeNode(mMaster);
{
Mutex::Autolock autoLock(mLock);
index = mDispatchers.indexOfKey(node); index = mDispatchers.indexOfKey(node);
CHECK(index >= 0); CHECK(index >= 0);
mDispatchers.removeItemsAt(index); mDispatchers.removeItemsAt(index);
}
return err; return err;
} }