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 <string.h>
     20 #include <math.h>
     21 
     22 #include <cutils/properties.h>
     23 
     24 #include <utils/RefBase.h>
     25 #include <utils/Log.h>
     26 
     27 #include <ui/DisplayInfo.h>
     28 #include <ui/PixelFormat.h>
     29 
     30 #include <gui/SurfaceTextureClient.h>
     31 
     32 #include <GLES/gl.h>
     33 #include <EGL/egl.h>
     34 #include <EGL/eglext.h>
     35 
     36 #include <hardware/gralloc.h>
     37 
     38 #include "DisplayHardware/FramebufferSurface.h"
     39 #include "DisplayHardware/HWComposer.h"
     40 
     41 #include "clz.h"
     42 #include "DisplayDevice.h"
     43 #include "GLExtensions.h"
     44 #include "SurfaceFlinger.h"
     45 #include "LayerBase.h"
     46 
     47 // ----------------------------------------------------------------------------
     48 using namespace android;
     49 // ----------------------------------------------------------------------------
     50 
     51 static __attribute__((noinline))
     52 void checkGLErrors()
     53 {
     54     do {
     55         // there could be more than one error flag
     56         GLenum error = glGetError();
     57         if (error == GL_NO_ERROR)
     58             break;
     59         ALOGE("GL error 0x%04x", int(error));
     60     } while(true);
     61 }
     62 
     63 // ----------------------------------------------------------------------------
     64 
     65 /*
     66  * Initialize the display to the specified values.
     67  *
     68  */
     69 
     70 DisplayDevice::DisplayDevice(
     71         const sp<SurfaceFlinger>& flinger,
     72         DisplayType type,
     73         bool isSecure,
     74         const wp<IBinder>& displayToken,
     75         const sp<ANativeWindow>& nativeWindow,
     76         const sp<FramebufferSurface>& framebufferSurface,
     77         EGLConfig config)
     78     : mFlinger(flinger),
     79       mType(type), mHwcDisplayId(-1),
     80       mNativeWindow(nativeWindow),
     81       mFramebufferSurface(framebufferSurface),
     82       mDisplay(EGL_NO_DISPLAY),
     83       mSurface(EGL_NO_SURFACE),
     84       mContext(EGL_NO_CONTEXT),
     85       mDisplayWidth(), mDisplayHeight(), mFormat(),
     86       mFlags(),
     87       mPageFlipCount(),
     88       mIsSecure(isSecure),
     89       mSecureLayerVisible(false),
     90       mScreenAcquired(false),
     91       mLayerStack(0),
     92       mOrientation()
     93 {
     94     init(config);
     95 }
     96 
     97 DisplayDevice::~DisplayDevice() {
     98     if (mSurface != EGL_NO_SURFACE) {
     99         eglDestroySurface(mDisplay, mSurface);
    100         mSurface = EGL_NO_SURFACE;
    101     }
    102 }
    103 
    104 bool DisplayDevice::isValid() const {
    105     return mFlinger != NULL;
    106 }
    107 
    108 int DisplayDevice::getWidth() const {
    109     return mDisplayWidth;
    110 }
    111 
    112 int DisplayDevice::getHeight() const {
    113     return mDisplayHeight;
    114 }
    115 
    116 PixelFormat DisplayDevice::getFormat() const {
    117     return mFormat;
    118 }
    119 
    120 EGLSurface DisplayDevice::getEGLSurface() const {
    121     return mSurface;
    122 }
    123 
    124 void DisplayDevice::init(EGLConfig config)
    125 {
    126     ANativeWindow* const window = mNativeWindow.get();
    127 
    128     int format;
    129     window->query(window, NATIVE_WINDOW_FORMAT, &format);
    130 
    131     /*
    132      * Create our display's surface
    133      */
    134 
    135     EGLSurface surface;
    136     EGLint w, h;
    137     EGLDisplay display = eglGetDisplay(EGL_DEFAULT_DISPLAY);
    138     surface = eglCreateWindowSurface(display, config, window, NULL);
    139     eglQuerySurface(display, surface, EGL_WIDTH,  &mDisplayWidth);
    140     eglQuerySurface(display, surface, EGL_HEIGHT, &mDisplayHeight);
    141 
    142     mDisplay = display;
    143     mSurface = surface;
    144     mFormat  = format;
    145     mPageFlipCount = 0;
    146     mViewport.makeInvalid();
    147     mFrame.makeInvalid();
    148 
    149     // external displays are always considered enabled
    150     mScreenAcquired = (mType >= DisplayDevice::NUM_DISPLAY_TYPES);
    151 
    152     // get an h/w composer ID
    153     mHwcDisplayId = mFlinger->allocateHwcDisplayId(mType);
    154 
    155     // Name the display.  The name will be replaced shortly if the display
    156     // was created with createDisplay().
    157     switch (mType) {
    158         case DISPLAY_PRIMARY:
    159             mDisplayName = "Built-in Screen";
    160             break;
    161         case DISPLAY_EXTERNAL:
    162             mDisplayName = "HDMI Screen";
    163             break;
    164         default:
    165             mDisplayName = "Virtual Screen";    // e.g. Overlay #n
    166             break;
    167     }
    168 
    169     // initialize the display orientation transform.
    170     setProjection(DisplayState::eOrientationDefault, mViewport, mFrame);
    171 }
    172 
    173 void DisplayDevice::setDisplayName(const String8& displayName) {
    174     if (!displayName.isEmpty()) {
    175         // never override the name with an empty name
    176         mDisplayName = displayName;
    177     }
    178 }
    179 
    180 uint32_t DisplayDevice::getPageFlipCount() const {
    181     return mPageFlipCount;
    182 }
    183 
    184 status_t DisplayDevice::compositionComplete() const {
    185     if (mFramebufferSurface == NULL) {
    186         return NO_ERROR;
    187     }
    188     return mFramebufferSurface->compositionComplete();
    189 }
    190 
    191 void DisplayDevice::flip(const Region& dirty) const
    192 {
    193     checkGLErrors();
    194 
    195     EGLDisplay dpy = mDisplay;
    196     EGLSurface surface = mSurface;
    197 
    198 #ifdef EGL_ANDROID_swap_rectangle
    199     if (mFlags & SWAP_RECTANGLE) {
    200         const Region newDirty(dirty.intersect(bounds()));
    201         const Rect b(newDirty.getBounds());
    202         eglSetSwapRectangleANDROID(dpy, surface,
    203                 b.left, b.top, b.width(), b.height());
    204     }
    205 #endif
    206 
    207     mPageFlipCount++;
    208 }
    209 
    210 void DisplayDevice::swapBuffers(HWComposer& hwc) const {
    211     EGLBoolean success = EGL_TRUE;
    212     if (hwc.initCheck() != NO_ERROR) {
    213         // no HWC, we call eglSwapBuffers()
    214         success = eglSwapBuffers(mDisplay, mSurface);
    215     } else {
    216         // We have a valid HWC, but not all displays can use it, in particular
    217         // the virtual displays are on their own.
    218         // TODO: HWC 1.2 will allow virtual displays
    219         if (mType >= DisplayDevice::DISPLAY_VIRTUAL) {
    220             // always call eglSwapBuffers() for virtual displays
    221             success = eglSwapBuffers(mDisplay, mSurface);
    222         } else if (hwc.supportsFramebufferTarget()) {
    223             // as of hwc 1.1 we always call eglSwapBuffers if we have some
    224             // GLES layers
    225             if (hwc.hasGlesComposition(mType)) {
    226                 success = eglSwapBuffers(mDisplay, mSurface);
    227             }
    228         } else {
    229             // HWC doesn't have the framebuffer target, we don't call
    230             // eglSwapBuffers(), since this is handled by HWComposer::commit().
    231         }
    232     }
    233 
    234     if (!success) {
    235         EGLint error = eglGetError();
    236         if (error == EGL_CONTEXT_LOST ||
    237                 mType == DisplayDevice::DISPLAY_PRIMARY) {
    238             LOG_ALWAYS_FATAL("eglSwapBuffers(%p, %p) failed with 0x%08x",
    239                     mDisplay, mSurface, error);
    240         }
    241     }
    242 }
    243 
    244 void DisplayDevice::onSwapBuffersCompleted(HWComposer& hwc) const {
    245     if (hwc.initCheck() == NO_ERROR) {
    246         if (hwc.supportsFramebufferTarget()) {
    247             int fd = hwc.getAndResetReleaseFenceFd(mType);
    248             mFramebufferSurface->setReleaseFenceFd(fd);
    249         }
    250     }
    251 }
    252 
    253 uint32_t DisplayDevice::getFlags() const
    254 {
    255     return mFlags;
    256 }
    257 
    258 EGLBoolean DisplayDevice::makeCurrent(EGLDisplay dpy,
    259         const sp<const DisplayDevice>& hw, EGLContext ctx) {
    260     EGLBoolean result = EGL_TRUE;
    261     EGLSurface sur = eglGetCurrentSurface(EGL_DRAW);
    262     if (sur != hw->mSurface) {
    263         result = eglMakeCurrent(dpy, hw->mSurface, hw->mSurface, ctx);
    264         if (result == EGL_TRUE) {
    265             setViewportAndProjection(hw);
    266         }
    267     }
    268     return result;
    269 }
    270 
    271 void DisplayDevice::setViewportAndProjection(const sp<const DisplayDevice>& hw) {
    272     GLsizei w = hw->mDisplayWidth;
    273     GLsizei h = hw->mDisplayHeight;
    274     glViewport(0, 0, w, h);
    275     glMatrixMode(GL_PROJECTION);
    276     glLoadIdentity();
    277     // put the origin in the left-bottom corner
    278     glOrthof(0, w, 0, h, 0, 1); // l=0, r=w ; b=0, t=h
    279     glMatrixMode(GL_MODELVIEW);
    280 }
    281 
    282 // ----------------------------------------------------------------------------
    283 
    284 void DisplayDevice::setVisibleLayersSortedByZ(const Vector< sp<LayerBase> >& layers) {
    285     mVisibleLayersSortedByZ = layers;
    286     mSecureLayerVisible = false;
    287     size_t count = layers.size();
    288     for (size_t i=0 ; i<count ; i++) {
    289         if (layers[i]->isSecure()) {
    290             mSecureLayerVisible = true;
    291         }
    292     }
    293 }
    294 
    295 const Vector< sp<LayerBase> >& DisplayDevice::getVisibleLayersSortedByZ() const {
    296     return mVisibleLayersSortedByZ;
    297 }
    298 
    299 bool DisplayDevice::getSecureLayerVisible() const {
    300     return mSecureLayerVisible;
    301 }
    302 
    303 Region DisplayDevice::getDirtyRegion(bool repaintEverything) const {
    304     Region dirty;
    305     if (repaintEverything) {
    306         dirty.set(getBounds());
    307     } else {
    308         const Transform& planeTransform(mGlobalTransform);
    309         dirty = planeTransform.transform(this->dirtyRegion);
    310         dirty.andSelf(getBounds());
    311     }
    312     return dirty;
    313 }
    314 
    315 // ----------------------------------------------------------------------------
    316 
    317 bool DisplayDevice::canDraw() const {
    318     return mScreenAcquired;
    319 }
    320 
    321 void DisplayDevice::releaseScreen() const {
    322     mScreenAcquired = false;
    323 }
    324 
    325 void DisplayDevice::acquireScreen() const {
    326     mScreenAcquired = true;
    327 }
    328 
    329 bool DisplayDevice::isScreenAcquired() const {
    330     return mScreenAcquired;
    331 }
    332 
    333 // ----------------------------------------------------------------------------
    334 
    335 void DisplayDevice::setLayerStack(uint32_t stack) {
    336     mLayerStack = stack;
    337     dirtyRegion.set(bounds());
    338 }
    339 
    340 // ----------------------------------------------------------------------------
    341 
    342 status_t DisplayDevice::orientationToTransfrom(
    343         int orientation, int w, int h, Transform* tr)
    344 {
    345     uint32_t flags = 0;
    346     switch (orientation) {
    347     case DisplayState::eOrientationDefault:
    348         flags = Transform::ROT_0;
    349         break;
    350     case DisplayState::eOrientation90:
    351         flags = Transform::ROT_90;
    352         break;
    353     case DisplayState::eOrientation180:
    354         flags = Transform::ROT_180;
    355         break;
    356     case DisplayState::eOrientation270:
    357         flags = Transform::ROT_270;
    358         break;
    359     default:
    360         return BAD_VALUE;
    361     }
    362     tr->set(flags, w, h);
    363     return NO_ERROR;
    364 }
    365 
    366 void DisplayDevice::setProjection(int orientation,
    367         const Rect& viewport, const Rect& frame) {
    368     mOrientation = orientation;
    369     mViewport = viewport;
    370     mFrame = frame;
    371     updateGeometryTransform();
    372 }
    373 
    374 void DisplayDevice::updateGeometryTransform() {
    375     int w = mDisplayWidth;
    376     int h = mDisplayHeight;
    377     Transform TL, TP, R, S;
    378     if (DisplayDevice::orientationToTransfrom(
    379             mOrientation, w, h, &R) == NO_ERROR) {
    380         dirtyRegion.set(bounds());
    381 
    382         Rect viewport(mViewport);
    383         Rect frame(mFrame);
    384 
    385         if (!frame.isValid()) {
    386             // the destination frame can be invalid if it has never been set,
    387             // in that case we assume the whole display frame.
    388             frame = Rect(w, h);
    389         }
    390 
    391         if (viewport.isEmpty()) {
    392             // viewport can be invalid if it has never been set, in that case
    393             // we assume the whole display size.
    394             // it's also invalid to have an empty viewport, so we handle that
    395             // case in the same way.
    396             viewport = Rect(w, h);
    397             if (R.getOrientation() & Transform::ROT_90) {
    398                 // viewport is always specified in the logical orientation
    399                 // of the display (ie: post-rotation).
    400                 swap(viewport.right, viewport.bottom);
    401             }
    402         }
    403 
    404         float src_width  = viewport.width();
    405         float src_height = viewport.height();
    406         float dst_width  = frame.width();
    407         float dst_height = frame.height();
    408         if (src_width != dst_width || src_height != dst_height) {
    409             float sx = dst_width  / src_width;
    410             float sy = dst_height / src_height;
    411             S.set(sx, 0, 0, sy);
    412         }
    413 
    414         float src_x = viewport.left;
    415         float src_y = viewport.top;
    416         float dst_x = frame.left;
    417         float dst_y = frame.top;
    418         TL.set(-src_x, -src_y);
    419         TP.set(dst_x, dst_y);
    420 
    421         // The viewport and frame are both in the logical orientation.
    422         // Apply the logical translation, scale to physical size, apply the
    423         // physical translation and finally rotate to the physical orientation.
    424         mGlobalTransform = R * TP * S * TL;
    425 
    426         const uint8_t type = mGlobalTransform.getType();
    427         mNeedsFiltering = (!mGlobalTransform.preserveRects() ||
    428                 (type >= Transform::SCALE));
    429     }
    430 }
    431 
    432 void DisplayDevice::dump(String8& result, char* buffer, size_t SIZE) const {
    433     const Transform& tr(mGlobalTransform);
    434     snprintf(buffer, SIZE,
    435         "+ DisplayDevice: %s\n"
    436         "   type=%x, layerStack=%u, (%4dx%4d), ANativeWindow=%p, orient=%2d (type=%08x), "
    437         "flips=%u, isSecure=%d, secureVis=%d, acquired=%d, numLayers=%u\n"
    438         "   v:[%d,%d,%d,%d], f:[%d,%d,%d,%d], "
    439         "transform:[[%0.3f,%0.3f,%0.3f][%0.3f,%0.3f,%0.3f][%0.3f,%0.3f,%0.3f]]\n",
    440         mDisplayName.string(), mType,
    441         mLayerStack, mDisplayWidth, mDisplayHeight, mNativeWindow.get(),
    442         mOrientation, tr.getType(), getPageFlipCount(),
    443         mIsSecure, mSecureLayerVisible, mScreenAcquired, mVisibleLayersSortedByZ.size(),
    444         mViewport.left, mViewport.top, mViewport.right, mViewport.bottom,
    445         mFrame.left, mFrame.top, mFrame.right, mFrame.bottom,
    446         tr[0][0], tr[1][0], tr[2][0],
    447         tr[0][1], tr[1][1], tr[2][1],
    448         tr[0][2], tr[1][2], tr[2][2]);
    449 
    450     result.append(buffer);
    451 
    452     String8 fbtargetDump;
    453     if (mFramebufferSurface != NULL) {
    454         mFramebufferSurface->dump(fbtargetDump);
    455         result.append(fbtargetDump);
    456     }
    457 }
    458