summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--include/gui/ISurfaceComposer.h8
-rw-r--r--include/gui/SurfaceComposerClient.h9
-rw-r--r--libs/gui/ISurfaceComposer.cpp51
-rw-r--r--libs/gui/SurfaceComposerClient.cpp9
-rw-r--r--services/surfaceflinger/SurfaceFlinger.cpp19
-rw-r--r--services/surfaceflinger/SurfaceFlinger.h1
6 files changed, 80 insertions, 17 deletions
diff --git a/include/gui/ISurfaceComposer.h b/include/gui/ISurfaceComposer.h
index 0606aff..5c3c99c 100644
--- a/include/gui/ISurfaceComposer.h
+++ b/include/gui/ISurfaceComposer.h
@@ -70,12 +70,17 @@ public:
/* return an IDisplayEventConnection */
virtual sp<IDisplayEventConnection> createDisplayEventConnection() = 0;
- /* create a display
+ /* create a virtual display
* requires ACCESS_SURFACE_FLINGER permission.
*/
virtual sp<IBinder> createDisplay(const String8& displayName,
bool secure) = 0;
+ /* destroy a virtual display
+ * requires ACCESS_SURFACE_FLINGER permission.
+ */
+ virtual void destroyDisplay(const sp<IBinder>& display) = 0;
+
/* get the token for the existing default displays. possible values
* for id are eDisplayIdMain and eDisplayIdHdmi.
*/
@@ -130,6 +135,7 @@ public:
CREATE_GRAPHIC_BUFFER_ALLOC,
CREATE_DISPLAY_EVENT_CONNECTION,
CREATE_DISPLAY,
+ DESTROY_DISPLAY,
GET_BUILT_IN_DISPLAY,
SET_TRANSACTION_STATE,
AUTHENTICATE_SURFACE,
diff --git a/include/gui/SurfaceComposerClient.h b/include/gui/SurfaceComposerClient.h
index 643d7cf..e982bcd 100644
--- a/include/gui/SurfaceComposerClient.h
+++ b/include/gui/SurfaceComposerClient.h
@@ -48,7 +48,7 @@ class Region;
class SurfaceComposerClient : public RefBase
{
friend class Composer;
-public:
+public:
SurfaceComposerClient();
virtual ~SurfaceComposerClient();
@@ -57,7 +57,7 @@ public:
// Return the connection of this client
sp<IBinder> connection() const;
-
+
// Forcibly remove connection before all references have gone away.
void dispose();
@@ -86,9 +86,12 @@ public:
uint32_t flags = 0 // usage flags
);
- //! Create a display
+ //! Create a virtual display
static sp<IBinder> createDisplay(const String8& displayName, bool secure);
+ //! Destroy a virtual display
+ static void destroyDisplay(const sp<IBinder>& display);
+
//! Get the token for the existing default displays.
//! Possible values for id are eDisplayIdMain and eDisplayIdHdmi.
static sp<IBinder> getBuiltInDisplay(int32_t id);
diff --git a/libs/gui/ISurfaceComposer.cpp b/libs/gui/ISurfaceComposer.cpp
index a9217ca..aab0604 100644
--- a/libs/gui/ISurfaceComposer.cpp
+++ b/libs/gui/ISurfaceComposer.cpp
@@ -185,6 +185,14 @@ public:
return reply.readStrongBinder();
}
+ virtual void destroyDisplay(const sp<IBinder>& display)
+ {
+ Parcel data, reply;
+ data.writeInterfaceToken(ISurfaceComposer::getInterfaceDescriptor());
+ data.writeStrongBinder(display);
+ remote()->transact(BnSurfaceComposer::DESTROY_DISPLAY, data, &reply);
+ }
+
virtual sp<IBinder> getBuiltInDisplay(int32_t id)
{
Parcel data, reply;
@@ -233,12 +241,14 @@ status_t BnSurfaceComposer::onTransact(
CHECK_INTERFACE(ISurfaceComposer, data, reply);
sp<IBinder> b = createConnection()->asBinder();
reply->writeStrongBinder(b);
- } break;
+ return NO_ERROR;
+ }
case CREATE_GRAPHIC_BUFFER_ALLOC: {
CHECK_INTERFACE(ISurfaceComposer, data, reply);
sp<IBinder> b = createGraphicBufferAlloc()->asBinder();
reply->writeStrongBinder(b);
- } break;
+ return NO_ERROR;
+ }
case SET_TRANSACTION_STATE: {
CHECK_INTERFACE(ISurfaceComposer, data, reply);
size_t count = data.readInt32();
@@ -259,11 +269,13 @@ status_t BnSurfaceComposer::onTransact(
}
uint32_t flags = data.readInt32();
setTransactionState(state, displays, flags);
- } break;
+ return NO_ERROR;
+ }
case BOOT_FINISHED: {
CHECK_INTERFACE(ISurfaceComposer, data, reply);
bootFinished();
- } break;
+ return NO_ERROR;
+ }
case CAPTURE_SCREEN: {
CHECK_INTERFACE(ISurfaceComposer, data, reply);
sp<IBinder> display = data.readStrongBinder();
@@ -276,20 +288,22 @@ status_t BnSurfaceComposer::onTransact(
status_t res = captureScreen(display, producer,
reqWidth, reqHeight, minLayerZ, maxLayerZ);
reply->writeInt32(res);
- } break;
+ return NO_ERROR;
+ }
case AUTHENTICATE_SURFACE: {
CHECK_INTERFACE(ISurfaceComposer, data, reply);
sp<IGraphicBufferProducer> bufferProducer =
interface_cast<IGraphicBufferProducer>(data.readStrongBinder());
int32_t result = authenticateSurfaceTexture(bufferProducer) ? 1 : 0;
reply->writeInt32(result);
- } break;
+ return NO_ERROR;
+ }
case CREATE_DISPLAY_EVENT_CONNECTION: {
CHECK_INTERFACE(ISurfaceComposer, data, reply);
sp<IDisplayEventConnection> connection(createDisplayEventConnection());
reply->writeStrongBinder(connection->asBinder());
return NO_ERROR;
- } break;
+ }
case CREATE_DISPLAY: {
CHECK_INTERFACE(ISurfaceComposer, data, reply);
String8 displayName = data.readString8();
@@ -297,24 +311,32 @@ status_t BnSurfaceComposer::onTransact(
sp<IBinder> display(createDisplay(displayName, secure));
reply->writeStrongBinder(display);
return NO_ERROR;
- } break;
+ }
+ case DESTROY_DISPLAY: {
+ CHECK_INTERFACE(ISurfaceComposer, data, reply);
+ sp<IBinder> display = data.readStrongBinder();
+ destroyDisplay(display);
+ return NO_ERROR;
+ }
case GET_BUILT_IN_DISPLAY: {
CHECK_INTERFACE(ISurfaceComposer, data, reply);
int32_t id = data.readInt32();
sp<IBinder> display(getBuiltInDisplay(id));
reply->writeStrongBinder(display);
return NO_ERROR;
- } break;
+ }
case BLANK: {
CHECK_INTERFACE(ISurfaceComposer, data, reply);
sp<IBinder> display = data.readStrongBinder();
blank(display);
- } break;
+ return NO_ERROR;
+ }
case UNBLANK: {
CHECK_INTERFACE(ISurfaceComposer, data, reply);
sp<IBinder> display = data.readStrongBinder();
unblank(display);
- } break;
+ return NO_ERROR;
+ }
case GET_DISPLAY_INFO: {
CHECK_INTERFACE(ISurfaceComposer, data, reply);
DisplayInfo info;
@@ -322,10 +344,13 @@ status_t BnSurfaceComposer::onTransact(
status_t result = getDisplayInfo(display, &info);
memcpy(reply->writeInplace(sizeof(DisplayInfo)), &info, sizeof(DisplayInfo));
reply->writeInt32(result);
- } break;
- default:
+ return NO_ERROR;
+ }
+ default: {
return BBinder::onTransact(code, data, reply, flags);
+ }
}
+ // should be unreachable
return NO_ERROR;
}
diff --git a/libs/gui/SurfaceComposerClient.cpp b/libs/gui/SurfaceComposerClient.cpp
index e067479..aafc4d2 100644
--- a/libs/gui/SurfaceComposerClient.cpp
+++ b/libs/gui/SurfaceComposerClient.cpp
@@ -135,6 +135,7 @@ class Composer : public Singleton<Composer>
public:
sp<IBinder> createDisplay(const String8& displayName, bool secure);
+ void destroyDisplay(const sp<IBinder>& display);
sp<IBinder> getBuiltInDisplay(int32_t id);
status_t setPosition(const sp<SurfaceComposerClient>& client, const sp<IBinder>& id,
@@ -188,6 +189,10 @@ sp<IBinder> Composer::createDisplay(const String8& displayName, bool secure) {
secure);
}
+void Composer::destroyDisplay(const sp<IBinder>& display) {
+ return ComposerService::getComposerService()->destroyDisplay(display);
+}
+
sp<IBinder> Composer::getBuiltInDisplay(int32_t id) {
return ComposerService::getComposerService()->getBuiltInDisplay(id);
}
@@ -490,6 +495,10 @@ sp<IBinder> SurfaceComposerClient::createDisplay(const String8& displayName,
return Composer::getInstance().createDisplay(displayName, secure);
}
+void SurfaceComposerClient::destroyDisplay(const sp<IBinder>& display) {
+ Composer::getInstance().destroyDisplay(display);
+}
+
sp<IBinder> SurfaceComposerClient::getBuiltInDisplay(int32_t id) {
return Composer::getInstance().getBuiltInDisplay(id);
}
diff --git a/services/surfaceflinger/SurfaceFlinger.cpp b/services/surfaceflinger/SurfaceFlinger.cpp
index b38ad10..bc10853 100644
--- a/services/surfaceflinger/SurfaceFlinger.cpp
+++ b/services/surfaceflinger/SurfaceFlinger.cpp
@@ -205,6 +205,25 @@ sp<IBinder> SurfaceFlinger::createDisplay(const String8& displayName,
return token;
}
+void SurfaceFlinger::destroyDisplay(const sp<IBinder>& display) {
+ Mutex::Autolock _l(mStateLock);
+
+ ssize_t idx = mCurrentState.displays.indexOfKey(display);
+ if (idx < 0) {
+ ALOGW("destroyDisplay: invalid display token");
+ return;
+ }
+
+ const DisplayDeviceState& info(mCurrentState.displays.valueAt(idx));
+ if (!info.isVirtualDisplay()) {
+ ALOGE("destroyDisplay called for non-virtual display");
+ return;
+ }
+
+ mCurrentState.displays.removeItemsAt(idx);
+ setTransactionFlags(eDisplayTransactionNeeded);
+}
+
void SurfaceFlinger::createBuiltinDisplayLocked(DisplayDevice::DisplayType type) {
ALOGW_IF(mBuiltinDisplays[type],
"Overwriting display token for display type %d", type);
diff --git a/services/surfaceflinger/SurfaceFlinger.h b/services/surfaceflinger/SurfaceFlinger.h
index acc8fab..92fcc25 100644
--- a/services/surfaceflinger/SurfaceFlinger.h
+++ b/services/surfaceflinger/SurfaceFlinger.h
@@ -184,6 +184,7 @@ private:
virtual sp<ISurfaceComposerClient> createConnection();
virtual sp<IGraphicBufferAlloc> createGraphicBufferAlloc();
virtual sp<IBinder> createDisplay(const String8& displayName, bool secure);
+ virtual void destroyDisplay(const sp<IBinder>& display);
virtual sp<IBinder> getBuiltInDisplay(int32_t id);
virtual void setTransactionState(const Vector<ComposerState>& state,
const Vector<DisplayState>& displays, uint32_t flags);