Home | History | Annotate | Download | only in surfaceflinger
      1 /*
      2  * Copyright (C) 2007 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 #include <stdlib.h>
     18 #include <stdio.h>
     19 #include <stdint.h>
     20 #include <unistd.h>
     21 #include <fcntl.h>
     22 #include <errno.h>
     23 #include <math.h>
     24 #include <limits.h>
     25 #include <sys/types.h>
     26 #include <sys/stat.h>
     27 #include <sys/ioctl.h>
     28 
     29 #include <cutils/log.h>
     30 #include <cutils/properties.h>
     31 
     32 #include <binder/IPCThreadState.h>
     33 #include <binder/IServiceManager.h>
     34 #include <binder/MemoryHeapBase.h>
     35 
     36 #include <utils/String8.h>
     37 #include <utils/String16.h>
     38 #include <utils/StopWatch.h>
     39 
     40 #include <ui/GraphicBufferAllocator.h>
     41 #include <ui/GraphicLog.h>
     42 #include <ui/PixelFormat.h>
     43 
     44 #include <pixelflinger/pixelflinger.h>
     45 #include <GLES/gl.h>
     46 
     47 #include "clz.h"
     48 #include "GLExtensions.h"
     49 #include "Layer.h"
     50 #include "LayerBlur.h"
     51 #include "LayerBuffer.h"
     52 #include "LayerDim.h"
     53 #include "SurfaceFlinger.h"
     54 
     55 #include "DisplayHardware/DisplayHardware.h"
     56 
     57 /* ideally AID_GRAPHICS would be in a semi-public header
     58  * or there would be a way to map a user/group name to its id
     59  */
     60 #ifndef AID_GRAPHICS
     61 #define AID_GRAPHICS 1003
     62 #endif
     63 
     64 #define DISPLAY_COUNT       1
     65 
     66 namespace android {
     67 // ---------------------------------------------------------------------------
     68 
     69 SurfaceFlinger::SurfaceFlinger()
     70     :   BnSurfaceComposer(), Thread(false),
     71         mTransactionFlags(0),
     72         mTransactionCount(0),
     73         mResizeTransationPending(false),
     74         mLayersRemoved(false),
     75         mBootTime(systemTime()),
     76         mHardwareTest("android.permission.HARDWARE_TEST"),
     77         mAccessSurfaceFlinger("android.permission.ACCESS_SURFACE_FLINGER"),
     78         mReadFramebuffer("android.permission.READ_FRAME_BUFFER"),
     79         mDump("android.permission.DUMP"),
     80         mVisibleRegionsDirty(false),
     81         mDeferReleaseConsole(false),
     82         mFreezeDisplay(false),
     83         mElectronBeamAnimationMode(0),
     84         mFreezeCount(0),
     85         mFreezeDisplayTime(0),
     86         mDebugRegion(0),
     87         mDebugBackground(0),
     88         mDebugInSwapBuffers(0),
     89         mLastSwapBufferTime(0),
     90         mDebugInTransaction(0),
     91         mLastTransactionTime(0),
     92         mBootFinished(false),
     93         mConsoleSignals(0),
     94         mSecureFrameBuffer(0)
     95 {
     96     init();
     97 }
     98 
     99 void SurfaceFlinger::init()
    100 {
    101     LOGI("SurfaceFlinger is starting");
    102 
    103     // debugging stuff...
    104     char value[PROPERTY_VALUE_MAX];
    105     property_get("debug.sf.showupdates", value, "0");
    106     mDebugRegion = atoi(value);
    107     property_get("debug.sf.showbackground", value, "0");
    108     mDebugBackground = atoi(value);
    109 
    110     LOGI_IF(mDebugRegion,       "showupdates enabled");
    111     LOGI_IF(mDebugBackground,   "showbackground enabled");
    112 }
    113 
    114 SurfaceFlinger::~SurfaceFlinger()
    115 {
    116     glDeleteTextures(1, &mWormholeTexName);
    117 }
    118 
    119 overlay_control_device_t* SurfaceFlinger::getOverlayEngine() const
    120 {
    121     return graphicPlane(0).displayHardware().getOverlayEngine();
    122 }
    123 
    124 sp<IMemoryHeap> SurfaceFlinger::getCblk() const
    125 {
    126     return mServerHeap;
    127 }
    128 
    129 sp<ISurfaceComposerClient> SurfaceFlinger::createConnection()
    130 {
    131     sp<ISurfaceComposerClient> bclient;
    132     sp<Client> client(new Client(this));
    133     status_t err = client->initCheck();
    134     if (err == NO_ERROR) {
    135         bclient = client;
    136     }
    137     return bclient;
    138 }
    139 
    140 sp<ISurfaceComposerClient> SurfaceFlinger::createClientConnection()
    141 {
    142     sp<ISurfaceComposerClient> bclient;
    143     sp<UserClient> client(new UserClient(this));
    144     status_t err = client->initCheck();
    145     if (err == NO_ERROR) {
    146         bclient = client;
    147     }
    148     return bclient;
    149 }
    150 
    151 
    152 const GraphicPlane& SurfaceFlinger::graphicPlane(int dpy) const
    153 {
    154     LOGE_IF(uint32_t(dpy) >= DISPLAY_COUNT, "Invalid DisplayID %d", dpy);
    155     const GraphicPlane& plane(mGraphicPlanes[dpy]);
    156     return plane;
    157 }
    158 
    159 GraphicPlane& SurfaceFlinger::graphicPlane(int dpy)
    160 {
    161     return const_cast<GraphicPlane&>(
    162         const_cast<SurfaceFlinger const *>(this)->graphicPlane(dpy));
    163 }
    164 
    165 void SurfaceFlinger::bootFinished()
    166 {
    167     const nsecs_t now = systemTime();
    168     const nsecs_t duration = now - mBootTime;
    169     LOGI("Boot is finished (%ld ms)", long(ns2ms(duration)) );
    170     mBootFinished = true;
    171     property_set("ctl.stop", "bootanim");
    172 }
    173 
    174 void SurfaceFlinger::onFirstRef()
    175 {
    176     run("SurfaceFlinger", PRIORITY_URGENT_DISPLAY);
    177 
    178     // Wait for the main thread to be done with its initialization
    179     mReadyToRunBarrier.wait();
    180 }
    181 
    182 static inline uint16_t pack565(int r, int g, int b) {
    183     return (r<<11)|(g<<5)|b;
    184 }
    185 
    186 status_t SurfaceFlinger::readyToRun()
    187 {
    188     LOGI(   "SurfaceFlinger's main thread ready to run. "
    189             "Initializing graphics H/W...");
    190 
    191     // we only support one display currently
    192     int dpy = 0;
    193 
    194     {
    195         // initialize the main display
    196         GraphicPlane& plane(graphicPlane(dpy));
    197         DisplayHardware* const hw = new DisplayHardware(this, dpy);
    198         plane.setDisplayHardware(hw);
    199     }
    200 
    201     // create the shared control-block
    202     mServerHeap = new MemoryHeapBase(4096,
    203             MemoryHeapBase::READ_ONLY, "SurfaceFlinger read-only heap");
    204     LOGE_IF(mServerHeap==0, "can't create shared memory dealer");
    205 
    206     mServerCblk = static_cast<surface_flinger_cblk_t*>(mServerHeap->getBase());
    207     LOGE_IF(mServerCblk==0, "can't get to shared control block's address");
    208 
    209     new(mServerCblk) surface_flinger_cblk_t;
    210 
    211     // initialize primary screen
    212     // (other display should be initialized in the same manner, but
    213     // asynchronously, as they could come and go. None of this is supported
    214     // yet).
    215     const GraphicPlane& plane(graphicPlane(dpy));
    216     const DisplayHardware& hw = plane.displayHardware();
    217     const uint32_t w = hw.getWidth();
    218     const uint32_t h = hw.getHeight();
    219     const uint32_t f = hw.getFormat();
    220     hw.makeCurrent();
    221 
    222     // initialize the shared control block
    223     mServerCblk->connected |= 1<<dpy;
    224     display_cblk_t* dcblk = mServerCblk->displays + dpy;
    225     memset(dcblk, 0, sizeof(display_cblk_t));
    226     dcblk->w            = plane.getWidth();
    227     dcblk->h            = plane.getHeight();
    228     dcblk->format       = f;
    229     dcblk->orientation  = ISurfaceComposer::eOrientationDefault;
    230     dcblk->xdpi         = hw.getDpiX();
    231     dcblk->ydpi         = hw.getDpiY();
    232     dcblk->fps          = hw.getRefreshRate();
    233     dcblk->density      = hw.getDensity();
    234 
    235     // Initialize OpenGL|ES
    236     glPixelStorei(GL_UNPACK_ALIGNMENT, 4);
    237     glPixelStorei(GL_PACK_ALIGNMENT, 4);
    238     glEnableClientState(GL_VERTEX_ARRAY);
    239     glEnable(GL_SCISSOR_TEST);
    240     glShadeModel(GL_FLAT);
    241     glDisable(GL_DITHER);
    242     glDisable(GL_CULL_FACE);
    243 
    244     const uint16_t g0 = pack565(0x0F,0x1F,0x0F);
    245     const uint16_t g1 = pack565(0x17,0x2f,0x17);
    246     const uint16_t textureData[4] = { g0, g1, g1, g0 };
    247     glGenTextures(1, &mWormholeTexName);
    248     glBindTexture(GL_TEXTURE_2D, mWormholeTexName);
    249     glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
    250     glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
    251     glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
    252     glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
    253     glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, 2, 2, 0,
    254             GL_RGB, GL_UNSIGNED_SHORT_5_6_5, textureData);
    255 
    256     glViewport(0, 0, w, h);
    257     glMatrixMode(GL_PROJECTION);
    258     glLoadIdentity();
    259     glOrthof(0, w, h, 0, 0, 1);
    260 
    261    LayerDim::initDimmer(this, w, h);
    262 
    263     mReadyToRunBarrier.open();
    264 
    265     /*
    266      *  We're now ready to accept clients...
    267      */
    268 
    269     // start boot animation
    270     property_set("ctl.start", "bootanim");
    271 
    272     return NO_ERROR;
    273 }
    274 
    275 // ----------------------------------------------------------------------------
    276 #if 0
    277 #pragma mark -
    278 #pragma mark Events Handler
    279 #endif
    280 
    281 void SurfaceFlinger::waitForEvent()
    282 {
    283     while (true) {
    284         nsecs_t timeout = -1;
    285         const nsecs_t freezeDisplayTimeout = ms2ns(5000);
    286         if (UNLIKELY(isFrozen())) {
    287             // wait 5 seconds
    288             const nsecs_t now = systemTime();
    289             if (mFreezeDisplayTime == 0) {
    290                 mFreezeDisplayTime = now;
    291             }
    292             nsecs_t waitTime = freezeDisplayTimeout - (now - mFreezeDisplayTime);
    293             timeout = waitTime>0 ? waitTime : 0;
    294         }
    295 
    296         sp<MessageBase> msg = mEventQueue.waitMessage(timeout);
    297 
    298         // see if we timed out
    299         if (isFrozen()) {
    300             const nsecs_t now = systemTime();
    301             nsecs_t frozenTime = (now - mFreezeDisplayTime);
    302             if (frozenTime >= freezeDisplayTimeout) {
    303                 // we timed out and are still frozen
    304                 LOGW("timeout expired mFreezeDisplay=%d, mFreezeCount=%d",
    305                         mFreezeDisplay, mFreezeCount);
    306                 mFreezeDisplayTime = 0;
    307                 mFreezeCount = 0;
    308                 mFreezeDisplay = false;
    309             }
    310         }
    311 
    312         if (msg != 0) {
    313             switch (msg->what) {
    314                 case MessageQueue::INVALIDATE:
    315                     // invalidate message, just return to the main loop
    316                     return;
    317             }
    318         }
    319     }
    320 }
    321 
    322 void SurfaceFlinger::signalEvent() {
    323     mEventQueue.invalidate();
    324 }
    325 
    326 void SurfaceFlinger::signal() const {
    327     // this is the IPC call
    328     const_cast<SurfaceFlinger*>(this)->signalEvent();
    329 }
    330 
    331 status_t SurfaceFlinger::postMessageAsync(const sp<MessageBase>& msg,
    332         nsecs_t reltime, uint32_t flags)
    333 {
    334     return mEventQueue.postMessage(msg, reltime, flags);
    335 }
    336 
    337 status_t SurfaceFlinger::postMessageSync(const sp<MessageBase>& msg,
    338         nsecs_t reltime, uint32_t flags)
    339 {
    340     status_t res = mEventQueue.postMessage(msg, reltime, flags);
    341     if (res == NO_ERROR) {
    342         msg->wait();
    343     }
    344     return res;
    345 }
    346 
    347 // ----------------------------------------------------------------------------
    348 #if 0
    349 #pragma mark -
    350 #pragma mark Main loop
    351 #endif
    352 
    353 bool SurfaceFlinger::threadLoop()
    354 {
    355     waitForEvent();
    356 
    357     // check for transactions
    358     if (UNLIKELY(mConsoleSignals)) {
    359         handleConsoleEvents();
    360     }
    361 
    362     if (LIKELY(mTransactionCount == 0)) {
    363         // if we're in a global transaction, don't do anything.
    364         const uint32_t mask = eTransactionNeeded | eTraversalNeeded;
    365         uint32_t transactionFlags = getTransactionFlags(mask);
    366         if (LIKELY(transactionFlags)) {
    367             handleTransaction(transactionFlags);
    368         }
    369     }
    370 
    371     // post surfaces (if needed)
    372     handlePageFlip();
    373 
    374     const DisplayHardware& hw(graphicPlane(0).displayHardware());
    375     if (LIKELY(hw.canDraw() && !isFrozen())) {
    376         // repaint the framebuffer (if needed)
    377 
    378         const int index = hw.getCurrentBufferIndex();
    379         GraphicLog& logger(GraphicLog::getInstance());
    380 
    381         logger.log(GraphicLog::SF_REPAINT, index);
    382         handleRepaint();
    383 
    384         // inform the h/w that we're done compositing
    385         logger.log(GraphicLog::SF_COMPOSITION_COMPLETE, index);
    386         hw.compositionComplete();
    387 
    388         // release the clients before we flip ('cause flip might block)
    389         logger.log(GraphicLog::SF_UNLOCK_CLIENTS, index);
    390         unlockClients();
    391 
    392         logger.log(GraphicLog::SF_SWAP_BUFFERS, index);
    393         postFramebuffer();
    394 
    395         logger.log(GraphicLog::SF_REPAINT_DONE, index);
    396     } else {
    397         // pretend we did the post
    398         unlockClients();
    399         usleep(16667); // 60 fps period
    400     }
    401     return true;
    402 }
    403 
    404 void SurfaceFlinger::postFramebuffer()
    405 {
    406     if (!mInvalidRegion.isEmpty()) {
    407         const DisplayHardware& hw(graphicPlane(0).displayHardware());
    408         const nsecs_t now = systemTime();
    409         mDebugInSwapBuffers = now;
    410         hw.flip(mInvalidRegion);
    411         mLastSwapBufferTime = systemTime() - now;
    412         mDebugInSwapBuffers = 0;
    413         mInvalidRegion.clear();
    414     }
    415 }
    416 
    417 void SurfaceFlinger::handleConsoleEvents()
    418 {
    419     // something to do with the console
    420     const DisplayHardware& hw = graphicPlane(0).displayHardware();
    421 
    422     int what = android_atomic_and(0, &mConsoleSignals);
    423     if (what & eConsoleAcquired) {
    424         hw.acquireScreen();
    425         // this is a temporary work-around, eventually this should be called
    426         // by the power-manager
    427         SurfaceFlinger::turnElectronBeamOn(mElectronBeamAnimationMode);
    428     }
    429 
    430     if (mDeferReleaseConsole && hw.isScreenAcquired()) {
    431         // We got the release signal before the acquire signal
    432         mDeferReleaseConsole = false;
    433         hw.releaseScreen();
    434     }
    435 
    436     if (what & eConsoleReleased) {
    437         if (hw.isScreenAcquired()) {
    438             hw.releaseScreen();
    439         } else {
    440             mDeferReleaseConsole = true;
    441         }
    442     }
    443 
    444     mDirtyRegion.set(hw.bounds());
    445 }
    446 
    447 void SurfaceFlinger::handleTransaction(uint32_t transactionFlags)
    448 {
    449     Vector< sp<LayerBase> > ditchedLayers;
    450 
    451     /*
    452      * Perform and commit the transaction
    453      */
    454 
    455     { // scope for the lock
    456         Mutex::Autolock _l(mStateLock);
    457         const nsecs_t now = systemTime();
    458         mDebugInTransaction = now;
    459         handleTransactionLocked(transactionFlags, ditchedLayers);
    460         mLastTransactionTime = systemTime() - now;
    461         mDebugInTransaction = 0;
    462         // here the transaction has been committed
    463     }
    464 
    465     /*
    466      * Clean-up all layers that went away
    467      * (do this without the lock held)
    468      */
    469     const size_t count = ditchedLayers.size();
    470     for (size_t i=0 ; i<count ; i++) {
    471         if (ditchedLayers[i] != 0) {
    472             //LOGD("ditching layer %p", ditchedLayers[i].get());
    473             ditchedLayers[i]->ditch();
    474         }
    475     }
    476 }
    477 
    478 void SurfaceFlinger::handleTransactionLocked(
    479         uint32_t transactionFlags, Vector< sp<LayerBase> >& ditchedLayers)
    480 {
    481     const LayerVector& currentLayers(mCurrentState.layersSortedByZ);
    482     const size_t count = currentLayers.size();
    483 
    484     /*
    485      * Traversal of the children
    486      * (perform the transaction for each of them if needed)
    487      */
    488 
    489     const bool layersNeedTransaction = transactionFlags & eTraversalNeeded;
    490     if (layersNeedTransaction) {
    491         for (size_t i=0 ; i<count ; i++) {
    492             const sp<LayerBase>& layer = currentLayers[i];
    493             uint32_t trFlags = layer->getTransactionFlags(eTransactionNeeded);
    494             if (!trFlags) continue;
    495 
    496             const uint32_t flags = layer->doTransaction(0);
    497             if (flags & Layer::eVisibleRegion)
    498                 mVisibleRegionsDirty = true;
    499         }
    500     }
    501 
    502     /*
    503      * Perform our own transaction if needed
    504      */
    505 
    506     if (transactionFlags & eTransactionNeeded) {
    507         if (mCurrentState.orientation != mDrawingState.orientation) {
    508             // the orientation has changed, recompute all visible regions
    509             // and invalidate everything.
    510 
    511             const int dpy = 0;
    512             const int orientation = mCurrentState.orientation;
    513             const uint32_t type = mCurrentState.orientationType;
    514             GraphicPlane& plane(graphicPlane(dpy));
    515             plane.setOrientation(orientation);
    516 
    517             // update the shared control block
    518             const DisplayHardware& hw(plane.displayHardware());
    519             volatile display_cblk_t* dcblk = mServerCblk->displays + dpy;
    520             dcblk->orientation = orientation;
    521             dcblk->w = plane.getWidth();
    522             dcblk->h = plane.getHeight();
    523 
    524             mVisibleRegionsDirty = true;
    525             mDirtyRegion.set(hw.bounds());
    526         }
    527 
    528         if (mCurrentState.freezeDisplay != mDrawingState.freezeDisplay) {
    529             // freezing or unfreezing the display -> trigger animation if needed
    530             mFreezeDisplay = mCurrentState.freezeDisplay;
    531             if (mFreezeDisplay)
    532                  mFreezeDisplayTime = 0;
    533         }
    534 
    535         if (currentLayers.size() > mDrawingState.layersSortedByZ.size()) {
    536             // layers have been added
    537             mVisibleRegionsDirty = true;
    538         }
    539 
    540         // some layers might have been removed, so
    541         // we need to update the regions they're exposing.
    542         if (mLayersRemoved) {
    543             mLayersRemoved = false;
    544             mVisibleRegionsDirty = true;
    545             const LayerVector& previousLayers(mDrawingState.layersSortedByZ);
    546             const size_t count = previousLayers.size();
    547             for (size_t i=0 ; i<count ; i++) {
    548                 const sp<LayerBase>& layer(previousLayers[i]);
    549                 if (currentLayers.indexOf( layer ) < 0) {
    550                     // this layer is not visible anymore
    551                     ditchedLayers.add(layer);
    552                     mDirtyRegionRemovedLayer.orSelf(layer->visibleRegionScreen);
    553                 }
    554             }
    555         }
    556     }
    557 
    558     commitTransaction();
    559 }
    560 
    561 sp<FreezeLock> SurfaceFlinger::getFreezeLock() const
    562 {
    563     return new FreezeLock(const_cast<SurfaceFlinger *>(this));
    564 }
    565 
    566 void SurfaceFlinger::computeVisibleRegions(
    567     LayerVector& currentLayers, Region& dirtyRegion, Region& opaqueRegion)
    568 {
    569     const GraphicPlane& plane(graphicPlane(0));
    570     const Transform& planeTransform(plane.transform());
    571     const DisplayHardware& hw(plane.displayHardware());
    572     const Region screenRegion(hw.bounds());
    573 
    574     Region aboveOpaqueLayers;
    575     Region aboveCoveredLayers;
    576     Region dirty;
    577 
    578     bool secureFrameBuffer = false;
    579 
    580     size_t i = currentLayers.size();
    581     while (i--) {
    582         const sp<LayerBase>& layer = currentLayers[i];
    583         layer->validateVisibility(planeTransform);
    584 
    585         // start with the whole surface at its current location
    586         const Layer::State& s(layer->drawingState());
    587 
    588         /*
    589          * opaqueRegion: area of a surface that is fully opaque.
    590          */
    591         Region opaqueRegion;
    592 
    593         /*
    594          * visibleRegion: area of a surface that is visible on screen
    595          * and not fully transparent. This is essentially the layer's
    596          * footprint minus the opaque regions above it.
    597          * Areas covered by a translucent surface are considered visible.
    598          */
    599         Region visibleRegion;
    600 
    601         /*
    602          * coveredRegion: area of a surface that is covered by all
    603          * visible regions above it (which includes the translucent areas).
    604          */
    605         Region coveredRegion;
    606 
    607 
    608         // handle hidden surfaces by setting the visible region to empty
    609         if (LIKELY(!(s.flags & ISurfaceComposer::eLayerHidden) && s.alpha)) {
    610             const bool translucent = layer->needsBlending();
    611             const Rect bounds(layer->visibleBounds());
    612             visibleRegion.set(bounds);
    613             visibleRegion.andSelf(screenRegion);
    614             if (!visibleRegion.isEmpty()) {
    615                 // Remove the transparent area from the visible region
    616                 if (translucent) {
    617                     visibleRegion.subtractSelf(layer->transparentRegionScreen);
    618                 }
    619 
    620                 // compute the opaque region
    621                 const int32_t layerOrientation = layer->getOrientation();
    622                 if (s.alpha==255 && !translucent &&
    623                         ((layerOrientation & Transform::ROT_INVALID) == false)) {
    624                     // the opaque region is the layer's footprint
    625                     opaqueRegion = visibleRegion;
    626                 }
    627             }
    628         }
    629 
    630         // Clip the covered region to the visible region
    631         coveredRegion = aboveCoveredLayers.intersect(visibleRegion);
    632 
    633         // Update aboveCoveredLayers for next (lower) layer
    634         aboveCoveredLayers.orSelf(visibleRegion);
    635 
    636         // subtract the opaque region covered by the layers above us
    637         visibleRegion.subtractSelf(aboveOpaqueLayers);
    638 
    639         // compute this layer's dirty region
    640         if (layer->contentDirty) {
    641             // we need to invalidate the whole region
    642             dirty = visibleRegion;
    643             // as well, as the old visible region
    644             dirty.orSelf(layer->visibleRegionScreen);
    645             layer->contentDirty = false;
    646         } else {
    647             /* compute the exposed region:
    648              *   the exposed region consists of two components:
    649              *   1) what's VISIBLE now and was COVERED before
    650              *   2) what's EXPOSED now less what was EXPOSED before
    651              *
    652              * note that (1) is conservative, we start with the whole
    653              * visible region but only keep what used to be covered by
    654              * something -- which mean it may have been exposed.
    655              *
    656              * (2) handles areas that were not covered by anything but got
    657              * exposed because of a resize.
    658              */
    659             const Region newExposed = visibleRegion - coveredRegion;
    660             const Region oldVisibleRegion = layer->visibleRegionScreen;
    661             const Region oldCoveredRegion = layer->coveredRegionScreen;
    662             const Region oldExposed = oldVisibleRegion - oldCoveredRegion;
    663             dirty = (visibleRegion&oldCoveredRegion) | (newExposed-oldExposed);
    664         }
    665         dirty.subtractSelf(aboveOpaqueLayers);
    666 
    667         // accumulate to the screen dirty region
    668         dirtyRegion.orSelf(dirty);
    669 
    670         // Update aboveOpaqueLayers for next (lower) layer
    671         aboveOpaqueLayers.orSelf(opaqueRegion);
    672 
    673         // Store the visible region is screen space
    674         layer->setVisibleRegion(visibleRegion);
    675         layer->setCoveredRegion(coveredRegion);
    676 
    677         // If a secure layer is partially visible, lock-down the screen!
    678         if (layer->isSecure() && !visibleRegion.isEmpty()) {
    679             secureFrameBuffer = true;
    680         }
    681     }
    682 
    683     // invalidate the areas where a layer was removed
    684     dirtyRegion.orSelf(mDirtyRegionRemovedLayer);
    685     mDirtyRegionRemovedLayer.clear();
    686 
    687     mSecureFrameBuffer = secureFrameBuffer;
    688     opaqueRegion = aboveOpaqueLayers;
    689 }
    690 
    691 
    692 void SurfaceFlinger::commitTransaction()
    693 {
    694     mDrawingState = mCurrentState;
    695     mResizeTransationPending = false;
    696     mTransactionCV.broadcast();
    697 }
    698 
    699 void SurfaceFlinger::handlePageFlip()
    700 {
    701     bool visibleRegions = mVisibleRegionsDirty;
    702     LayerVector& currentLayers = const_cast<LayerVector&>(
    703             mDrawingState.layersSortedByZ);
    704     visibleRegions |= lockPageFlip(currentLayers);
    705 
    706         const DisplayHardware& hw = graphicPlane(0).displayHardware();
    707         const Region screenRegion(hw.bounds());
    708         if (visibleRegions) {
    709             Region opaqueRegion;
    710             computeVisibleRegions(currentLayers, mDirtyRegion, opaqueRegion);
    711 
    712             /*
    713              *  rebuild the visible layer list
    714              */
    715             mVisibleLayersSortedByZ.clear();
    716             const LayerVector& currentLayers(mDrawingState.layersSortedByZ);
    717             size_t count = currentLayers.size();
    718             mVisibleLayersSortedByZ.setCapacity(count);
    719             for (size_t i=0 ; i<count ; i++) {
    720                 if (!currentLayers[i]->visibleRegionScreen.isEmpty())
    721                     mVisibleLayersSortedByZ.add(currentLayers[i]);
    722             }
    723 
    724             mWormholeRegion = screenRegion.subtract(opaqueRegion);
    725             mVisibleRegionsDirty = false;
    726         }
    727 
    728     unlockPageFlip(currentLayers);
    729     mDirtyRegion.andSelf(screenRegion);
    730 }
    731 
    732 bool SurfaceFlinger::lockPageFlip(const LayerVector& currentLayers)
    733 {
    734     bool recomputeVisibleRegions = false;
    735     size_t count = currentLayers.size();
    736     sp<LayerBase> const* layers = currentLayers.array();
    737     for (size_t i=0 ; i<count ; i++) {
    738         const sp<LayerBase>& layer(layers[i]);
    739         layer->lockPageFlip(recomputeVisibleRegions);
    740     }
    741     return recomputeVisibleRegions;
    742 }
    743 
    744 void SurfaceFlinger::unlockPageFlip(const LayerVector& currentLayers)
    745 {
    746     const GraphicPlane& plane(graphicPlane(0));
    747     const Transform& planeTransform(plane.transform());
    748     size_t count = currentLayers.size();
    749     sp<LayerBase> const* layers = currentLayers.array();
    750     for (size_t i=0 ; i<count ; i++) {
    751         const sp<LayerBase>& layer(layers[i]);
    752         layer->unlockPageFlip(planeTransform, mDirtyRegion);
    753     }
    754 }
    755 
    756 
    757 void SurfaceFlinger::handleRepaint()
    758 {
    759     // compute the invalid region
    760     mInvalidRegion.orSelf(mDirtyRegion);
    761     if (mInvalidRegion.isEmpty()) {
    762         // nothing to do
    763         return;
    764     }
    765 
    766     if (UNLIKELY(mDebugRegion)) {
    767         debugFlashRegions();
    768     }
    769 
    770     // set the frame buffer
    771     const DisplayHardware& hw(graphicPlane(0).displayHardware());
    772     glMatrixMode(GL_MODELVIEW);
    773     glLoadIdentity();
    774 
    775     uint32_t flags = hw.getFlags();
    776     if ((flags & DisplayHardware::SWAP_RECTANGLE) ||
    777         (flags & DisplayHardware::BUFFER_PRESERVED))
    778     {
    779         // we can redraw only what's dirty, but since SWAP_RECTANGLE only
    780         // takes a rectangle, we must make sure to update that whole
    781         // rectangle in that case
    782         if (flags & DisplayHardware::SWAP_RECTANGLE) {
    783             // TODO: we really should be able to pass a region to
    784             // SWAP_RECTANGLE so that we don't have to redraw all this.
    785             mDirtyRegion.set(mInvalidRegion.bounds());
    786         } else {
    787             // in the BUFFER_PRESERVED case, obviously, we can update only
    788             // what's needed and nothing more.
    789             // NOTE: this is NOT a common case, as preserving the backbuffer
    790             // is costly and usually involves copying the whole update back.
    791         }
    792     } else {
    793         if (flags & DisplayHardware::PARTIAL_UPDATES) {
    794             // We need to redraw the rectangle that will be updated
    795             // (pushed to the framebuffer).
    796             // This is needed because PARTIAL_UPDATES only takes one
    797             // rectangle instead of a region (see DisplayHardware::flip())
    798             mDirtyRegion.set(mInvalidRegion.bounds());
    799         } else {
    800             // we need to redraw everything (the whole screen)
    801             mDirtyRegion.set(hw.bounds());
    802             mInvalidRegion = mDirtyRegion;
    803         }
    804     }
    805 
    806     // compose all surfaces
    807     composeSurfaces(mDirtyRegion);
    808 
    809     // clear the dirty regions
    810     mDirtyRegion.clear();
    811 }
    812 
    813 void SurfaceFlinger::composeSurfaces(const Region& dirty)
    814 {
    815     if (UNLIKELY(!mWormholeRegion.isEmpty())) {
    816         // should never happen unless the window manager has a bug
    817         // draw something...
    818         drawWormhole();
    819     }
    820     const Vector< sp<LayerBase> >& layers(mVisibleLayersSortedByZ);
    821     const size_t count = layers.size();
    822     for (size_t i=0 ; i<count ; ++i) {
    823         const sp<LayerBase>& layer(layers[i]);
    824         const Region clip(dirty.intersect(layer->visibleRegionScreen));
    825         if (!clip.isEmpty()) {
    826             layer->draw(clip);
    827         }
    828     }
    829 }
    830 
    831 void SurfaceFlinger::unlockClients()
    832 {
    833     const LayerVector& drawingLayers(mDrawingState.layersSortedByZ);
    834     const size_t count = drawingLayers.size();
    835     sp<LayerBase> const* const layers = drawingLayers.array();
    836     for (size_t i=0 ; i<count ; ++i) {
    837         const sp<LayerBase>& layer = layers[i];
    838         layer->finishPageFlip();
    839     }
    840 }
    841 
    842 void SurfaceFlinger::debugFlashRegions()
    843 {
    844     const DisplayHardware& hw(graphicPlane(0).displayHardware());
    845     const uint32_t flags = hw.getFlags();
    846 
    847     if (!((flags & DisplayHardware::SWAP_RECTANGLE) ||
    848             (flags & DisplayHardware::BUFFER_PRESERVED))) {
    849         const Region repaint((flags & DisplayHardware::PARTIAL_UPDATES) ?
    850                 mDirtyRegion.bounds() : hw.bounds());
    851         composeSurfaces(repaint);
    852     }
    853 
    854     TextureManager::deactivateTextures();
    855 
    856     glDisable(GL_BLEND);
    857     glDisable(GL_DITHER);
    858     glDisable(GL_SCISSOR_TEST);
    859 
    860     static int toggle = 0;
    861     toggle = 1 - toggle;
    862     if (toggle) {
    863         glColor4f(1, 0, 1, 1);
    864     } else {
    865         glColor4f(1, 1, 0, 1);
    866     }
    867 
    868     Region::const_iterator it = mDirtyRegion.begin();
    869     Region::const_iterator const end = mDirtyRegion.end();
    870     while (it != end) {
    871         const Rect& r = *it++;
    872         GLfloat vertices[][2] = {
    873                 { r.left,  r.top },
    874                 { r.left,  r.bottom },
    875                 { r.right, r.bottom },
    876                 { r.right, r.top }
    877         };
    878         glVertexPointer(2, GL_FLOAT, 0, vertices);
    879         glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
    880     }
    881 
    882     if (mInvalidRegion.isEmpty()) {
    883         mDirtyRegion.dump("mDirtyRegion");
    884         mInvalidRegion.dump("mInvalidRegion");
    885     }
    886     hw.flip(mInvalidRegion);
    887 
    888     if (mDebugRegion > 1)
    889         usleep(mDebugRegion * 1000);
    890 
    891     glEnable(GL_SCISSOR_TEST);
    892     //mDirtyRegion.dump("mDirtyRegion");
    893 }
    894 
    895 void SurfaceFlinger::drawWormhole() const
    896 {
    897     const Region region(mWormholeRegion.intersect(mDirtyRegion));
    898     if (region.isEmpty())
    899         return;
    900 
    901     const DisplayHardware& hw(graphicPlane(0).displayHardware());
    902     const int32_t width = hw.getWidth();
    903     const int32_t height = hw.getHeight();
    904 
    905     glDisable(GL_BLEND);
    906     glDisable(GL_DITHER);
    907 
    908     if (LIKELY(!mDebugBackground)) {
    909         glClearColor(0,0,0,0);
    910         Region::const_iterator it = region.begin();
    911         Region::const_iterator const end = region.end();
    912         while (it != end) {
    913             const Rect& r = *it++;
    914             const GLint sy = height - (r.top + r.height());
    915             glScissor(r.left, sy, r.width(), r.height());
    916             glClear(GL_COLOR_BUFFER_BIT);
    917         }
    918     } else {
    919         const GLshort vertices[][2] = { { 0, 0 }, { width, 0 },
    920                 { width, height }, { 0, height }  };
    921         const GLshort tcoords[][2] = { { 0, 0 }, { 1, 0 },  { 1, 1 }, { 0, 1 } };
    922         glVertexPointer(2, GL_SHORT, 0, vertices);
    923         glTexCoordPointer(2, GL_SHORT, 0, tcoords);
    924         glEnableClientState(GL_TEXTURE_COORD_ARRAY);
    925 #if defined(GL_OES_EGL_image_external)
    926         if (GLExtensions::getInstance().haveTextureExternal()) {
    927             glDisable(GL_TEXTURE_EXTERNAL_OES);
    928         }
    929 #endif
    930         glEnable(GL_TEXTURE_2D);
    931         glBindTexture(GL_TEXTURE_2D, mWormholeTexName);
    932         glTexEnvx(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
    933         glMatrixMode(GL_TEXTURE);
    934         glLoadIdentity();
    935         glScalef(width*(1.0f/32.0f), height*(1.0f/32.0f), 1);
    936         Region::const_iterator it = region.begin();
    937         Region::const_iterator const end = region.end();
    938         while (it != end) {
    939             const Rect& r = *it++;
    940             const GLint sy = height - (r.top + r.height());
    941             glScissor(r.left, sy, r.width(), r.height());
    942             glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
    943         }
    944         glDisableClientState(GL_TEXTURE_COORD_ARRAY);
    945     }
    946 }
    947 
    948 void SurfaceFlinger::debugShowFPS() const
    949 {
    950     static int mFrameCount;
    951     static int mLastFrameCount = 0;
    952     static nsecs_t mLastFpsTime = 0;
    953     static float mFps = 0;
    954     mFrameCount++;
    955     nsecs_t now = systemTime();
    956     nsecs_t diff = now - mLastFpsTime;
    957     if (diff > ms2ns(250)) {
    958         mFps =  ((mFrameCount - mLastFrameCount) * float(s2ns(1))) / diff;
    959         mLastFpsTime = now;
    960         mLastFrameCount = mFrameCount;
    961     }
    962     // XXX: mFPS has the value we want
    963  }
    964 
    965 status_t SurfaceFlinger::addLayer(const sp<LayerBase>& layer)
    966 {
    967     Mutex::Autolock _l(mStateLock);
    968     addLayer_l(layer);
    969     setTransactionFlags(eTransactionNeeded|eTraversalNeeded);
    970     return NO_ERROR;
    971 }
    972 
    973 status_t SurfaceFlinger::addLayer_l(const sp<LayerBase>& layer)
    974 {
    975     ssize_t i = mCurrentState.layersSortedByZ.add(layer);
    976     return (i < 0) ? status_t(i) : status_t(NO_ERROR);
    977 }
    978 
    979 ssize_t SurfaceFlinger::addClientLayer(const sp<Client>& client,
    980         const sp<LayerBaseClient>& lbc)
    981 {
    982     Mutex::Autolock _l(mStateLock);
    983 
    984     // attach this layer to the client
    985     ssize_t name = client->attachLayer(lbc);
    986 
    987     // add this layer to the current state list
    988     addLayer_l(lbc);
    989 
    990     return name;
    991 }
    992 
    993 status_t SurfaceFlinger::removeLayer(const sp<LayerBase>& layer)
    994 {
    995     Mutex::Autolock _l(mStateLock);
    996     status_t err = purgatorizeLayer_l(layer);
    997     if (err == NO_ERROR)
    998         setTransactionFlags(eTransactionNeeded);
    999     return err;
   1000 }
   1001 
   1002 status_t SurfaceFlinger::removeLayer_l(const sp<LayerBase>& layerBase)
   1003 {
   1004     sp<LayerBaseClient> lbc(layerBase->getLayerBaseClient());
   1005     if (lbc != 0) {
   1006         mLayerMap.removeItem( lbc->getSurface()->asBinder() );
   1007     }
   1008     ssize_t index = mCurrentState.layersSortedByZ.remove(layerBase);
   1009     if (index >= 0) {
   1010         mLayersRemoved = true;
   1011         return NO_ERROR;
   1012     }
   1013     return status_t(index);
   1014 }
   1015 
   1016 status_t SurfaceFlinger::purgatorizeLayer_l(const sp<LayerBase>& layerBase)
   1017 {
   1018     // remove the layer from the main list (through a transaction).
   1019     ssize_t err = removeLayer_l(layerBase);
   1020 
   1021     layerBase->onRemoved();
   1022 
   1023     // it's possible that we don't find a layer, because it might
   1024     // have been destroyed already -- this is not technically an error
   1025     // from the user because there is a race between Client::destroySurface(),
   1026     // ~Client() and ~ISurface().
   1027     return (err == NAME_NOT_FOUND) ? status_t(NO_ERROR) : err;
   1028 }
   1029 
   1030 status_t SurfaceFlinger::invalidateLayerVisibility(const sp<LayerBase>& layer)
   1031 {
   1032     layer->forceVisibilityTransaction();
   1033     setTransactionFlags(eTraversalNeeded);
   1034     return NO_ERROR;
   1035 }
   1036 
   1037 uint32_t SurfaceFlinger::getTransactionFlags(uint32_t flags)
   1038 {
   1039     return android_atomic_and(~flags, &mTransactionFlags) & flags;
   1040 }
   1041 
   1042 uint32_t SurfaceFlinger::setTransactionFlags(uint32_t flags)
   1043 {
   1044     uint32_t old = android_atomic_or(flags, &mTransactionFlags);
   1045     if ((old & flags)==0) { // wake the server up
   1046         signalEvent();
   1047     }
   1048     return old;
   1049 }
   1050 
   1051 void SurfaceFlinger::openGlobalTransaction()
   1052 {
   1053     android_atomic_inc(&mTransactionCount);
   1054 }
   1055 
   1056 void SurfaceFlinger::closeGlobalTransaction()
   1057 {
   1058     if (android_atomic_dec(&mTransactionCount) == 1) {
   1059         signalEvent();
   1060 
   1061         // if there is a transaction with a resize, wait for it to
   1062         // take effect before returning.
   1063         Mutex::Autolock _l(mStateLock);
   1064         while (mResizeTransationPending) {
   1065             status_t err = mTransactionCV.waitRelative(mStateLock, s2ns(5));
   1066             if (CC_UNLIKELY(err != NO_ERROR)) {
   1067                 // just in case something goes wrong in SF, return to the
   1068                 // called after a few seconds.
   1069                 LOGW_IF(err == TIMED_OUT, "closeGlobalTransaction timed out!");
   1070                 mResizeTransationPending = false;
   1071                 break;
   1072             }
   1073         }
   1074     }
   1075 }
   1076 
   1077 status_t SurfaceFlinger::freezeDisplay(DisplayID dpy, uint32_t flags)
   1078 {
   1079     if (UNLIKELY(uint32_t(dpy) >= DISPLAY_COUNT))
   1080         return BAD_VALUE;
   1081 
   1082     Mutex::Autolock _l(mStateLock);
   1083     mCurrentState.freezeDisplay = 1;
   1084     setTransactionFlags(eTransactionNeeded);
   1085 
   1086     // flags is intended to communicate some sort of animation behavior
   1087     // (for instance fading)
   1088     return NO_ERROR;
   1089 }
   1090 
   1091 status_t SurfaceFlinger::unfreezeDisplay(DisplayID dpy, uint32_t flags)
   1092 {
   1093     if (UNLIKELY(uint32_t(dpy) >= DISPLAY_COUNT))
   1094         return BAD_VALUE;
   1095 
   1096     Mutex::Autolock _l(mStateLock);
   1097     mCurrentState.freezeDisplay = 0;
   1098     setTransactionFlags(eTransactionNeeded);
   1099 
   1100     // flags is intended to communicate some sort of animation behavior
   1101     // (for instance fading)
   1102     return NO_ERROR;
   1103 }
   1104 
   1105 int SurfaceFlinger::setOrientation(DisplayID dpy,
   1106         int orientation, uint32_t flags)
   1107 {
   1108     if (UNLIKELY(uint32_t(dpy) >= DISPLAY_COUNT))
   1109         return BAD_VALUE;
   1110 
   1111     Mutex::Autolock _l(mStateLock);
   1112     if (mCurrentState.orientation != orientation) {
   1113         if (uint32_t(orientation)<=eOrientation270 || orientation==42) {
   1114             mCurrentState.orientationType = flags;
   1115             mCurrentState.orientation = orientation;
   1116             setTransactionFlags(eTransactionNeeded);
   1117             mTransactionCV.wait(mStateLock);
   1118         } else {
   1119             orientation = BAD_VALUE;
   1120         }
   1121     }
   1122     return orientation;
   1123 }
   1124 
   1125 sp<ISurface> SurfaceFlinger::createSurface(const sp<Client>& client, int pid,
   1126         const String8& name, ISurfaceComposerClient::surface_data_t* params,
   1127         DisplayID d, uint32_t w, uint32_t h, PixelFormat format,
   1128         uint32_t flags)
   1129 {
   1130     sp<LayerBaseClient> layer;
   1131     sp<LayerBaseClient::Surface> surfaceHandle;
   1132 
   1133     if (int32_t(w|h) < 0) {
   1134         LOGE("createSurface() failed, w or h is negative (w=%d, h=%d)",
   1135                 int(w), int(h));
   1136         return surfaceHandle;
   1137     }
   1138 
   1139     //LOGD("createSurface for pid %d (%d x %d)", pid, w, h);
   1140     sp<Layer> normalLayer;
   1141     switch (flags & eFXSurfaceMask) {
   1142         case eFXSurfaceNormal:
   1143             if (UNLIKELY(flags & ePushBuffers)) {
   1144                 layer = createPushBuffersSurface(client, d, w, h, flags);
   1145             } else {
   1146                 normalLayer = createNormalSurface(client, d, w, h, flags, format);
   1147                 layer = normalLayer;
   1148             }
   1149             break;
   1150         case eFXSurfaceBlur:
   1151             layer = createBlurSurface(client, d, w, h, flags);
   1152             break;
   1153         case eFXSurfaceDim:
   1154             layer = createDimSurface(client, d, w, h, flags);
   1155             break;
   1156     }
   1157 
   1158     if (layer != 0) {
   1159         layer->initStates(w, h, flags);
   1160         layer->setName(name);
   1161         ssize_t token = addClientLayer(client, layer);
   1162 
   1163         surfaceHandle = layer->getSurface();
   1164         if (surfaceHandle != 0) {
   1165             params->token = token;
   1166             params->identity = surfaceHandle->getIdentity();
   1167             params->width = w;
   1168             params->height = h;
   1169             params->format = format;
   1170             if (normalLayer != 0) {
   1171                 Mutex::Autolock _l(mStateLock);
   1172                 mLayerMap.add(surfaceHandle->asBinder(), normalLayer);
   1173             }
   1174         }
   1175 
   1176         setTransactionFlags(eTransactionNeeded);
   1177     }
   1178 
   1179     return surfaceHandle;
   1180 }
   1181 
   1182 sp<Layer> SurfaceFlinger::createNormalSurface(
   1183         const sp<Client>& client, DisplayID display,
   1184         uint32_t w, uint32_t h, uint32_t flags,
   1185         PixelFormat& format)
   1186 {
   1187     // initialize the surfaces
   1188     switch (format) { // TODO: take h/w into account
   1189     case PIXEL_FORMAT_TRANSPARENT:
   1190     case PIXEL_FORMAT_TRANSLUCENT:
   1191         format = PIXEL_FORMAT_RGBA_8888;
   1192         break;
   1193     case PIXEL_FORMAT_OPAQUE:
   1194 #ifdef NO_RGBX_8888
   1195         format = PIXEL_FORMAT_RGB_565;
   1196 #else
   1197         format = PIXEL_FORMAT_RGBX_8888;
   1198 #endif
   1199         break;
   1200     }
   1201 
   1202 #ifdef NO_RGBX_8888
   1203     if (format == PIXEL_FORMAT_RGBX_8888)
   1204         format = PIXEL_FORMAT_RGBA_8888;
   1205 #endif
   1206 
   1207     sp<Layer> layer = new Layer(this, display, client);
   1208     status_t err = layer->setBuffers(w, h, format, flags);
   1209     if (LIKELY(err != NO_ERROR)) {
   1210         LOGE("createNormalSurfaceLocked() failed (%s)", strerror(-err));
   1211         layer.clear();
   1212     }
   1213     return layer;
   1214 }
   1215 
   1216 sp<LayerBlur> SurfaceFlinger::createBlurSurface(
   1217         const sp<Client>& client, DisplayID display,
   1218         uint32_t w, uint32_t h, uint32_t flags)
   1219 {
   1220     sp<LayerBlur> layer = new LayerBlur(this, display, client);
   1221     layer->initStates(w, h, flags);
   1222     return layer;
   1223 }
   1224 
   1225 sp<LayerDim> SurfaceFlinger::createDimSurface(
   1226         const sp<Client>& client, DisplayID display,
   1227         uint32_t w, uint32_t h, uint32_t flags)
   1228 {
   1229     sp<LayerDim> layer = new LayerDim(this, display, client);
   1230     layer->initStates(w, h, flags);
   1231     return layer;
   1232 }
   1233 
   1234 sp<LayerBuffer> SurfaceFlinger::createPushBuffersSurface(
   1235         const sp<Client>& client, DisplayID display,
   1236         uint32_t w, uint32_t h, uint32_t flags)
   1237 {
   1238     sp<LayerBuffer> layer = new LayerBuffer(this, display, client);
   1239     layer->initStates(w, h, flags);
   1240     return layer;
   1241 }
   1242 
   1243 status_t SurfaceFlinger::removeSurface(const sp<Client>& client, SurfaceID sid)
   1244 {
   1245     /*
   1246      * called by the window manager, when a surface should be marked for
   1247      * destruction.
   1248      *
   1249      * The surface is removed from the current and drawing lists, but placed
   1250      * in the purgatory queue, so it's not destroyed right-away (we need
   1251      * to wait for all client's references to go away first).
   1252      */
   1253 
   1254     status_t err = NAME_NOT_FOUND;
   1255     Mutex::Autolock _l(mStateLock);
   1256     sp<LayerBaseClient> layer = client->getLayerUser(sid);
   1257     if (layer != 0) {
   1258         err = purgatorizeLayer_l(layer);
   1259         if (err == NO_ERROR) {
   1260             setTransactionFlags(eTransactionNeeded);
   1261         }
   1262     }
   1263     return err;
   1264 }
   1265 
   1266 status_t SurfaceFlinger::destroySurface(const sp<LayerBaseClient>& layer)
   1267 {
   1268     // called by ~ISurface() when all references are gone
   1269 
   1270     class MessageDestroySurface : public MessageBase {
   1271         SurfaceFlinger* flinger;
   1272         sp<LayerBaseClient> layer;
   1273     public:
   1274         MessageDestroySurface(
   1275                 SurfaceFlinger* flinger, const sp<LayerBaseClient>& layer)
   1276             : flinger(flinger), layer(layer) { }
   1277         virtual bool handler() {
   1278             sp<LayerBaseClient> l(layer);
   1279             layer.clear(); // clear it outside of the lock;
   1280             Mutex::Autolock _l(flinger->mStateLock);
   1281             /*
   1282              * remove the layer from the current list -- chances are that it's
   1283              * not in the list anyway, because it should have been removed
   1284              * already upon request of the client (eg: window manager).
   1285              * However, a buggy client could have not done that.
   1286              * Since we know we don't have any more clients, we don't need
   1287              * to use the purgatory.
   1288              */
   1289             status_t err = flinger->removeLayer_l(l);
   1290             LOGE_IF(err<0 && err != NAME_NOT_FOUND,
   1291                     "error removing layer=%p (%s)", l.get(), strerror(-err));
   1292             return true;
   1293         }
   1294     };
   1295 
   1296     postMessageAsync( new MessageDestroySurface(this, layer) );
   1297     return NO_ERROR;
   1298 }
   1299 
   1300 status_t SurfaceFlinger::setClientState(
   1301         const sp<Client>& client,
   1302         int32_t count,
   1303         const layer_state_t* states)
   1304 {
   1305     Mutex::Autolock _l(mStateLock);
   1306     uint32_t flags = 0;
   1307     for (int i=0 ; i<count ; i++) {
   1308         const layer_state_t& s(states[i]);
   1309         sp<LayerBaseClient> layer(client->getLayerUser(s.surface));
   1310         if (layer != 0) {
   1311             const uint32_t what = s.what;
   1312             if (what & ePositionChanged) {
   1313                 if (layer->setPosition(s.x, s.y))
   1314                     flags |= eTraversalNeeded;
   1315             }
   1316             if (what & eLayerChanged) {
   1317                 ssize_t idx = mCurrentState.layersSortedByZ.indexOf(layer);
   1318                 if (layer->setLayer(s.z)) {
   1319                     mCurrentState.layersSortedByZ.removeAt(idx);
   1320                     mCurrentState.layersSortedByZ.add(layer);
   1321                     // we need traversal (state changed)
   1322                     // AND transaction (list changed)
   1323                     flags |= eTransactionNeeded|eTraversalNeeded;
   1324                 }
   1325             }
   1326             if (what & eSizeChanged) {
   1327                 if (layer->setSize(s.w, s.h)) {
   1328                     flags |= eTraversalNeeded;
   1329                     mResizeTransationPending = true;
   1330                 }
   1331             }
   1332             if (what & eAlphaChanged) {
   1333                 if (layer->setAlpha(uint8_t(255.0f*s.alpha+0.5f)))
   1334                     flags |= eTraversalNeeded;
   1335             }
   1336             if (what & eMatrixChanged) {
   1337                 if (layer->setMatrix(s.matrix))
   1338                     flags |= eTraversalNeeded;
   1339             }
   1340             if (what & eTransparentRegionChanged) {
   1341                 if (layer->setTransparentRegionHint(s.transparentRegion))
   1342                     flags |= eTraversalNeeded;
   1343             }
   1344             if (what & eVisibilityChanged) {
   1345                 if (layer->setFlags(s.flags, s.mask))
   1346                     flags |= eTraversalNeeded;
   1347             }
   1348         }
   1349     }
   1350     if (flags) {
   1351         setTransactionFlags(flags);
   1352     }
   1353     return NO_ERROR;
   1354 }
   1355 
   1356 void SurfaceFlinger::screenReleased(int dpy)
   1357 {
   1358     // this may be called by a signal handler, we can't do too much in here
   1359     android_atomic_or(eConsoleReleased, &mConsoleSignals);
   1360     signalEvent();
   1361 }
   1362 
   1363 void SurfaceFlinger::screenAcquired(int dpy)
   1364 {
   1365     // this may be called by a signal handler, we can't do too much in here
   1366     android_atomic_or(eConsoleAcquired, &mConsoleSignals);
   1367     signalEvent();
   1368 }
   1369 
   1370 status_t SurfaceFlinger::dump(int fd, const Vector<String16>& args)
   1371 {
   1372     const size_t SIZE = 1024;
   1373     char buffer[SIZE];
   1374     String8 result;
   1375     if (!mDump.checkCalling()) {
   1376         snprintf(buffer, SIZE, "Permission Denial: "
   1377                 "can't dump SurfaceFlinger from pid=%d, uid=%d\n",
   1378                 IPCThreadState::self()->getCallingPid(),
   1379                 IPCThreadState::self()->getCallingUid());
   1380         result.append(buffer);
   1381     } else {
   1382 
   1383         // figure out if we're stuck somewhere
   1384         const nsecs_t now = systemTime();
   1385         const nsecs_t inSwapBuffers(mDebugInSwapBuffers);
   1386         const nsecs_t inTransaction(mDebugInTransaction);
   1387         nsecs_t inSwapBuffersDuration = (inSwapBuffers) ? now-inSwapBuffers : 0;
   1388         nsecs_t inTransactionDuration = (inTransaction) ? now-inTransaction : 0;
   1389 
   1390         // Try to get the main lock, but don't insist if we can't
   1391         // (this would indicate SF is stuck, but we want to be able to
   1392         // print something in dumpsys).
   1393         int retry = 3;
   1394         while (mStateLock.tryLock()<0 && --retry>=0) {
   1395             usleep(1000000);
   1396         }
   1397         const bool locked(retry >= 0);
   1398         if (!locked) {
   1399             snprintf(buffer, SIZE,
   1400                     "SurfaceFlinger appears to be unresponsive, "
   1401                     "dumping anyways (no locks held)\n");
   1402             result.append(buffer);
   1403         }
   1404 
   1405         const LayerVector& currentLayers = mCurrentState.layersSortedByZ;
   1406         const size_t count = currentLayers.size();
   1407         for (size_t i=0 ; i<count ; i++) {
   1408             const sp<LayerBase>& layer(currentLayers[i]);
   1409             layer->dump(result, buffer, SIZE);
   1410             const Layer::State& s(layer->drawingState());
   1411             s.transparentRegion.dump(result, "transparentRegion");
   1412             layer->transparentRegionScreen.dump(result, "transparentRegionScreen");
   1413             layer->visibleRegionScreen.dump(result, "visibleRegionScreen");
   1414         }
   1415 
   1416         mWormholeRegion.dump(result, "WormholeRegion");
   1417         const DisplayHardware& hw(graphicPlane(0).displayHardware());
   1418         snprintf(buffer, SIZE,
   1419                 "  display frozen: %s, freezeCount=%d, orientation=%d, canDraw=%d\n",
   1420                 mFreezeDisplay?"yes":"no", mFreezeCount,
   1421                 mCurrentState.orientation, hw.canDraw());
   1422         result.append(buffer);
   1423         snprintf(buffer, SIZE,
   1424                 "  last eglSwapBuffers() time: %f us\n"
   1425                 "  last transaction time     : %f us\n",
   1426                 mLastSwapBufferTime/1000.0, mLastTransactionTime/1000.0);
   1427         result.append(buffer);
   1428 
   1429         if (inSwapBuffersDuration || !locked) {
   1430             snprintf(buffer, SIZE, "  eglSwapBuffers time: %f us\n",
   1431                     inSwapBuffersDuration/1000.0);
   1432             result.append(buffer);
   1433         }
   1434 
   1435         if (inTransactionDuration || !locked) {
   1436             snprintf(buffer, SIZE, "  transaction time: %f us\n",
   1437                     inTransactionDuration/1000.0);
   1438             result.append(buffer);
   1439         }
   1440 
   1441         const GraphicBufferAllocator& alloc(GraphicBufferAllocator::get());
   1442         alloc.dump(result);
   1443 
   1444         if (locked) {
   1445             mStateLock.unlock();
   1446         }
   1447     }
   1448     write(fd, result.string(), result.size());
   1449     return NO_ERROR;
   1450 }
   1451 
   1452 status_t SurfaceFlinger::onTransact(
   1453     uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags)
   1454 {
   1455     switch (code) {
   1456         case CREATE_CONNECTION:
   1457         case OPEN_GLOBAL_TRANSACTION:
   1458         case CLOSE_GLOBAL_TRANSACTION:
   1459         case SET_ORIENTATION:
   1460         case FREEZE_DISPLAY:
   1461         case UNFREEZE_DISPLAY:
   1462         case BOOT_FINISHED:
   1463         case TURN_ELECTRON_BEAM_OFF:
   1464         case TURN_ELECTRON_BEAM_ON:
   1465         {
   1466             // codes that require permission check
   1467             IPCThreadState* ipc = IPCThreadState::self();
   1468             const int pid = ipc->getCallingPid();
   1469             const int uid = ipc->getCallingUid();
   1470             if ((uid != AID_GRAPHICS) && !mAccessSurfaceFlinger.check(pid, uid)) {
   1471                 LOGE("Permission Denial: "
   1472                         "can't access SurfaceFlinger pid=%d, uid=%d", pid, uid);
   1473                 return PERMISSION_DENIED;
   1474             }
   1475             break;
   1476         }
   1477         case CAPTURE_SCREEN:
   1478         {
   1479             // codes that require permission check
   1480             IPCThreadState* ipc = IPCThreadState::self();
   1481             const int pid = ipc->getCallingPid();
   1482             const int uid = ipc->getCallingUid();
   1483             if ((uid != AID_GRAPHICS) && !mReadFramebuffer.check(pid, uid)) {
   1484                 LOGE("Permission Denial: "
   1485                         "can't read framebuffer pid=%d, uid=%d", pid, uid);
   1486                 return PERMISSION_DENIED;
   1487             }
   1488             break;
   1489         }
   1490     }
   1491 
   1492     status_t err = BnSurfaceComposer::onTransact(code, data, reply, flags);
   1493     if (err == UNKNOWN_TRANSACTION || err == PERMISSION_DENIED) {
   1494         CHECK_INTERFACE(ISurfaceComposer, data, reply);
   1495         if (UNLIKELY(!mHardwareTest.checkCalling())) {
   1496             IPCThreadState* ipc = IPCThreadState::self();
   1497             const int pid = ipc->getCallingPid();
   1498             const int uid = ipc->getCallingUid();
   1499             LOGE("Permission Denial: "
   1500                     "can't access SurfaceFlinger pid=%d, uid=%d", pid, uid);
   1501             return PERMISSION_DENIED;
   1502         }
   1503         int n;
   1504         switch (code) {
   1505             case 1000: // SHOW_CPU, NOT SUPPORTED ANYMORE
   1506             case 1001: // SHOW_FPS, NOT SUPPORTED ANYMORE
   1507                 return NO_ERROR;
   1508             case 1002:  // SHOW_UPDATES
   1509                 n = data.readInt32();
   1510                 mDebugRegion = n ? n : (mDebugRegion ? 0 : 1);
   1511                 return NO_ERROR;
   1512             case 1003:  // SHOW_BACKGROUND
   1513                 n = data.readInt32();
   1514                 mDebugBackground = n ? 1 : 0;
   1515                 return NO_ERROR;
   1516             case 1004:{ // repaint everything
   1517                 Mutex::Autolock _l(mStateLock);
   1518                 const DisplayHardware& hw(graphicPlane(0).displayHardware());
   1519                 mDirtyRegion.set(hw.bounds()); // careful that's not thread-safe
   1520                 signalEvent();
   1521                 return NO_ERROR;
   1522             }
   1523             case 1005:{ // force transaction
   1524                 setTransactionFlags(eTransactionNeeded|eTraversalNeeded);
   1525                 return NO_ERROR;
   1526             }
   1527             case 1006:{ // enable/disable GraphicLog
   1528                 int enabled = data.readInt32();
   1529                 GraphicLog::getInstance().setEnabled(enabled);
   1530                 return NO_ERROR;
   1531             }
   1532             case 1007: // set mFreezeCount
   1533                 mFreezeCount = data.readInt32();
   1534                 mFreezeDisplayTime = 0;
   1535                 return NO_ERROR;
   1536             case 1010:  // interrogate.
   1537                 reply->writeInt32(0);
   1538                 reply->writeInt32(0);
   1539                 reply->writeInt32(mDebugRegion);
   1540                 reply->writeInt32(mDebugBackground);
   1541                 return NO_ERROR;
   1542             case 1013: {
   1543                 Mutex::Autolock _l(mStateLock);
   1544                 const DisplayHardware& hw(graphicPlane(0).displayHardware());
   1545                 reply->writeInt32(hw.getPageFlipCount());
   1546             }
   1547             return NO_ERROR;
   1548         }
   1549     }
   1550     return err;
   1551 }
   1552 
   1553 // ---------------------------------------------------------------------------
   1554 
   1555 status_t SurfaceFlinger::renderScreenToTextureLocked(DisplayID dpy,
   1556         GLuint* textureName, GLfloat* uOut, GLfloat* vOut)
   1557 {
   1558     if (!GLExtensions::getInstance().haveFramebufferObject())
   1559         return INVALID_OPERATION;
   1560 
   1561     // get screen geometry
   1562     const DisplayHardware& hw(graphicPlane(dpy).displayHardware());
   1563     const uint32_t hw_w = hw.getWidth();
   1564     const uint32_t hw_h = hw.getHeight();
   1565     GLfloat u = 1;
   1566     GLfloat v = 1;
   1567 
   1568     // make sure to clear all GL error flags
   1569     while ( glGetError() != GL_NO_ERROR ) ;
   1570 
   1571     // create a FBO
   1572     GLuint name, tname;
   1573     glGenTextures(1, &tname);
   1574     glBindTexture(GL_TEXTURE_2D, tname);
   1575     glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB,
   1576             hw_w, hw_h, 0, GL_RGB, GL_UNSIGNED_BYTE, 0);
   1577     if (glGetError() != GL_NO_ERROR) {
   1578         while ( glGetError() != GL_NO_ERROR ) ;
   1579         GLint tw = (2 << (31 - clz(hw_w)));
   1580         GLint th = (2 << (31 - clz(hw_h)));
   1581         glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB,
   1582                 tw, th, 0, GL_RGB, GL_UNSIGNED_BYTE, 0);
   1583         u = GLfloat(hw_w) / tw;
   1584         v = GLfloat(hw_h) / th;
   1585     }
   1586     glGenFramebuffersOES(1, &name);
   1587     glBindFramebufferOES(GL_FRAMEBUFFER_OES, name);
   1588     glFramebufferTexture2DOES(GL_FRAMEBUFFER_OES,
   1589             GL_COLOR_ATTACHMENT0_OES, GL_TEXTURE_2D, tname, 0);
   1590 
   1591     // redraw the screen entirely...
   1592     glClearColor(0,0,0,1);
   1593     glClear(GL_COLOR_BUFFER_BIT);
   1594     const Vector< sp<LayerBase> >& layers(mVisibleLayersSortedByZ);
   1595     const size_t count = layers.size();
   1596     for (size_t i=0 ; i<count ; ++i) {
   1597         const sp<LayerBase>& layer(layers[i]);
   1598         layer->drawForSreenShot();
   1599     }
   1600 
   1601     // back to main framebuffer
   1602     glBindFramebufferOES(GL_FRAMEBUFFER_OES, 0);
   1603     glDisable(GL_SCISSOR_TEST);
   1604     glDeleteFramebuffersOES(1, &name);
   1605 
   1606     *textureName = tname;
   1607     *uOut = u;
   1608     *vOut = v;
   1609     return NO_ERROR;
   1610 }
   1611 
   1612 // ---------------------------------------------------------------------------
   1613 
   1614 status_t SurfaceFlinger::electronBeamOffAnimationImplLocked()
   1615 {
   1616     status_t result = PERMISSION_DENIED;
   1617 
   1618     if (!GLExtensions::getInstance().haveFramebufferObject())
   1619         return INVALID_OPERATION;
   1620 
   1621     // get screen geometry
   1622     const DisplayHardware& hw(graphicPlane(0).displayHardware());
   1623     const uint32_t hw_w = hw.getWidth();
   1624     const uint32_t hw_h = hw.getHeight();
   1625     const Region screenBounds(hw.bounds());
   1626 
   1627     GLfloat u, v;
   1628     GLuint tname;
   1629     result = renderScreenToTextureLocked(0, &tname, &u, &v);
   1630     if (result != NO_ERROR) {
   1631         return result;
   1632     }
   1633 
   1634     GLfloat vtx[8];
   1635     const GLfloat texCoords[4][2] = { {0,v}, {0,0}, {u,0}, {u,v} };
   1636     glEnable(GL_TEXTURE_2D);
   1637     glBindTexture(GL_TEXTURE_2D, tname);
   1638     glTexEnvx(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
   1639     glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
   1640     glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
   1641     glTexCoordPointer(2, GL_FLOAT, 0, texCoords);
   1642     glEnableClientState(GL_TEXTURE_COORD_ARRAY);
   1643     glVertexPointer(2, GL_FLOAT, 0, vtx);
   1644 
   1645     class s_curve_interpolator {
   1646         const float nbFrames, s, v;
   1647     public:
   1648         s_curve_interpolator(int nbFrames, float s)
   1649         : nbFrames(1.0f / (nbFrames-1)), s(s),
   1650           v(1.0f + expf(-s + 0.5f*s)) {
   1651         }
   1652         float operator()(int f) {
   1653             const float x = f * nbFrames;
   1654             return ((1.0f/(1.0f + expf(-x*s + 0.5f*s))) - 0.5f) * v + 0.5f;
   1655         }
   1656     };
   1657 
   1658     class v_stretch {
   1659         const GLfloat hw_w, hw_h;
   1660     public:
   1661         v_stretch(uint32_t hw_w, uint32_t hw_h)
   1662         : hw_w(hw_w), hw_h(hw_h) {
   1663         }
   1664         void operator()(GLfloat* vtx, float v) {
   1665             const GLfloat w = hw_w + (hw_w * v);
   1666             const GLfloat h = hw_h - (hw_h * v);
   1667             const GLfloat x = (hw_w - w) * 0.5f;
   1668             const GLfloat y = (hw_h - h) * 0.5f;
   1669             vtx[0] = x;         vtx[1] = y;
   1670             vtx[2] = x;         vtx[3] = y + h;
   1671             vtx[4] = x + w;     vtx[5] = y + h;
   1672             vtx[6] = x + w;     vtx[7] = y;
   1673         }
   1674     };
   1675 
   1676     class h_stretch {
   1677         const GLfloat hw_w, hw_h;
   1678     public:
   1679         h_stretch(uint32_t hw_w, uint32_t hw_h)
   1680         : hw_w(hw_w), hw_h(hw_h) {
   1681         }
   1682         void operator()(GLfloat* vtx, float v) {
   1683             const GLfloat w = hw_w - (hw_w * v);
   1684             const GLfloat h = 1.0f;
   1685             const GLfloat x = (hw_w - w) * 0.5f;
   1686             const GLfloat y = (hw_h - h) * 0.5f;
   1687             vtx[0] = x;         vtx[1] = y;
   1688             vtx[2] = x;         vtx[3] = y + h;
   1689             vtx[4] = x + w;     vtx[5] = y + h;
   1690             vtx[6] = x + w;     vtx[7] = y;
   1691         }
   1692     };
   1693 
   1694     // the full animation is 24 frames
   1695     const int nbFrames = 12;
   1696     s_curve_interpolator itr(nbFrames, 7.5f);
   1697     s_curve_interpolator itg(nbFrames, 8.0f);
   1698     s_curve_interpolator itb(nbFrames, 8.5f);
   1699 
   1700     v_stretch vverts(hw_w, hw_h);
   1701     glEnable(GL_BLEND);
   1702     glBlendFunc(GL_ONE, GL_ONE);
   1703     for (int i=0 ; i<nbFrames ; i++) {
   1704         float x, y, w, h;
   1705         const float vr = itr(i);
   1706         const float vg = itg(i);
   1707         const float vb = itb(i);
   1708 
   1709         // clear screen
   1710         glColorMask(1,1,1,1);
   1711         glClear(GL_COLOR_BUFFER_BIT);
   1712         glEnable(GL_TEXTURE_2D);
   1713 
   1714         // draw the red plane
   1715         vverts(vtx, vr);
   1716         glColorMask(1,0,0,1);
   1717         glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
   1718 
   1719         // draw the green plane
   1720         vverts(vtx, vg);
   1721         glColorMask(0,1,0,1);
   1722         glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
   1723 
   1724         // draw the blue plane
   1725         vverts(vtx, vb);
   1726         glColorMask(0,0,1,1);
   1727         glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
   1728 
   1729         // draw the white highlight (we use the last vertices)
   1730         glDisable(GL_TEXTURE_2D);
   1731         glColorMask(1,1,1,1);
   1732         glColor4f(vg, vg, vg, 1);
   1733         glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
   1734         hw.flip(screenBounds);
   1735     }
   1736 
   1737     h_stretch hverts(hw_w, hw_h);
   1738     glDisable(GL_BLEND);
   1739     glDisable(GL_TEXTURE_2D);
   1740     glColorMask(1,1,1,1);
   1741     for (int i=0 ; i<nbFrames ; i++) {
   1742         const float v = itg(i);
   1743         hverts(vtx, v);
   1744         glClear(GL_COLOR_BUFFER_BIT);
   1745         glColor4f(1-v, 1-v, 1-v, 1);
   1746         glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
   1747         hw.flip(screenBounds);
   1748     }
   1749 
   1750     glColorMask(1,1,1,1);
   1751     glEnable(GL_SCISSOR_TEST);
   1752     glDisableClientState(GL_TEXTURE_COORD_ARRAY);
   1753     glDeleteTextures(1, &tname);
   1754     return NO_ERROR;
   1755 }
   1756 
   1757 status_t SurfaceFlinger::electronBeamOnAnimationImplLocked()
   1758 {
   1759     status_t result = PERMISSION_DENIED;
   1760 
   1761     if (!GLExtensions::getInstance().haveFramebufferObject())
   1762         return INVALID_OPERATION;
   1763 
   1764 
   1765     // get screen geometry
   1766     const DisplayHardware& hw(graphicPlane(0).displayHardware());
   1767     const uint32_t hw_w = hw.getWidth();
   1768     const uint32_t hw_h = hw.getHeight();
   1769     const Region screenBounds(hw.bounds());
   1770 
   1771     GLfloat u, v;
   1772     GLuint tname;
   1773     result = renderScreenToTextureLocked(0, &tname, &u, &v);
   1774     if (result != NO_ERROR) {
   1775         return result;
   1776     }
   1777 
   1778     // back to main framebuffer
   1779     glBindFramebufferOES(GL_FRAMEBUFFER_OES, 0);
   1780     glDisable(GL_SCISSOR_TEST);
   1781 
   1782     GLfloat vtx[8];
   1783     const GLfloat texCoords[4][2] = { {0,v}, {0,0}, {u,0}, {u,v} };
   1784     glEnable(GL_TEXTURE_2D);
   1785     glBindTexture(GL_TEXTURE_2D, tname);
   1786     glTexEnvx(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
   1787     glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
   1788     glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
   1789     glTexCoordPointer(2, GL_FLOAT, 0, texCoords);
   1790     glEnableClientState(GL_TEXTURE_COORD_ARRAY);
   1791     glVertexPointer(2, GL_FLOAT, 0, vtx);
   1792 
   1793     class s_curve_interpolator {
   1794         const float nbFrames, s, v;
   1795     public:
   1796         s_curve_interpolator(int nbFrames, float s)
   1797         : nbFrames(1.0f / (nbFrames-1)), s(s),
   1798           v(1.0f + expf(-s + 0.5f*s)) {
   1799         }
   1800         float operator()(int f) {
   1801             const float x = f * nbFrames;
   1802             return ((1.0f/(1.0f + expf(-x*s + 0.5f*s))) - 0.5f) * v + 0.5f;
   1803         }
   1804     };
   1805 
   1806     class v_stretch {
   1807         const GLfloat hw_w, hw_h;
   1808     public:
   1809         v_stretch(uint32_t hw_w, uint32_t hw_h)
   1810         : hw_w(hw_w), hw_h(hw_h) {
   1811         }
   1812         void operator()(GLfloat* vtx, float v) {
   1813             const GLfloat w = hw_w + (hw_w * v);
   1814             const GLfloat h = hw_h - (hw_h * v);
   1815             const GLfloat x = (hw_w - w) * 0.5f;
   1816             const GLfloat y = (hw_h - h) * 0.5f;
   1817             vtx[0] = x;         vtx[1] = y;
   1818             vtx[2] = x;         vtx[3] = y + h;
   1819             vtx[4] = x + w;     vtx[5] = y + h;
   1820             vtx[6] = x + w;     vtx[7] = y;
   1821         }
   1822     };
   1823 
   1824     class h_stretch {
   1825         const GLfloat hw_w, hw_h;
   1826     public:
   1827         h_stretch(uint32_t hw_w, uint32_t hw_h)
   1828         : hw_w(hw_w), hw_h(hw_h) {
   1829         }
   1830         void operator()(GLfloat* vtx, float v) {
   1831             const GLfloat w = hw_w - (hw_w * v);
   1832             const GLfloat h = 1.0f;
   1833             const GLfloat x = (hw_w - w) * 0.5f;
   1834             const GLfloat y = (hw_h - h) * 0.5f;
   1835             vtx[0] = x;         vtx[1] = y;
   1836             vtx[2] = x;         vtx[3] = y + h;
   1837             vtx[4] = x + w;     vtx[5] = y + h;
   1838             vtx[6] = x + w;     vtx[7] = y;
   1839         }
   1840     };
   1841 
   1842     // the full animation is 12 frames
   1843     int nbFrames = 8;
   1844     s_curve_interpolator itr(nbFrames, 7.5f);
   1845     s_curve_interpolator itg(nbFrames, 8.0f);
   1846     s_curve_interpolator itb(nbFrames, 8.5f);
   1847 
   1848     h_stretch hverts(hw_w, hw_h);
   1849     glDisable(GL_BLEND);
   1850     glDisable(GL_TEXTURE_2D);
   1851     glColorMask(1,1,1,1);
   1852     for (int i=nbFrames-1 ; i>=0 ; i--) {
   1853         const float v = itg(i);
   1854         hverts(vtx, v);
   1855         glClear(GL_COLOR_BUFFER_BIT);
   1856         glColor4f(1-v, 1-v, 1-v, 1);
   1857         glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
   1858         hw.flip(screenBounds);
   1859     }
   1860 
   1861     nbFrames = 4;
   1862     v_stretch vverts(hw_w, hw_h);
   1863     glEnable(GL_BLEND);
   1864     glBlendFunc(GL_ONE, GL_ONE);
   1865     for (int i=nbFrames-1 ; i>=0 ; i--) {
   1866         float x, y, w, h;
   1867         const float vr = itr(i);
   1868         const float vg = itg(i);
   1869         const float vb = itb(i);
   1870 
   1871         // clear screen
   1872         glColorMask(1,1,1,1);
   1873         glClear(GL_COLOR_BUFFER_BIT);
   1874         glEnable(GL_TEXTURE_2D);
   1875 
   1876         // draw the red plane
   1877         vverts(vtx, vr);
   1878         glColorMask(1,0,0,1);
   1879         glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
   1880 
   1881         // draw the green plane
   1882         vverts(vtx, vg);
   1883         glColorMask(0,1,0,1);
   1884         glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
   1885 
   1886         // draw the blue plane
   1887         vverts(vtx, vb);
   1888         glColorMask(0,0,1,1);
   1889         glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
   1890 
   1891         hw.flip(screenBounds);
   1892     }
   1893 
   1894     glColorMask(1,1,1,1);
   1895     glEnable(GL_SCISSOR_TEST);
   1896     glDisableClientState(GL_TEXTURE_COORD_ARRAY);
   1897     glDeleteTextures(1, &tname);
   1898 
   1899     return NO_ERROR;
   1900 }
   1901 
   1902 // ---------------------------------------------------------------------------
   1903 
   1904 status_t SurfaceFlinger::turnElectronBeamOffImplLocked(int32_t mode)
   1905 {
   1906     DisplayHardware& hw(graphicPlane(0).editDisplayHardware());
   1907     if (!hw.canDraw()) {
   1908         // we're already off
   1909         return NO_ERROR;
   1910     }
   1911     if (mode & ISurfaceComposer::eElectronBeamAnimationOff) {
   1912         electronBeamOffAnimationImplLocked();
   1913     }
   1914 
   1915     // always clear the whole screen at the end of the animation
   1916     glClearColor(0,0,0,1);
   1917     glDisable(GL_SCISSOR_TEST);
   1918     glClear(GL_COLOR_BUFFER_BIT);
   1919     glEnable(GL_SCISSOR_TEST);
   1920     hw.flip( Region(hw.bounds()) );
   1921 
   1922     hw.setCanDraw(false);
   1923     return NO_ERROR;
   1924 }
   1925 
   1926 status_t SurfaceFlinger::turnElectronBeamOff(int32_t mode)
   1927 {
   1928     class MessageTurnElectronBeamOff : public MessageBase {
   1929         SurfaceFlinger* flinger;
   1930         int32_t mode;
   1931         status_t result;
   1932     public:
   1933         MessageTurnElectronBeamOff(SurfaceFlinger* flinger, int32_t mode)
   1934             : flinger(flinger), mode(mode), result(PERMISSION_DENIED) {
   1935         }
   1936         status_t getResult() const {
   1937             return result;
   1938         }
   1939         virtual bool handler() {
   1940             Mutex::Autolock _l(flinger->mStateLock);
   1941             result = flinger->turnElectronBeamOffImplLocked(mode);
   1942             return true;
   1943         }
   1944     };
   1945 
   1946     sp<MessageBase> msg = new MessageTurnElectronBeamOff(this, mode);
   1947     status_t res = postMessageSync(msg);
   1948     if (res == NO_ERROR) {
   1949         res = static_cast<MessageTurnElectronBeamOff*>( msg.get() )->getResult();
   1950 
   1951         // work-around: when the power-manager calls us we activate the
   1952         // animation. eventually, the "on" animation will be called
   1953         // by the power-manager itself
   1954         mElectronBeamAnimationMode = mode;
   1955     }
   1956     return res;
   1957 }
   1958 
   1959 // ---------------------------------------------------------------------------
   1960 
   1961 status_t SurfaceFlinger::turnElectronBeamOnImplLocked(int32_t mode)
   1962 {
   1963     DisplayHardware& hw(graphicPlane(0).editDisplayHardware());
   1964     if (hw.canDraw()) {
   1965         // we're already on
   1966         return NO_ERROR;
   1967     }
   1968     if (mode & ISurfaceComposer::eElectronBeamAnimationOn) {
   1969         electronBeamOnAnimationImplLocked();
   1970     }
   1971     hw.setCanDraw(true);
   1972 
   1973     // make sure to redraw the whole screen when the animation is done
   1974     mDirtyRegion.set(hw.bounds());
   1975     signalEvent();
   1976 
   1977     return NO_ERROR;
   1978 }
   1979 
   1980 status_t SurfaceFlinger::turnElectronBeamOn(int32_t mode)
   1981 {
   1982     class MessageTurnElectronBeamOn : public MessageBase {
   1983         SurfaceFlinger* flinger;
   1984         int32_t mode;
   1985         status_t result;
   1986     public:
   1987         MessageTurnElectronBeamOn(SurfaceFlinger* flinger, int32_t mode)
   1988             : flinger(flinger), mode(mode), result(PERMISSION_DENIED) {
   1989         }
   1990         status_t getResult() const {
   1991             return result;
   1992         }
   1993         virtual bool handler() {
   1994             Mutex::Autolock _l(flinger->mStateLock);
   1995             result = flinger->turnElectronBeamOnImplLocked(mode);
   1996             return true;
   1997         }
   1998     };
   1999 
   2000     postMessageAsync( new MessageTurnElectronBeamOn(this, mode) );
   2001     return NO_ERROR;
   2002 }
   2003 
   2004 // ---------------------------------------------------------------------------
   2005 
   2006 status_t SurfaceFlinger::captureScreenImplLocked(DisplayID dpy,
   2007         sp<IMemoryHeap>* heap,
   2008         uint32_t* w, uint32_t* h, PixelFormat* f,
   2009         uint32_t sw, uint32_t sh)
   2010 {
   2011     status_t result = PERMISSION_DENIED;
   2012 
   2013     // only one display supported for now
   2014     if (UNLIKELY(uint32_t(dpy) >= DISPLAY_COUNT))
   2015         return BAD_VALUE;
   2016 
   2017     if (!GLExtensions::getInstance().haveFramebufferObject())
   2018         return INVALID_OPERATION;
   2019 
   2020     // get screen geometry
   2021     const DisplayHardware& hw(graphicPlane(dpy).displayHardware());
   2022     const uint32_t hw_w = hw.getWidth();
   2023     const uint32_t hw_h = hw.getHeight();
   2024 
   2025     if ((sw > hw_w) || (sh > hw_h))
   2026         return BAD_VALUE;
   2027 
   2028     sw = (!sw) ? hw_w : sw;
   2029     sh = (!sh) ? hw_h : sh;
   2030     const size_t size = sw * sh * 4;
   2031 
   2032     // make sure to clear all GL error flags
   2033     while ( glGetError() != GL_NO_ERROR ) ;
   2034 
   2035     // create a FBO
   2036     GLuint name, tname;
   2037     glGenRenderbuffersOES(1, &tname);
   2038     glBindRenderbufferOES(GL_RENDERBUFFER_OES, tname);
   2039     glRenderbufferStorageOES(GL_RENDERBUFFER_OES, GL_RGBA8_OES, sw, sh);
   2040     glGenFramebuffersOES(1, &name);
   2041     glBindFramebufferOES(GL_FRAMEBUFFER_OES, name);
   2042     glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES,
   2043             GL_COLOR_ATTACHMENT0_OES, GL_RENDERBUFFER_OES, tname);
   2044 
   2045     GLenum status = glCheckFramebufferStatusOES(GL_FRAMEBUFFER_OES);
   2046     if (status == GL_FRAMEBUFFER_COMPLETE_OES) {
   2047 
   2048         // invert everything, b/c glReadPixel() below will invert the FB
   2049         glViewport(0, 0, sw, sh);
   2050         glMatrixMode(GL_PROJECTION);
   2051         glPushMatrix();
   2052         glLoadIdentity();
   2053         glOrthof(0, hw_w, 0, hw_h, 0, 1);
   2054         glMatrixMode(GL_MODELVIEW);
   2055 
   2056         // redraw the screen entirely...
   2057         glClearColor(0,0,0,1);
   2058         glClear(GL_COLOR_BUFFER_BIT);
   2059         const Vector< sp<LayerBase> >& layers(mVisibleLayersSortedByZ);
   2060         const size_t count = layers.size();
   2061         for (size_t i=0 ; i<count ; ++i) {
   2062             const sp<LayerBase>& layer(layers[i]);
   2063             layer->drawForSreenShot();
   2064         }
   2065 
   2066         // XXX: this is needed on tegra
   2067         glScissor(0, 0, sw, sh);
   2068 
   2069         // check for errors and return screen capture
   2070         if (glGetError() != GL_NO_ERROR) {
   2071             // error while rendering
   2072             result = INVALID_OPERATION;
   2073         } else {
   2074             // allocate shared memory large enough to hold the
   2075             // screen capture
   2076             sp<MemoryHeapBase> base(
   2077                     new MemoryHeapBase(size, 0, "screen-capture") );
   2078             void* const ptr = base->getBase();
   2079             if (ptr) {
   2080                 // capture the screen with glReadPixels()
   2081                 glReadPixels(0, 0, sw, sh, GL_RGBA, GL_UNSIGNED_BYTE, ptr);
   2082                 if (glGetError() == GL_NO_ERROR) {
   2083                     *heap = base;
   2084                     *w = sw;
   2085                     *h = sh;
   2086                     *f = PIXEL_FORMAT_RGBA_8888;
   2087                     result = NO_ERROR;
   2088                 }
   2089             } else {
   2090                 result = NO_MEMORY;
   2091             }
   2092         }
   2093 
   2094         glEnable(GL_SCISSOR_TEST);
   2095         glViewport(0, 0, hw_w, hw_h);
   2096         glMatrixMode(GL_PROJECTION);
   2097         glPopMatrix();
   2098         glMatrixMode(GL_MODELVIEW);
   2099 
   2100 
   2101     } else {
   2102         result = BAD_VALUE;
   2103     }
   2104 
   2105     // release FBO resources
   2106     glBindFramebufferOES(GL_FRAMEBUFFER_OES, 0);
   2107     glDeleteRenderbuffersOES(1, &tname);
   2108     glDeleteFramebuffersOES(1, &name);
   2109     return result;
   2110 }
   2111 
   2112 
   2113 status_t SurfaceFlinger::captureScreen(DisplayID dpy,
   2114         sp<IMemoryHeap>* heap,
   2115         uint32_t* width, uint32_t* height, PixelFormat* format,
   2116         uint32_t sw, uint32_t sh)
   2117 {
   2118     // only one display supported for now
   2119     if (UNLIKELY(uint32_t(dpy) >= DISPLAY_COUNT))
   2120         return BAD_VALUE;
   2121 
   2122     if (!GLExtensions::getInstance().haveFramebufferObject())
   2123         return INVALID_OPERATION;
   2124 
   2125     class MessageCaptureScreen : public MessageBase {
   2126         SurfaceFlinger* flinger;
   2127         DisplayID dpy;
   2128         sp<IMemoryHeap>* heap;
   2129         uint32_t* w;
   2130         uint32_t* h;
   2131         PixelFormat* f;
   2132         uint32_t sw;
   2133         uint32_t sh;
   2134         status_t result;
   2135     public:
   2136         MessageCaptureScreen(SurfaceFlinger* flinger, DisplayID dpy,
   2137                 sp<IMemoryHeap>* heap, uint32_t* w, uint32_t* h, PixelFormat* f,
   2138                 uint32_t sw, uint32_t sh)
   2139             : flinger(flinger), dpy(dpy),
   2140               heap(heap), w(w), h(h), f(f), sw(sw), sh(sh), result(PERMISSION_DENIED)
   2141         {
   2142         }
   2143         status_t getResult() const {
   2144             return result;
   2145         }
   2146         virtual bool handler() {
   2147             Mutex::Autolock _l(flinger->mStateLock);
   2148 
   2149             // if we have secure windows, never allow the screen capture
   2150             if (flinger->mSecureFrameBuffer)
   2151                 return true;
   2152 
   2153             result = flinger->captureScreenImplLocked(dpy,
   2154                     heap, w, h, f, sw, sh);
   2155 
   2156             return true;
   2157         }
   2158     };
   2159 
   2160     sp<MessageBase> msg = new MessageCaptureScreen(this,
   2161             dpy, heap, width, height, format, sw, sh);
   2162     status_t res = postMessageSync(msg);
   2163     if (res == NO_ERROR) {
   2164         res = static_cast<MessageCaptureScreen*>( msg.get() )->getResult();
   2165     }
   2166     return res;
   2167 }
   2168 
   2169 // ---------------------------------------------------------------------------
   2170 
   2171 sp<Layer> SurfaceFlinger::getLayer(const sp<ISurface>& sur) const
   2172 {
   2173     sp<Layer> result;
   2174     Mutex::Autolock _l(mStateLock);
   2175     result = mLayerMap.valueFor( sur->asBinder() ).promote();
   2176     return result;
   2177 }
   2178 
   2179 // ---------------------------------------------------------------------------
   2180 
   2181 Client::Client(const sp<SurfaceFlinger>& flinger)
   2182     : mFlinger(flinger), mNameGenerator(1)
   2183 {
   2184 }
   2185 
   2186 Client::~Client()
   2187 {
   2188     const size_t count = mLayers.size();
   2189     for (size_t i=0 ; i<count ; i++) {
   2190         sp<LayerBaseClient> layer(mLayers.valueAt(i).promote());
   2191         if (layer != 0) {
   2192             mFlinger->removeLayer(layer);
   2193         }
   2194     }
   2195 }
   2196 
   2197 status_t Client::initCheck() const {
   2198     return NO_ERROR;
   2199 }
   2200 
   2201 ssize_t Client::attachLayer(const sp<LayerBaseClient>& layer)
   2202 {
   2203     int32_t name = android_atomic_inc(&mNameGenerator);
   2204     mLayers.add(name, layer);
   2205     return name;
   2206 }
   2207 
   2208 void Client::detachLayer(const LayerBaseClient* layer)
   2209 {
   2210     // we do a linear search here, because this doesn't happen often
   2211     const size_t count = mLayers.size();
   2212     for (size_t i=0 ; i<count ; i++) {
   2213         if (mLayers.valueAt(i) == layer) {
   2214             mLayers.removeItemsAt(i, 1);
   2215             break;
   2216         }
   2217     }
   2218 }
   2219 sp<LayerBaseClient> Client::getLayerUser(int32_t i) const {
   2220     sp<LayerBaseClient> lbc;
   2221     const wp<LayerBaseClient>& layer(mLayers.valueFor(i));
   2222     if (layer != 0) {
   2223         lbc = layer.promote();
   2224         LOGE_IF(lbc==0, "getLayerUser(name=%d) is dead", int(i));
   2225     }
   2226     return lbc;
   2227 }
   2228 
   2229 sp<IMemoryHeap> Client::getControlBlock() const {
   2230     return 0;
   2231 }
   2232 ssize_t Client::getTokenForSurface(const sp<ISurface>& sur) const {
   2233     return -1;
   2234 }
   2235 sp<ISurface> Client::createSurface(
   2236         ISurfaceComposerClient::surface_data_t* params, int pid,
   2237         const String8& name,
   2238         DisplayID display, uint32_t w, uint32_t h, PixelFormat format,
   2239         uint32_t flags)
   2240 {
   2241     return mFlinger->createSurface(this, pid, name, params,
   2242             display, w, h, format, flags);
   2243 }
   2244 status_t Client::destroySurface(SurfaceID sid) {
   2245     return mFlinger->removeSurface(this, sid);
   2246 }
   2247 status_t Client::setState(int32_t count, const layer_state_t* states) {
   2248     return mFlinger->setClientState(this, count, states);
   2249 }
   2250 
   2251 // ---------------------------------------------------------------------------
   2252 
   2253 UserClient::UserClient(const sp<SurfaceFlinger>& flinger)
   2254     : ctrlblk(0), mBitmap(0), mFlinger(flinger)
   2255 {
   2256     const int pgsize = getpagesize();
   2257     const int cblksize = ((sizeof(SharedClient)+(pgsize-1))&~(pgsize-1));
   2258 
   2259     mCblkHeap = new MemoryHeapBase(cblksize, 0,
   2260             "SurfaceFlinger Client control-block");
   2261 
   2262     ctrlblk = static_cast<SharedClient *>(mCblkHeap->getBase());
   2263     if (ctrlblk) { // construct the shared structure in-place.
   2264         new(ctrlblk) SharedClient;
   2265     }
   2266 }
   2267 
   2268 UserClient::~UserClient()
   2269 {
   2270     if (ctrlblk) {
   2271         ctrlblk->~SharedClient();  // destroy our shared-structure.
   2272     }
   2273 
   2274     /*
   2275      * When a UserClient dies, it's unclear what to do exactly.
   2276      * We could go ahead and destroy all surfaces linked to that client
   2277      * however, it wouldn't be fair to the main Client
   2278      * (usually the the window-manager), which might want to re-target
   2279      * the layer to another UserClient.
   2280      * I think the best is to do nothing, or not much; in most cases the
   2281      * WM itself will go ahead and clean things up when it detects a client of
   2282      * his has died.
   2283      * The remaining question is what to display? currently we keep
   2284      * just keep the current buffer.
   2285      */
   2286 }
   2287 
   2288 status_t UserClient::initCheck() const {
   2289     return ctrlblk == 0 ? NO_INIT : NO_ERROR;
   2290 }
   2291 
   2292 void UserClient::detachLayer(const Layer* layer)
   2293 {
   2294     int32_t name = layer->getToken();
   2295     if (name >= 0) {
   2296         int32_t mask = 1LU<<name;
   2297         if ((android_atomic_and(~mask, &mBitmap) & mask) == 0) {
   2298             LOGW("token %d wasn't marked as used %08x", name, int(mBitmap));
   2299         }
   2300     }
   2301 }
   2302 
   2303 sp<IMemoryHeap> UserClient::getControlBlock() const {
   2304     return mCblkHeap;
   2305 }
   2306 
   2307 ssize_t UserClient::getTokenForSurface(const sp<ISurface>& sur) const
   2308 {
   2309     int32_t name = NAME_NOT_FOUND;
   2310     sp<Layer> layer(mFlinger->getLayer(sur));
   2311     if (layer == 0) return name;
   2312 
   2313     // if this layer already has a token, just return it
   2314     name = layer->getToken();
   2315     if ((name >= 0) && (layer->getClient() == this))
   2316         return name;
   2317 
   2318     name = 0;
   2319     do {
   2320         int32_t mask = 1LU<<name;
   2321         if ((android_atomic_or(mask, &mBitmap) & mask) == 0) {
   2322             // we found and locked that name
   2323             status_t err = layer->setToken(
   2324                     const_cast<UserClient*>(this), ctrlblk, name);
   2325             if (err != NO_ERROR) {
   2326                 // free the name
   2327                 android_atomic_and(~mask, &mBitmap);
   2328                 name = err;
   2329             }
   2330             break;
   2331         }
   2332         if (++name > 31)
   2333             name = NO_MEMORY;
   2334     } while(name >= 0);
   2335 
   2336     //LOGD("getTokenForSurface(%p) => %d (client=%p, bitmap=%08lx)",
   2337     //        sur->asBinder().get(), name, this, mBitmap);
   2338     return name;
   2339 }
   2340 
   2341 sp<ISurface> UserClient::createSurface(
   2342         ISurfaceComposerClient::surface_data_t* params, int pid,
   2343         const String8& name,
   2344         DisplayID display, uint32_t w, uint32_t h, PixelFormat format,
   2345         uint32_t flags) {
   2346     return 0;
   2347 }
   2348 status_t UserClient::destroySurface(SurfaceID sid) {
   2349     return INVALID_OPERATION;
   2350 }
   2351 status_t UserClient::setState(int32_t count, const layer_state_t* states) {
   2352     return INVALID_OPERATION;
   2353 }
   2354 
   2355 // ---------------------------------------------------------------------------
   2356 
   2357 GraphicPlane::GraphicPlane()
   2358     : mHw(0)
   2359 {
   2360 }
   2361 
   2362 GraphicPlane::~GraphicPlane() {
   2363     delete mHw;
   2364 }
   2365 
   2366 bool GraphicPlane::initialized() const {
   2367     return mHw ? true : false;
   2368 }
   2369 
   2370 int GraphicPlane::getWidth() const {
   2371     return mWidth;
   2372 }
   2373 
   2374 int GraphicPlane::getHeight() const {
   2375     return mHeight;
   2376 }
   2377 
   2378 void GraphicPlane::setDisplayHardware(DisplayHardware *hw)
   2379 {
   2380     mHw = hw;
   2381 
   2382     // initialize the display orientation transform.
   2383     // it's a constant that should come from the display driver.
   2384     int displayOrientation = ISurfaceComposer::eOrientationDefault;
   2385     char property[PROPERTY_VALUE_MAX];
   2386     if (property_get("ro.sf.hwrotation", property, NULL) > 0) {
   2387         //displayOrientation
   2388         switch (atoi(property)) {
   2389         case 90:
   2390             displayOrientation = ISurfaceComposer::eOrientation90;
   2391             break;
   2392         case 270:
   2393             displayOrientation = ISurfaceComposer::eOrientation270;
   2394             break;
   2395         }
   2396     }
   2397 
   2398     const float w = hw->getWidth();
   2399     const float h = hw->getHeight();
   2400     GraphicPlane::orientationToTransfrom(displayOrientation, w, h,
   2401             &mDisplayTransform);
   2402     if (displayOrientation & ISurfaceComposer::eOrientationSwapMask) {
   2403         mDisplayWidth = h;
   2404         mDisplayHeight = w;
   2405     } else {
   2406         mDisplayWidth = w;
   2407         mDisplayHeight = h;
   2408     }
   2409 
   2410     setOrientation(ISurfaceComposer::eOrientationDefault);
   2411 }
   2412 
   2413 status_t GraphicPlane::orientationToTransfrom(
   2414         int orientation, int w, int h, Transform* tr)
   2415 {
   2416     uint32_t flags = 0;
   2417     switch (orientation) {
   2418     case ISurfaceComposer::eOrientationDefault:
   2419         flags = Transform::ROT_0;
   2420         break;
   2421     case ISurfaceComposer::eOrientation90:
   2422         flags = Transform::ROT_90;
   2423         break;
   2424     case ISurfaceComposer::eOrientation180:
   2425         flags = Transform::ROT_180;
   2426         break;
   2427     case ISurfaceComposer::eOrientation270:
   2428         flags = Transform::ROT_270;
   2429         break;
   2430     default:
   2431         return BAD_VALUE;
   2432     }
   2433     tr->set(flags, w, h);
   2434     return NO_ERROR;
   2435 }
   2436 
   2437 status_t GraphicPlane::setOrientation(int orientation)
   2438 {
   2439     // If the rotation can be handled in hardware, this is where
   2440     // the magic should happen.
   2441 
   2442     const DisplayHardware& hw(displayHardware());
   2443     const float w = mDisplayWidth;
   2444     const float h = mDisplayHeight;
   2445     mWidth = int(w);
   2446     mHeight = int(h);
   2447 
   2448     Transform orientationTransform;
   2449     GraphicPlane::orientationToTransfrom(orientation, w, h,
   2450             &orientationTransform);
   2451     if (orientation & ISurfaceComposer::eOrientationSwapMask) {
   2452         mWidth = int(h);
   2453         mHeight = int(w);
   2454     }
   2455 
   2456     mOrientation = orientation;
   2457     mGlobalTransform = mDisplayTransform * orientationTransform;
   2458     return NO_ERROR;
   2459 }
   2460 
   2461 const DisplayHardware& GraphicPlane::displayHardware() const {
   2462     return *mHw;
   2463 }
   2464 
   2465 DisplayHardware& GraphicPlane::editDisplayHardware() {
   2466     return *mHw;
   2467 }
   2468 
   2469 const Transform& GraphicPlane::transform() const {
   2470     return mGlobalTransform;
   2471 }
   2472 
   2473 EGLDisplay GraphicPlane::getEGLDisplay() const {
   2474     return mHw->getEGLDisplay();
   2475 }
   2476 
   2477 // ---------------------------------------------------------------------------
   2478 
   2479 }; // namespace android
   2480