SurfaceFlinger.cpp revision 9a14392256354538f1f43a5e80fe46c2c2b965cb
1326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams/*
2a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk * Copyright (C) 2007 The Android Open Source Project
3326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams *
4326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * Licensed under the Apache License, Version 2.0 (the "License");
5326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * you may not use this file except in compliance with the License.
6326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * You may obtain a copy of the License at
7326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams *
8326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams *      http://www.apache.org/licenses/LICENSE-2.0
9326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams *
10326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * Unless required by applicable law or agreed to in writing, software
11326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * distributed under the License is distributed on an "AS IS" BASIS,
12326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * See the License for the specific language governing permissions and
14326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * limitations under the License.
15326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams */
16326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams
17326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams#define ATRACE_TAG ATRACE_TAG_GRAPHICS
18326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams
19326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams#include <stdint.h>
205ae678f2e68e25bd74cdc408df354c3b6fe481bfMathias Agopian#include <sys/types.h>
21326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams#include <errno.h>
22158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams#include <math.h>
23158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams#include <dlfcn.h>
247bf29ddc35450d8064541c42c99a1f48be6cf0ddJason Sams
25158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams#include <EGL/egl.h>
2676371fff76412fd020e24ddb8bf1ddb5c75f0ed1Joe Onorato#include <GLES/gl.h>
2776371fff76412fd020e24ddb8bf1ddb5c75f0ed1Joe Onorato
28158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams#include <cutils/log.h>
298d957fa762eff6c03a93ddea9405d9575665f1ecJason Sams#include <cutils/properties.h>
308d957fa762eff6c03a93ddea9405d9575665f1ecJason Sams
31158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams#include <binder/IPCThreadState.h>
32326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams#include <binder/IServiceManager.h>
33326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams#include <binder/MemoryHeapBase.h>
34326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams#include <binder/PermissionCache.h>
35fb03a22ad2adadc1ff50a8b50d43ad7fcc3fa6edJason Sams
36ca3f09c0924e9515901dfd47fa5f95385d53cf80Stephen Hines#include <ui/DisplayInfo.h>
37326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams
38afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk#include <gui/BitTube.h>
396b8552a4f6a44848255d77222e66aa92dd21b1b5Jason Sams#include <gui/BufferQueue.h>
406b8552a4f6a44848255d77222e66aa92dd21b1b5Jason Sams#include <gui/GuiConfig.h>
414b3de47071d875faaa7d419d050a464b09538797Jason Sams#include <gui/IDisplayEventConnection.h>
425c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams#include <gui/SurfaceTextureClient.h>
43af12ac6a08651464f8d823add667c706f993b587Steve Block
445c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams#include <ui/GraphicBufferAllocator.h>
456b8552a4f6a44848255d77222e66aa92dd21b1b5Jason Sams#include <ui/PixelFormat.h>
466b8552a4f6a44848255d77222e66aa92dd21b1b5Jason Sams#include <ui/UiConfig.h>
476b8552a4f6a44848255d77222e66aa92dd21b1b5Jason Sams
485c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams#include <utils/misc.h>
49326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams#include <utils/String8.h>
50326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams#include <utils/String16.h>
51afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk#include <utils/StopWatch.h>
524b3de47071d875faaa7d419d050a464b09538797Jason Sams#include <utils/Trace.h>
5333b6e3b91329080e5cdd0b8fdbcd3e6a906032aeJason Sams
5433b6e3b91329080e5cdd0b8fdbcd3e6a906032aeJason Sams#include <private/android_filesystem_config.h>
5560709257bbdeb0c50f39b9c8969dc76264d6e142Jason Sams
5660709257bbdeb0c50f39b9c8969dc76264d6e142Jason Sams#include "clz.h"
57c946b614ee6c983215cc3de7834a7a334f860d68Jason Sams#include "DdmConnection.h"
58c946b614ee6c983215cc3de7834a7a334f860d68Jason Sams#include "DisplayDevice.h"
59c946b614ee6c983215cc3de7834a7a334f860d68Jason Sams#include "Client.h"
60c946b614ee6c983215cc3de7834a7a334f860d68Jason Sams#include "EventThread.h"
61c946b614ee6c983215cc3de7834a7a334f860d68Jason Sams#include "GLExtensions.h"
62c946b614ee6c983215cc3de7834a7a334f860d68Jason Sams#include "Layer.h"
63c946b614ee6c983215cc3de7834a7a334f860d68Jason Sams#include "LayerDim.h"
6460709257bbdeb0c50f39b9c8969dc76264d6e142Jason Sams#include "LayerScreenshot.h"
6560709257bbdeb0c50f39b9c8969dc76264d6e142Jason Sams#include "SurfaceFlinger.h"
6660709257bbdeb0c50f39b9c8969dc76264d6e142Jason Sams
67c946b614ee6c983215cc3de7834a7a334f860d68Jason Sams#include "DisplayHardware/FramebufferSurface.h"
68c946b614ee6c983215cc3de7834a7a334f860d68Jason Sams#include "DisplayHardware/GraphicBufferAlloc.h"
69c946b614ee6c983215cc3de7834a7a334f860d68Jason Sams#include "DisplayHardware/HWComposer.h"
70c946b614ee6c983215cc3de7834a7a334f860d68Jason Sams
71c946b614ee6c983215cc3de7834a7a334f860d68Jason Sams
72c946b614ee6c983215cc3de7834a7a334f860d68Jason Sams#define EGL_VERSION_HW_ANDROID  0x3143
73c946b614ee6c983215cc3de7834a7a334f860d68Jason Sams
7460709257bbdeb0c50f39b9c8969dc76264d6e142Jason Sams#define DISPLAY_COUNT       1
7560709257bbdeb0c50f39b9c8969dc76264d6e142Jason Sams
7633b6e3b91329080e5cdd0b8fdbcd3e6a906032aeJason Samsnamespace android {
77afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk// ---------------------------------------------------------------------------
7860709257bbdeb0c50f39b9c8969dc76264d6e142Jason Sams
791030893d9b99b72468034da13df025bda479bb97Jason Samsconst String16 sHardwareTest("android.permission.HARDWARE_TEST");
80c61346b91434307c5003029017b54ce9c49112beJason Samsconst String16 sAccessSurfaceFlinger("android.permission.ACCESS_SURFACE_FLINGER");
81c9d43db4d216b01b13aebfdb31d5615909591b33Jason Samsconst String16 sReadFramebuffer("android.permission.READ_FRAME_BUFFER");
821030893d9b99b72468034da13df025bda479bb97Jason Samsconst String16 sDump("android.permission.DUMP");
831030893d9b99b72468034da13df025bda479bb97Jason Sams
84afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk// ---------------------------------------------------------------------------
852dca84dd6c07992f78ad050177975f16486dd77eJason Sams
868c401effb0837155fc39ca0364f57a882d127d38Jason SamsSurfaceFlinger::SurfaceFlinger()
872382aba4a55c6ae74789c478eead8fbd96593321Jason Sams    :   BnSurfaceComposer(), Thread(false),
88c61346b91434307c5003029017b54ce9c49112beJason Sams        mTransactionFlags(0),
892382aba4a55c6ae74789c478eead8fbd96593321Jason Sams        mTransationPending(false),
908cfdd24fec22080b72266d33f61befc4a98b77c6Jason Sams        mLayersRemoved(false),
9124371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams        mRepaintEverything(0),
9224371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams        mBootTime(systemTime()),
93cfb1d11ce6826fce7241d316d8b7dcab661f63a6Jason Sams        mVisibleRegionsDirty(false),
94afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk        mHwWorkListDirty(false),
95b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk        mDebugRegion(0),
9624371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams        mDebugDDMS(0),
9724371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams        mDebugDisableHWC(0),
9824371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams        mDebugDisableTransformHint(0),
99b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk        mDebugInSwapBuffers(0),
100b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk        mLastSwapBufferTime(0),
101b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk        mDebugInTransaction(0),
10224371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams        mLastTransactionTime(0),
103cfb1d11ce6826fce7241d316d8b7dcab661f63a6Jason Sams        mBootFinished(false)
104afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk{
10524371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams    ALOGI("SurfaceFlinger is starting");
10624371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams
10724371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams    // debugging stuff...
10824371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams    char value[PROPERTY_VALUE_MAX];
109cfb1d11ce6826fce7241d316d8b7dcab661f63a6Jason Sams
110afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk    property_get("debug.sf.showupdates", value, "0");
11124371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams    mDebugRegion = atoi(value);
1121d54f10f3c23e0d7ec57e52ec3b0701a2a5ed24eJason Sams
1131d54f10f3c23e0d7ec57e52ec3b0701a2a5ed24eJason Sams    property_get("debug.sf.ddms", value, "0");
11424371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams    mDebugDDMS = atoi(value);
115c8fb69e4a3e01501a3d38a6d3ea185e583d3f493Alex Sakhartchouk    if (mDebugDDMS) {
116c8fb69e4a3e01501a3d38a6d3ea185e583d3f493Alex Sakhartchouk        if (!startDdmConnection()) {
117c8fb69e4a3e01501a3d38a6d3ea185e583d3f493Alex Sakhartchouk            // start failed, and DDMS debugging not enabled
11824371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams            mDebugDDMS = 0;
11924371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams        }
12024371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams    }
121afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk    ALOGI_IF(mDebugRegion, "showupdates enabled");
1221d54f10f3c23e0d7ec57e52ec3b0701a2a5ed24eJason Sams    ALOGI_IF(mDebugDDMS, "DDMS debugging enabled");
1231d54f10f3c23e0d7ec57e52ec3b0701a2a5ed24eJason Sams}
124c8fb69e4a3e01501a3d38a6d3ea185e583d3f493Alex Sakhartchouk
125c8fb69e4a3e01501a3d38a6d3ea185e583d3f493Alex Sakhartchoukvoid SurfaceFlinger::onFirstRef()
126c8fb69e4a3e01501a3d38a6d3ea185e583d3f493Alex Sakhartchouk{
127c8fb69e4a3e01501a3d38a6d3ea185e583d3f493Alex Sakhartchouk    mEventQueue.init(this);
128afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk
129c8fb69e4a3e01501a3d38a6d3ea185e583d3f493Alex Sakhartchouk    run("SurfaceFlinger", PRIORITY_URGENT_DISPLAY);
130c8fb69e4a3e01501a3d38a6d3ea185e583d3f493Alex Sakhartchouk
131c8fb69e4a3e01501a3d38a6d3ea185e583d3f493Alex Sakhartchouk    // Wait for the main thread to be done with its initialization
132c8fb69e4a3e01501a3d38a6d3ea185e583d3f493Alex Sakhartchouk    mReadyToRunBarrier.wait();
133c8fb69e4a3e01501a3d38a6d3ea185e583d3f493Alex Sakhartchouk}
1341d54f10f3c23e0d7ec57e52ec3b0701a2a5ed24eJason Sams
1351d54f10f3c23e0d7ec57e52ec3b0701a2a5ed24eJason Sams
136afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex SakhartchoukSurfaceFlinger::~SurfaceFlinger()
13724371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams{
13824371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams    EGLDisplay display = eglGetDisplay(EGL_DEFAULT_DISPLAY);
13924371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams    eglMakeCurrent(display, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT);
14024371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams    eglTerminate(display);
14124371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams}
14224371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams
143afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchoukvoid SurfaceFlinger::binderDied(const wp<IBinder>& who)
14424371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams{
14524371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams    // the window manager died on us. prepare its eulogy.
14624371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams
14724371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams    // restore initial conditions (default device unblank, etc)
1481d54f10f3c23e0d7ec57e52ec3b0701a2a5ed24eJason Sams    initializeDisplays();
1492dca84dd6c07992f78ad050177975f16486dd77eJason Sams
1502dca84dd6c07992f78ad050177975f16486dd77eJason Sams    // restart the boot-animation
1512dca84dd6c07992f78ad050177975f16486dd77eJason Sams    startBootAnim();
15224371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams}
1532dca84dd6c07992f78ad050177975f16486dd77eJason Sams
1542dca84dd6c07992f78ad050177975f16486dd77eJason Samssp<ISurfaceComposerClient> SurfaceFlinger::createConnection()
1556598201f1c4f409defac9a5af789fb53a7cc00f8Steve Block{
1562dca84dd6c07992f78ad050177975f16486dd77eJason Sams    sp<ISurfaceComposerClient> bclient;
1572dca84dd6c07992f78ad050177975f16486dd77eJason Sams    sp<Client> client(new Client(this));
1582dca84dd6c07992f78ad050177975f16486dd77eJason Sams    status_t err = client->initCheck();
1592dca84dd6c07992f78ad050177975f16486dd77eJason Sams    if (err == NO_ERROR) {
160c8fb69e4a3e01501a3d38a6d3ea185e583d3f493Alex Sakhartchouk        bclient = client;
161c8fb69e4a3e01501a3d38a6d3ea185e583d3f493Alex Sakhartchouk    }
1622dca84dd6c07992f78ad050177975f16486dd77eJason Sams    return bclient;
163326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams}
164326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams
165afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouksp<IBinder> SurfaceFlinger::createDisplay(const String8& displayName)
166900f1616bf33c7ba13cf2a737832a95bcd176388Jason Sams{
167721acc495b859c6d884725a4f9b5523583dd11c7Jason Sams    class DisplayToken : public BBinder {
168c19ff0177a7a0dadfc01b1990f822354fdc95991Alex Sakhartchouk        sp<SurfaceFlinger> flinger;
169721acc495b859c6d884725a4f9b5523583dd11c7Jason Sams        virtual ~DisplayToken() {
170c19ff0177a7a0dadfc01b1990f822354fdc95991Alex Sakhartchouk             // no more references, this display must be terminated
171c19ff0177a7a0dadfc01b1990f822354fdc95991Alex Sakhartchouk             Mutex::Autolock _l(flinger->mStateLock);
172a2cf755a28a1e7ffff2955df656d714f40e4d715Jason Sams             flinger->mCurrentState.displays.removeItem(this);
173326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams             flinger->setTransactionFlags(eDisplayTransactionNeeded);
174326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams         }
175889fe50e7aaebed8cb8284b16a0e51e64e8a3a9cAlex Sakhartchouk     public:
176721acc495b859c6d884725a4f9b5523583dd11c7Jason Sams        DisplayToken(const sp<SurfaceFlinger>& flinger)
177889fe50e7aaebed8cb8284b16a0e51e64e8a3a9cAlex Sakhartchouk            : flinger(flinger) {
178889fe50e7aaebed8cb8284b16a0e51e64e8a3a9cAlex Sakhartchouk        }
179afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk    };
18076371fff76412fd020e24ddb8bf1ddb5c75f0ed1Joe Onorato
1811fddd90849deaae89b546ff492c345d485bbce42Jason Sams    sp<BBinder> token = new DisplayToken(this);
18276371fff76412fd020e24ddb8bf1ddb5c75f0ed1Joe Onorato
18376371fff76412fd020e24ddb8bf1ddb5c75f0ed1Joe Onorato    Mutex::Autolock _l(mStateLock);
184326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    DisplayDeviceState info(DisplayDevice::DISPLAY_VIRTUAL);
185afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk    info.displayName = displayName;
1860cae59f7d8dd63d1bf0ca4abedecb4cfa3ab1921Alex Sakhartchouk    mCurrentState.displays.add(token, info);
187c8fb69e4a3e01501a3d38a6d3ea185e583d3f493Alex Sakhartchouk
188ca5a454e022caec6c6d3cbb404cc09ea095ba97aAlex Sakhartchouk    return token;
189ca5a454e022caec6c6d3cbb404cc09ea095ba97aAlex Sakhartchouk}
19009c67356bbeee0a97a20a06c95b66756838cb541Alex Sakhartchouk
1910cae59f7d8dd63d1bf0ca4abedecb4cfa3ab1921Alex Sakhartchouksp<IBinder> SurfaceFlinger::getBuiltInDisplay(int32_t id) {
1921809bde133e0d66f06cea65887d9ceb3c70f8b95Alex Sakhartchouk    if (uint32_t(id) >= DisplayDevice::NUM_DISPLAY_TYPES) {
1931809bde133e0d66f06cea65887d9ceb3c70f8b95Alex Sakhartchouk        ALOGE("getDefaultDisplay: id=%d is not a valid default display id", id);
19409c67356bbeee0a97a20a06c95b66756838cb541Alex Sakhartchouk        return NULL;
195ca5a454e022caec6c6d3cbb404cc09ea095ba97aAlex Sakhartchouk    }
196c8fb69e4a3e01501a3d38a6d3ea185e583d3f493Alex Sakhartchouk    return mDefaultDisplays[id];
1970cae59f7d8dd63d1bf0ca4abedecb4cfa3ab1921Alex Sakhartchouk}
19809c67356bbeee0a97a20a06c95b66756838cb541Alex Sakhartchouk
199c8fb69e4a3e01501a3d38a6d3ea185e583d3f493Alex Sakhartchouksp<IGraphicBufferAlloc> SurfaceFlinger::createGraphicBufferAlloc()
2000cae59f7d8dd63d1bf0ca4abedecb4cfa3ab1921Alex Sakhartchouk{
2011809bde133e0d66f06cea65887d9ceb3c70f8b95Alex Sakhartchouk    sp<GraphicBufferAlloc> gba(new GraphicBufferAlloc());
202ca5a454e022caec6c6d3cbb404cc09ea095ba97aAlex Sakhartchouk    return gba;
2030cae59f7d8dd63d1bf0ca4abedecb4cfa3ab1921Alex Sakhartchouk}
2040cae59f7d8dd63d1bf0ca4abedecb4cfa3ab1921Alex Sakhartchouk
205afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchoukvoid SurfaceFlinger::bootFinished()
20683c451a4ef4388e002482e383d488ca9b7b7600dJason Sams{
207b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    const nsecs_t now = systemTime();
20883c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    const nsecs_t duration = now - mBootTime;
20983c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    ALOGI("Boot is finished (%ld ms)", long(ns2ms(duration)) );
21083c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    mBootFinished = true;
211b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk
21283c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    // wait patiently for the window manager death
21383c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    const String16 name("window");
21483c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    sp<IBinder> window(defaultServiceManager()->getService(name));
21583c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    if (window != 0) {
21683c451a4ef4388e002482e383d488ca9b7b7600dJason Sams        window->linkToDeath(static_cast<IBinder::DeathRecipient*>(this));
21783c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    }
21883c451a4ef4388e002482e383d488ca9b7b7600dJason Sams
21983c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    // stop boot animation
22083c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    // formerly we would just kill the process, but we now ask it to exit so it
221d3e7107c60ce06d637d83fa0db783ecdd0ad534cJason Sams    // can choose where to stop the animation.
222af12ac6a08651464f8d823add667c706f993b587Steve Block    property_set("service.bootanim.exit", "1");
22383c451a4ef4388e002482e383d488ca9b7b7600dJason Sams}
22483c451a4ef4388e002482e383d488ca9b7b7600dJason Sams
22583c451a4ef4388e002482e383d488ca9b7b7600dJason Samsvoid SurfaceFlinger::deleteTextureAsync(GLuint texture) {
22683c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    class MessageDestroyGLTexture : public MessageBase {
22783c451a4ef4388e002482e383d488ca9b7b7600dJason Sams        GLuint texture;
228d3e7107c60ce06d637d83fa0db783ecdd0ad534cJason Sams    public:
229d3e7107c60ce06d637d83fa0db783ecdd0ad534cJason Sams        MessageDestroyGLTexture(GLuint texture)
230d3e7107c60ce06d637d83fa0db783ecdd0ad534cJason Sams            : texture(texture) {
231d3e7107c60ce06d637d83fa0db783ecdd0ad534cJason Sams        }
232d3e7107c60ce06d637d83fa0db783ecdd0ad534cJason Sams        virtual bool handler() {
23383c451a4ef4388e002482e383d488ca9b7b7600dJason Sams            glDeleteTextures(1, &texture);
23483c451a4ef4388e002482e383d488ca9b7b7600dJason Sams            return true;
23583c451a4ef4388e002482e383d488ca9b7b7600dJason Sams        }
23683c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    };
23783c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    postMessageAsync(new MessageDestroyGLTexture(texture));
23883c451a4ef4388e002482e383d488ca9b7b7600dJason Sams}
23983c451a4ef4388e002482e383d488ca9b7b7600dJason Sams
24083c451a4ef4388e002482e383d488ca9b7b7600dJason Samsstatus_t SurfaceFlinger::selectConfigForAttribute(
24183c451a4ef4388e002482e383d488ca9b7b7600dJason Sams        EGLDisplay dpy,
24283c451a4ef4388e002482e383d488ca9b7b7600dJason Sams        EGLint const* attrs,
243c700e649ca44d0dcff8b271e42d949ea72fe3c63Alex Sakhartchouk        EGLint attribute, EGLint wanted,
244da6d34a5a6ece8c30d20673b9b6ff07d8c91768bAlex Sakhartchouk        EGLConfig* outConfig)
24583c451a4ef4388e002482e383d488ca9b7b7600dJason Sams{
24683c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    EGLConfig config = NULL;
24783c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    EGLint numConfigs = -1, n=0;
24883c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    eglGetConfigs(dpy, NULL, 0, &numConfigs);
249e0aab4a8ff1cffd8cfaedc2623db94072549e0e5Jason Sams    EGLConfig* const configs = new EGLConfig[numConfigs];
250e0aab4a8ff1cffd8cfaedc2623db94072549e0e5Jason Sams    eglChooseConfig(dpy, attrs, configs, numConfigs, &n);
251e0aab4a8ff1cffd8cfaedc2623db94072549e0e5Jason Sams
25283c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    if (n) {
253e0aab4a8ff1cffd8cfaedc2623db94072549e0e5Jason Sams        if (attribute != EGL_NONE) {
254e0aab4a8ff1cffd8cfaedc2623db94072549e0e5Jason Sams            for (int i=0 ; i<n ; i++) {
255dc314a172d48479053f258b485d7d0284b5b5b1fJason Sams                EGLint value = 0;
256dc314a172d48479053f258b485d7d0284b5b5b1fJason Sams                eglGetConfigAttrib(dpy, configs[i], attribute, &value);
257dc314a172d48479053f258b485d7d0284b5b5b1fJason Sams                if (wanted == value) {
258dc314a172d48479053f258b485d7d0284b5b5b1fJason Sams                    *outConfig = configs[i];
259dc314a172d48479053f258b485d7d0284b5b5b1fJason Sams                    delete [] configs;
260e0aab4a8ff1cffd8cfaedc2623db94072549e0e5Jason Sams                    return NO_ERROR;
261e0aab4a8ff1cffd8cfaedc2623db94072549e0e5Jason Sams                }
262e0aab4a8ff1cffd8cfaedc2623db94072549e0e5Jason Sams            }
26383c451a4ef4388e002482e383d488ca9b7b7600dJason Sams        } else {
2647257c7ee4b66f00c43d9235f3ac600061ae79968Alex Sakhartchouk            // just pick the first one
26583c451a4ef4388e002482e383d488ca9b7b7600dJason Sams            *outConfig = configs[0];
26683c451a4ef4388e002482e383d488ca9b7b7600dJason Sams            delete [] configs;
267e0aab4a8ff1cffd8cfaedc2623db94072549e0e5Jason Sams            return NO_ERROR;
268e0aab4a8ff1cffd8cfaedc2623db94072549e0e5Jason Sams        }
269dc314a172d48479053f258b485d7d0284b5b5b1fJason Sams    }
27083c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    delete [] configs;
27183c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    return NAME_NOT_FOUND;
27283c451a4ef4388e002482e383d488ca9b7b7600dJason Sams}
27383c451a4ef4388e002482e383d488ca9b7b7600dJason Sams
27483c451a4ef4388e002482e383d488ca9b7b7600dJason Samsclass EGLAttributeVector {
275e0aab4a8ff1cffd8cfaedc2623db94072549e0e5Jason Sams    struct Attribute;
27683c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    class Adder;
27783c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    friend class Adder;
27883c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    KeyedVector<Attribute, EGLint> mList;
27983c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    struct Attribute {
28083c451a4ef4388e002482e383d488ca9b7b7600dJason Sams        Attribute() {};
28183c451a4ef4388e002482e383d488ca9b7b7600dJason Sams        Attribute(EGLint v) : v(v) { }
282ca7c202abc3853e96d1d0d77b672789622eff99dJason Sams        EGLint v;
283ca7c202abc3853e96d1d0d77b672789622eff99dJason Sams        bool operator < (const Attribute& other) const {
28483c451a4ef4388e002482e383d488ca9b7b7600dJason Sams            // this places EGL_NONE at the end
28583c451a4ef4388e002482e383d488ca9b7b7600dJason Sams            EGLint lhs(v);
28683c451a4ef4388e002482e383d488ca9b7b7600dJason Sams            EGLint rhs(other.v);
2876598201f1c4f409defac9a5af789fb53a7cc00f8Steve Block            if (lhs == EGL_NONE) lhs = 0x7FFFFFFF;
28883c451a4ef4388e002482e383d488ca9b7b7600dJason Sams            if (rhs == EGL_NONE) rhs = 0x7FFFFFFF;
28983c451a4ef4388e002482e383d488ca9b7b7600dJason Sams            return lhs < rhs;
29083c451a4ef4388e002482e383d488ca9b7b7600dJason Sams        }
29183c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    };
29283c451a4ef4388e002482e383d488ca9b7b7600dJason Sams    class Adder {
29383c451a4ef4388e002482e383d488ca9b7b7600dJason Sams        friend class EGLAttributeVector;
29483c451a4ef4388e002482e383d488ca9b7b7600dJason Sams        EGLAttributeVector& v;
2956598201f1c4f409defac9a5af789fb53a7cc00f8Steve Block        EGLint attribute;
29683c451a4ef4388e002482e383d488ca9b7b7600dJason Sams        Adder(EGLAttributeVector& v, EGLint attribute)
297326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams            : v(v), attribute(attribute) {
298326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams        }
299741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams    public:
3006598201f1c4f409defac9a5af789fb53a7cc00f8Steve Block        void operator = (EGLint value) {
3012e8665de7c0eb4514c67baf8693d61c892e5303dJason Sams            if (attribute != EGL_NONE) {
302741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams                v.mList.add(attribute, value);
303741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams            }
304741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams        }
305741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams        operator EGLint () const { return v.mList[attribute]; }
306741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams    };
307741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Samspublic:
308741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams    EGLAttributeVector() {
309741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams        mList.add(EGL_NONE, EGL_NONE);
310741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams    }
311741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams    void remove(EGLint attribute) {
312741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams        if (attribute != EGL_NONE) {
313741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams            mList.removeItem(attribute);
314c700e649ca44d0dcff8b271e42d949ea72fe3c63Alex Sakhartchouk        }
315da6d34a5a6ece8c30d20673b9b6ff07d8c91768bAlex Sakhartchouk    }
316741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams    Adder operator [] (EGLint attribute) {
317c7cec1e3577cc77a5a73d5bd5a82733b1b9936a1Jason Sams        return Adder(*this, attribute);
3186598201f1c4f409defac9a5af789fb53a7cc00f8Steve Block    }
319cf912de17f1e086ccea707d8607a3d2eda56b98fJason Sams    EGLint operator [] (EGLint attribute) const {
320741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams       return mList[attribute];
321741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams    }
3222382aba4a55c6ae74789c478eead8fbd96593321Jason Sams    // cast-operator to (EGLint const*)
3232382aba4a55c6ae74789c478eead8fbd96593321Jason Sams    operator EGLint const* () const { return &mList.keyAt(0).v; }
324ee803446857b14d97f3e90a4f530604b6be9c867Jason Sams};
325af12ac6a08651464f8d823add667c706f993b587Steve Block
326ee803446857b14d97f3e90a4f530604b6be9c867Jason SamsEGLConfig SurfaceFlinger::selectEGLConfig(EGLDisplay display, EGLint nativeVisualId) {
327ee803446857b14d97f3e90a4f530604b6be9c867Jason Sams    // select our EGLConfig. It must support EGL_RECORDABLE_ANDROID if
328af12ac6a08651464f8d823add667c706f993b587Steve Block    // it is to be used with WIFI displays
329ee803446857b14d97f3e90a4f530604b6be9c867Jason Sams    EGLConfig config;
3302382aba4a55c6ae74789c478eead8fbd96593321Jason Sams    EGLint dummy;
3312382aba4a55c6ae74789c478eead8fbd96593321Jason Sams    status_t err;
3322382aba4a55c6ae74789c478eead8fbd96593321Jason Sams
333afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk    EGLAttributeVector attribs;
334158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams    attribs[EGL_SURFACE_TYPE]               = EGL_WINDOW_BIT;
335158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams    attribs[EGL_RECORDABLE_ANDROID]         = EGL_TRUE;
336158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams    attribs[EGL_FRAMEBUFFER_TARGET_ANDROID] = EGL_TRUE;
337158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams    attribs[EGL_RED_SIZE]                   = 8;
3382dca84dd6c07992f78ad050177975f16486dd77eJason Sams    attribs[EGL_GREEN_SIZE]                 = 8;
339158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams    attribs[EGL_BLUE_SIZE]                  = 8;
340158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams
341158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams    err = selectConfigForAttribute(display, attribs, EGL_NONE, EGL_NONE, &config);
342158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams    if (!err)
343158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams        goto success;
344158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams
345158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams    // maybe we failed because of EGL_FRAMEBUFFER_TARGET_ANDROID
346158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams    ALOGW("no suitable EGLConfig found, trying without EGL_FRAMEBUFFER_TARGET_ANDROID");
347158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams    attribs.remove(EGL_FRAMEBUFFER_TARGET_ANDROID);
3487bf29ddc35450d8064541c42c99a1f48be6cf0ddJason Sams    err = selectConfigForAttribute(display, attribs,
349158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams            EGL_NATIVE_VISUAL_ID, nativeVisualId, &config);
350158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams    if (!err)
351158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams        goto success;
352afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk
3535c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams    // maybe we failed because of EGL_RECORDABLE_ANDROID
354326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    ALOGW("no suitable EGLConfig found, trying without EGL_RECORDABLE_ANDROID");
355326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    attribs.remove(EGL_RECORDABLE_ANDROID);
35686f1b23aaaf9b8822a009d8c3e585e46768abb6aJason Sams    err = selectConfigForAttribute(display, attribs,
357e514b45de8561fbc6ef6770845102ca10b0a69d7Jason Sams            EGL_NATIVE_VISUAL_ID, nativeVisualId, &config);
358a2cf755a28a1e7ffff2955df656d714f40e4d715Jason Sams    if (!err)
359cbb0b8aceedb9146ba901cba1fbd6d1e9ca88f51Stephen Hines        goto success;
3607b3e9bd825901e33661e3c385e3e7c6f40ca6000Alex Sakhartchouk
361b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    // allow less than 24-bit color; the non-gpu-accelerated emulator only
36286c6b5fecb3e4e68668fdb5640770545501e778fStephen Hines    // supports 16-bit color
3635c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams    ALOGW("no suitable EGLConfig found, trying with 16-bit color allowed");
3645c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams    attribs.remove(EGL_RED_SIZE);
365afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk    attribs.remove(EGL_GREEN_SIZE);
3665c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams    attribs.remove(EGL_BLUE_SIZE);
367b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    err = selectConfigForAttribute(display, attribs,
3685c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams            EGL_NATIVE_VISUAL_ID, nativeVisualId, &config);
3695c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams    if (!err)
3705c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams        goto success;
3715c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams
3725c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams    // this EGL is too lame for Android
3735c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams    ALOGE("no suitable EGLConfig found, giving up");
3745c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams
375b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    return 0;
376b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk
377b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouksuccess:
378b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    if (eglGetConfigAttrib(display, config, EGL_CONFIG_CAVEAT, &dummy))
379b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk        ALOGW_IF(dummy == EGL_SLOW_CONFIG, "EGL_SLOW_CONFIG selected!");
380b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    return config;
381afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk}
3825c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams
3835c1c79a54c63b9de8c391f7ed890c02f280ec17fJason SamsEGLContext SurfaceFlinger::createGLContext(EGLDisplay display, EGLConfig config) {
3841a4efa363916977ef9aeab756725b3bdc880a15bJason Sams    // Also create our EGLContext
3852382aba4a55c6ae74789c478eead8fbd96593321Jason Sams    EGLint contextAttributes[] = {
3861a4efa363916977ef9aeab756725b3bdc880a15bJason Sams#ifdef EGL_IMG_context_priority
3875c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams#ifdef HAS_CONTEXT_PRIORITY
3885c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams#warning "using EGL_IMG_context_priority"
3896b8552a4f6a44848255d77222e66aa92dd21b1b5Jason Sams            EGL_CONTEXT_PRIORITY_LEVEL_IMG, EGL_CONTEXT_PRIORITY_HIGH_IMG,
3906b8552a4f6a44848255d77222e66aa92dd21b1b5Jason Sams#endif
3916b8552a4f6a44848255d77222e66aa92dd21b1b5Jason Sams#endif
3926b8552a4f6a44848255d77222e66aa92dd21b1b5Jason Sams            EGL_NONE, EGL_NONE
3936b8552a4f6a44848255d77222e66aa92dd21b1b5Jason Sams    };
394a2cf755a28a1e7ffff2955df656d714f40e4d715Jason Sams    EGLContext ctxt = eglCreateContext(display, config, NULL, contextAttributes);
3956b8552a4f6a44848255d77222e66aa92dd21b1b5Jason Sams    ALOGE_IF(ctxt==EGL_NO_CONTEXT, "EGLContext creation failed");
396326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    return ctxt;
397a658e905f14fe500bfee3812b213a73cb37ef6f2Jason Sams}
398a658e905f14fe500bfee3812b213a73cb37ef6f2Jason Sams
399a658e905f14fe500bfee3812b213a73cb37ef6f2Jason Samsvoid SurfaceFlinger::initializeGL(EGLDisplay display) {
400fb03a22ad2adadc1ff50a8b50d43ad7fcc3fa6edJason Sams    GLExtensions& extensions(GLExtensions::getInstance());
401fb03a22ad2adadc1ff50a8b50d43ad7fcc3fa6edJason Sams    extensions.initWithGLStrings(
402fb03a22ad2adadc1ff50a8b50d43ad7fcc3fa6edJason Sams            glGetString(GL_VENDOR),
403e57691037aea219562ac686429b4b98202aab7bcJason Sams            glGetString(GL_RENDERER),
404a658e905f14fe500bfee3812b213a73cb37ef6f2Jason Sams            glGetString(GL_VERSION),
405a658e905f14fe500bfee3812b213a73cb37ef6f2Jason Sams            glGetString(GL_EXTENSIONS),
406af12ac6a08651464f8d823add667c706f993b587Steve Block            eglQueryString(display, EGL_VENDOR),
4075c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams            eglQueryString(display, EGL_VERSION),
408a658e905f14fe500bfee3812b213a73cb37ef6f2Jason Sams            eglQueryString(display, EGL_EXTENSIONS));
409a658e905f14fe500bfee3812b213a73cb37ef6f2Jason Sams
4107257c7ee4b66f00c43d9235f3ac600061ae79968Alex Sakhartchouk    glGetIntegerv(GL_MAX_TEXTURE_SIZE, &mMaxTextureSize);
411992a0b70d8fd7a14f0c57bc3c7e16c1f269a6609Jason Sams    glGetIntegerv(GL_MAX_VIEWPORT_DIMS, mMaxViewportDims);
41224371d93cdb6999971c4058f78974da3c3d5fc64Jason Sams
413a891933b4c5ab1b63103add167269cfc404c2adfJason Sams    glPixelStorei(GL_UNPACK_ALIGNMENT, 4);
4145086938044e0a9b6b1138f915d0d252fe046e102Jason Sams    glPixelStorei(GL_PACK_ALIGNMENT, 4);
415a658e905f14fe500bfee3812b213a73cb37ef6f2Jason Sams    glEnableClientState(GL_VERTEX_ARRAY);
416326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    glShadeModel(GL_FLAT);
417af12ac6a08651464f8d823add667c706f993b587Steve Block    glDisable(GL_DITHER);
4185c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams    glDisable(GL_CULL_FACE);
4197bf29ddc35450d8064541c42c99a1f48be6cf0ddJason Sams
420afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk    struct pack565 {
421181334092f78273d0da2d854ebbe7b24508d3bfcJason Sams        inline uint16_t operator() (int r, int g, int b) const {
422181334092f78273d0da2d854ebbe7b24508d3bfcJason Sams            return (r<<11)|(g<<5)|b;
423181334092f78273d0da2d854ebbe7b24508d3bfcJason Sams        }
4245c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams    } pack565;
425af12ac6a08651464f8d823add667c706f993b587Steve Block
4265c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams    const uint16_t protTexData[] = { pack565(0x03, 0x03, 0x03) };
4275c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams    glGenTextures(1, &mProtectedTexName);
4285c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams    glBindTexture(GL_TEXTURE_2D, mProtectedTexName);
429a658e905f14fe500bfee3812b213a73cb37ef6f2Jason Sams    glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
4305c1c79a54c63b9de8c391f7ed890c02f280ec17fJason Sams    glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
431326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
432326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
433afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, 1, 1, 0,
4346598201f1c4f409defac9a5af789fb53a7cc00f8Steve Block            GL_RGB, GL_UNSIGNED_SHORT_5_6_5, protTexData);
435cf912de17f1e086ccea707d8607a3d2eda56b98fJason Sams
436b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    // print some debugging info
437b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    EGLint r,g,b,a;
438b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    eglGetConfigAttrib(display, mEGLConfig, EGL_RED_SIZE,   &r);
439b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    eglGetConfigAttrib(display, mEGLConfig, EGL_GREEN_SIZE, &g);
440b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    eglGetConfigAttrib(display, mEGLConfig, EGL_BLUE_SIZE,  &b);
441b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    eglGetConfigAttrib(display, mEGLConfig, EGL_ALPHA_SIZE, &a);
442326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    ALOGI("EGL informations:");
443b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    ALOGI("vendor    : %s", extensions.getEglVendor());
444b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    ALOGI("version   : %s", extensions.getEglVersion());
445326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    ALOGI("extensions: %s", extensions.getEglExtension());
446b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    ALOGI("Client API: %s", eglQueryString(display, EGL_CLIENT_APIS)?:"Not Supported");
447b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    ALOGI("EGLSurface: %d-%d-%d-%d, config=%p", r, g, b, a, mEGLConfig);
448b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    ALOGI("OpenGL ES informations:");
449249d453869cca82dcb57123f6d1c8df3ca9f4372Jason Sams    ALOGI("vendor    : %s", extensions.getVendor());
450b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    ALOGI("renderer  : %s", extensions.getRenderer());
451b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    ALOGI("version   : %s", extensions.getVersion());
452b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    ALOGI("extensions: %s", extensions.getExtension());
453b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    ALOGI("GL_MAX_TEXTURE_SIZE = %d", mMaxTextureSize);
454b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    ALOGI("GL_MAX_VIEWPORT_DIMS = %d x %d", mMaxViewportDims[0], mMaxViewportDims[1]);
455b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk}
456b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk
457326e0ddf89e8df2837752fbfd7a014814b32082cJason Samsstatus_t SurfaceFlinger::readyToRun()
4586598201f1c4f409defac9a5af789fb53a7cc00f8Steve Block{
459326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    ALOGI(  "SurfaceFlinger's main thread ready to run. "
460326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams            "Initializing graphics H/W...");
4617257c7ee4b66f00c43d9235f3ac600061ae79968Alex Sakhartchouk
4624820e8bb83b1f78e6232ebe853221f737da2a1eaJason Sams    // initialize EGL for the default display
4634b3de47071d875faaa7d419d050a464b09538797Jason Sams    mEGLDisplay = eglGetDisplay(EGL_DEFAULT_DISPLAY);
464458f2dc26b7d34c2138c7bfbd95914240084e6bdJason Sams    eglInitialize(mEGLDisplay, NULL, NULL);
4657257c7ee4b66f00c43d9235f3ac600061ae79968Alex Sakhartchouk
4664b3de47071d875faaa7d419d050a464b09538797Jason Sams    // Initialize the H/W composer object.  There may or may not be an
4674b3de47071d875faaa7d419d050a464b09538797Jason Sams    // actual hardware composer underneath.
468613cad1702dbb76eb2a6ba0cfcb43b9fe207cebcJason Sams    mHwc = new HWComposer(this,
4694b3de47071d875faaa7d419d050a464b09538797Jason Sams            *static_cast<HWComposer::EventHandler *>(this));
470771565f47fc44608444c00aa8fa3bda769ceaeceJason Sams
471a544b6368d7ddae47985da92d6bcf86798b376c6Alex Sakhartchouk    // initialize the config and context
472458f2dc26b7d34c2138c7bfbd95914240084e6bdJason Sams    EGLint format = mHwc->getVisualID();
473458f2dc26b7d34c2138c7bfbd95914240084e6bdJason Sams    mEGLConfig  = selectEGLConfig(mEGLDisplay, format);
474458f2dc26b7d34c2138c7bfbd95914240084e6bdJason Sams    mEGLContext = createGLContext(mEGLDisplay, mEGLConfig);
475a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk
476a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk    LOG_ALWAYS_FATAL_IF(mEGLContext == EGL_NO_CONTEXT,
477a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk            "couldn't create EGLContext");
478a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk
479a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk    // initialize our non-virtual displays
480a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk    for (size_t i=0 ; i<DisplayDevice::NUM_DISPLAY_TYPES ; i++) {
481a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk        DisplayDevice::DisplayType type((DisplayDevice::DisplayType)i);
482a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk        mDefaultDisplays[i] = new BBinder();
483a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk        wp<IBinder> token = mDefaultDisplays[i];
484a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk
485a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk        // set-up the displays that are already connected
486a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk        if (mHwc->isConnected(i) || type==DisplayDevice::DISPLAY_PRIMARY) {
487a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk            mCurrentState.displays.add(token, DisplayDeviceState(type));
488a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk            sp<FramebufferSurface> fbs = new FramebufferSurface(*mHwc, i);
489a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk            sp<SurfaceTextureClient> stc = new SurfaceTextureClient(
490a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk                        static_cast< sp<ISurfaceTexture> >(fbs->getBufferQueue()));
491a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk            sp<DisplayDevice> hw = new DisplayDevice(this,
492a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk                    type, token, stc, fbs, mEGLConfig);
493a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk            if (i > DisplayDevice::DISPLAY_PRIMARY) {
494a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk                // FIXME: currently we don't get blank/unblank requests
495a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk                // for displays other than the main display, so we always
496a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk                // assume a connected display is unblanked.
497a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk                ALOGD("marking display %d as acquired/unblanked", i);
498a74a8f635ce4fae0a9d4b9c79e9fa412787bf6a2Alex Sakhartchouk                hw->acquireScreen();
499afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk            }
5004820e8bb83b1f78e6232ebe853221f737da2a1eaJason Sams            mDisplays.add(token, hw);
50186f1b23aaaf9b8822a009d8c3e585e46768abb6aJason Sams        }
50286f1b23aaaf9b8822a009d8c3e585e46768abb6aJason Sams    }
50386f1b23aaaf9b8822a009d8c3e585e46768abb6aJason Sams
504afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk    //  we need a GL context current in a few places, when initializing
5054820e8bb83b1f78e6232ebe853221f737da2a1eaJason Sams    //  OpenGL ES (see below), or creating a layer,
50686f1b23aaaf9b8822a009d8c3e585e46768abb6aJason Sams    //  or when a texture is (asynchronously) destroyed, and for that
50786f1b23aaaf9b8822a009d8c3e585e46768abb6aJason Sams    //  we need a valid surface, so it's convenient to use the main display
50886f1b23aaaf9b8822a009d8c3e585e46768abb6aJason Sams    //  for that.
509afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk    sp<const DisplayDevice> hw = getDefaultDisplayDevice();
5104820e8bb83b1f78e6232ebe853221f737da2a1eaJason Sams
511326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    //  initialize OpenGL ES
512326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    DisplayDevice::makeCurrent(mEGLDisplay, hw, mEGLContext);
513326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    initializeGL(mEGLDisplay);
51460709257bbdeb0c50f39b9c8969dc76264d6e142Jason Sams
5154820e8bb83b1f78e6232ebe853221f737da2a1eaJason Sams    // start the EventThread
5168ce125be69531dbf3a7e856d5e59d1b8e2789db0Jason Sams    mEventThread = new EventThread(this);
5178ce125be69531dbf3a7e856d5e59d1b8e2789db0Jason Sams    mEventQueue.setEventThread(mEventThread);
5188ce125be69531dbf3a7e856d5e59d1b8e2789db0Jason Sams
5198ce125be69531dbf3a7e856d5e59d1b8e2789db0Jason Sams    // initialize our drawing state
5208ce125be69531dbf3a7e856d5e59d1b8e2789db0Jason Sams    mDrawingState = mCurrentState;
521326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams
522326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams
52360709257bbdeb0c50f39b9c8969dc76264d6e142Jason Sams    // We're now ready to accept clients...
5244820e8bb83b1f78e6232ebe853221f737da2a1eaJason Sams    mReadyToRunBarrier.open();
5258ce125be69531dbf3a7e856d5e59d1b8e2789db0Jason Sams
5268ce125be69531dbf3a7e856d5e59d1b8e2789db0Jason Sams    // set initial conditions (e.g. unblank default device)
5278ce125be69531dbf3a7e856d5e59d1b8e2789db0Jason Sams    initializeDisplays();
5288ce125be69531dbf3a7e856d5e59d1b8e2789db0Jason Sams
5298ce125be69531dbf3a7e856d5e59d1b8e2789db0Jason Sams    // start boot animation
530cfb1d11ce6826fce7241d316d8b7dcab661f63a6Jason Sams    startBootAnim();
531cfb1d11ce6826fce7241d316d8b7dcab661f63a6Jason Sams
53260709257bbdeb0c50f39b9c8969dc76264d6e142Jason Sams    return NO_ERROR;
5334820e8bb83b1f78e6232ebe853221f737da2a1eaJason Sams}
5345fd09d847586f9680b4f495413b6ca5fbb69af6eJason Sams
5355fd09d847586f9680b4f495413b6ca5fbb69af6eJason Samsint32_t SurfaceFlinger::allocateHwcDisplayId(DisplayDevice::DisplayType type) {
5365fd09d847586f9680b4f495413b6ca5fbb69af6eJason Sams    return (uint32_t(type) < DisplayDevice::NUM_DISPLAY_TYPES) ?
5375fd09d847586f9680b4f495413b6ca5fbb69af6eJason Sams            type : mHwc->allocateDisplayId();
5385fd09d847586f9680b4f495413b6ca5fbb69af6eJason Sams}
5395fd09d847586f9680b4f495413b6ca5fbb69af6eJason Sams
5405fd09d847586f9680b4f495413b6ca5fbb69af6eJason Samsvoid SurfaceFlinger::startBootAnim() {
54160709257bbdeb0c50f39b9c8969dc76264d6e142Jason Sams    // start boot animation
5424820e8bb83b1f78e6232ebe853221f737da2a1eaJason Sams    property_set("service.bootanim.exit", "0");
5438ce125be69531dbf3a7e856d5e59d1b8e2789db0Jason Sams    property_set("ctl.start", "bootanim");
5448ce125be69531dbf3a7e856d5e59d1b8e2789db0Jason Sams}
5458ce125be69531dbf3a7e856d5e59d1b8e2789db0Jason Sams
5468ce125be69531dbf3a7e856d5e59d1b8e2789db0Jason Samsuint32_t SurfaceFlinger::getMaxTextureSize() const {
5478ce125be69531dbf3a7e856d5e59d1b8e2789db0Jason Sams    return mMaxTextureSize;
548326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams}
549326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams
550afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchoukuint32_t SurfaceFlinger::getMaxViewportDims() const {
551d3e0ad43dc758c409fc23d1893dab67b18520c24Alex Sakhartchouk    return mMaxViewportDims[0] < mMaxViewportDims[1] ?
552d3e0ad43dc758c409fc23d1893dab67b18520c24Alex Sakhartchouk            mMaxViewportDims[0] : mMaxViewportDims[1];
553d3e0ad43dc758c409fc23d1893dab67b18520c24Alex Sakhartchouk}
554d3e0ad43dc758c409fc23d1893dab67b18520c24Alex Sakhartchouk
555d3e0ad43dc758c409fc23d1893dab67b18520c24Alex Sakhartchouk// ----------------------------------------------------------------------------
556d3e0ad43dc758c409fc23d1893dab67b18520c24Alex Sakhartchouk
557d3e0ad43dc758c409fc23d1893dab67b18520c24Alex Sakhartchoukbool SurfaceFlinger::authenticateSurfaceTexture(
558d3e0ad43dc758c409fc23d1893dab67b18520c24Alex Sakhartchouk        const sp<ISurfaceTexture>& surfaceTexture) const {
559afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk    Mutex::Autolock _l(mStateLock);
560a0a1b6fbece2eb8d72d788422ab3e5f58d5a9216Jason Sams    sp<IBinder> surfaceTextureBinder(surfaceTexture->asBinder());
561a4a54e42fc710a62b47cbcb9d64c34a190429d9eJason Sams
562a0a1b6fbece2eb8d72d788422ab3e5f58d5a9216Jason Sams    // Check the visible layer list for the ISurface
563a0a1b6fbece2eb8d72d788422ab3e5f58d5a9216Jason Sams    const LayerVector& currentLayers = mCurrentState.layersSortedByZ;
564a0a1b6fbece2eb8d72d788422ab3e5f58d5a9216Jason Sams    size_t count = currentLayers.size();
565afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk    for (size_t i=0 ; i<count ; i++) {
566afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk        const sp<LayerBase>& layer(currentLayers[i]);
567a0a1b6fbece2eb8d72d788422ab3e5f58d5a9216Jason Sams        sp<LayerBaseClient> lbc(layer->getLayerBaseClient());
568a0a1b6fbece2eb8d72d788422ab3e5f58d5a9216Jason Sams        if (lbc != NULL) {
569a0a1b6fbece2eb8d72d788422ab3e5f58d5a9216Jason Sams            wp<IBinder> lbcBinder = lbc->getSurfaceTextureBinder();
570a0a1b6fbece2eb8d72d788422ab3e5f58d5a9216Jason Sams            if (lbcBinder == surfaceTextureBinder) {
571a0a1b6fbece2eb8d72d788422ab3e5f58d5a9216Jason Sams                return true;
572a0a1b6fbece2eb8d72d788422ab3e5f58d5a9216Jason Sams            }
573a0a1b6fbece2eb8d72d788422ab3e5f58d5a9216Jason Sams        }
5741a4efa363916977ef9aeab756725b3bdc880a15bJason Sams    }
5751a4efa363916977ef9aeab756725b3bdc880a15bJason Sams
576aad4bc5231dd7059fc5148b34a951117d9b5f4adJason Sams    // Check the layers in the purgatory.  This check is here so that if a
577aad4bc5231dd7059fc5148b34a951117d9b5f4adJason Sams    // SurfaceTexture gets destroyed before all the clients are done using it,
5781a4efa363916977ef9aeab756725b3bdc880a15bJason Sams    // the error will not be reported as "surface XYZ is not authenticated", but
5791a4efa363916977ef9aeab756725b3bdc880a15bJason Sams    // will instead fail later on when the client tries to use the surface,
5808c401effb0837155fc39ca0364f57a882d127d38Jason Sams    // which should be reported as "surface XYZ returned an -ENODEV".  The
5818c401effb0837155fc39ca0364f57a882d127d38Jason Sams    // purgatorized layers are no less authentic than the visible ones, so this
58287319de2b16a185cf360827c96a42cf1fcaae744Jason Sams    // should not cause any harm.
58387319de2b16a185cf360827c96a42cf1fcaae744Jason Sams    size_t purgatorySize =  mLayerPurgatory.size();
5841a4efa363916977ef9aeab756725b3bdc880a15bJason Sams    for (size_t i=0 ; i<purgatorySize ; i++) {
5851a4efa363916977ef9aeab756725b3bdc880a15bJason Sams        const sp<LayerBase>& layer(mLayerPurgatory.itemAt(i));
5868c401effb0837155fc39ca0364f57a882d127d38Jason Sams        sp<LayerBaseClient> lbc(layer->getLayerBaseClient());
5878c401effb0837155fc39ca0364f57a882d127d38Jason Sams        if (lbc != NULL) {
588afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk            wp<IBinder> lbcBinder = lbc->getSurfaceTextureBinder();
589afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk            if (lbcBinder == surfaceTextureBinder) {
5908c401effb0837155fc39ca0364f57a882d127d38Jason Sams                return true;
5918c401effb0837155fc39ca0364f57a882d127d38Jason Sams            }
5928c401effb0837155fc39ca0364f57a882d127d38Jason Sams        }
5938c401effb0837155fc39ca0364f57a882d127d38Jason Sams    }
594afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk
5951a4efa363916977ef9aeab756725b3bdc880a15bJason Sams    return false;
5968c401effb0837155fc39ca0364f57a882d127d38Jason Sams}
5975086938044e0a9b6b1138f915d0d252fe046e102Jason Sams
59887319de2b16a185cf360827c96a42cf1fcaae744Jason Samsstatus_t SurfaceFlinger::getDisplayInfo(const sp<IBinder>& display, DisplayInfo* info) {
599a2cf755a28a1e7ffff2955df656d714f40e4d715Jason Sams    int32_t type = BAD_VALUE;
600aad4bc5231dd7059fc5148b34a951117d9b5f4adJason Sams    for (int i=0 ; i<DisplayDevice::NUM_DISPLAY_TYPES ; i++) {
601a2cf755a28a1e7ffff2955df656d714f40e4d715Jason Sams        if (display == mDefaultDisplays[i]) {
602a2cf755a28a1e7ffff2955df656d714f40e4d715Jason Sams            type = i;
603a2cf755a28a1e7ffff2955df656d714f40e4d715Jason Sams            break;
604afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk        }
605af12ac6a08651464f8d823add667c706f993b587Steve Block    }
606af12ac6a08651464f8d823add667c706f993b587Steve Block
60713e2634a71a30d289ed8d821aef61c7d1687460eJason Sams    if (type < 0) {
608af12ac6a08651464f8d823add667c706f993b587Steve Block        return type;
609af12ac6a08651464f8d823add667c706f993b587Steve Block    }
610af12ac6a08651464f8d823add667c706f993b587Steve Block
61113e2634a71a30d289ed8d821aef61c7d1687460eJason Sams    const HWComposer& hwc(getHwComposer());
612a4a54e42fc710a62b47cbcb9d64c34a190429d9eJason Sams    if (!hwc.isConnected(type)) {
613326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams        return NAME_NOT_FOUND;
614a44cb29164726cd9d812117819abdd7b60dfdd93Jason Sams    }
615326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams
616326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    float xdpi = hwc.getDpiX(type);
617326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    float ydpi = hwc.getDpiY(type);
618326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams
619afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk    // TODO: Not sure if display density should handled by SF any longer
6208c88090e8cccab103eebe2ff569e116e9f5fb208Jason Sams    class Density {
621326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams        static int getDensityFromProperty(char const* propName) {
622afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk            char property[PROPERTY_VALUE_MAX];
623326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams            int density = 0;
624326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams            if (property_get(propName, property, NULL) > 0) {
625326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams                density = atoi(property);
626326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams            }
627afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk            return density;
628326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams        }
629326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    public:
630326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams        static int getEmuDensity() {
631af12ac6a08651464f8d823add667c706f993b587Steve Block            return getDensityFromProperty("qemu.sf.lcd_density"); }
632326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams        static int getBuildDensity()  {
633326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams            return getDensityFromProperty("ro.sf.lcd_density"); }
634326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    };
635326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams
636326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    if (type == DisplayDevice::DISPLAY_PRIMARY) {
637326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams        // The density of the device is provided by a build property
638afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk        float density = Density::getBuildDensity() / 160.0f;
639ccc010bb7c0f89e162bf60033968a20be90a903aJason Sams        if (density == 0) {
64060709257bbdeb0c50f39b9c8969dc76264d6e142Jason Sams            // the build doesn't provide a density -- this is wrong!
641326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams            // use xdpi instead
642326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams            ALOGE("ro.sf.lcd_density must be defined as a build property");
643afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk            density = xdpi / 160.0f;
644326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams        }
64560709257bbdeb0c50f39b9c8969dc76264d6e142Jason Sams        if (Density::getEmuDensity()) {
646326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams            // if "qemu.sf.lcd_density" is specified, it overrides everything
647326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams            xdpi = ydpi = density = Density::getEmuDensity();
648afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk            density /= 160.0f;
6495fd09d847586f9680b4f495413b6ca5fbb69af6eJason Sams        }
65060709257bbdeb0c50f39b9c8969dc76264d6e142Jason Sams        info->density = density;
6515fd09d847586f9680b4f495413b6ca5fbb69af6eJason Sams
6525fd09d847586f9680b4f495413b6ca5fbb69af6eJason Sams        // TODO: this needs to go away (currently needed only by webkit)
653afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk        sp<const DisplayDevice> hw(getDefaultDisplayDevice());
654326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams        info->orientation = hw->getOrientation();
65560709257bbdeb0c50f39b9c8969dc76264d6e142Jason Sams        getPixelFormatInfo(hw->getFormat(), &info->pixelFormatInfo);
656326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    } else {
657326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams        // TODO: where should this value come from?
658afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk        static const int TV_DENSITY = 213;
659d3e0ad43dc758c409fc23d1893dab67b18520c24Alex Sakhartchouk        info->density = TV_DENSITY / 160.0f;
660d3e0ad43dc758c409fc23d1893dab67b18520c24Alex Sakhartchouk        info->orientation = 0;
661d3e0ad43dc758c409fc23d1893dab67b18520c24Alex Sakhartchouk    }
662d3e0ad43dc758c409fc23d1893dab67b18520c24Alex Sakhartchouk
663b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk    info->w = hwc.getWidth(type);
664a0a1b6fbece2eb8d72d788422ab3e5f58d5a9216Jason Sams    info->h = hwc.getHeight(type);
66570b83c111beceaf8fbb700580833e7fec99272cfAlex Sakhartchouk    info->xdpi = xdpi;
666a0a1b6fbece2eb8d72d788422ab3e5f58d5a9216Jason Sams    info->ydpi = ydpi;
667326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams    info->fps = float(1e9 / hwc.getRefreshPeriod(type));
668afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk    return NO_ERROR;
6692353ae303868d04e3a26002b2f2dc456c15e8170Jason Sams}
670707aaf341a4b068e6ccadf923af85acdd85fd775Jason Sams
6719397e30ce5fe3f6af9212a93b490836b04fdfffaJason Sams// ----------------------------------------------------------------------------
672707aaf341a4b068e6ccadf923af85acdd85fd775Jason Sams
673707aaf341a4b068e6ccadf923af85acdd85fd775Jason Samssp<IDisplayEventConnection> SurfaceFlinger::createDisplayEventConnection() {
674afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk    return mEventThread->createEventConnection();
67586f1b23aaaf9b8822a009d8c3e585e46768abb6aJason Sams}
67686f1b23aaaf9b8822a009d8c3e585e46768abb6aJason Sams
67786f1b23aaaf9b8822a009d8c3e585e46768abb6aJason Samsvoid SurfaceFlinger::connectDisplay(const sp<ISurfaceTexture>& surface) {
678afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk
67986f1b23aaaf9b8822a009d8c3e585e46768abb6aJason Sams    sp<IBinder> token;
68086f1b23aaaf9b8822a009d8c3e585e46768abb6aJason Sams    { // scope for the lock
68186f1b23aaaf9b8822a009d8c3e585e46768abb6aJason Sams        Mutex::Autolock _l(mStateLock);
6827257c7ee4b66f00c43d9235f3ac600061ae79968Alex Sakhartchouk        token = mExtDisplayToken;
683fa4028663712dbb1a3d13c507c3bc13c6e4be80dMathias Agopian    }
684613cad1702dbb76eb2a6ba0cfcb43b9fe207cebcJason Sams
685613cad1702dbb76eb2a6ba0cfcb43b9fe207cebcJason Sams    if (token == 0) {
686afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk        token = createDisplay(String8("Display from connectDisplay"));
687158324456b8dbf40f684dd0a4af3493b9549f3f5Jason Sams    }
688458f2dc26b7d34c2138c7bfbd95914240084e6bdJason Sams
689458f2dc26b7d34c2138c7bfbd95914240084e6bdJason Sams    { // scope for the lock
690afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk        Mutex::Autolock _l(mStateLock);
691c21cf40f6ae69091bf24f87b5eeabc95e73dd271Jason Sams        if (surface == 0) {
692c21cf40f6ae69091bf24f87b5eeabc95e73dd271Jason Sams            // release our current display. we're guarantee to have
693c21cf40f6ae69091bf24f87b5eeabc95e73dd271Jason Sams            // a reference to it (token), while we hold the lock
694741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams            mExtDisplayToken = 0;
695b81a0eb8180791e4eaab1253b59fa8bd562b046bAlex Sakhartchouk        } else {
6961dcefab7178f0644b0e0a6998007b1acae5261cfJason Sams            mExtDisplayToken = token;
6971dcefab7178f0644b0e0a6998007b1acae5261cfJason Sams        }
698c975cf4a71b63ccbd20f1f3b3341c5f2e6025b45Jason Sams
6996598201f1c4f409defac9a5af789fb53a7cc00f8Steve Block        DisplayDeviceState& info(mCurrentState.displays.editValueFor(token));
700741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams        info.surface = surface;
701741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams        setTransactionFlags(eDisplayTransactionNeeded);
7026598201f1c4f409defac9a5af789fb53a7cc00f8Steve Block    }
703741aac95b777b2e6cb90f484a05e489a79a6ef05Jason Sams}
704326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams
705326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams// ----------------------------------------------------------------------------
706c975cf4a71b63ccbd20f1f3b3341c5f2e6025b45Jason Sams
707186e59154a0fb86e05e283e9c083b69878c06720Jason Samsvoid SurfaceFlinger::waitForEvent() {
7081a4efa363916977ef9aeab756725b3bdc880a15bJason Sams    mEventQueue.waitMessage();
7091a4efa363916977ef9aeab756725b3bdc880a15bJason Sams}
710aad4bc5231dd7059fc5148b34a951117d9b5f4adJason Sams
711aad4bc5231dd7059fc5148b34a951117d9b5f4adJason Samsvoid SurfaceFlinger::signalTransaction() {
712c975cf4a71b63ccbd20f1f3b3341c5f2e6025b45Jason Sams    mEventQueue.invalidate();
713186e59154a0fb86e05e283e9c083b69878c06720Jason Sams}
7141a4efa363916977ef9aeab756725b3bdc880a15bJason Sams
715186e59154a0fb86e05e283e9c083b69878c06720Jason Samsvoid SurfaceFlinger::signalLayerUpdate() {
716186e59154a0fb86e05e283e9c083b69878c06720Jason Sams    mEventQueue.invalidate();
7171a4efa363916977ef9aeab756725b3bdc880a15bJason Sams}
7188c401effb0837155fc39ca0364f57a882d127d38Jason Sams
7198c401effb0837155fc39ca0364f57a882d127d38Jason Samsvoid SurfaceFlinger::signalRefresh() {
720c975cf4a71b63ccbd20f1f3b3341c5f2e6025b45Jason Sams    mEventQueue.refresh();
7218c401effb0837155fc39ca0364f57a882d127d38Jason Sams}
7228c401effb0837155fc39ca0364f57a882d127d38Jason Sams
7238c401effb0837155fc39ca0364f57a882d127d38Jason Samsstatus_t SurfaceFlinger::postMessageAsync(const sp<MessageBase>& msg,
724c975cf4a71b63ccbd20f1f3b3341c5f2e6025b45Jason Sams        nsecs_t reltime, uint32_t flags) {
7258c401effb0837155fc39ca0364f57a882d127d38Jason Sams    return mEventQueue.postMessage(msg, reltime);
7268c401effb0837155fc39ca0364f57a882d127d38Jason Sams}
7278c401effb0837155fc39ca0364f57a882d127d38Jason Sams
728c975cf4a71b63ccbd20f1f3b3341c5f2e6025b45Jason Samsstatus_t SurfaceFlinger::postMessageSync(const sp<MessageBase>& msg,
729c975cf4a71b63ccbd20f1f3b3341c5f2e6025b45Jason Sams        nsecs_t reltime, uint32_t flags) {
730c975cf4a71b63ccbd20f1f3b3341c5f2e6025b45Jason Sams    status_t res = mEventQueue.postMessage(msg, reltime);
731cbb0b8aceedb9146ba901cba1fbd6d1e9ca88f51Stephen Hines    if (res == NO_ERROR) {
732cbb0b8aceedb9146ba901cba1fbd6d1e9ca88f51Stephen Hines        msg->wait();
7336598201f1c4f409defac9a5af789fb53a7cc00f8Steve Block    }
734789ca83c794cb7196c9bac97d39eaf1f7947af2aJason Sams    return res;
735789ca83c794cb7196c9bac97d39eaf1f7947af2aJason Sams}
736cbb0b8aceedb9146ba901cba1fbd6d1e9ca88f51Stephen Hines
737cbb0b8aceedb9146ba901cba1fbd6d1e9ca88f51Stephen Hinesbool SurfaceFlinger::threadLoop() {
738cbb0b8aceedb9146ba901cba1fbd6d1e9ca88f51Stephen Hines    waitForEvent();
739789ca83c794cb7196c9bac97d39eaf1f7947af2aJason Sams    return true;
740789ca83c794cb7196c9bac97d39eaf1f7947af2aJason Sams}
741789ca83c794cb7196c9bac97d39eaf1f7947af2aJason Sams
742789ca83c794cb7196c9bac97d39eaf1f7947af2aJason Samsvoid SurfaceFlinger::onVSyncReceived(int type, nsecs_t timestamp) {
743cbb0b8aceedb9146ba901cba1fbd6d1e9ca88f51Stephen Hines    if (mEventThread == NULL) {
744cbb0b8aceedb9146ba901cba1fbd6d1e9ca88f51Stephen Hines        // This is a temporary workaround for b/7145521.  A non-null pointer
7456598201f1c4f409defac9a5af789fb53a7cc00f8Steve Block        // does not mean EventThread has finished initializing, so this
746789ca83c794cb7196c9bac97d39eaf1f7947af2aJason Sams        // is not a correct fix.
747789ca83c794cb7196c9bac97d39eaf1f7947af2aJason Sams        ALOGW("WARNING: EventThread not started, ignoring vsync");
7489544f76195de22f655fd7a1894934667e7e55f6aJason Sams        return;
749cbb0b8aceedb9146ba901cba1fbd6d1e9ca88f51Stephen Hines    }
7509544f76195de22f655fd7a1894934667e7e55f6aJason Sams    if (uint32_t(type) < DisplayDevice::NUM_DISPLAY_TYPES) {
7519544f76195de22f655fd7a1894934667e7e55f6aJason Sams        // we should only receive DisplayDevice::DisplayType from the vsync callback
7526598201f1c4f409defac9a5af789fb53a7cc00f8Steve Block        mEventThread->onVSyncReceived(type, timestamp);
753789ca83c794cb7196c9bac97d39eaf1f7947af2aJason Sams    }
754789ca83c794cb7196c9bac97d39eaf1f7947af2aJason Sams}
755789ca83c794cb7196c9bac97d39eaf1f7947af2aJason Sams
756dc763f345db3e796efc28dc4b4d8edffda5a803eAlex Sakhartchoukvoid SurfaceFlinger::onHotplugReceived(int type, bool connected) {
757dc763f345db3e796efc28dc4b4d8edffda5a803eAlex Sakhartchouk    if (mEventThread == NULL) {
758afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk        // This is a temporary workaround for b/7145521.  A non-null pointer
759dc763f345db3e796efc28dc4b4d8edffda5a803eAlex Sakhartchouk        // does not mean EventThread has finished initializing, so this
760dc763f345db3e796efc28dc4b4d8edffda5a803eAlex Sakhartchouk        // is not a correct fix.
761dc763f345db3e796efc28dc4b4d8edffda5a803eAlex Sakhartchouk        ALOGW("WARNING: EventThread not started, ignoring hotplug");
762        return;
763    }
764
765    if (uint32_t(type) < DisplayDevice::NUM_DISPLAY_TYPES) {
766        Mutex::Autolock _l(mStateLock);
767        if (connected == false) {
768            mCurrentState.displays.removeItem(mDefaultDisplays[type]);
769        } else {
770            DisplayDeviceState info((DisplayDevice::DisplayType)type);
771            mCurrentState.displays.add(mDefaultDisplays[type], info);
772        }
773        setTransactionFlags(eDisplayTransactionNeeded);
774
775        // we should only receive DisplayDevice::DisplayType from the vsync callback
776        mEventThread->onHotplugReceived(type, connected);
777    }
778}
779
780void SurfaceFlinger::eventControl(int disp, int event, int enabled) {
781    getHwComposer().eventControl(disp, event, enabled);
782}
783
784void SurfaceFlinger::onMessageReceived(int32_t what) {
785    ATRACE_CALL();
786    switch (what) {
787    case MessageQueue::INVALIDATE:
788        handleMessageTransaction();
789        handleMessageInvalidate();
790        signalRefresh();
791        break;
792    case MessageQueue::REFRESH:
793        handleMessageRefresh();
794        break;
795    }
796}
797
798void SurfaceFlinger::handleMessageTransaction() {
799    uint32_t transactionFlags = peekTransactionFlags(eTransactionMask);
800    if (transactionFlags) {
801        handleTransaction(transactionFlags);
802    }
803}
804
805void SurfaceFlinger::handleMessageInvalidate() {
806    ATRACE_CALL();
807    handlePageFlip();
808}
809
810void SurfaceFlinger::handleMessageRefresh() {
811    ATRACE_CALL();
812    preComposition();
813    rebuildLayerStacks();
814    setUpHWComposer();
815    doDebugFlashRegions();
816    doComposition();
817    postComposition();
818}
819
820void SurfaceFlinger::doDebugFlashRegions()
821{
822    // is debugging enabled
823    if (CC_LIKELY(!mDebugRegion))
824        return;
825
826    const bool repaintEverything = mRepaintEverything;
827    for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
828        const sp<DisplayDevice>& hw(mDisplays[dpy]);
829        if (hw->canDraw()) {
830            // transform the dirty region into this screen's coordinate space
831            const Region dirtyRegion(hw->getDirtyRegion(repaintEverything));
832            if (!dirtyRegion.isEmpty()) {
833                // redraw the whole screen
834                doComposeSurfaces(hw, Region(hw->bounds()));
835
836                // and draw the dirty region
837                glDisable(GL_TEXTURE_EXTERNAL_OES);
838                glDisable(GL_TEXTURE_2D);
839                glDisable(GL_BLEND);
840                glColor4f(1, 0, 1, 1);
841                const int32_t height = hw->getHeight();
842                Region::const_iterator it = dirtyRegion.begin();
843                Region::const_iterator const end = dirtyRegion.end();
844                while (it != end) {
845                    const Rect& r = *it++;
846                    GLfloat vertices[][2] = {
847                            { r.left,  height - r.top },
848                            { r.left,  height - r.bottom },
849                            { r.right, height - r.bottom },
850                            { r.right, height - r.top }
851                    };
852                    glVertexPointer(2, GL_FLOAT, 0, vertices);
853                    glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
854                }
855                hw->compositionComplete();
856                hw->swapBuffers(getHwComposer());
857            }
858        }
859    }
860
861    postFramebuffer();
862
863    if (mDebugRegion > 1) {
864        usleep(mDebugRegion * 1000);
865    }
866
867    HWComposer& hwc(getHwComposer());
868    if (hwc.initCheck() == NO_ERROR) {
869        status_t err = hwc.prepare();
870        ALOGE_IF(err, "HWComposer::prepare failed (%s)", strerror(-err));
871    }
872}
873
874void SurfaceFlinger::preComposition()
875{
876    bool needExtraInvalidate = false;
877    const LayerVector& currentLayers(mDrawingState.layersSortedByZ);
878    const size_t count = currentLayers.size();
879    for (size_t i=0 ; i<count ; i++) {
880        if (currentLayers[i]->onPreComposition()) {
881            needExtraInvalidate = true;
882        }
883    }
884    if (needExtraInvalidate) {
885        signalLayerUpdate();
886    }
887}
888
889void SurfaceFlinger::postComposition()
890{
891    const LayerVector& currentLayers(mDrawingState.layersSortedByZ);
892    const size_t count = currentLayers.size();
893    for (size_t i=0 ; i<count ; i++) {
894        currentLayers[i]->onPostComposition();
895    }
896}
897
898void SurfaceFlinger::rebuildLayerStacks() {
899    // rebuild the visible layer list per screen
900    if (CC_UNLIKELY(mVisibleRegionsDirty)) {
901        ATRACE_CALL();
902        mVisibleRegionsDirty = false;
903        invalidateHwcGeometry();
904
905        const LayerVector& currentLayers(mDrawingState.layersSortedByZ);
906        for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
907            Region opaqueRegion;
908            Region dirtyRegion;
909            Vector< sp<LayerBase> > layersSortedByZ;
910            const sp<DisplayDevice>& hw(mDisplays[dpy]);
911            const Transform& tr(hw->getTransform());
912            const Rect bounds(hw->getBounds());
913            if (hw->canDraw()) {
914                SurfaceFlinger::computeVisibleRegions(currentLayers,
915                        hw->getLayerStack(), dirtyRegion, opaqueRegion);
916
917                const size_t count = currentLayers.size();
918                for (size_t i=0 ; i<count ; i++) {
919                    const sp<LayerBase>& layer(currentLayers[i]);
920                    const Layer::State& s(layer->drawingState());
921                    if (s.layerStack == hw->getLayerStack()) {
922                        Region drawRegion(tr.transform(
923                                layer->visibleNonTransparentRegion));
924                        drawRegion.andSelf(bounds);
925                        if (!drawRegion.isEmpty()) {
926                            layersSortedByZ.add(layer);
927                        }
928                    }
929                }
930            }
931            hw->setVisibleLayersSortedByZ(layersSortedByZ);
932            hw->undefinedRegion.set(bounds);
933            hw->undefinedRegion.subtractSelf(tr.transform(opaqueRegion));
934            hw->dirtyRegion.orSelf(dirtyRegion);
935        }
936    }
937}
938
939void SurfaceFlinger::setUpHWComposer() {
940    HWComposer& hwc(getHwComposer());
941    if (hwc.initCheck() == NO_ERROR) {
942        // build the h/w work list
943        if (CC_UNLIKELY(mHwWorkListDirty)) {
944            mHwWorkListDirty = false;
945            for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
946                sp<const DisplayDevice> hw(mDisplays[dpy]);
947                const int32_t id = hw->getHwcDisplayId();
948                if (id >= 0) {
949                    const Vector< sp<LayerBase> >& currentLayers(
950                        hw->getVisibleLayersSortedByZ());
951                    const size_t count = currentLayers.size();
952                    if (hwc.createWorkList(id, count) == NO_ERROR) {
953                        HWComposer::LayerListIterator cur = hwc.begin(id);
954                        const HWComposer::LayerListIterator end = hwc.end(id);
955                        for (size_t i=0 ; cur!=end && i<count ; ++i, ++cur) {
956                            const sp<LayerBase>& layer(currentLayers[i]);
957                            layer->setGeometry(hw, *cur);
958                            if (mDebugDisableHWC || mDebugRegion) {
959                                cur->setSkip(true);
960                            }
961                        }
962                    }
963                }
964            }
965        }
966
967        // set the per-frame data
968        for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
969            sp<const DisplayDevice> hw(mDisplays[dpy]);
970            const int32_t id = hw->getHwcDisplayId();
971            if (id >= 0) {
972                const Vector< sp<LayerBase> >& currentLayers(
973                    hw->getVisibleLayersSortedByZ());
974                const size_t count = currentLayers.size();
975                HWComposer::LayerListIterator cur = hwc.begin(id);
976                const HWComposer::LayerListIterator end = hwc.end(id);
977                for (size_t i=0 ; cur!=end && i<count ; ++i, ++cur) {
978                    /*
979                     * update the per-frame h/w composer data for each layer
980                     * and build the transparent region of the FB
981                     */
982                    const sp<LayerBase>& layer(currentLayers[i]);
983                    layer->setPerFrameData(hw, *cur);
984                }
985            }
986        }
987
988        status_t err = hwc.prepare();
989        ALOGE_IF(err, "HWComposer::prepare failed (%s)", strerror(-err));
990    }
991}
992
993void SurfaceFlinger::doComposition() {
994    ATRACE_CALL();
995    const bool repaintEverything = android_atomic_and(0, &mRepaintEverything);
996    for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
997        const sp<DisplayDevice>& hw(mDisplays[dpy]);
998        if (hw->canDraw()) {
999            // transform the dirty region into this screen's coordinate space
1000            const Region dirtyRegion(hw->getDirtyRegion(repaintEverything));
1001            if (!dirtyRegion.isEmpty()) {
1002                // repaint the framebuffer (if needed)
1003                doDisplayComposition(hw, dirtyRegion);
1004            }
1005            hw->dirtyRegion.clear();
1006            hw->flip(hw->swapRegion);
1007            hw->swapRegion.clear();
1008        }
1009        // inform the h/w that we're done compositing
1010        hw->compositionComplete();
1011    }
1012    postFramebuffer();
1013}
1014
1015void SurfaceFlinger::postFramebuffer()
1016{
1017    ATRACE_CALL();
1018
1019    const nsecs_t now = systemTime();
1020    mDebugInSwapBuffers = now;
1021
1022    HWComposer& hwc(getHwComposer());
1023    if (hwc.initCheck() == NO_ERROR) {
1024        if (!hwc.supportsFramebufferTarget()) {
1025            // EGL spec says:
1026            //   "surface must be bound to the calling thread's current context,
1027            //    for the current rendering API."
1028            DisplayDevice::makeCurrent(mEGLDisplay,
1029                    getDefaultDisplayDevice(), mEGLContext);
1030        }
1031        hwc.commit();
1032    }
1033
1034    for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
1035        sp<const DisplayDevice> hw(mDisplays[dpy]);
1036        const Vector< sp<LayerBase> >& currentLayers(hw->getVisibleLayersSortedByZ());
1037        hw->onSwapBuffersCompleted(hwc);
1038        const size_t count = currentLayers.size();
1039        int32_t id = hw->getHwcDisplayId();
1040        if (id >=0 && hwc.initCheck() == NO_ERROR) {
1041            HWComposer::LayerListIterator cur = hwc.begin(id);
1042            const HWComposer::LayerListIterator end = hwc.end(id);
1043            for (size_t i = 0; cur != end && i < count; ++i, ++cur) {
1044                currentLayers[i]->onLayerDisplayed(hw, &*cur);
1045            }
1046        } else {
1047            for (size_t i = 0; i < count; i++) {
1048                currentLayers[i]->onLayerDisplayed(hw, NULL);
1049            }
1050        }
1051    }
1052
1053    mLastSwapBufferTime = systemTime() - now;
1054    mDebugInSwapBuffers = 0;
1055}
1056
1057void SurfaceFlinger::handleTransaction(uint32_t transactionFlags)
1058{
1059    ATRACE_CALL();
1060
1061    Mutex::Autolock _l(mStateLock);
1062    const nsecs_t now = systemTime();
1063    mDebugInTransaction = now;
1064
1065    // Here we're guaranteed that some transaction flags are set
1066    // so we can call handleTransactionLocked() unconditionally.
1067    // We call getTransactionFlags(), which will also clear the flags,
1068    // with mStateLock held to guarantee that mCurrentState won't change
1069    // until the transaction is committed.
1070
1071    transactionFlags = getTransactionFlags(eTransactionMask);
1072    handleTransactionLocked(transactionFlags);
1073
1074    mLastTransactionTime = systemTime() - now;
1075    mDebugInTransaction = 0;
1076    invalidateHwcGeometry();
1077    // here the transaction has been committed
1078}
1079
1080void SurfaceFlinger::handleTransactionLocked(uint32_t transactionFlags)
1081{
1082    const LayerVector& currentLayers(mCurrentState.layersSortedByZ);
1083    const size_t count = currentLayers.size();
1084
1085    /*
1086     * Traversal of the children
1087     * (perform the transaction for each of them if needed)
1088     */
1089
1090    if (transactionFlags & eTraversalNeeded) {
1091        for (size_t i=0 ; i<count ; i++) {
1092            const sp<LayerBase>& layer = currentLayers[i];
1093            uint32_t trFlags = layer->getTransactionFlags(eTransactionNeeded);
1094            if (!trFlags) continue;
1095
1096            const uint32_t flags = layer->doTransaction(0);
1097            if (flags & Layer::eVisibleRegion)
1098                mVisibleRegionsDirty = true;
1099        }
1100    }
1101
1102    /*
1103     * Perform display own transactions if needed
1104     */
1105
1106    if (transactionFlags & eDisplayTransactionNeeded) {
1107        // here we take advantage of Vector's copy-on-write semantics to
1108        // improve performance by skipping the transaction entirely when
1109        // know that the lists are identical
1110        const KeyedVector<  wp<IBinder>, DisplayDeviceState>& curr(mCurrentState.displays);
1111        const KeyedVector<  wp<IBinder>, DisplayDeviceState>& draw(mDrawingState.displays);
1112        if (!curr.isIdenticalTo(draw)) {
1113            mVisibleRegionsDirty = true;
1114            const size_t cc = curr.size();
1115                  size_t dc = draw.size();
1116
1117            // find the displays that were removed
1118            // (ie: in drawing state but not in current state)
1119            // also handle displays that changed
1120            // (ie: displays that are in both lists)
1121            for (size_t i=0 ; i<dc ; i++) {
1122                const ssize_t j = curr.indexOfKey(draw.keyAt(i));
1123                if (j < 0) {
1124                    // in drawing state but not in current state
1125                    if (!draw[i].isMainDisplay()) {
1126                        // Call makeCurrent() on the primary display so we can
1127                        // be sure that nothing associated with this display
1128                        // is current.
1129                        const sp<const DisplayDevice>& hw(getDefaultDisplayDevice());
1130                        DisplayDevice::makeCurrent(mEGLDisplay, hw, mEGLContext);
1131                        mDisplays.removeItem(draw.keyAt(i));
1132                        getHwComposer().disconnectDisplay(draw[i].type);
1133                    } else {
1134                        ALOGW("trying to remove the main display");
1135                    }
1136                } else {
1137                    // this display is in both lists. see if something changed.
1138                    const DisplayDeviceState& state(curr[j]);
1139                    const wp<IBinder>& display(curr.keyAt(j));
1140                    if (state.surface->asBinder() != draw[i].surface->asBinder()) {
1141                        // changing the surface is like destroying and
1142                        // recreating the DisplayDevice, so we just remove it
1143                        // from the drawing state, so that it get re-added
1144                        // below.
1145                        mDisplays.removeItem(display);
1146                        mDrawingState.displays.removeItemsAt(i);
1147                        dc--; i--;
1148                        // at this point we must loop to the next item
1149                        continue;
1150                    }
1151
1152                    const sp<DisplayDevice>& disp(getDisplayDevice(display));
1153                    if (disp != NULL) {
1154                        if (state.layerStack != draw[i].layerStack) {
1155                            disp->setLayerStack(state.layerStack);
1156                        }
1157                        if ((state.orientation != draw[i].orientation)
1158                                || (state.viewport != draw[i].viewport)
1159                                || (state.frame != draw[i].frame))
1160                        {
1161                            disp->setProjection(state.orientation,
1162                                    state.viewport, state.frame);
1163                        }
1164
1165                        // Walk through all the layers in currentLayers,
1166                        // and update their transform hint.
1167                        //
1168                        // TODO: we could be much more clever about which
1169                        // layers we touch and how often we do these updates
1170                        // (e.g. only touch the layers associated with this
1171                        // display, and only on a rotation).
1172                        for (size_t i = 0; i < count; i++) {
1173                            const sp<LayerBase>& layerBase = currentLayers[i];
1174                            layerBase->updateTransformHint();
1175                        }
1176                    }
1177                }
1178            }
1179
1180            // find displays that were added
1181            // (ie: in current state but not in drawing state)
1182            for (size_t i=0 ; i<cc ; i++) {
1183                if (draw.indexOfKey(curr.keyAt(i)) < 0) {
1184                    const DisplayDeviceState& state(curr[i]);
1185
1186                    sp<FramebufferSurface> fbs;
1187                    sp<SurfaceTextureClient> stc;
1188                    if (!state.isVirtualDisplay()) {
1189
1190                        ALOGE_IF(state.surface!=NULL,
1191                                "adding a supported display, but rendering "
1192                                "surface is provided (%p), ignoring it",
1193                                state.surface.get());
1194
1195                        // for supported (by hwc) displays we provide our
1196                        // own rendering surface
1197                        fbs = new FramebufferSurface(*mHwc, state.type);
1198                        stc = new SurfaceTextureClient(
1199                                static_cast< sp<ISurfaceTexture> >(fbs->getBufferQueue()));
1200                    } else {
1201                        if (state.surface != NULL) {
1202                            stc = new SurfaceTextureClient(state.surface);
1203                        }
1204                    }
1205
1206                    const wp<IBinder>& display(curr.keyAt(i));
1207                    if (stc != NULL) {
1208                        sp<DisplayDevice> hw = new DisplayDevice(this,
1209                                state.type, display, stc, fbs, mEGLConfig);
1210                        hw->setLayerStack(state.layerStack);
1211                        hw->setProjection(state.orientation,
1212                                state.viewport, state.frame);
1213                        hw->setDisplayName(state.displayName);
1214                        mDisplays.add(display, hw);
1215                        if (hw->getDisplayType() < DisplayDevice::NUM_DISPLAY_TYPES) {
1216                            // notify the system that this display is now up
1217                            // (note onScreenAcquired() is safe to call from
1218                            // here because we're in the main thread)
1219                            onScreenAcquired(hw);
1220                        }
1221                    }
1222                }
1223            }
1224        }
1225    }
1226
1227    /*
1228     * Perform our own transaction if needed
1229     */
1230
1231    const LayerVector& previousLayers(mDrawingState.layersSortedByZ);
1232    if (currentLayers.size() > previousLayers.size()) {
1233        // layers have been added
1234        mVisibleRegionsDirty = true;
1235    }
1236
1237    // some layers might have been removed, so
1238    // we need to update the regions they're exposing.
1239    if (mLayersRemoved) {
1240        mLayersRemoved = false;
1241        mVisibleRegionsDirty = true;
1242        const size_t count = previousLayers.size();
1243        for (size_t i=0 ; i<count ; i++) {
1244            const sp<LayerBase>& layer(previousLayers[i]);
1245            if (currentLayers.indexOf(layer) < 0) {
1246                // this layer is not visible anymore
1247                // TODO: we could traverse the tree from front to back and
1248                //       compute the actual visible region
1249                // TODO: we could cache the transformed region
1250                const Layer::State& s(layer->drawingState());
1251                Region visibleReg = s.transform.transform(
1252                        Region(Rect(s.active.w, s.active.h)));
1253                invalidateLayerStack(s.layerStack, visibleReg);
1254            }
1255        }
1256    }
1257
1258    commitTransaction();
1259}
1260
1261void SurfaceFlinger::commitTransaction()
1262{
1263    if (!mLayersPendingRemoval.isEmpty()) {
1264        // Notify removed layers now that they can't be drawn from
1265        for (size_t i = 0; i < mLayersPendingRemoval.size(); i++) {
1266            mLayersPendingRemoval[i]->onRemoved();
1267        }
1268        mLayersPendingRemoval.clear();
1269    }
1270
1271    mDrawingState = mCurrentState;
1272    mTransationPending = false;
1273    mTransactionCV.broadcast();
1274}
1275
1276void SurfaceFlinger::computeVisibleRegions(
1277        const LayerVector& currentLayers, uint32_t layerStack,
1278        Region& outDirtyRegion, Region& outOpaqueRegion)
1279{
1280    ATRACE_CALL();
1281
1282    Region aboveOpaqueLayers;
1283    Region aboveCoveredLayers;
1284    Region dirty;
1285
1286    outDirtyRegion.clear();
1287
1288    size_t i = currentLayers.size();
1289    while (i--) {
1290        const sp<LayerBase>& layer = currentLayers[i];
1291
1292        // start with the whole surface at its current location
1293        const Layer::State& s(layer->drawingState());
1294
1295        // only consider the layers on the given later stack
1296        if (s.layerStack != layerStack)
1297            continue;
1298
1299        /*
1300         * opaqueRegion: area of a surface that is fully opaque.
1301         */
1302        Region opaqueRegion;
1303
1304        /*
1305         * visibleRegion: area of a surface that is visible on screen
1306         * and not fully transparent. This is essentially the layer's
1307         * footprint minus the opaque regions above it.
1308         * Areas covered by a translucent surface are considered visible.
1309         */
1310        Region visibleRegion;
1311
1312        /*
1313         * coveredRegion: area of a surface that is covered by all
1314         * visible regions above it (which includes the translucent areas).
1315         */
1316        Region coveredRegion;
1317
1318        /*
1319         * transparentRegion: area of a surface that is hinted to be completely
1320         * transparent. This is only used to tell when the layer has no visible
1321         * non-transparent regions and can be removed from the layer list. It
1322         * does not affect the visibleRegion of this layer or any layers
1323         * beneath it. The hint may not be correct if apps don't respect the
1324         * SurfaceView restrictions (which, sadly, some don't).
1325         */
1326        Region transparentRegion;
1327
1328
1329        // handle hidden surfaces by setting the visible region to empty
1330        if (CC_LIKELY(layer->isVisible())) {
1331            const bool translucent = !layer->isOpaque();
1332            Rect bounds(layer->computeBounds());
1333            visibleRegion.set(bounds);
1334            if (!visibleRegion.isEmpty()) {
1335                // Remove the transparent area from the visible region
1336                if (translucent) {
1337                    const Transform tr(s.transform);
1338                    if (tr.transformed()) {
1339                        if (tr.preserveRects()) {
1340                            // transform the transparent region
1341                            transparentRegion = tr.transform(s.transparentRegion);
1342                        } else {
1343                            // transformation too complex, can't do the
1344                            // transparent region optimization.
1345                            transparentRegion.clear();
1346                        }
1347                    } else {
1348                        transparentRegion = s.transparentRegion;
1349                    }
1350                }
1351
1352                // compute the opaque region
1353                const int32_t layerOrientation = s.transform.getOrientation();
1354                if (s.alpha==255 && !translucent &&
1355                        ((layerOrientation & Transform::ROT_INVALID) == false)) {
1356                    // the opaque region is the layer's footprint
1357                    opaqueRegion = visibleRegion;
1358                }
1359            }
1360        }
1361
1362        // Clip the covered region to the visible region
1363        coveredRegion = aboveCoveredLayers.intersect(visibleRegion);
1364
1365        // Update aboveCoveredLayers for next (lower) layer
1366        aboveCoveredLayers.orSelf(visibleRegion);
1367
1368        // subtract the opaque region covered by the layers above us
1369        visibleRegion.subtractSelf(aboveOpaqueLayers);
1370
1371        // compute this layer's dirty region
1372        if (layer->contentDirty) {
1373            // we need to invalidate the whole region
1374            dirty = visibleRegion;
1375            // as well, as the old visible region
1376            dirty.orSelf(layer->visibleRegion);
1377            layer->contentDirty = false;
1378        } else {
1379            /* compute the exposed region:
1380             *   the exposed region consists of two components:
1381             *   1) what's VISIBLE now and was COVERED before
1382             *   2) what's EXPOSED now less what was EXPOSED before
1383             *
1384             * note that (1) is conservative, we start with the whole
1385             * visible region but only keep what used to be covered by
1386             * something -- which mean it may have been exposed.
1387             *
1388             * (2) handles areas that were not covered by anything but got
1389             * exposed because of a resize.
1390             */
1391            const Region newExposed = visibleRegion - coveredRegion;
1392            const Region oldVisibleRegion = layer->visibleRegion;
1393            const Region oldCoveredRegion = layer->coveredRegion;
1394            const Region oldExposed = oldVisibleRegion - oldCoveredRegion;
1395            dirty = (visibleRegion&oldCoveredRegion) | (newExposed-oldExposed);
1396        }
1397        dirty.subtractSelf(aboveOpaqueLayers);
1398
1399        // accumulate to the screen dirty region
1400        outDirtyRegion.orSelf(dirty);
1401
1402        // Update aboveOpaqueLayers for next (lower) layer
1403        aboveOpaqueLayers.orSelf(opaqueRegion);
1404
1405        // Store the visible region in screen space
1406        layer->setVisibleRegion(visibleRegion);
1407        layer->setCoveredRegion(coveredRegion);
1408        layer->setVisibleNonTransparentRegion(
1409                visibleRegion.subtract(transparentRegion));
1410    }
1411
1412    outOpaqueRegion = aboveOpaqueLayers;
1413}
1414
1415void SurfaceFlinger::invalidateLayerStack(uint32_t layerStack,
1416        const Region& dirty) {
1417    for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
1418        const sp<DisplayDevice>& hw(mDisplays[dpy]);
1419        if (hw->getLayerStack() == layerStack) {
1420            hw->dirtyRegion.orSelf(dirty);
1421        }
1422    }
1423}
1424
1425void SurfaceFlinger::handlePageFlip()
1426{
1427    Region dirtyRegion;
1428
1429    bool visibleRegions = false;
1430    const LayerVector& currentLayers(mDrawingState.layersSortedByZ);
1431    const size_t count = currentLayers.size();
1432    for (size_t i=0 ; i<count ; i++) {
1433        const sp<LayerBase>& layer(currentLayers[i]);
1434        const Region dirty(layer->latchBuffer(visibleRegions));
1435        const Layer::State& s(layer->drawingState());
1436        invalidateLayerStack(s.layerStack, dirty);
1437    }
1438
1439    mVisibleRegionsDirty |= visibleRegions;
1440}
1441
1442void SurfaceFlinger::invalidateHwcGeometry()
1443{
1444    mHwWorkListDirty = true;
1445}
1446
1447
1448void SurfaceFlinger::doDisplayComposition(const sp<const DisplayDevice>& hw,
1449        const Region& inDirtyRegion)
1450{
1451    Region dirtyRegion(inDirtyRegion);
1452
1453    // compute the invalid region
1454    hw->swapRegion.orSelf(dirtyRegion);
1455
1456    uint32_t flags = hw->getFlags();
1457    if (flags & DisplayDevice::SWAP_RECTANGLE) {
1458        // we can redraw only what's dirty, but since SWAP_RECTANGLE only
1459        // takes a rectangle, we must make sure to update that whole
1460        // rectangle in that case
1461        dirtyRegion.set(hw->swapRegion.bounds());
1462    } else {
1463        if (flags & DisplayDevice::PARTIAL_UPDATES) {
1464            // We need to redraw the rectangle that will be updated
1465            // (pushed to the framebuffer).
1466            // This is needed because PARTIAL_UPDATES only takes one
1467            // rectangle instead of a region (see DisplayDevice::flip())
1468            dirtyRegion.set(hw->swapRegion.bounds());
1469        } else {
1470            // we need to redraw everything (the whole screen)
1471            dirtyRegion.set(hw->bounds());
1472            hw->swapRegion = dirtyRegion;
1473        }
1474    }
1475
1476    doComposeSurfaces(hw, dirtyRegion);
1477
1478    // update the swap region and clear the dirty region
1479    hw->swapRegion.orSelf(dirtyRegion);
1480
1481    // swap buffers (presentation)
1482    hw->swapBuffers(getHwComposer());
1483}
1484
1485void SurfaceFlinger::doComposeSurfaces(const sp<const DisplayDevice>& hw, const Region& dirty)
1486{
1487    const int32_t id = hw->getHwcDisplayId();
1488    HWComposer& hwc(getHwComposer());
1489    HWComposer::LayerListIterator cur = hwc.begin(id);
1490    const HWComposer::LayerListIterator end = hwc.end(id);
1491
1492    const bool hasGlesComposition = hwc.hasGlesComposition(id) || (cur==end);
1493    if (hasGlesComposition) {
1494        DisplayDevice::makeCurrent(mEGLDisplay, hw, mEGLContext);
1495
1496        // set the frame buffer
1497        glMatrixMode(GL_MODELVIEW);
1498        glLoadIdentity();
1499
1500        // Never touch the framebuffer if we don't have any framebuffer layers
1501        const bool hasHwcComposition = hwc.hasHwcComposition(id);
1502        if (hasHwcComposition) {
1503            // when using overlays, we assume a fully transparent framebuffer
1504            // NOTE: we could reduce how much we need to clear, for instance
1505            // remove where there are opaque FB layers. however, on some
1506            // GPUs doing a "clean slate" glClear might be more efficient.
1507            // We'll revisit later if needed.
1508            glClearColor(0, 0, 0, 0);
1509            glClear(GL_COLOR_BUFFER_BIT);
1510        } else {
1511            const Region region(hw->undefinedRegion.intersect(dirty));
1512            // screen is already cleared here
1513            if (!region.isEmpty()) {
1514                // can happen with SurfaceView
1515                drawWormhole(hw, region);
1516            }
1517        }
1518    }
1519
1520    /*
1521     * and then, render the layers targeted at the framebuffer
1522     */
1523
1524    const Vector< sp<LayerBase> >& layers(hw->getVisibleLayersSortedByZ());
1525    const size_t count = layers.size();
1526    const Transform& tr = hw->getTransform();
1527    if (cur != end) {
1528        // we're using h/w composer
1529        for (size_t i=0 ; i<count && cur!=end ; ++i, ++cur) {
1530            const sp<LayerBase>& layer(layers[i]);
1531            const Region clip(dirty.intersect(tr.transform(layer->visibleRegion)));
1532            if (!clip.isEmpty()) {
1533                switch (cur->getCompositionType()) {
1534                    case HWC_OVERLAY: {
1535                        if ((cur->getHints() & HWC_HINT_CLEAR_FB)
1536                                && i
1537                                && layer->isOpaque()
1538                                && hasGlesComposition) {
1539                            // never clear the very first layer since we're
1540                            // guaranteed the FB is already cleared
1541                            layer->clearWithOpenGL(hw, clip);
1542                        }
1543                        break;
1544                    }
1545                    case HWC_FRAMEBUFFER: {
1546                        layer->draw(hw, clip);
1547                        break;
1548                    }
1549                    case HWC_FRAMEBUFFER_TARGET: {
1550                        // this should not happen as the iterator shouldn't
1551                        // let us get there.
1552                        ALOGW("HWC_FRAMEBUFFER_TARGET found in hwc list (index=%d)", i);
1553                        break;
1554                    }
1555                }
1556            }
1557            layer->setAcquireFence(hw, *cur);
1558        }
1559    } else {
1560        // we're not using h/w composer
1561        for (size_t i=0 ; i<count ; ++i) {
1562            const sp<LayerBase>& layer(layers[i]);
1563            const Region clip(dirty.intersect(
1564                    tr.transform(layer->visibleRegion)));
1565            if (!clip.isEmpty()) {
1566                layer->draw(hw, clip);
1567            }
1568        }
1569    }
1570}
1571
1572void SurfaceFlinger::drawWormhole(const sp<const DisplayDevice>& hw,
1573        const Region& region) const
1574{
1575    glDisable(GL_TEXTURE_EXTERNAL_OES);
1576    glDisable(GL_TEXTURE_2D);
1577    glDisable(GL_BLEND);
1578    glColor4f(0,0,0,0);
1579
1580    const int32_t height = hw->getHeight();
1581    Region::const_iterator it = region.begin();
1582    Region::const_iterator const end = region.end();
1583    while (it != end) {
1584        const Rect& r = *it++;
1585        GLfloat vertices[][2] = {
1586                { r.left,  height - r.top },
1587                { r.left,  height - r.bottom },
1588                { r.right, height - r.bottom },
1589                { r.right, height - r.top }
1590        };
1591        glVertexPointer(2, GL_FLOAT, 0, vertices);
1592        glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
1593    }
1594}
1595
1596ssize_t SurfaceFlinger::addClientLayer(const sp<Client>& client,
1597        const sp<LayerBaseClient>& lbc)
1598{
1599    // attach this layer to the client
1600    size_t name = client->attachLayer(lbc);
1601
1602    // add this layer to the current state list
1603    Mutex::Autolock _l(mStateLock);
1604    mCurrentState.layersSortedByZ.add(lbc);
1605
1606    return ssize_t(name);
1607}
1608
1609status_t SurfaceFlinger::removeLayer(const sp<LayerBase>& layer)
1610{
1611    Mutex::Autolock _l(mStateLock);
1612    status_t err = purgatorizeLayer_l(layer);
1613    if (err == NO_ERROR)
1614        setTransactionFlags(eTransactionNeeded);
1615    return err;
1616}
1617
1618status_t SurfaceFlinger::removeLayer_l(const sp<LayerBase>& layerBase)
1619{
1620    ssize_t index = mCurrentState.layersSortedByZ.remove(layerBase);
1621    if (index >= 0) {
1622        mLayersRemoved = true;
1623        return NO_ERROR;
1624    }
1625    return status_t(index);
1626}
1627
1628status_t SurfaceFlinger::purgatorizeLayer_l(const sp<LayerBase>& layerBase)
1629{
1630    // First add the layer to the purgatory list, which makes sure it won't
1631    // go away, then remove it from the main list (through a transaction).
1632    ssize_t err = removeLayer_l(layerBase);
1633    if (err >= 0) {
1634        mLayerPurgatory.add(layerBase);
1635    }
1636
1637    mLayersPendingRemoval.push(layerBase);
1638
1639    // it's possible that we don't find a layer, because it might
1640    // have been destroyed already -- this is not technically an error
1641    // from the user because there is a race between Client::destroySurface(),
1642    // ~Client() and ~ISurface().
1643    return (err == NAME_NOT_FOUND) ? status_t(NO_ERROR) : err;
1644}
1645
1646uint32_t SurfaceFlinger::peekTransactionFlags(uint32_t flags)
1647{
1648    return android_atomic_release_load(&mTransactionFlags);
1649}
1650
1651uint32_t SurfaceFlinger::getTransactionFlags(uint32_t flags)
1652{
1653    return android_atomic_and(~flags, &mTransactionFlags) & flags;
1654}
1655
1656uint32_t SurfaceFlinger::setTransactionFlags(uint32_t flags)
1657{
1658    uint32_t old = android_atomic_or(flags, &mTransactionFlags);
1659    if ((old & flags)==0) { // wake the server up
1660        signalTransaction();
1661    }
1662    return old;
1663}
1664
1665void SurfaceFlinger::setTransactionState(
1666        const Vector<ComposerState>& state,
1667        const Vector<DisplayState>& displays,
1668        uint32_t flags)
1669{
1670    Mutex::Autolock _l(mStateLock);
1671    uint32_t transactionFlags = 0;
1672
1673    size_t count = displays.size();
1674    for (size_t i=0 ; i<count ; i++) {
1675        const DisplayState& s(displays[i]);
1676        transactionFlags |= setDisplayStateLocked(s);
1677    }
1678
1679    count = state.size();
1680    for (size_t i=0 ; i<count ; i++) {
1681        const ComposerState& s(state[i]);
1682        sp<Client> client( static_cast<Client *>(s.client.get()) );
1683        transactionFlags |= setClientStateLocked(client, s.state);
1684    }
1685
1686    if (transactionFlags) {
1687        // this triggers the transaction
1688        setTransactionFlags(transactionFlags);
1689
1690        // if this is a synchronous transaction, wait for it to take effect
1691        // before returning.
1692        if (flags & eSynchronous) {
1693            mTransationPending = true;
1694        }
1695        while (mTransationPending) {
1696            status_t err = mTransactionCV.waitRelative(mStateLock, s2ns(5));
1697            if (CC_UNLIKELY(err != NO_ERROR)) {
1698                // just in case something goes wrong in SF, return to the
1699                // called after a few seconds.
1700                ALOGW_IF(err == TIMED_OUT, "closeGlobalTransaction timed out!");
1701                mTransationPending = false;
1702                break;
1703            }
1704        }
1705    }
1706}
1707
1708uint32_t SurfaceFlinger::setDisplayStateLocked(const DisplayState& s)
1709{
1710    ssize_t dpyIdx = mCurrentState.displays.indexOfKey(s.token);
1711    if (dpyIdx < 0)
1712        return 0;
1713
1714    uint32_t flags = 0;
1715    DisplayDeviceState& disp(mCurrentState.displays.editValueAt(dpyIdx));
1716    if (disp.isValid()) {
1717        const uint32_t what = s.what;
1718        if (what & DisplayState::eSurfaceChanged) {
1719            if (disp.surface->asBinder() != s.surface->asBinder()) {
1720                disp.surface = s.surface;
1721                flags |= eDisplayTransactionNeeded;
1722            }
1723        }
1724        if (what & DisplayState::eLayerStackChanged) {
1725            if (disp.layerStack != s.layerStack) {
1726                disp.layerStack = s.layerStack;
1727                flags |= eDisplayTransactionNeeded;
1728            }
1729        }
1730        if (what & DisplayState::eDisplayProjectionChanged) {
1731            if (disp.orientation != s.orientation) {
1732                disp.orientation = s.orientation;
1733                flags |= eDisplayTransactionNeeded;
1734            }
1735            if (disp.frame != s.frame) {
1736                disp.frame = s.frame;
1737                flags |= eDisplayTransactionNeeded;
1738            }
1739            if (disp.viewport != s.viewport) {
1740                disp.viewport = s.viewport;
1741                flags |= eDisplayTransactionNeeded;
1742            }
1743        }
1744    }
1745    return flags;
1746}
1747
1748uint32_t SurfaceFlinger::setClientStateLocked(
1749        const sp<Client>& client,
1750        const layer_state_t& s)
1751{
1752    uint32_t flags = 0;
1753    sp<LayerBaseClient> layer(client->getLayerUser(s.surface));
1754    if (layer != 0) {
1755        const uint32_t what = s.what;
1756        if (what & layer_state_t::ePositionChanged) {
1757            if (layer->setPosition(s.x, s.y))
1758                flags |= eTraversalNeeded;
1759        }
1760        if (what & layer_state_t::eLayerChanged) {
1761            // NOTE: index needs to be calculated before we update the state
1762            ssize_t idx = mCurrentState.layersSortedByZ.indexOf(layer);
1763            if (layer->setLayer(s.z)) {
1764                mCurrentState.layersSortedByZ.removeAt(idx);
1765                mCurrentState.layersSortedByZ.add(layer);
1766                // we need traversal (state changed)
1767                // AND transaction (list changed)
1768                flags |= eTransactionNeeded|eTraversalNeeded;
1769            }
1770        }
1771        if (what & layer_state_t::eSizeChanged) {
1772            if (layer->setSize(s.w, s.h)) {
1773                flags |= eTraversalNeeded;
1774            }
1775        }
1776        if (what & layer_state_t::eAlphaChanged) {
1777            if (layer->setAlpha(uint8_t(255.0f*s.alpha+0.5f)))
1778                flags |= eTraversalNeeded;
1779        }
1780        if (what & layer_state_t::eMatrixChanged) {
1781            if (layer->setMatrix(s.matrix))
1782                flags |= eTraversalNeeded;
1783        }
1784        if (what & layer_state_t::eTransparentRegionChanged) {
1785            if (layer->setTransparentRegionHint(s.transparentRegion))
1786                flags |= eTraversalNeeded;
1787        }
1788        if (what & layer_state_t::eVisibilityChanged) {
1789            if (layer->setFlags(s.flags, s.mask))
1790                flags |= eTraversalNeeded;
1791        }
1792        if (what & layer_state_t::eCropChanged) {
1793            if (layer->setCrop(s.crop))
1794                flags |= eTraversalNeeded;
1795        }
1796        if (what & layer_state_t::eLayerStackChanged) {
1797            // NOTE: index needs to be calculated before we update the state
1798            ssize_t idx = mCurrentState.layersSortedByZ.indexOf(layer);
1799            if (layer->setLayerStack(s.layerStack)) {
1800                mCurrentState.layersSortedByZ.removeAt(idx);
1801                mCurrentState.layersSortedByZ.add(layer);
1802                // we need traversal (state changed)
1803                // AND transaction (list changed)
1804                flags |= eTransactionNeeded|eTraversalNeeded;
1805            }
1806        }
1807    }
1808    return flags;
1809}
1810
1811sp<ISurface> SurfaceFlinger::createLayer(
1812        ISurfaceComposerClient::surface_data_t* params,
1813        const String8& name,
1814        const sp<Client>& client,
1815       uint32_t w, uint32_t h, PixelFormat format,
1816        uint32_t flags)
1817{
1818    sp<LayerBaseClient> layer;
1819    sp<ISurface> surfaceHandle;
1820
1821    if (int32_t(w|h) < 0) {
1822        ALOGE("createLayer() failed, w or h is negative (w=%d, h=%d)",
1823                int(w), int(h));
1824        return surfaceHandle;
1825    }
1826
1827    //ALOGD("createLayer for (%d x %d), name=%s", w, h, name.string());
1828    switch (flags & ISurfaceComposerClient::eFXSurfaceMask) {
1829        case ISurfaceComposerClient::eFXSurfaceNormal:
1830            layer = createNormalLayer(client, w, h, flags, format);
1831            break;
1832        case ISurfaceComposerClient::eFXSurfaceBlur:
1833        case ISurfaceComposerClient::eFXSurfaceDim:
1834            layer = createDimLayer(client, w, h, flags);
1835            break;
1836        case ISurfaceComposerClient::eFXSurfaceScreenshot:
1837            layer = createScreenshotLayer(client, w, h, flags);
1838            break;
1839    }
1840
1841    if (layer != 0) {
1842        layer->initStates(w, h, flags);
1843        layer->setName(name);
1844        ssize_t token = addClientLayer(client, layer);
1845        surfaceHandle = layer->getSurface();
1846        if (surfaceHandle != 0) {
1847            params->token = token;
1848            params->identity = layer->getIdentity();
1849        }
1850        setTransactionFlags(eTransactionNeeded);
1851    }
1852
1853    return surfaceHandle;
1854}
1855
1856sp<Layer> SurfaceFlinger::createNormalLayer(
1857        const sp<Client>& client,
1858        uint32_t w, uint32_t h, uint32_t flags,
1859        PixelFormat& format)
1860{
1861    // initialize the surfaces
1862    switch (format) {
1863    case PIXEL_FORMAT_TRANSPARENT:
1864    case PIXEL_FORMAT_TRANSLUCENT:
1865        format = PIXEL_FORMAT_RGBA_8888;
1866        break;
1867    case PIXEL_FORMAT_OPAQUE:
1868#ifdef NO_RGBX_8888
1869        format = PIXEL_FORMAT_RGB_565;
1870#else
1871        format = PIXEL_FORMAT_RGBX_8888;
1872#endif
1873        break;
1874    }
1875
1876#ifdef NO_RGBX_8888
1877    if (format == PIXEL_FORMAT_RGBX_8888)
1878        format = PIXEL_FORMAT_RGBA_8888;
1879#endif
1880
1881    sp<Layer> layer = new Layer(this, client);
1882    status_t err = layer->setBuffers(w, h, format, flags);
1883    if (CC_LIKELY(err != NO_ERROR)) {
1884        ALOGE("createNormalLayer() failed (%s)", strerror(-err));
1885        layer.clear();
1886    }
1887    return layer;
1888}
1889
1890sp<LayerDim> SurfaceFlinger::createDimLayer(
1891        const sp<Client>& client,
1892        uint32_t w, uint32_t h, uint32_t flags)
1893{
1894    sp<LayerDim> layer = new LayerDim(this, client);
1895    return layer;
1896}
1897
1898sp<LayerScreenshot> SurfaceFlinger::createScreenshotLayer(
1899        const sp<Client>& client,
1900        uint32_t w, uint32_t h, uint32_t flags)
1901{
1902    sp<LayerScreenshot> layer = new LayerScreenshot(this, client);
1903    return layer;
1904}
1905
1906status_t SurfaceFlinger::onLayerRemoved(const sp<Client>& client, SurfaceID sid)
1907{
1908    /*
1909     * called by the window manager, when a surface should be marked for
1910     * destruction.
1911     *
1912     * The surface is removed from the current and drawing lists, but placed
1913     * in the purgatory queue, so it's not destroyed right-away (we need
1914     * to wait for all client's references to go away first).
1915     */
1916
1917    status_t err = NAME_NOT_FOUND;
1918    Mutex::Autolock _l(mStateLock);
1919    sp<LayerBaseClient> layer = client->getLayerUser(sid);
1920
1921    if (layer != 0) {
1922        err = purgatorizeLayer_l(layer);
1923        if (err == NO_ERROR) {
1924            setTransactionFlags(eTransactionNeeded);
1925        }
1926    }
1927    return err;
1928}
1929
1930status_t SurfaceFlinger::onLayerDestroyed(const wp<LayerBaseClient>& layer)
1931{
1932    // called by ~ISurface() when all references are gone
1933    status_t err = NO_ERROR;
1934    sp<LayerBaseClient> l(layer.promote());
1935    if (l != NULL) {
1936        Mutex::Autolock _l(mStateLock);
1937        err = removeLayer_l(l);
1938        if (err == NAME_NOT_FOUND) {
1939            // The surface wasn't in the current list, which means it was
1940            // removed already, which means it is in the purgatory,
1941            // and need to be removed from there.
1942            ssize_t idx = mLayerPurgatory.remove(l);
1943            ALOGE_IF(idx < 0,
1944                    "layer=%p is not in the purgatory list", l.get());
1945        }
1946        ALOGE_IF(err<0 && err != NAME_NOT_FOUND,
1947                "error removing layer=%p (%s)", l.get(), strerror(-err));
1948    }
1949    return err;
1950}
1951
1952// ---------------------------------------------------------------------------
1953
1954void SurfaceFlinger::onInitializeDisplays() {
1955    // reset screen orientation
1956    Vector<ComposerState> state;
1957    Vector<DisplayState> displays;
1958    DisplayState d;
1959    d.what = DisplayState::eDisplayProjectionChanged;
1960    d.token = mDefaultDisplays[DisplayDevice::DISPLAY_PRIMARY];
1961    d.orientation = DisplayState::eOrientationDefault;
1962    d.frame.makeInvalid();
1963    d.viewport.makeInvalid();
1964    displays.add(d);
1965    setTransactionState(state, displays, 0);
1966    onScreenAcquired(getDefaultDisplayDevice());
1967}
1968
1969void SurfaceFlinger::initializeDisplays() {
1970    class MessageScreenInitialized : public MessageBase {
1971        SurfaceFlinger* flinger;
1972    public:
1973        MessageScreenInitialized(SurfaceFlinger* flinger) : flinger(flinger) { }
1974        virtual bool handler() {
1975            flinger->onInitializeDisplays();
1976            return true;
1977        }
1978    };
1979    sp<MessageBase> msg = new MessageScreenInitialized(this);
1980    postMessageAsync(msg);  // we may be called from main thread, use async message
1981}
1982
1983
1984void SurfaceFlinger::onScreenAcquired(const sp<const DisplayDevice>& hw) {
1985    ALOGD("Screen acquired, type=%d flinger=%p", hw->getDisplayType(), this);
1986    if (hw->isScreenAcquired()) {
1987        // this is expected, e.g. when power manager wakes up during boot
1988        ALOGD(" screen was previously acquired");
1989        return;
1990    }
1991
1992    hw->acquireScreen();
1993    int32_t type = hw->getDisplayType();
1994    if (type < DisplayDevice::NUM_DISPLAY_TYPES) {
1995        // built-in display, tell the HWC
1996        getHwComposer().acquire(type);
1997
1998        if (type == DisplayDevice::DISPLAY_PRIMARY) {
1999            // FIXME: eventthread only knows about the main display right now
2000            mEventThread->onScreenAcquired();
2001        }
2002    }
2003    mVisibleRegionsDirty = true;
2004    repaintEverything();
2005}
2006
2007void SurfaceFlinger::onScreenReleased(const sp<const DisplayDevice>& hw) {
2008    ALOGD("Screen released, type=%d flinger=%p", hw->getDisplayType(), this);
2009    if (!hw->isScreenAcquired()) {
2010        ALOGD(" screen was previously released");
2011        return;
2012    }
2013
2014    hw->releaseScreen();
2015    int32_t type = hw->getDisplayType();
2016    if (type < DisplayDevice::NUM_DISPLAY_TYPES) {
2017        if (type == DisplayDevice::DISPLAY_PRIMARY) {
2018            // FIXME: eventthread only knows about the main display right now
2019            mEventThread->onScreenReleased();
2020        }
2021
2022        // built-in display, tell the HWC
2023        getHwComposer().release(type);
2024    }
2025    mVisibleRegionsDirty = true;
2026    // from this point on, SF will stop drawing on this display
2027}
2028
2029void SurfaceFlinger::unblank(const sp<IBinder>& display) {
2030    class MessageScreenAcquired : public MessageBase {
2031        SurfaceFlinger* mFlinger;
2032        const sp<DisplayDevice>& mHw;
2033    public:
2034        MessageScreenAcquired(SurfaceFlinger* flinger,
2035                const sp<DisplayDevice>& hw) : mFlinger(flinger), mHw(hw) { }
2036        virtual bool handler() {
2037            mFlinger->onScreenAcquired(mHw);
2038            return true;
2039        }
2040    };
2041    const sp<DisplayDevice>& hw = getDisplayDevice(display);
2042    if (hw == NULL) {
2043        ALOGE("Attempt to unblank null display %p", display.get());
2044    } else if (hw->getDisplayType() >= DisplayDevice::NUM_DISPLAY_TYPES) {
2045        ALOGW("Attempt to unblank virtual display");
2046    } else {
2047        sp<MessageBase> msg = new MessageScreenAcquired(this, hw);
2048        postMessageSync(msg);
2049    }
2050}
2051
2052void SurfaceFlinger::blank(const sp<IBinder>& display) {
2053    class MessageScreenReleased : public MessageBase {
2054        SurfaceFlinger* mFlinger;
2055        const sp<DisplayDevice>& mHw;
2056    public:
2057        MessageScreenReleased(SurfaceFlinger* flinger,
2058                const sp<DisplayDevice>& hw) : mFlinger(flinger), mHw(hw) { }
2059        virtual bool handler() {
2060            mFlinger->onScreenReleased(mHw);
2061            return true;
2062        }
2063    };
2064    const sp<DisplayDevice>& hw = getDisplayDevice(display);
2065    if (hw == NULL) {
2066        ALOGE("Attempt to blank null display %p", display.get());
2067    } else if (hw->getDisplayType() >= DisplayDevice::NUM_DISPLAY_TYPES) {
2068        ALOGW("Attempt to blank virtual display");
2069    } else {
2070        sp<MessageBase> msg = new MessageScreenReleased(this, hw);
2071        postMessageSync(msg);
2072    }
2073}
2074
2075// ---------------------------------------------------------------------------
2076
2077status_t SurfaceFlinger::dump(int fd, const Vector<String16>& args)
2078{
2079    const size_t SIZE = 4096;
2080    char buffer[SIZE];
2081    String8 result;
2082
2083    if (!PermissionCache::checkCallingPermission(sDump)) {
2084        snprintf(buffer, SIZE, "Permission Denial: "
2085                "can't dump SurfaceFlinger from pid=%d, uid=%d\n",
2086                IPCThreadState::self()->getCallingPid(),
2087                IPCThreadState::self()->getCallingUid());
2088        result.append(buffer);
2089    } else {
2090        // Try to get the main lock, but don't insist if we can't
2091        // (this would indicate SF is stuck, but we want to be able to
2092        // print something in dumpsys).
2093        int retry = 3;
2094        while (mStateLock.tryLock()<0 && --retry>=0) {
2095            usleep(1000000);
2096        }
2097        const bool locked(retry >= 0);
2098        if (!locked) {
2099            snprintf(buffer, SIZE,
2100                    "SurfaceFlinger appears to be unresponsive, "
2101                    "dumping anyways (no locks held)\n");
2102            result.append(buffer);
2103        }
2104
2105        bool dumpAll = true;
2106        size_t index = 0;
2107        size_t numArgs = args.size();
2108        if (numArgs) {
2109            if ((index < numArgs) &&
2110                    (args[index] == String16("--list"))) {
2111                index++;
2112                listLayersLocked(args, index, result, buffer, SIZE);
2113                dumpAll = false;
2114            }
2115
2116            if ((index < numArgs) &&
2117                    (args[index] == String16("--latency"))) {
2118                index++;
2119                dumpStatsLocked(args, index, result, buffer, SIZE);
2120                dumpAll = false;
2121            }
2122
2123            if ((index < numArgs) &&
2124                    (args[index] == String16("--latency-clear"))) {
2125                index++;
2126                clearStatsLocked(args, index, result, buffer, SIZE);
2127                dumpAll = false;
2128            }
2129        }
2130
2131        if (dumpAll) {
2132            dumpAllLocked(result, buffer, SIZE);
2133        }
2134
2135        if (locked) {
2136            mStateLock.unlock();
2137        }
2138    }
2139    write(fd, result.string(), result.size());
2140    return NO_ERROR;
2141}
2142
2143void SurfaceFlinger::listLayersLocked(const Vector<String16>& args, size_t& index,
2144        String8& result, char* buffer, size_t SIZE) const
2145{
2146    const LayerVector& currentLayers = mCurrentState.layersSortedByZ;
2147    const size_t count = currentLayers.size();
2148    for (size_t i=0 ; i<count ; i++) {
2149        const sp<LayerBase>& layer(currentLayers[i]);
2150        snprintf(buffer, SIZE, "%s\n", layer->getName().string());
2151        result.append(buffer);
2152    }
2153}
2154
2155void SurfaceFlinger::dumpStatsLocked(const Vector<String16>& args, size_t& index,
2156        String8& result, char* buffer, size_t SIZE) const
2157{
2158    String8 name;
2159    if (index < args.size()) {
2160        name = String8(args[index]);
2161        index++;
2162    }
2163
2164    const LayerVector& currentLayers = mCurrentState.layersSortedByZ;
2165    const size_t count = currentLayers.size();
2166    for (size_t i=0 ; i<count ; i++) {
2167        const sp<LayerBase>& layer(currentLayers[i]);
2168        if (name.isEmpty()) {
2169            snprintf(buffer, SIZE, "%s\n", layer->getName().string());
2170            result.append(buffer);
2171        }
2172        if (name.isEmpty() || (name == layer->getName())) {
2173            layer->dumpStats(result, buffer, SIZE);
2174        }
2175    }
2176}
2177
2178void SurfaceFlinger::clearStatsLocked(const Vector<String16>& args, size_t& index,
2179        String8& result, char* buffer, size_t SIZE) const
2180{
2181    String8 name;
2182    if (index < args.size()) {
2183        name = String8(args[index]);
2184        index++;
2185    }
2186
2187    const LayerVector& currentLayers = mCurrentState.layersSortedByZ;
2188    const size_t count = currentLayers.size();
2189    for (size_t i=0 ; i<count ; i++) {
2190        const sp<LayerBase>& layer(currentLayers[i]);
2191        if (name.isEmpty() || (name == layer->getName())) {
2192            layer->clearStats();
2193        }
2194    }
2195}
2196
2197/*static*/ void SurfaceFlinger::appendSfConfigString(String8& result)
2198{
2199    static const char* config =
2200            " [sf"
2201#ifdef NO_RGBX_8888
2202            " NO_RGBX_8888"
2203#endif
2204#ifdef HAS_CONTEXT_PRIORITY
2205            " HAS_CONTEXT_PRIORITY"
2206#endif
2207#ifdef NEVER_DEFAULT_TO_ASYNC_MODE
2208            " NEVER_DEFAULT_TO_ASYNC_MODE"
2209#endif
2210#ifdef TARGET_DISABLE_TRIPLE_BUFFERING
2211            " TARGET_DISABLE_TRIPLE_BUFFERING"
2212#endif
2213            "]";
2214    result.append(config);
2215}
2216
2217void SurfaceFlinger::dumpAllLocked(
2218        String8& result, char* buffer, size_t SIZE) const
2219{
2220    // figure out if we're stuck somewhere
2221    const nsecs_t now = systemTime();
2222    const nsecs_t inSwapBuffers(mDebugInSwapBuffers);
2223    const nsecs_t inTransaction(mDebugInTransaction);
2224    nsecs_t inSwapBuffersDuration = (inSwapBuffers) ? now-inSwapBuffers : 0;
2225    nsecs_t inTransactionDuration = (inTransaction) ? now-inTransaction : 0;
2226
2227    /*
2228     * Dump library configuration.
2229     */
2230    result.append("Build configuration:");
2231    appendSfConfigString(result);
2232    appendUiConfigString(result);
2233    appendGuiConfigString(result);
2234    result.append("\n");
2235
2236    /*
2237     * Dump the visible layer list
2238     */
2239    const LayerVector& currentLayers = mCurrentState.layersSortedByZ;
2240    const size_t count = currentLayers.size();
2241    snprintf(buffer, SIZE, "Visible layers (count = %d)\n", count);
2242    result.append(buffer);
2243    for (size_t i=0 ; i<count ; i++) {
2244        const sp<LayerBase>& layer(currentLayers[i]);
2245        layer->dump(result, buffer, SIZE);
2246    }
2247
2248    /*
2249     * Dump the layers in the purgatory
2250     */
2251
2252    const size_t purgatorySize = mLayerPurgatory.size();
2253    snprintf(buffer, SIZE, "Purgatory state (%d entries)\n", purgatorySize);
2254    result.append(buffer);
2255    for (size_t i=0 ; i<purgatorySize ; i++) {
2256        const sp<LayerBase>& layer(mLayerPurgatory.itemAt(i));
2257        layer->shortDump(result, buffer, SIZE);
2258    }
2259
2260    /*
2261     * Dump Display state
2262     */
2263
2264    snprintf(buffer, SIZE, "Displays (%d entries)\n", mDisplays.size());
2265    result.append(buffer);
2266    for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
2267        const sp<const DisplayDevice>& hw(mDisplays[dpy]);
2268        hw->dump(result, buffer, SIZE);
2269    }
2270
2271    /*
2272     * Dump SurfaceFlinger global state
2273     */
2274
2275    snprintf(buffer, SIZE, "SurfaceFlinger global state:\n");
2276    result.append(buffer);
2277
2278    HWComposer& hwc(getHwComposer());
2279    sp<const DisplayDevice> hw(getDefaultDisplayDevice());
2280    const GLExtensions& extensions(GLExtensions::getInstance());
2281    snprintf(buffer, SIZE, "GLES: %s, %s, %s\n",
2282            extensions.getVendor(),
2283            extensions.getRenderer(),
2284            extensions.getVersion());
2285    result.append(buffer);
2286
2287    snprintf(buffer, SIZE, "EGL : %s\n",
2288            eglQueryString(mEGLDisplay, EGL_VERSION_HW_ANDROID));
2289    result.append(buffer);
2290
2291    snprintf(buffer, SIZE, "EXTS: %s\n", extensions.getExtension());
2292    result.append(buffer);
2293
2294    hw->undefinedRegion.dump(result, "undefinedRegion");
2295    snprintf(buffer, SIZE,
2296            "  orientation=%d, canDraw=%d\n",
2297            hw->getOrientation(), hw->canDraw());
2298    result.append(buffer);
2299    snprintf(buffer, SIZE,
2300            "  last eglSwapBuffers() time: %f us\n"
2301            "  last transaction time     : %f us\n"
2302            "  transaction-flags         : %08x\n"
2303            "  refresh-rate              : %f fps\n"
2304            "  x-dpi                     : %f\n"
2305            "  y-dpi                     : %f\n",
2306            mLastSwapBufferTime/1000.0,
2307            mLastTransactionTime/1000.0,
2308            mTransactionFlags,
2309            1e9 / hwc.getRefreshPeriod(HWC_DISPLAY_PRIMARY),
2310            hwc.getDpiX(HWC_DISPLAY_PRIMARY),
2311            hwc.getDpiY(HWC_DISPLAY_PRIMARY));
2312    result.append(buffer);
2313
2314    snprintf(buffer, SIZE, "  eglSwapBuffers time: %f us\n",
2315            inSwapBuffersDuration/1000.0);
2316    result.append(buffer);
2317
2318    snprintf(buffer, SIZE, "  transaction time: %f us\n",
2319            inTransactionDuration/1000.0);
2320    result.append(buffer);
2321
2322    /*
2323     * VSYNC state
2324     */
2325    mEventThread->dump(result, buffer, SIZE);
2326
2327    /*
2328     * Dump HWComposer state
2329     */
2330    snprintf(buffer, SIZE, "h/w composer state:\n");
2331    result.append(buffer);
2332    snprintf(buffer, SIZE, "  h/w composer %s and %s\n",
2333            hwc.initCheck()==NO_ERROR ? "present" : "not present",
2334                    (mDebugDisableHWC || mDebugRegion) ? "disabled" : "enabled");
2335    result.append(buffer);
2336    hwc.dump(result, buffer, SIZE, hw->getVisibleLayersSortedByZ());
2337
2338    /*
2339     * Dump gralloc state
2340     */
2341    const GraphicBufferAllocator& alloc(GraphicBufferAllocator::get());
2342    alloc.dump(result);
2343}
2344
2345bool SurfaceFlinger::startDdmConnection()
2346{
2347    void* libddmconnection_dso =
2348            dlopen("libsurfaceflinger_ddmconnection.so", RTLD_NOW);
2349    if (!libddmconnection_dso) {
2350        return false;
2351    }
2352    void (*DdmConnection_start)(const char* name);
2353    DdmConnection_start =
2354            (typeof DdmConnection_start)dlsym(libddmconnection_dso, "DdmConnection_start");
2355    if (!DdmConnection_start) {
2356        dlclose(libddmconnection_dso);
2357        return false;
2358    }
2359    (*DdmConnection_start)(getServiceName());
2360    return true;
2361}
2362
2363status_t SurfaceFlinger::onTransact(
2364    uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags)
2365{
2366    switch (code) {
2367        case CREATE_CONNECTION:
2368        case SET_TRANSACTION_STATE:
2369        case BOOT_FINISHED:
2370        case BLANK:
2371        case UNBLANK:
2372        {
2373            // codes that require permission check
2374            IPCThreadState* ipc = IPCThreadState::self();
2375            const int pid = ipc->getCallingPid();
2376            const int uid = ipc->getCallingUid();
2377            if ((uid != AID_GRAPHICS) &&
2378                    !PermissionCache::checkPermission(sAccessSurfaceFlinger, pid, uid)) {
2379                ALOGE("Permission Denial: "
2380                        "can't access SurfaceFlinger pid=%d, uid=%d", pid, uid);
2381                return PERMISSION_DENIED;
2382            }
2383            break;
2384        }
2385        case CAPTURE_SCREEN:
2386        {
2387            // codes that require permission check
2388            IPCThreadState* ipc = IPCThreadState::self();
2389            const int pid = ipc->getCallingPid();
2390            const int uid = ipc->getCallingUid();
2391            if ((uid != AID_GRAPHICS) &&
2392                    !PermissionCache::checkPermission(sReadFramebuffer, pid, uid)) {
2393                ALOGE("Permission Denial: "
2394                        "can't read framebuffer pid=%d, uid=%d", pid, uid);
2395                return PERMISSION_DENIED;
2396            }
2397            break;
2398        }
2399    }
2400
2401    status_t err = BnSurfaceComposer::onTransact(code, data, reply, flags);
2402    if (err == UNKNOWN_TRANSACTION || err == PERMISSION_DENIED) {
2403        CHECK_INTERFACE(ISurfaceComposer, data, reply);
2404        if (CC_UNLIKELY(!PermissionCache::checkCallingPermission(sHardwareTest))) {
2405            IPCThreadState* ipc = IPCThreadState::self();
2406            const int pid = ipc->getCallingPid();
2407            const int uid = ipc->getCallingUid();
2408            ALOGE("Permission Denial: "
2409                    "can't access SurfaceFlinger pid=%d, uid=%d", pid, uid);
2410            return PERMISSION_DENIED;
2411        }
2412        int n;
2413        switch (code) {
2414            case 1000: // SHOW_CPU, NOT SUPPORTED ANYMORE
2415            case 1001: // SHOW_FPS, NOT SUPPORTED ANYMORE
2416                return NO_ERROR;
2417            case 1002:  // SHOW_UPDATES
2418                n = data.readInt32();
2419                mDebugRegion = n ? n : (mDebugRegion ? 0 : 1);
2420                invalidateHwcGeometry();
2421                repaintEverything();
2422                return NO_ERROR;
2423            case 1004:{ // repaint everything
2424                repaintEverything();
2425                return NO_ERROR;
2426            }
2427            case 1005:{ // force transaction
2428                setTransactionFlags(
2429                        eTransactionNeeded|
2430                        eDisplayTransactionNeeded|
2431                        eTraversalNeeded);
2432                return NO_ERROR;
2433            }
2434            case 1006:{ // send empty update
2435                signalRefresh();
2436                return NO_ERROR;
2437            }
2438            case 1008:  // toggle use of hw composer
2439                n = data.readInt32();
2440                mDebugDisableHWC = n ? 1 : 0;
2441                invalidateHwcGeometry();
2442                repaintEverything();
2443                return NO_ERROR;
2444            case 1009:  // toggle use of transform hint
2445                n = data.readInt32();
2446                mDebugDisableTransformHint = n ? 1 : 0;
2447                invalidateHwcGeometry();
2448                repaintEverything();
2449                return NO_ERROR;
2450            case 1010:  // interrogate.
2451                reply->writeInt32(0);
2452                reply->writeInt32(0);
2453                reply->writeInt32(mDebugRegion);
2454                reply->writeInt32(0);
2455                reply->writeInt32(mDebugDisableHWC);
2456                return NO_ERROR;
2457            case 1013: {
2458                Mutex::Autolock _l(mStateLock);
2459                sp<const DisplayDevice> hw(getDefaultDisplayDevice());
2460                reply->writeInt32(hw->getPageFlipCount());
2461            }
2462            return NO_ERROR;
2463        }
2464    }
2465    return err;
2466}
2467
2468void SurfaceFlinger::repaintEverything() {
2469    android_atomic_or(1, &mRepaintEverything);
2470    signalTransaction();
2471}
2472
2473// ---------------------------------------------------------------------------
2474
2475status_t SurfaceFlinger::renderScreenToTexture(uint32_t layerStack,
2476        GLuint* textureName, GLfloat* uOut, GLfloat* vOut)
2477{
2478    Mutex::Autolock _l(mStateLock);
2479    return renderScreenToTextureLocked(layerStack, textureName, uOut, vOut);
2480}
2481
2482status_t SurfaceFlinger::renderScreenToTextureLocked(uint32_t layerStack,
2483        GLuint* textureName, GLfloat* uOut, GLfloat* vOut)
2484{
2485    ATRACE_CALL();
2486
2487    if (!GLExtensions::getInstance().haveFramebufferObject())
2488        return INVALID_OPERATION;
2489
2490    // get screen geometry
2491    // FIXME: figure out what it means to have a screenshot texture w/ multi-display
2492    sp<const DisplayDevice> hw(getDefaultDisplayDevice());
2493    const uint32_t hw_w = hw->getWidth();
2494    const uint32_t hw_h = hw->getHeight();
2495    GLfloat u = 1;
2496    GLfloat v = 1;
2497
2498    // make sure to clear all GL error flags
2499    while ( glGetError() != GL_NO_ERROR ) ;
2500
2501    // create a FBO
2502    GLuint name, tname;
2503    glGenTextures(1, &tname);
2504    glBindTexture(GL_TEXTURE_2D, tname);
2505    glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
2506    glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
2507    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB,
2508            hw_w, hw_h, 0, GL_RGB, GL_UNSIGNED_BYTE, 0);
2509    if (glGetError() != GL_NO_ERROR) {
2510        while ( glGetError() != GL_NO_ERROR ) ;
2511        GLint tw = (2 << (31 - clz(hw_w)));
2512        GLint th = (2 << (31 - clz(hw_h)));
2513        glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB,
2514                tw, th, 0, GL_RGB, GL_UNSIGNED_BYTE, 0);
2515        u = GLfloat(hw_w) / tw;
2516        v = GLfloat(hw_h) / th;
2517    }
2518    glGenFramebuffersOES(1, &name);
2519    glBindFramebufferOES(GL_FRAMEBUFFER_OES, name);
2520    glFramebufferTexture2DOES(GL_FRAMEBUFFER_OES,
2521            GL_COLOR_ATTACHMENT0_OES, GL_TEXTURE_2D, tname, 0);
2522
2523    DisplayDevice::setViewportAndProjection(hw);
2524
2525    // redraw the screen entirely...
2526    glDisable(GL_TEXTURE_EXTERNAL_OES);
2527    glDisable(GL_TEXTURE_2D);
2528    glClearColor(0,0,0,1);
2529    glClear(GL_COLOR_BUFFER_BIT);
2530    glMatrixMode(GL_MODELVIEW);
2531    glLoadIdentity();
2532    const Vector< sp<LayerBase> >& layers(hw->getVisibleLayersSortedByZ());
2533    const size_t count = layers.size();
2534    for (size_t i=0 ; i<count ; ++i) {
2535        const sp<LayerBase>& layer(layers[i]);
2536        layer->draw(hw);
2537    }
2538
2539    hw->compositionComplete();
2540
2541    // back to main framebuffer
2542    glBindFramebufferOES(GL_FRAMEBUFFER_OES, 0);
2543    glDeleteFramebuffersOES(1, &name);
2544
2545    *textureName = tname;
2546    *uOut = u;
2547    *vOut = v;
2548    return NO_ERROR;
2549}
2550
2551// ---------------------------------------------------------------------------
2552
2553status_t SurfaceFlinger::captureScreenImplLocked(const sp<IBinder>& display,
2554        sp<IMemoryHeap>* heap,
2555        uint32_t* w, uint32_t* h, PixelFormat* f,
2556        uint32_t sw, uint32_t sh,
2557        uint32_t minLayerZ, uint32_t maxLayerZ)
2558{
2559    ATRACE_CALL();
2560
2561    status_t result = PERMISSION_DENIED;
2562
2563    if (!GLExtensions::getInstance().haveFramebufferObject()) {
2564        return INVALID_OPERATION;
2565    }
2566
2567    // get screen geometry
2568    sp<const DisplayDevice> hw(getDisplayDevice(display));
2569    const uint32_t hw_w = hw->getWidth();
2570    const uint32_t hw_h = hw->getHeight();
2571
2572    // if we have secure windows on this display, never allow the screen capture
2573    if (hw->getSecureLayerVisible()) {
2574        ALOGW("FB is protected: PERMISSION_DENIED");
2575        return PERMISSION_DENIED;
2576    }
2577
2578    if ((sw > hw_w) || (sh > hw_h)) {
2579        ALOGE("size mismatch (%d, %d) > (%d, %d)", sw, sh, hw_w, hw_h);
2580        return BAD_VALUE;
2581    }
2582
2583    sw = (!sw) ? hw_w : sw;
2584    sh = (!sh) ? hw_h : sh;
2585    const size_t size = sw * sh * 4;
2586    const bool filtering = sw != hw_w || sh != hw_h;
2587
2588//    ALOGD("screenshot: sw=%d, sh=%d, minZ=%d, maxZ=%d",
2589//            sw, sh, minLayerZ, maxLayerZ);
2590
2591    // make sure to clear all GL error flags
2592    while ( glGetError() != GL_NO_ERROR ) ;
2593
2594    // create a FBO
2595    GLuint name, tname;
2596    glGenRenderbuffersOES(1, &tname);
2597    glBindRenderbufferOES(GL_RENDERBUFFER_OES, tname);
2598    glRenderbufferStorageOES(GL_RENDERBUFFER_OES, GL_RGBA8_OES, sw, sh);
2599
2600    glGenFramebuffersOES(1, &name);
2601    glBindFramebufferOES(GL_FRAMEBUFFER_OES, name);
2602    glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES,
2603            GL_COLOR_ATTACHMENT0_OES, GL_RENDERBUFFER_OES, tname);
2604
2605    GLenum status = glCheckFramebufferStatusOES(GL_FRAMEBUFFER_OES);
2606
2607    if (status == GL_FRAMEBUFFER_COMPLETE_OES) {
2608
2609        // invert everything, b/c glReadPixel() below will invert the FB
2610        GLint  viewport[4];
2611        glGetIntegerv(GL_VIEWPORT, viewport);
2612        glViewport(0, 0, sw, sh);
2613        glMatrixMode(GL_PROJECTION);
2614        glPushMatrix();
2615        glLoadIdentity();
2616        glOrthof(0, hw_w, hw_h, 0, 0, 1);
2617        glMatrixMode(GL_MODELVIEW);
2618
2619        // redraw the screen entirely...
2620        glClearColor(0,0,0,1);
2621        glClear(GL_COLOR_BUFFER_BIT);
2622
2623        const Vector< sp<LayerBase> >& layers(hw->getVisibleLayersSortedByZ());
2624        const size_t count = layers.size();
2625        for (size_t i=0 ; i<count ; ++i) {
2626            const sp<LayerBase>& layer(layers[i]);
2627            const uint32_t z = layer->drawingState().z;
2628            if (z >= minLayerZ && z <= maxLayerZ) {
2629                if (filtering) layer->setFiltering(true);
2630                layer->draw(hw);
2631                if (filtering) layer->setFiltering(false);
2632            }
2633        }
2634
2635        // check for errors and return screen capture
2636        if (glGetError() != GL_NO_ERROR) {
2637            // error while rendering
2638            result = INVALID_OPERATION;
2639        } else {
2640            // allocate shared memory large enough to hold the
2641            // screen capture
2642            sp<MemoryHeapBase> base(
2643                    new MemoryHeapBase(size, 0, "screen-capture") );
2644            void* const ptr = base->getBase();
2645            if (ptr != MAP_FAILED) {
2646                // capture the screen with glReadPixels()
2647                ScopedTrace _t(ATRACE_TAG, "glReadPixels");
2648                glReadPixels(0, 0, sw, sh, GL_RGBA, GL_UNSIGNED_BYTE, ptr);
2649                if (glGetError() == GL_NO_ERROR) {
2650                    *heap = base;
2651                    *w = sw;
2652                    *h = sh;
2653                    *f = PIXEL_FORMAT_RGBA_8888;
2654                    result = NO_ERROR;
2655                }
2656            } else {
2657                result = NO_MEMORY;
2658            }
2659        }
2660        glViewport(viewport[0], viewport[1], viewport[2], viewport[3]);
2661        glMatrixMode(GL_PROJECTION);
2662        glPopMatrix();
2663        glMatrixMode(GL_MODELVIEW);
2664    } else {
2665        result = BAD_VALUE;
2666    }
2667
2668    // release FBO resources
2669    glBindFramebufferOES(GL_FRAMEBUFFER_OES, 0);
2670    glDeleteRenderbuffersOES(1, &tname);
2671    glDeleteFramebuffersOES(1, &name);
2672
2673    hw->compositionComplete();
2674
2675//    ALOGD("screenshot: result = %s", result<0 ? strerror(result) : "OK");
2676
2677    return result;
2678}
2679
2680
2681status_t SurfaceFlinger::captureScreen(const sp<IBinder>& display,
2682        sp<IMemoryHeap>* heap,
2683        uint32_t* width, uint32_t* height, PixelFormat* format,
2684        uint32_t sw, uint32_t sh,
2685        uint32_t minLayerZ, uint32_t maxLayerZ)
2686{
2687    if (CC_UNLIKELY(display == 0))
2688        return BAD_VALUE;
2689
2690    if (!GLExtensions::getInstance().haveFramebufferObject())
2691        return INVALID_OPERATION;
2692
2693    class MessageCaptureScreen : public MessageBase {
2694        SurfaceFlinger* flinger;
2695        sp<IBinder> display;
2696        sp<IMemoryHeap>* heap;
2697        uint32_t* w;
2698        uint32_t* h;
2699        PixelFormat* f;
2700        uint32_t sw;
2701        uint32_t sh;
2702        uint32_t minLayerZ;
2703        uint32_t maxLayerZ;
2704        status_t result;
2705    public:
2706        MessageCaptureScreen(SurfaceFlinger* flinger, const sp<IBinder>& display,
2707                sp<IMemoryHeap>* heap, uint32_t* w, uint32_t* h, PixelFormat* f,
2708                uint32_t sw, uint32_t sh,
2709                uint32_t minLayerZ, uint32_t maxLayerZ)
2710            : flinger(flinger), display(display),
2711              heap(heap), w(w), h(h), f(f), sw(sw), sh(sh),
2712              minLayerZ(minLayerZ), maxLayerZ(maxLayerZ),
2713              result(PERMISSION_DENIED)
2714        {
2715        }
2716        status_t getResult() const {
2717            return result;
2718        }
2719        virtual bool handler() {
2720            Mutex::Autolock _l(flinger->mStateLock);
2721            result = flinger->captureScreenImplLocked(display,
2722                    heap, w, h, f, sw, sh, minLayerZ, maxLayerZ);
2723            return true;
2724        }
2725    };
2726
2727    sp<MessageBase> msg = new MessageCaptureScreen(this,
2728            display, heap, width, height, format, sw, sh, minLayerZ, maxLayerZ);
2729    status_t res = postMessageSync(msg);
2730    if (res == NO_ERROR) {
2731        res = static_cast<MessageCaptureScreen*>( msg.get() )->getResult();
2732    }
2733    return res;
2734}
2735
2736// ---------------------------------------------------------------------------
2737
2738SurfaceFlinger::LayerVector::LayerVector() {
2739}
2740
2741SurfaceFlinger::LayerVector::LayerVector(const LayerVector& rhs)
2742    : SortedVector<sp<LayerBase> >(rhs) {
2743}
2744
2745int SurfaceFlinger::LayerVector::do_compare(const void* lhs,
2746    const void* rhs) const
2747{
2748    // sort layers per layer-stack, then by z-order and finally by sequence
2749    const sp<LayerBase>& l(*reinterpret_cast<const sp<LayerBase>*>(lhs));
2750    const sp<LayerBase>& r(*reinterpret_cast<const sp<LayerBase>*>(rhs));
2751
2752    uint32_t ls = l->currentState().layerStack;
2753    uint32_t rs = r->currentState().layerStack;
2754    if (ls != rs)
2755        return ls - rs;
2756
2757    uint32_t lz = l->currentState().z;
2758    uint32_t rz = r->currentState().z;
2759    if (lz != rz)
2760        return lz - rz;
2761
2762    return l->sequence - r->sequence;
2763}
2764
2765// ---------------------------------------------------------------------------
2766
2767SurfaceFlinger::DisplayDeviceState::DisplayDeviceState()
2768    : type(DisplayDevice::DISPLAY_ID_INVALID) {
2769}
2770
2771SurfaceFlinger::DisplayDeviceState::DisplayDeviceState(DisplayDevice::DisplayType type)
2772    : type(type), layerStack(0), orientation(0) {
2773    viewport.makeInvalid();
2774    frame.makeInvalid();
2775}
2776
2777// ---------------------------------------------------------------------------
2778
2779}; // namespace android
2780