Surface.cpp revision b0e76f456afaada43ddb0968bb37145219f90cd3
1edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project/*
2edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * Copyright (C) 2007 The Android Open Source Project
3edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project *
4edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License");
5edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * you may not use this file except in compliance with the License.
6edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * You may obtain a copy of the License at
7edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project *
8edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project *      http://www.apache.org/licenses/LICENSE-2.0
9edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project *
10edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * Unless required by applicable law or agreed to in writing, software
11edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS,
12edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * See the License for the specific language governing permissions and
14edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * limitations under the License.
15edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project */
16edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project
17edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project#define LOG_TAG "Surface"
18edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project
19edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project#include <stdint.h>
20edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project#include <errno.h>
21edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project#include <sys/types.h>
22edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project#include <sys/stat.h>
23edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project
24b0e76f456afaada43ddb0968bb37145219f90cd3Mathias Agopian#include <android/native_window.h>
25b0e76f456afaada43ddb0968bb37145219f90cd3Mathias Agopian
26cbb288bfe89f585bf48371bd31b2d4aafa32f32eMathias Agopian#include <utils/CallStack.h>
27a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian#include <utils/Errors.h>
289cce325fae8adcf7560a28eef394489f09bad74dMathias Agopian#include <utils/Log.h>
29a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian#include <utils/threads.h>
309cce325fae8adcf7560a28eef394489f09bad74dMathias Agopian
31a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian#include <binder/IPCThreadState.h>
32a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian
33076b1cc3a9b90aa5b381a1ed268ca0b548444c9bMathias Agopian#include <ui/DisplayInfo.h>
343330b203039dea366d4981db1408a460134b2d2cMathias Agopian#include <ui/GraphicBuffer.h>
35edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project#include <ui/Rect.h>
36edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project
3790ac799241f077a7b7e6c1875fd933864c8dd2a7Mathias Agopian#include <gui/ISurface.h>
3890ac799241f077a7b7e6c1875fd933864c8dd2a7Mathias Agopian#include <gui/ISurfaceComposer.h>
3990ac799241f077a7b7e6c1875fd933864c8dd2a7Mathias Agopian#include <gui/Surface.h>
4090ac799241f077a7b7e6c1875fd933864c8dd2a7Mathias Agopian#include <gui/SurfaceComposerClient.h>
4190ac799241f077a7b7e6c1875fd933864c8dd2a7Mathias Agopian#include <gui/SurfaceTextureClient.h>
42076b1cc3a9b90aa5b381a1ed268ca0b548444c9bMathias Agopian
43edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Projectnamespace android {
44edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project
4562185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian// ============================================================================
4662185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian//  SurfaceControl
4762185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian// ============================================================================
4862185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian
4901b766839e06c32540cef100e3a7710d12cf1eefMathias AgopianSurfaceControl::SurfaceControl(
5001b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian        const sp<SurfaceComposerClient>& client,
5162185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian        const sp<ISurface>& surface,
52c10d9d90b2088a3304076e0dc4bf05cdbb5d45abMathias Agopian        const ISurfaceComposerClient::surface_data_t& data)
5362185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    : mClient(client), mSurface(surface),
54c10d9d90b2088a3304076e0dc4bf05cdbb5d45abMathias Agopian      mToken(data.token), mIdentity(data.identity)
5562185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian{
5662185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian}
5718d8446fe1596cd50561777e1d1a8c7b39c689f6Mathias Agopian
5862185b7335e85211dc4d0e2003354eb3ea2e66efMathias AgopianSurfaceControl::~SurfaceControl()
5962185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian{
6062185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    destroy();
6162185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian}
6262185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian
6362185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopianvoid SurfaceControl::destroy()
6462185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian{
6518d8446fe1596cd50561777e1d1a8c7b39c689f6Mathias Agopian    if (isValid()) {
6662185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian        mClient->destroySurface(mToken);
6762185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    }
6862185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian
6962185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    // clear all references and trigger an IPC now, to make sure things
7062185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    // happen without delay, since these resources are quite heavy.
7162185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    mClient.clear();
7262185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    mSurface.clear();
7362185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    IPCThreadState::self()->flushCommands();
7462185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian}
7562185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian
7662185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopianvoid SurfaceControl::clear()
7762185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian{
7862185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    // here, the window manager tells us explicitly that we should destroy
7962185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    // the surface's resource. Soon after this call, it will also release
8062185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    // its last reference (which will call the dtor); however, it is possible
8162185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    // that a client living in the same process still holds references which
8262185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    // would delay the call to the dtor -- that is why we need this explicit
8362185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    // "clear()" call.
8462185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    destroy();
8562185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian}
8662185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian
8701b766839e06c32540cef100e3a7710d12cf1eefMathias Agopianbool SurfaceControl::isSameSurface(
8801b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian        const sp<SurfaceControl>& lhs, const sp<SurfaceControl>& rhs)
8901b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian{
9001b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian    if (lhs == 0 || rhs == 0)
9101b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian        return false;
9201b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian    return lhs->mSurface->asBinder() == rhs->mSurface->asBinder();
9301b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian}
9401b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian
9562185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopianstatus_t SurfaceControl::setLayer(int32_t layer) {
96963abad79ae64dae9bf4c32bfb110d9e6314c857Mathias Agopian    status_t err = validate();
9762185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    if (err < 0) return err;
98631f358d348ea5e7813ca01f86fc9f2a6536add6Mathias Agopian    const sp<SurfaceComposerClient>& client(mClient);
9962185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    return client->setLayer(mToken, layer);
10062185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian}
10162185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopianstatus_t SurfaceControl::setPosition(int32_t x, int32_t y) {
102963abad79ae64dae9bf4c32bfb110d9e6314c857Mathias Agopian    status_t err = validate();
10362185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    if (err < 0) return err;
104631f358d348ea5e7813ca01f86fc9f2a6536add6Mathias Agopian    const sp<SurfaceComposerClient>& client(mClient);
10562185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    return client->setPosition(mToken, x, y);
10662185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian}
10762185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopianstatus_t SurfaceControl::setSize(uint32_t w, uint32_t h) {
108963abad79ae64dae9bf4c32bfb110d9e6314c857Mathias Agopian    status_t err = validate();
10962185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    if (err < 0) return err;
110631f358d348ea5e7813ca01f86fc9f2a6536add6Mathias Agopian    const sp<SurfaceComposerClient>& client(mClient);
11162185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    return client->setSize(mToken, w, h);
11262185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian}
11362185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopianstatus_t SurfaceControl::hide() {
114963abad79ae64dae9bf4c32bfb110d9e6314c857Mathias Agopian    status_t err = validate();
11562185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    if (err < 0) return err;
116631f358d348ea5e7813ca01f86fc9f2a6536add6Mathias Agopian    const sp<SurfaceComposerClient>& client(mClient);
11762185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    return client->hide(mToken);
11862185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian}
11962185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopianstatus_t SurfaceControl::show(int32_t layer) {
120963abad79ae64dae9bf4c32bfb110d9e6314c857Mathias Agopian    status_t err = validate();
12162185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    if (err < 0) return err;
122631f358d348ea5e7813ca01f86fc9f2a6536add6Mathias Agopian    const sp<SurfaceComposerClient>& client(mClient);
12362185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    return client->show(mToken, layer);
12462185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian}
12562185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopianstatus_t SurfaceControl::freeze() {
126963abad79ae64dae9bf4c32bfb110d9e6314c857Mathias Agopian    status_t err = validate();
12762185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    if (err < 0) return err;
128631f358d348ea5e7813ca01f86fc9f2a6536add6Mathias Agopian    const sp<SurfaceComposerClient>& client(mClient);
12962185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    return client->freeze(mToken);
13062185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian}
13162185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopianstatus_t SurfaceControl::unfreeze() {
132963abad79ae64dae9bf4c32bfb110d9e6314c857Mathias Agopian    status_t err = validate();
13362185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    if (err < 0) return err;
134631f358d348ea5e7813ca01f86fc9f2a6536add6Mathias Agopian    const sp<SurfaceComposerClient>& client(mClient);
13562185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    return client->unfreeze(mToken);
13662185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian}
13762185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopianstatus_t SurfaceControl::setFlags(uint32_t flags, uint32_t mask) {
138963abad79ae64dae9bf4c32bfb110d9e6314c857Mathias Agopian    status_t err = validate();
13962185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    if (err < 0) return err;
140631f358d348ea5e7813ca01f86fc9f2a6536add6Mathias Agopian    const sp<SurfaceComposerClient>& client(mClient);
14162185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    return client->setFlags(mToken, flags, mask);
14262185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian}
14362185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopianstatus_t SurfaceControl::setTransparentRegionHint(const Region& transparent) {
144963abad79ae64dae9bf4c32bfb110d9e6314c857Mathias Agopian    status_t err = validate();
14562185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    if (err < 0) return err;
146631f358d348ea5e7813ca01f86fc9f2a6536add6Mathias Agopian    const sp<SurfaceComposerClient>& client(mClient);
14762185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    return client->setTransparentRegionHint(mToken, transparent);
14862185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian}
14962185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopianstatus_t SurfaceControl::setAlpha(float alpha) {
150963abad79ae64dae9bf4c32bfb110d9e6314c857Mathias Agopian    status_t err = validate();
15162185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    if (err < 0) return err;
152631f358d348ea5e7813ca01f86fc9f2a6536add6Mathias Agopian    const sp<SurfaceComposerClient>& client(mClient);
15362185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    return client->setAlpha(mToken, alpha);
15462185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian}
15562185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopianstatus_t SurfaceControl::setMatrix(float dsdx, float dtdx, float dsdy, float dtdy) {
156963abad79ae64dae9bf4c32bfb110d9e6314c857Mathias Agopian    status_t err = validate();
15762185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    if (err < 0) return err;
158631f358d348ea5e7813ca01f86fc9f2a6536add6Mathias Agopian    const sp<SurfaceComposerClient>& client(mClient);
15962185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    return client->setMatrix(mToken, dsdx, dtdx, dsdy, dtdy);
16062185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian}
16162185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopianstatus_t SurfaceControl::setFreezeTint(uint32_t tint) {
162963abad79ae64dae9bf4c32bfb110d9e6314c857Mathias Agopian    status_t err = validate();
16362185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    if (err < 0) return err;
164631f358d348ea5e7813ca01f86fc9f2a6536add6Mathias Agopian    const sp<SurfaceComposerClient>& client(mClient);
16562185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    return client->setFreezeTint(mToken, tint);
16662185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian}
16762185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian
168963abad79ae64dae9bf4c32bfb110d9e6314c857Mathias Agopianstatus_t SurfaceControl::validate() const
16962185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian{
17062185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    if (mToken<0 || mClient==0) {
171e6f43ddce78d6846af12550ff9193c5c6fe5844bSteve Block        ALOGE("invalid token (%d, identity=%u) or client (%p)",
17262185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian                mToken, mIdentity, mClient.get());
17362185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian        return NO_INIT;
17462185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    }
17562185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian    return NO_ERROR;
17662185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian}
17762185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian
17801b766839e06c32540cef100e3a7710d12cf1eefMathias Agopianstatus_t SurfaceControl::writeSurfaceToParcel(
17901b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian        const sp<SurfaceControl>& control, Parcel* parcel)
18001b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian{
181579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopian    sp<ISurface> sur;
18201b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian    uint32_t identity = 0;
18301b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian    if (SurfaceControl::isValid(control)) {
18401b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian        sur      = control->mSurface;
185579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopian        identity = control->mIdentity;
18601b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian    }
187b7e930db175c192464cebdeb49eb56cf6dd60114Mathias Agopian    parcel->writeStrongBinder(sur!=0 ? sur->asBinder() : NULL);
188bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    parcel->writeStrongBinder(NULL);  // NULL ISurfaceTexture in this case.
18901b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian    parcel->writeInt32(identity);
19001b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian    return NO_ERROR;
19101b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian}
19201b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian
19301b766839e06c32540cef100e3a7710d12cf1eefMathias Agopiansp<Surface> SurfaceControl::getSurface() const
19401b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian{
19501b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian    Mutex::Autolock _l(mLock);
19601b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian    if (mSurfaceData == 0) {
197bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg        sp<SurfaceControl> surface_control(const_cast<SurfaceControl*>(this));
198bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg        mSurfaceData = new Surface(surface_control);
19901b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian    }
20001b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian    return mSurfaceData;
20101b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian}
20201b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian
203076b1cc3a9b90aa5b381a1ed268ca0b548444c9bMathias Agopian// ============================================================================
204076b1cc3a9b90aa5b381a1ed268ca0b548444c9bMathias Agopian//  Surface
205076b1cc3a9b90aa5b381a1ed268ca0b548444c9bMathias Agopian// ============================================================================
206edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project
207b7e930db175c192464cebdeb49eb56cf6dd60114Mathias Agopian// ---------------------------------------------------------------------------
208b7e930db175c192464cebdeb49eb56cf6dd60114Mathias Agopian
20901b766839e06c32540cef100e3a7710d12cf1eefMathias AgopianSurface::Surface(const sp<SurfaceControl>& surface)
2108f9dbf9e13b927de2524116c30544f7dfbbbf56cMathias Agopian    : SurfaceTextureClient(),
211b7e930db175c192464cebdeb49eb56cf6dd60114Mathias Agopian      mSurface(surface->mSurface),
212c10d9d90b2088a3304076e0dc4bf05cdbb5d45abMathias Agopian      mIdentity(surface->mIdentity)
213edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project{
214bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    sp<ISurfaceTexture> st;
215bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    if (mSurface != NULL) {
216bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg        st = mSurface->getSurfaceTexture();
217bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    }
218bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    init(st);
21901b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian}
22062185b7335e85211dc4d0e2003354eb3ea2e66efMathias Agopian
221a0c30e924193da57723fd53b710ce6be24fb26f5Mathias AgopianSurface::Surface(const Parcel& parcel, const sp<IBinder>& ref)
222c10d9d90b2088a3304076e0dc4bf05cdbb5d45abMathias Agopian    : SurfaceTextureClient()
22301b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian{
224bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    mSurface = interface_cast<ISurface>(ref);
225bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    sp<IBinder> st_binder(parcel.readStrongBinder());
226bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    sp<ISurfaceTexture> st;
227bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    if (st_binder != NULL) {
228bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg        st = interface_cast<ISurfaceTexture>(st_binder);
229bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    } else if (mSurface != NULL) {
230bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg        st = mSurface->getSurfaceTexture();
231bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    }
232bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg
23301b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian    mIdentity   = parcel.readInt32();
234bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    init(st);
235bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg}
236bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg
237bd050ab2af1421d527d1a80ce59dd8d9940a838cTed BonkenburgSurface::Surface(const sp<ISurfaceTexture>& st)
238bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    : SurfaceTextureClient(),
239bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg      mSurface(NULL),
240bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg      mIdentity(0)
241bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg{
242bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    init(st);
24301b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian}
24401b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian
245579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopianstatus_t Surface::writeToParcel(
246579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopian        const sp<Surface>& surface, Parcel* parcel)
247579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopian{
248579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopian    sp<ISurface> sur;
249bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    sp<ISurfaceTexture> st;
250579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopian    uint32_t identity = 0;
251579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopian    if (Surface::isValid(surface)) {
252579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopian        sur      = surface->mSurface;
253bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg        st       = surface->getISurfaceTexture();
254579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopian        identity = surface->mIdentity;
255bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    } else if (surface != 0 &&
256bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg            (surface->mSurface != NULL ||
257bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg             surface->getISurfaceTexture() != NULL)) {
258e6f43ddce78d6846af12550ff9193c5c6fe5844bSteve Block        ALOGE("Parceling invalid surface with non-NULL ISurface/ISurfaceTexture as NULL: "
259bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg             "mSurface = %p, surfaceTexture = %p, mIdentity = %d, ",
260bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg             surface->mSurface.get(), surface->getISurfaceTexture().get(),
261bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg             surface->mIdentity);
262579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopian    }
263bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg
264bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    parcel->writeStrongBinder(sur != NULL ? sur->asBinder() : NULL);
265bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    parcel->writeStrongBinder(st != NULL ? st->asBinder() : NULL);
266579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopian    parcel->writeInt32(identity);
267579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopian    return NO_ERROR;
268579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopian
269579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopian}
270579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopian
271aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie GennisMutex Surface::sCachedSurfacesLock;
272455d18d4c26a823bff62ca14771986cca52d3462Mathias AgopianDefaultKeyedVector<wp<IBinder>, wp<Surface> > Surface::sCachedSurfaces;
273aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis
274aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennissp<Surface> Surface::readFromParcel(const Parcel& data) {
275aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis    Mutex::Autolock _l(sCachedSurfacesLock);
276a0c30e924193da57723fd53b710ce6be24fb26f5Mathias Agopian    sp<IBinder> binder(data.readStrongBinder());
277aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis    sp<Surface> surface = sCachedSurfaces.valueFor(binder).promote();
278aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis    if (surface == 0) {
279aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis       surface = new Surface(data, binder);
280aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis       sCachedSurfaces.add(binder, surface);
281e5d6eb81e29e0fb914ce8fdaae17190b0dbae1a1Ted Bonkenburg    } else {
282e5d6eb81e29e0fb914ce8fdaae17190b0dbae1a1Ted Bonkenburg        // The Surface was found in the cache, but we still should clear any
283e5d6eb81e29e0fb914ce8fdaae17190b0dbae1a1Ted Bonkenburg        // remaining data from the parcel.
284e5d6eb81e29e0fb914ce8fdaae17190b0dbae1a1Ted Bonkenburg        data.readStrongBinder();  // ISurfaceTexture
285e5d6eb81e29e0fb914ce8fdaae17190b0dbae1a1Ted Bonkenburg        data.readInt32();         // identity
286aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis    }
287bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    if (surface->mSurface == NULL && surface->getISurfaceTexture() == NULL) {
288bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg        surface = 0;
289aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis    }
290455d18d4c26a823bff62ca14771986cca52d3462Mathias Agopian    cleanCachedSurfacesLocked();
291aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis    return surface;
292aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis}
293aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis
294aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis// Remove the stale entries from the surface cache.  This should only be called
295aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis// with sCachedSurfacesLock held.
296455d18d4c26a823bff62ca14771986cca52d3462Mathias Agopianvoid Surface::cleanCachedSurfacesLocked() {
297aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis    for (int i = sCachedSurfaces.size()-1; i >= 0; --i) {
298aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis        wp<Surface> s(sCachedSurfaces.valueAt(i));
299aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis        if (s == 0 || s.promote() == 0) {
300aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis            sCachedSurfaces.removeItemsAt(i);
301aca4e2287939b4ce3d9e9aced64c5c9641333503Jamie Gennis        }
302a0c30e924193da57723fd53b710ce6be24fb26f5Mathias Agopian    }
303a0c30e924193da57723fd53b710ce6be24fb26f5Mathias Agopian}
304a0c30e924193da57723fd53b710ce6be24fb26f5Mathias Agopian
305bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburgvoid Surface::init(const sp<ISurfaceTexture>& surfaceTexture)
30601b766839e06c32540cef100e3a7710d12cf1eefMathias Agopian{
307bd050ab2af1421d527d1a80ce59dd8d9940a838cTed Bonkenburg    if (mSurface != NULL || surfaceTexture != NULL) {
308e6f43ddce78d6846af12550ff9193c5c6fe5844bSteve Block        ALOGE_IF(surfaceTexture==0, "got a NULL ISurfaceTexture from ISurface");
309a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian        if (surfaceTexture != NULL) {
3108f9dbf9e13b927de2524116c30544f7dfbbbf56cMathias Agopian            setISurfaceTexture(surfaceTexture);
3118f9dbf9e13b927de2524116c30544f7dfbbbf56cMathias Agopian            setUsage(GraphicBuffer::USAGE_HW_RENDER);
312a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian        }
313a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian
314a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian        DisplayInfo dinfo;
315a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian        SurfaceComposerClient::getDisplayInfo(0, &dinfo);
316a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian        const_cast<float&>(ANativeWindow::xdpi) = dinfo.xdpi;
317a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian        const_cast<float&>(ANativeWindow::ydpi) = dinfo.ydpi;
318a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian        const_cast<uint32_t&>(ANativeWindow::flags) = 0;
319631f358d348ea5e7813ca01f86fc9f2a6536add6Mathias Agopian    }
320edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project}
321edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project
32240b7f6e0433b89c27b2fe5a1c0c47f67b42eceb2Mathias AgopianSurface::~Surface()
323edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project{
32440b7f6e0433b89c27b2fe5a1c0c47f67b42eceb2Mathias Agopian    // clear all references and trigger an IPC now, to make sure things
32540b7f6e0433b89c27b2fe5a1c0c47f67b42eceb2Mathias Agopian    // happen without delay, since these resources are quite heavy.
326edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project    mSurface.clear();
327edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project    IPCThreadState::self()->flushCommands();
328edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project}
329edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project
330ba5972ffdc7179dd9a387f22032eb18666d97917Mathias Agopianbool Surface::isValid() {
331c10d9d90b2088a3304076e0dc4bf05cdbb5d45abMathias Agopian    return getISurfaceTexture() != NULL;
332076b1cc3a9b90aa5b381a1ed268ca0b548444c9bMathias Agopian}
333076b1cc3a9b90aa5b381a1ed268ca0b548444c9bMathias Agopian
3341e7fa9e945d98eab76ff92f37c25040429a6c0a0tedbosp<ISurfaceTexture> Surface::getSurfaceTexture() {
335c10d9d90b2088a3304076e0dc4bf05cdbb5d45abMathias Agopian    return getISurfaceTexture();
3361e7fa9e945d98eab76ff92f37c25040429a6c0a0tedbo}
3371e7fa9e945d98eab76ff92f37c25040429a6c0a0tedbo
33847d8730a2463f38a695ab95b533b0d9728f266a3Mathias Agopiansp<IBinder> Surface::asBinder() const {
33947d8730a2463f38a695ab95b533b0d9728f266a3Mathias Agopian    return mSurface!=0 ? mSurface->asBinder() : 0;
340631f358d348ea5e7813ca01f86fc9f2a6536add6Mathias Agopian}
341631f358d348ea5e7813ca01f86fc9f2a6536add6Mathias Agopian
342076b1cc3a9b90aa5b381a1ed268ca0b548444c9bMathias Agopian// ----------------------------------------------------------------------------
343076b1cc3a9b90aa5b381a1ed268ca0b548444c9bMathias Agopian
344a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopianint Surface::query(int what, int* value) const {
345cb6b9041647b4f080324742eee5ce709960ff610Mathias Agopian    switch (what) {
346391bbe2246a7547dbf3460c231b3c5ba691d4eb1Jamie Gennis    case NATIVE_WINDOW_CONCRETE_TYPE:
347391bbe2246a7547dbf3460c231b3c5ba691d4eb1Jamie Gennis        *value = NATIVE_WINDOW_SURFACE;
348391bbe2246a7547dbf3460c231b3c5ba691d4eb1Jamie Gennis        return NO_ERROR;
349391bbe2246a7547dbf3460c231b3c5ba691d4eb1Jamie Gennis    }
3508f9dbf9e13b927de2524116c30544f7dfbbbf56cMathias Agopian    return SurfaceTextureClient::query(what, value);
3511d01a12e7150be569557b64da9b8663c62c13594Eino-Ville Talvala}
3521d01a12e7150be569557b64da9b8663c62c13594Eino-Ville Talvala
353a138f89c5e78b7e8994823e97d6e860869762837Mathias Agopian// ----------------------------------------------------------------------------
354a138f89c5e78b7e8994823e97d6e860869762837Mathias Agopian
35587a96ea9eae3f998381735ec65496e256f871c3cMathias Agopianstatus_t Surface::lock(SurfaceInfo* other, Region* inOutDirtyRegion) {
3568f9dbf9e13b927de2524116c30544f7dfbbbf56cMathias Agopian    ANativeWindow_Buffer outBuffer;
35755fa25161a7626ae6a15bc2cc46e22771455ed80Mathias Agopian
3588f9dbf9e13b927de2524116c30544f7dfbbbf56cMathias Agopian    ARect temp;
3598f9dbf9e13b927de2524116c30544f7dfbbbf56cMathias Agopian    ARect* inOutDirtyBounds = NULL;
36087a96ea9eae3f998381735ec65496e256f871c3cMathias Agopian    if (inOutDirtyRegion) {
36187a96ea9eae3f998381735ec65496e256f871c3cMathias Agopian        temp = inOutDirtyRegion->getBounds();
3628f9dbf9e13b927de2524116c30544f7dfbbbf56cMathias Agopian        inOutDirtyBounds = &temp;
363cbb288bfe89f585bf48371bd31b2d4aafa32f32eMathias Agopian    }
3649014726d8954a003323d65ba639b2544f8ecea2eMathias Agopian
3658f9dbf9e13b927de2524116c30544f7dfbbbf56cMathias Agopian    status_t err = SurfaceTextureClient::lock(&outBuffer, inOutDirtyBounds);
366ba5972ffdc7179dd9a387f22032eb18666d97917Mathias Agopian
367076b1cc3a9b90aa5b381a1ed268ca0b548444c9bMathias Agopian    if (err == NO_ERROR) {
3688f9dbf9e13b927de2524116c30544f7dfbbbf56cMathias Agopian        other->w = uint32_t(outBuffer.width);
3698f9dbf9e13b927de2524116c30544f7dfbbbf56cMathias Agopian        other->h = uint32_t(outBuffer.height);
3708f9dbf9e13b927de2524116c30544f7dfbbbf56cMathias Agopian        other->s = uint32_t(outBuffer.stride);
3718f9dbf9e13b927de2524116c30544f7dfbbbf56cMathias Agopian        other->usage = GRALLOC_USAGE_SW_READ_OFTEN | GRALLOC_USAGE_SW_WRITE_OFTEN;
3728f9dbf9e13b927de2524116c30544f7dfbbbf56cMathias Agopian        other->format = uint32_t(outBuffer.format);
3738f9dbf9e13b927de2524116c30544f7dfbbbf56cMathias Agopian        other->bits = outBuffer.bits;
374076b1cc3a9b90aa5b381a1ed268ca0b548444c9bMathias Agopian    }
37587a96ea9eae3f998381735ec65496e256f871c3cMathias Agopian
37687a96ea9eae3f998381735ec65496e256f871c3cMathias Agopian    if (inOutDirtyRegion) {
37787a96ea9eae3f998381735ec65496e256f871c3cMathias Agopian        inOutDirtyRegion->set( static_cast<Rect const&>(temp) );
37887a96ea9eae3f998381735ec65496e256f871c3cMathias Agopian    }
37987a96ea9eae3f998381735ec65496e256f871c3cMathias Agopian
380076b1cc3a9b90aa5b381a1ed268ca0b548444c9bMathias Agopian    return err;
381edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project}
382cbb288bfe89f585bf48371bd31b2d4aafa32f32eMathias Agopian
3838f9dbf9e13b927de2524116c30544f7dfbbbf56cMathias Agopianstatus_t Surface::unlockAndPost() {
3848f9dbf9e13b927de2524116c30544f7dfbbbf56cMathias Agopian    return SurfaceTextureClient::unlockAndPost();
385edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project}
386edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project
387a138f89c5e78b7e8994823e97d6e860869762837Mathias Agopian// ----------------------------------------------------------------------------
388edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project}; // namespace android
389