19066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project/* 29066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Copyright (C) 2007 The Android Open Source Project 39066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * 49066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License"); 59066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * you may not use this file except in compliance with the License. 69066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * You may obtain a copy of the License at 79066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * 89066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * http://www.apache.org/licenses/LICENSE-2.0 99066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * 109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Unless required by applicable law or agreed to in writing, software 119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS, 129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * See the License for the specific language governing permissions and 149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * limitations under the License. 159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project */ 169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include <stdlib.h> 189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include <stdio.h> 199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include <string.h> 209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include <math.h> 219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include <cutils/properties.h> 239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 241473f46cbc82aa6f0ba744cc896a36923823d55bMathias Agopian#include <utils/RefBase.h> 259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include <utils/Log.h> 269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 271473f46cbc82aa6f0ba744cc896a36923823d55bMathias Agopian#include <ui/PixelFormat.h> 28dff8e58d47ede6e748c0b02e128ca33b42a4f362Mathias Agopian#include <ui/FramebufferNativeWindow.h> 29265d9c076a588cf4cd811fbafd999c7ffe36641bMathias Agopian#include <ui/EGLUtils.h> 309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include <GLES/gl.h> 321473f46cbc82aa6f0ba744cc896a36923823d55bMathias Agopian#include <EGL/egl.h> 339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include <EGL/eglext.h> 349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 351473f46cbc82aa6f0ba744cc896a36923823d55bMathias Agopian#include <pixelflinger/pixelflinger.h> 369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include "DisplayHardware/DisplayHardware.h" 389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 391473f46cbc82aa6f0ba744cc896a36923823d55bMathias Agopian#include <hardware/gralloc.h> 409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 41781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian#include "GLExtensions.h" 42e0d5f5bcf5a8b26f4ad75f549cbf380b2c9faf20Mathias Agopian#include "HWComposer.h" 43a0bd0d84555c8e503e05b60cd959406a47d76f70Mathias Agopian#include "SurfaceFlinger.h" 44781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian 459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectusing namespace android; 469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic __attribute__((noinline)) 499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectvoid checkGLErrors() 509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{ 519779b221e999583ff89e0dfc40e56398737adbb3Mathias Agopian do { 529779b221e999583ff89e0dfc40e56398737adbb3Mathias Agopian // there could be more than one error flag 539779b221e999583ff89e0dfc40e56398737adbb3Mathias Agopian GLenum error = glGetError(); 549779b221e999583ff89e0dfc40e56398737adbb3Mathias Agopian if (error == GL_NO_ERROR) 559779b221e999583ff89e0dfc40e56398737adbb3Mathias Agopian break; 569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project LOGE("GL error 0x%04x", int(error)); 579779b221e999583ff89e0dfc40e56398737adbb3Mathias Agopian } while(true); 589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project} 599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic __attribute__((noinline)) 619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectvoid checkEGLErrors(const char* token) 629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{ 639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project EGLint error = eglGetError(); 649779b221e999583ff89e0dfc40e56398737adbb3Mathias Agopian if (error && error != EGL_SUCCESS) { 659779b221e999583ff89e0dfc40e56398737adbb3Mathias Agopian LOGE("%s: EGL error 0x%04x (%s)", 669ca4dd6011e30cbb3bc40cf0bba7d11362b8bc38Mathias Agopian token, int(error), EGLUtils::strerror(error)); 679779b221e999583ff89e0dfc40e56398737adbb3Mathias Agopian } 689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project} 699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project/* 719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Initialize the display to the specified values. 729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * 739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project */ 749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source ProjectDisplayHardware::DisplayHardware( 769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project const sp<SurfaceFlinger>& flinger, 779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project uint32_t dpy) 78781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian : DisplayHardwareBase(flinger, dpy), 79a0bd0d84555c8e503e05b60cd959406a47d76f70Mathias Agopian mFlinger(flinger), mFlags(0), mHwc(0) 809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{ 819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project init(dpy); 829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project} 839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source ProjectDisplayHardware::~DisplayHardware() 859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{ 869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project fini(); 879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project} 889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectfloat DisplayHardware::getDpiX() const { return mDpiX; } 909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectfloat DisplayHardware::getDpiY() const { return mDpiY; } 919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectfloat DisplayHardware::getDensity() const { return mDensity; } 929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectfloat DisplayHardware::getRefreshRate() const { return mRefreshRate; } 939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectint DisplayHardware::getWidth() const { return mWidth; } 949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectint DisplayHardware::getHeight() const { return mHeight; } 959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source ProjectPixelFormat DisplayHardware::getFormat() const { return mFormat; } 96967dce306267109a6e8aec408b65609ac5642a03Mathias Agopianuint32_t DisplayHardware::getMaxTextureSize() const { return mMaxTextureSize; } 97c94dce521b57763c6ace6cee206214fd476fe8f9Mathias Agopian 98c94dce521b57763c6ace6cee206214fd476fe8f9Mathias Agopianuint32_t DisplayHardware::getMaxViewportDims() const { 99c94dce521b57763c6ace6cee206214fd476fe8f9Mathias Agopian return mMaxViewportDims[0] < mMaxViewportDims[1] ? 100c94dce521b57763c6ace6cee206214fd476fe8f9Mathias Agopian mMaxViewportDims[0] : mMaxViewportDims[1]; 101c94dce521b57763c6ace6cee206214fd476fe8f9Mathias Agopian} 1029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 1031861786a97209ed75010a54cca5167593dbfec21Mathias Agopianstatic status_t selectConfigForPixelFormat( 1041861786a97209ed75010a54cca5167593dbfec21Mathias Agopian EGLDisplay dpy, 1051861786a97209ed75010a54cca5167593dbfec21Mathias Agopian EGLint const* attrs, 1061861786a97209ed75010a54cca5167593dbfec21Mathias Agopian PixelFormat format, 1071861786a97209ed75010a54cca5167593dbfec21Mathias Agopian EGLConfig* outConfig) 1081861786a97209ed75010a54cca5167593dbfec21Mathias Agopian{ 1091861786a97209ed75010a54cca5167593dbfec21Mathias Agopian EGLConfig config = NULL; 1101861786a97209ed75010a54cca5167593dbfec21Mathias Agopian EGLint numConfigs = -1, n=0; 1111861786a97209ed75010a54cca5167593dbfec21Mathias Agopian eglGetConfigs(dpy, NULL, 0, &numConfigs); 1121861786a97209ed75010a54cca5167593dbfec21Mathias Agopian EGLConfig* const configs = new EGLConfig[numConfigs]; 1131861786a97209ed75010a54cca5167593dbfec21Mathias Agopian eglChooseConfig(dpy, attrs, configs, numConfigs, &n); 1141861786a97209ed75010a54cca5167593dbfec21Mathias Agopian for (int i=0 ; i<n ; i++) { 1151861786a97209ed75010a54cca5167593dbfec21Mathias Agopian EGLint nativeVisualId = 0; 1161861786a97209ed75010a54cca5167593dbfec21Mathias Agopian eglGetConfigAttrib(dpy, configs[i], EGL_NATIVE_VISUAL_ID, &nativeVisualId); 1171861786a97209ed75010a54cca5167593dbfec21Mathias Agopian if (nativeVisualId>0 && format == nativeVisualId) { 1181861786a97209ed75010a54cca5167593dbfec21Mathias Agopian *outConfig = configs[i]; 1191861786a97209ed75010a54cca5167593dbfec21Mathias Agopian delete [] configs; 1201861786a97209ed75010a54cca5167593dbfec21Mathias Agopian return NO_ERROR; 1211861786a97209ed75010a54cca5167593dbfec21Mathias Agopian } 1221861786a97209ed75010a54cca5167593dbfec21Mathias Agopian } 1231861786a97209ed75010a54cca5167593dbfec21Mathias Agopian delete [] configs; 1241861786a97209ed75010a54cca5167593dbfec21Mathias Agopian return NAME_NOT_FOUND; 1251861786a97209ed75010a54cca5167593dbfec21Mathias Agopian} 1261861786a97209ed75010a54cca5167593dbfec21Mathias Agopian 1271861786a97209ed75010a54cca5167593dbfec21Mathias Agopian 1289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectvoid DisplayHardware::init(uint32_t dpy) 1299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{ 1301473f46cbc82aa6f0ba744cc896a36923823d55bMathias Agopian mNativeWindow = new FramebufferNativeWindow(); 1319ca4dd6011e30cbb3bc40cf0bba7d11362b8bc38Mathias Agopian framebuffer_device_t const * fbDev = mNativeWindow->getDevice(); 1320c63ef5091def41e91a2202560c57b2f6caabfbeMathias Agopian if (!fbDev) { 1330c63ef5091def41e91a2202560c57b2f6caabfbeMathias Agopian LOGE("Display subsystem failed to initialize. check logs. exiting..."); 1340c63ef5091def41e91a2202560c57b2f6caabfbeMathias Agopian exit(0); 1350c63ef5091def41e91a2202560c57b2f6caabfbeMathias Agopian } 1360c63ef5091def41e91a2202560c57b2f6caabfbeMathias Agopian 1371861786a97209ed75010a54cca5167593dbfec21Mathias Agopian int format; 1381861786a97209ed75010a54cca5167593dbfec21Mathias Agopian ANativeWindow const * const window = mNativeWindow.get(); 1391861786a97209ed75010a54cca5167593dbfec21Mathias Agopian window->query(window, NATIVE_WINDOW_FORMAT, &format); 140781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian mDpiX = mNativeWindow->xdpi; 141781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian mDpiY = mNativeWindow->ydpi; 142781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian mRefreshRate = fbDev->fps; 1431473f46cbc82aa6f0ba744cc896a36923823d55bMathias Agopian 144222357f33a105ce08177b94334c7d14af29df8f6Mathias Agopian 145222357f33a105ce08177b94334c7d14af29df8f6Mathias Agopian/* FIXME: this is a temporary HACK until we are able to report the refresh rate 146222357f33a105ce08177b94334c7d14af29df8f6Mathias Agopian * properly from the HAL. The WindowManagerService now relies on this value. 147222357f33a105ce08177b94334c7d14af29df8f6Mathias Agopian */ 148222357f33a105ce08177b94334c7d14af29df8f6Mathias Agopian#ifndef REFRESH_RATE 149222357f33a105ce08177b94334c7d14af29df8f6Mathias Agopian mRefreshRate = fbDev->fps; 150222357f33a105ce08177b94334c7d14af29df8f6Mathias Agopian#else 151222357f33a105ce08177b94334c7d14af29df8f6Mathias Agopian mRefreshRate = REFRESH_RATE; 152222357f33a105ce08177b94334c7d14af29df8f6Mathias Agopian#warning "refresh rate set via makefile to REFRESH_RATE" 153222357f33a105ce08177b94334c7d14af29df8f6Mathias Agopian#endif 154222357f33a105ce08177b94334c7d14af29df8f6Mathias Agopian 155781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian EGLint w, h, dummy; 156781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian EGLint numConfigs=0; 157781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian EGLSurface surface; 158781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian EGLContext context; 1591861786a97209ed75010a54cca5167593dbfec21Mathias Agopian EGLBoolean result; 1601861786a97209ed75010a54cca5167593dbfec21Mathias Agopian status_t err; 161781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian 1629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project // initialize EGL 16324d237db943051942b5966f5e788d67050ec0ba5Mathias Agopian EGLint attribs[] = { 1641861786a97209ed75010a54cca5167593dbfec21Mathias Agopian EGL_SURFACE_TYPE, EGL_WINDOW_BIT, 1651861786a97209ed75010a54cca5167593dbfec21Mathias Agopian EGL_NONE, 0, 1669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project EGL_NONE 1679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project }; 16824d237db943051942b5966f5e788d67050ec0ba5Mathias Agopian 16924d237db943051942b5966f5e788d67050ec0ba5Mathias Agopian // debug: disable h/w rendering 17024d237db943051942b5966f5e788d67050ec0ba5Mathias Agopian char property[PROPERTY_VALUE_MAX]; 17124d237db943051942b5966f5e788d67050ec0ba5Mathias Agopian if (property_get("debug.sf.hw", property, NULL) > 0) { 17224d237db943051942b5966f5e788d67050ec0ba5Mathias Agopian if (atoi(property) == 0) { 17324d237db943051942b5966f5e788d67050ec0ba5Mathias Agopian LOGW("H/W composition disabled"); 17424d237db943051942b5966f5e788d67050ec0ba5Mathias Agopian attribs[2] = EGL_CONFIG_CAVEAT; 17524d237db943051942b5966f5e788d67050ec0ba5Mathias Agopian attribs[3] = EGL_SLOW_CONFIG; 17624d237db943051942b5966f5e788d67050ec0ba5Mathias Agopian } 17724d237db943051942b5966f5e788d67050ec0ba5Mathias Agopian } 17824d237db943051942b5966f5e788d67050ec0ba5Mathias Agopian 1799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project // TODO: all the extensions below should be queried through 1809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project // eglGetProcAddress(). 1819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 1829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project EGLDisplay display = eglGetDisplay(EGL_DEFAULT_DISPLAY); 1839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project eglInitialize(display, NULL, NULL); 1849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project eglGetConfigs(display, NULL, 0, &numConfigs); 1851473f46cbc82aa6f0ba744cc896a36923823d55bMathias Agopian 1861861786a97209ed75010a54cca5167593dbfec21Mathias Agopian EGLConfig config = NULL; 1871861786a97209ed75010a54cca5167593dbfec21Mathias Agopian err = selectConfigForPixelFormat(display, attribs, format, &config); 188265d9c076a588cf4cd811fbafd999c7ffe36641bMathias Agopian LOGE_IF(err, "couldn't find an EGLConfig matching the screen format"); 189265d9c076a588cf4cd811fbafd999c7ffe36641bMathias Agopian 1909ca4dd6011e30cbb3bc40cf0bba7d11362b8bc38Mathias Agopian EGLint r,g,b,a; 1919ca4dd6011e30cbb3bc40cf0bba7d11362b8bc38Mathias Agopian eglGetConfigAttrib(display, config, EGL_RED_SIZE, &r); 1929ca4dd6011e30cbb3bc40cf0bba7d11362b8bc38Mathias Agopian eglGetConfigAttrib(display, config, EGL_GREEN_SIZE, &g); 1939ca4dd6011e30cbb3bc40cf0bba7d11362b8bc38Mathias Agopian eglGetConfigAttrib(display, config, EGL_BLUE_SIZE, &b); 1949ca4dd6011e30cbb3bc40cf0bba7d11362b8bc38Mathias Agopian eglGetConfigAttrib(display, config, EGL_ALPHA_SIZE, &a); 1959ca4dd6011e30cbb3bc40cf0bba7d11362b8bc38Mathias Agopian 19697b8056c3182a973c67d3c1b196150d4b9e30f3aMathias Agopian if (mNativeWindow->isUpdateOnDemand()) { 197f2d28b74850ea0869aef2ce0727a6abb7b166a5cMathias Agopian mFlags |= PARTIAL_UPDATES; 19897b8056c3182a973c67d3c1b196150d4b9e30f3aMathias Agopian } 19997b8056c3182a973c67d3c1b196150d4b9e30f3aMathias Agopian 2009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project if (eglGetConfigAttrib(display, config, EGL_CONFIG_CAVEAT, &dummy) == EGL_TRUE) { 2019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project if (dummy == EGL_SLOW_CONFIG) 2029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project mFlags |= SLOW_CONFIG; 2039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project } 2049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 2059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project /* 2069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Create our main surface 2079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project */ 2089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 2091473f46cbc82aa6f0ba744cc896a36923823d55bMathias Agopian surface = eglCreateWindowSurface(display, config, mNativeWindow.get(), NULL); 210781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian eglQuerySurface(display, surface, EGL_WIDTH, &mWidth); 211781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian eglQuerySurface(display, surface, EGL_HEIGHT, &mHeight); 2129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 213f2d28b74850ea0869aef2ce0727a6abb7b166a5cMathias Agopian if (mFlags & PARTIAL_UPDATES) { 214f2d28b74850ea0869aef2ce0727a6abb7b166a5cMathias Agopian // if we have partial updates, we definitely don't need to 215f2d28b74850ea0869aef2ce0727a6abb7b166a5cMathias Agopian // preserve the backbuffer, which may be costly. 216af369f6280c9eec0caa3f53f8e27f3713e1a7d25Mathias Agopian eglSurfaceAttrib(display, surface, 217af369f6280c9eec0caa3f53f8e27f3713e1a7d25Mathias Agopian EGL_SWAP_BEHAVIOR, EGL_BUFFER_DESTROYED); 218af369f6280c9eec0caa3f53f8e27f3713e1a7d25Mathias Agopian } 219af369f6280c9eec0caa3f53f8e27f3713e1a7d25Mathias Agopian 2209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project if (eglQuerySurface(display, surface, EGL_SWAP_BEHAVIOR, &dummy) == EGL_TRUE) { 2219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project if (dummy == EGL_BUFFER_PRESERVED) { 2229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project mFlags |= BUFFER_PRESERVED; 2239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project } 2249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project } 2259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 2263c08a446c5b4f2682da1d8461bd1ed94060c29dcDavid 'Digit' Turner /* Read density from build-specific ro.sf.lcd_density property 22788e3e6bd04dcf166ddd92ce3a84e1f9f54ac2f66Mathias Agopian * except if it is overridden by qemu.sf.lcd_density. 2283c08a446c5b4f2682da1d8461bd1ed94060c29dcDavid 'Digit' Turner */ 2293c08a446c5b4f2682da1d8461bd1ed94060c29dcDavid 'Digit' Turner if (property_get("qemu.sf.lcd_density", property, NULL) <= 0) { 2303c08a446c5b4f2682da1d8461bd1ed94060c29dcDavid 'Digit' Turner if (property_get("ro.sf.lcd_density", property, NULL) <= 0) { 2313c08a446c5b4f2682da1d8461bd1ed94060c29dcDavid 'Digit' Turner LOGW("ro.sf.lcd_density not defined, using 160 dpi by default."); 2323c08a446c5b4f2682da1d8461bd1ed94060c29dcDavid 'Digit' Turner strcpy(property, "160"); 2332a578ae518ff3d8a2d4768b3d190e4702509e82cDavid 'Digit' Turner } 234d75fe9aa835b0811911e1727de8e15b329dafd49David 'Digit' Turner } else { 235d75fe9aa835b0811911e1727de8e15b329dafd49David 'Digit' Turner /* for the emulator case, reset the dpi values too */ 236d75fe9aa835b0811911e1727de8e15b329dafd49David 'Digit' Turner mDpiX = mDpiY = atoi(property); 2379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project } 2389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project mDensity = atoi(property) * (1.0f/160.0f); 2399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 2409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 2419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project /* 2429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Create our OpenGL ES context 2439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project */ 2449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 245cd54dc26f7ac23da6c920dd83b30242049470f00Mathias Agopian 246cd54dc26f7ac23da6c920dd83b30242049470f00Mathias Agopian EGLint contextAttributes[] = { 247cd54dc26f7ac23da6c920dd83b30242049470f00Mathias Agopian#ifdef EGL_IMG_context_priority 248cd54dc26f7ac23da6c920dd83b30242049470f00Mathias Agopian#ifdef HAS_CONTEXT_PRIORITY 249cd54dc26f7ac23da6c920dd83b30242049470f00Mathias Agopian#warning "using EGL_IMG_context_priority" 250cd54dc26f7ac23da6c920dd83b30242049470f00Mathias Agopian EGL_CONTEXT_PRIORITY_LEVEL_IMG, EGL_CONTEXT_PRIORITY_HIGH_IMG, 251cd54dc26f7ac23da6c920dd83b30242049470f00Mathias Agopian#endif 252cd54dc26f7ac23da6c920dd83b30242049470f00Mathias Agopian#endif 253cd54dc26f7ac23da6c920dd83b30242049470f00Mathias Agopian EGL_NONE, EGL_NONE 254cd54dc26f7ac23da6c920dd83b30242049470f00Mathias Agopian }; 255cd54dc26f7ac23da6c920dd83b30242049470f00Mathias Agopian context = eglCreateContext(display, config, NULL, contextAttributes); 256cd54dc26f7ac23da6c920dd83b30242049470f00Mathias Agopian 257781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian mDisplay = display; 258781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian mConfig = config; 259781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian mSurface = surface; 260781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian mContext = context; 261781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian mFormat = fbDev->format; 262781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian mPageFlipCount = 0; 263781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian 2649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project /* 2659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Gather OpenGL ES extensions 2669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project */ 2679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 2681861786a97209ed75010a54cca5167593dbfec21Mathias Agopian result = eglMakeCurrent(display, surface, surface, context); 2691861786a97209ed75010a54cca5167593dbfec21Mathias Agopian if (!result) { 2701861786a97209ed75010a54cca5167593dbfec21Mathias Agopian LOGE("Couldn't create a working GLES context. check logs. exiting..."); 2711861786a97209ed75010a54cca5167593dbfec21Mathias Agopian exit(0); 2721861786a97209ed75010a54cca5167593dbfec21Mathias Agopian } 273781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian 274781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian GLExtensions& extensions(GLExtensions::getInstance()); 275781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian extensions.initWithGLStrings( 276781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian glGetString(GL_VENDOR), 277781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian glGetString(GL_RENDERER), 278781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian glGetString(GL_VERSION), 279781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian glGetString(GL_EXTENSIONS), 280781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian eglQueryString(display, EGL_VENDOR), 281781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian eglQueryString(display, EGL_VERSION), 282781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian eglQueryString(display, EGL_EXTENSIONS)); 2839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 284967dce306267109a6e8aec408b65609ac5642a03Mathias Agopian glGetIntegerv(GL_MAX_TEXTURE_SIZE, &mMaxTextureSize); 285c94dce521b57763c6ace6cee206214fd476fe8f9Mathias Agopian glGetIntegerv(GL_MAX_VIEWPORT_DIMS, mMaxViewportDims); 286967dce306267109a6e8aec408b65609ac5642a03Mathias Agopian 287781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian LOGI("EGL informations:"); 288781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian LOGI("# of configs : %d", numConfigs); 289781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian LOGI("vendor : %s", extensions.getEglVendor()); 290781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian LOGI("version : %s", extensions.getEglVersion()); 291781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian LOGI("extensions: %s", extensions.getEglExtension()); 292781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian LOGI("Client API: %s", eglQueryString(display, EGL_CLIENT_APIS)?:"Not Supported"); 293781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian LOGI("EGLSurface: %d-%d-%d-%d, config=%p", r, g, b, a, config); 294781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian 295781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian LOGI("OpenGL informations:"); 296781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian LOGI("vendor : %s", extensions.getVendor()); 297781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian LOGI("renderer : %s", extensions.getRenderer()); 298781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian LOGI("version : %s", extensions.getVersion()); 299781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian LOGI("extensions: %s", extensions.getExtension()); 300781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian LOGI("GL_MAX_TEXTURE_SIZE = %d", mMaxTextureSize); 301c94dce521b57763c6ace6cee206214fd476fe8f9Mathias Agopian LOGI("GL_MAX_VIEWPORT_DIMS = %d x %d", mMaxViewportDims[0], mMaxViewportDims[1]); 302781953d62dc17d761e39540f0480e5ca7451cdbeMathias Agopian LOGI("flags = %08x", mFlags); 303967dce306267109a6e8aec408b65609ac5642a03Mathias Agopian 3049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project // Unbind the context from this thread 3059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project eglMakeCurrent(display, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT); 306e0d5f5bcf5a8b26f4ad75f549cbf380b2c9faf20Mathias Agopian 307e0d5f5bcf5a8b26f4ad75f549cbf380b2c9faf20Mathias Agopian 308e0d5f5bcf5a8b26f4ad75f549cbf380b2c9faf20Mathias Agopian // initialize the H/W composer 309a0bd0d84555c8e503e05b60cd959406a47d76f70Mathias Agopian mHwc = new HWComposer(mFlinger); 310e0d5f5bcf5a8b26f4ad75f549cbf380b2c9faf20Mathias Agopian if (mHwc->initCheck() == NO_ERROR) { 311e0d5f5bcf5a8b26f4ad75f549cbf380b2c9faf20Mathias Agopian mHwc->setFrameBuffer(mDisplay, mSurface); 312e0d5f5bcf5a8b26f4ad75f549cbf380b2c9faf20Mathias Agopian } 313e0d5f5bcf5a8b26f4ad75f549cbf380b2c9faf20Mathias Agopian} 314e0d5f5bcf5a8b26f4ad75f549cbf380b2c9faf20Mathias Agopian 315e0d5f5bcf5a8b26f4ad75f549cbf380b2c9faf20Mathias AgopianHWComposer& DisplayHardware::getHwComposer() const { 316e0d5f5bcf5a8b26f4ad75f549cbf380b2c9faf20Mathias Agopian return *mHwc; 3179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project} 3189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 3199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project/* 3209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Clean up. Throw out our local state. 3219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * 3229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * (It's entirely possible we'll never get here, since this is meant 3239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * for real hardware, which doesn't restart.) 3249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project */ 3259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 3269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectvoid DisplayHardware::fini() 3279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{ 3289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project eglMakeCurrent(mDisplay, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT); 3299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project eglTerminate(mDisplay); 3309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project} 3319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 3329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectvoid DisplayHardware::releaseScreen() const 3339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{ 3349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project DisplayHardwareBase::releaseScreen(); 33511042a41c1fe1415df0f45ef5fd3905d34b6e01aAntti Hatala if (mHwc->initCheck() == NO_ERROR) { 33611042a41c1fe1415df0f45ef5fd3905d34b6e01aAntti Hatala mHwc->release(); 33711042a41c1fe1415df0f45ef5fd3905d34b6e01aAntti Hatala } 3389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project} 3399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 3409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectvoid DisplayHardware::acquireScreen() const 3419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{ 3429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project DisplayHardwareBase::acquireScreen(); 3439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project} 3449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 3459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectuint32_t DisplayHardware::getPageFlipCount() const { 3461473f46cbc82aa6f0ba744cc896a36923823d55bMathias Agopian return mPageFlipCount; 3479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project} 3489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 349b1a1874625a6aca967601fcda53a82d8d712df45Mathias Agopianstatus_t DisplayHardware::compositionComplete() const { 350b1a1874625a6aca967601fcda53a82d8d712df45Mathias Agopian return mNativeWindow->compositionComplete(); 351b1a1874625a6aca967601fcda53a82d8d712df45Mathias Agopian} 3529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 35304262e9f842edf20168399b6a70f0d67e518fe69Mathias Agopianint DisplayHardware::getCurrentBufferIndex() const { 35404262e9f842edf20168399b6a70f0d67e518fe69Mathias Agopian return mNativeWindow->getCurrentBufferIndex(); 35504262e9f842edf20168399b6a70f0d67e518fe69Mathias Agopian} 35604262e9f842edf20168399b6a70f0d67e518fe69Mathias Agopian 3579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectvoid DisplayHardware::flip(const Region& dirty) const 3589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{ 3599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project checkGLErrors(); 3609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 3619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project EGLDisplay dpy = mDisplay; 3629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project EGLSurface surface = mSurface; 3639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 364e19476214a2fe718c82461f54e6b56cee7faa5f4Mathias Agopian#ifdef EGL_ANDROID_swap_rectangle 3652e20bffbab8084fedce39d14d7dd17b08f6e9ba2Mathias Agopian if (mFlags & SWAP_RECTANGLE) { 3668c9687ae291a1e0a63d4236069066284f56192cdMathias Agopian const Region newDirty(dirty.intersect(bounds())); 3678c9687ae291a1e0a63d4236069066284f56192cdMathias Agopian const Rect b(newDirty.getBounds()); 3682e20bffbab8084fedce39d14d7dd17b08f6e9ba2Mathias Agopian eglSetSwapRectangleANDROID(dpy, surface, 3692e20bffbab8084fedce39d14d7dd17b08f6e9ba2Mathias Agopian b.left, b.top, b.width(), b.height()); 3709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project } 371e19476214a2fe718c82461f54e6b56cee7faa5f4Mathias Agopian#endif 372e19476214a2fe718c82461f54e6b56cee7faa5f4Mathias Agopian 373f2d28b74850ea0869aef2ce0727a6abb7b166a5cMathias Agopian if (mFlags & PARTIAL_UPDATES) { 374ecfa7ccd4fc3066a4cfd4d84d7de286d95581c78Mathias Agopian mNativeWindow->setUpdateRectangle(dirty.getBounds()); 37597b8056c3182a973c67d3c1b196150d4b9e30f3aMathias Agopian } 37697b8056c3182a973c67d3c1b196150d4b9e30f3aMathias Agopian 3771473f46cbc82aa6f0ba744cc896a36923823d55bMathias Agopian mPageFlipCount++; 378e0d5f5bcf5a8b26f4ad75f549cbf380b2c9faf20Mathias Agopian 379e0d5f5bcf5a8b26f4ad75f549cbf380b2c9faf20Mathias Agopian if (mHwc->initCheck() == NO_ERROR) { 380e0d5f5bcf5a8b26f4ad75f549cbf380b2c9faf20Mathias Agopian mHwc->commit(); 381e0d5f5bcf5a8b26f4ad75f549cbf380b2c9faf20Mathias Agopian } else { 382e0d5f5bcf5a8b26f4ad75f549cbf380b2c9faf20Mathias Agopian eglSwapBuffers(dpy, surface); 383e0d5f5bcf5a8b26f4ad75f549cbf380b2c9faf20Mathias Agopian } 3849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project checkEGLErrors("eglSwapBuffers"); 3859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 3869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project // for debugging 3879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project //glClearColor(1,0,0,0); 3889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project //glClear(GL_COLOR_BUFFER_BIT); 3899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project} 3909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 3919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectuint32_t DisplayHardware::getFlags() const 3929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{ 3939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project return mFlags; 3949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project} 3959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 3969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectvoid DisplayHardware::makeCurrent() const 3979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{ 3989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project eglMakeCurrent(mDisplay, mSurface, mSurface, mContext); 3999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project} 40094720d7ec40d2b5ee200d95a46588cdb0fb30e66Erik Gilling 40194720d7ec40d2b5ee200d95a46588cdb0fb30e66Erik Gillingvoid DisplayHardware::dump(String8& res) const 40294720d7ec40d2b5ee200d95a46588cdb0fb30e66Erik Gilling{ 40394720d7ec40d2b5ee200d95a46588cdb0fb30e66Erik Gilling mNativeWindow->dump(res); 40494720d7ec40d2b5ee200d95a46588cdb0fb30e66Erik Gilling} 405