diff options
author | Jamie Gennis <jgennis@google.com> | 2011-10-28 02:14:01 +0000 |
---|---|---|
committer | Android Git Automerger <android-git-automerger@android.com> | 2011-10-28 02:14:01 +0000 |
commit | 262620399c228b3b201c2c4b39c87508d3047d74 (patch) | |
tree | 96e7fd612606424311873d34492def7da58bd6d8 /media/libmediaplayerservice/MediaPlayerService.cpp | |
parent | be1480bade58688d201335860247734aec6b11cb (diff) | |
parent | 7dae00baa6e8957be15523c46bb948bd1dde64c3 (diff) | |
download | frameworks_av-262620399c228b3b201c2c4b39c87508d3047d74.zip frameworks_av-262620399c228b3b201c2c4b39c87508d3047d74.tar.gz frameworks_av-262620399c228b3b201c2c4b39c87508d3047d74.tar.bz2 |
am 08479cee: Merge "Stagefright: ANW::connect in MediaPlayerService" into ics-mr0
* commit '08479ceeba56c460fb52f60a24df27776f1936c3':
Stagefright: ANW::connect in MediaPlayerService
Diffstat (limited to 'media/libmediaplayerservice/MediaPlayerService.cpp')
-rw-r--r-- | media/libmediaplayerservice/MediaPlayerService.cpp | 59 |
1 files changed, 58 insertions, 1 deletions
diff --git a/media/libmediaplayerservice/MediaPlayerService.cpp b/media/libmediaplayerservice/MediaPlayerService.cpp index 2ea2af9..b655358 100644 --- a/media/libmediaplayerservice/MediaPlayerService.cpp +++ b/media/libmediaplayerservice/MediaPlayerService.cpp @@ -40,6 +40,7 @@ #include <binder/IServiceManager.h> #include <binder/MemoryHeapBase.h> #include <binder/MemoryBase.h> +#include <gui/SurfaceTextureClient.h> #include <utils/Errors.h> // for status_t #include <utils/String8.h> #include <utils/SystemClock.h> @@ -528,6 +529,8 @@ void MediaPlayerService::Client::disconnect() p->reset(); } + disconnectNativeWindow(); + IPCThreadState::self()->flushCommands(); } @@ -793,13 +796,67 @@ status_t MediaPlayerService::Client::setVideoSurface(const sp<Surface>& surface) return p->setVideoSurface(surface); } +void MediaPlayerService::Client::disconnectNativeWindow() { + if (mConnectedWindow != NULL) { + status_t err = native_window_api_disconnect(mConnectedWindow.get(), + NATIVE_WINDOW_API_MEDIA); + + if (err != OK) { + LOGW("native_window_api_disconnect returned an error: %s (%d)", + strerror(-err), err); + } + } + mConnectedWindow.clear(); +} + status_t MediaPlayerService::Client::setVideoSurfaceTexture( const sp<ISurfaceTexture>& surfaceTexture) { LOGV("[%d] setVideoSurfaceTexture(%p)", mConnId, surfaceTexture.get()); sp<MediaPlayerBase> p = getPlayer(); if (p == 0) return UNKNOWN_ERROR; - return p->setVideoSurfaceTexture(surfaceTexture); + + sp<IBinder> binder(surfaceTexture == NULL ? NULL : + surfaceTexture->asBinder()); + if (mConnectedWindowBinder == binder) { + return OK; + } + + sp<ANativeWindow> anw; + if (surfaceTexture != NULL) { + anw = new SurfaceTextureClient(surfaceTexture); + status_t err = native_window_api_connect(anw.get(), + NATIVE_WINDOW_API_MEDIA); + + if (err != OK) { + LOGE("setVideoSurfaceTexture failed: %d", err); + // Note that we must do the reset before disconnecting from the ANW. + // Otherwise queue/dequeue calls could be made on the disconnected + // ANW, which may result in errors. + reset(); + + disconnectNativeWindow(); + + return err; + } + } + + // Note that we must set the player's new SurfaceTexture before + // disconnecting the old one. Otherwise queue/dequeue calls could be made + // on the disconnected ANW, which may result in errors. + status_t err = p->setVideoSurfaceTexture(surfaceTexture); + + disconnectNativeWindow(); + + mConnectedWindow = anw; + + if (err == OK) { + mConnectedWindowBinder = binder; + } else { + disconnectNativeWindow(); + } + + return err; } status_t MediaPlayerService::Client::invoke(const Parcel& request, |