summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMathias Agopian <mathias@google.com>2013-03-28 17:44:13 -0700
committerMathias Agopian <mathias@google.com>2013-03-29 15:33:47 -0700
commitca08833d5ea99130797e10ad68a651b50e99da74 (patch)
treebcb05693b2bc34a0c7467d95a85b19df9af5dc1e
parent8171aece3d89a2107eda02c0e9daf79518b40174 (diff)
downloadframeworks_native-ca08833d5ea99130797e10ad68a651b50e99da74.zip
frameworks_native-ca08833d5ea99130797e10ad68a651b50e99da74.tar.gz
frameworks_native-ca08833d5ea99130797e10ad68a651b50e99da74.tar.bz2
don't use compile-time configuration of libgui as much as possible
We now detect at runtime which sync features to use, which allows us to remove a lot of the compile-time configuration options. There is still one option though, to disable KHR_fence_sync on some devices (which are more efficient without it). - added a backdoor to get the vendor's EGL strings the new logic is: - use always ANDROID_native_fence_sync if available - fallback to KHR_fence_sync if available and not disabled by the compile-time option - use KHR_wait_sync if available and either of the above is enabled Change-Id: I9c4b49d9ff1151faf902cc93bd53ea5f205aaabf
-rw-r--r--include/gui/GLConsumer.h4
-rw-r--r--include/private/gui/SyncFeatures.h45
-rw-r--r--libs/gui/Android.mk21
-rw-r--r--libs/gui/ConsumerBase.cpp1
-rw-r--r--libs/gui/GLConsumer.cpp49
-rw-r--r--libs/gui/GuiConfig.cpp10
-rw-r--r--libs/gui/SyncFeatures.cpp94
-rw-r--r--opengl/libs/EGL/eglApi.cpp23
-rw-r--r--services/surfaceflinger/GLExtensions.cpp2
-rw-r--r--services/surfaceflinger/SurfaceFlinger.cpp25
-rw-r--r--services/surfaceflinger/SurfaceFlingerConsumer.cpp5
11 files changed, 190 insertions, 89 deletions
diff --git a/include/gui/GLConsumer.h b/include/gui/GLConsumer.h
index b1622d2..3b8dd77 100644
--- a/include/gui/GLConsumer.h
+++ b/include/gui/GLConsumer.h
@@ -267,10 +267,6 @@ protected:
// values.
status_t checkAndUpdateEglStateLocked();
- // If set, GLConsumer will use the EGL_ANDROID_native_fence_sync
- // extension to create Android native fences for GLES activity.
- static const bool sUseNativeFenceSync;
-
private:
// createImage creates a new EGLImage from a GraphicBuffer.
EGLImageKHR createImage(EGLDisplay dpy,
diff --git a/include/private/gui/SyncFeatures.h b/include/private/gui/SyncFeatures.h
new file mode 100644
index 0000000..79fb75b
--- /dev/null
+++ b/include/private/gui/SyncFeatures.h
@@ -0,0 +1,45 @@
+/*
+ * Copyright (C) 2013 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef ANDROID_GUI_SYNC_FEATURES_H
+#define ANDROID_GUI_SYNC_FEATURES_H
+
+#include <utils/Singleton.h>
+#include <utils/String8.h>
+
+
+namespace android {
+// ----------------------------------------------------------------------------
+
+class SyncFeatures : public Singleton<SyncFeatures> {
+ friend class Singleton<SyncFeatures>;
+ bool mHasNativeFenceSync;
+ bool mHasFenceSync;
+ bool mHasWaitSync;
+ String8 mString;
+ SyncFeatures();
+
+public:
+ bool useNativeFenceSync() const;
+ bool useFenceSync() const;
+ bool useWaitSync() const;
+ String8 toString() const;
+};
+
+// ----------------------------------------------------------------------------
+}; // namespace android
+
+#endif // ANDROID_GUI_SYNC_FEATURES_H
diff --git a/libs/gui/Android.mk b/libs/gui/Android.mk
index 5c7bb4c..8fcfa7d 100644
--- a/libs/gui/Android.mk
+++ b/libs/gui/Android.mk
@@ -26,6 +26,7 @@ LOCAL_SRC_FILES:= \
Surface.cpp \
SurfaceControl.cpp \
SurfaceComposerClient.cpp \
+ SyncFeatures.cpp \
LOCAL_SHARED_LIBRARIES := \
libbinder \
@@ -39,23 +40,11 @@ LOCAL_SHARED_LIBRARIES := \
LOCAL_MODULE:= libgui
-ifeq ($(TARGET_BOARD_PLATFORM), omap4)
- LOCAL_CFLAGS += -DUSE_FENCE_SYNC
+ifeq ($(TARGET_BOARD_PLATFORM), tegra)
+ LOCAL_CFLAGS += -DDONT_USE_FENCE_SYNC
endif
-ifeq ($(TARGET_BOARD_PLATFORM), s5pc110)
- LOCAL_CFLAGS += -DUSE_FENCE_SYNC
-endif
-ifeq ($(TARGET_BOARD_PLATFORM), exynos5)
- LOCAL_CFLAGS += -DUSE_NATIVE_FENCE_SYNC
- LOCAL_CFLAGS += -DUSE_WAIT_SYNC
-endif
-ifneq ($(filter generic%,$(TARGET_DEVICE)),)
- # Emulator build
- LOCAL_CFLAGS += -DUSE_FENCE_SYNC
-endif
-
-ifeq ($(TARGET_BOARD_PLATFORM), msm8960)
- LOCAL_CFLAGS += -DUSE_NATIVE_FENCE_SYNC
+ifeq ($(TARGET_BOARD_PLATFORM), tegra3)
+ LOCAL_CFLAGS += -DDONT_USE_FENCE_SYNC
endif
include $(BUILD_SHARED_LIBRARY)
diff --git a/libs/gui/ConsumerBase.cpp b/libs/gui/ConsumerBase.cpp
index fb6ba7d..8694d21 100644
--- a/libs/gui/ConsumerBase.cpp
+++ b/libs/gui/ConsumerBase.cpp
@@ -18,7 +18,6 @@
#define ATRACE_TAG ATRACE_TAG_GRAPHICS
//#define LOG_NDEBUG 0
-#define GL_GLEXT_PROTOTYPES
#define EGL_EGLEXT_PROTOTYPES
#include <EGL/egl.h>
diff --git a/libs/gui/GLConsumer.cpp b/libs/gui/GLConsumer.cpp
index 1ce75ea..f8f1241 100644
--- a/libs/gui/GLConsumer.cpp
+++ b/libs/gui/GLConsumer.cpp
@@ -28,12 +28,13 @@
#include <hardware/hardware.h>
+#include <gui/GLConsumer.h>
#include <gui/IGraphicBufferAlloc.h>
#include <gui/ISurfaceComposer.h>
#include <gui/SurfaceComposerClient.h>
-#include <gui/GLConsumer.h>
#include <private/gui/ComposerService.h>
+#include <private/gui/SyncFeatures.h>
#include <utils/Log.h>
#include <utils/String8.h>
@@ -41,30 +42,6 @@
namespace android {
-// This compile option makes GLConsumer use the
-// EGL_ANDROID_native_fence_sync extension to create Android native fences to
-// signal when all GLES reads for a given buffer have completed. It is not
-// compatible with using the EGL_KHR_fence_sync extension for the same
-// purpose.
-#ifdef USE_NATIVE_FENCE_SYNC
-#ifdef USE_FENCE_SYNC
-#error "USE_NATIVE_FENCE_SYNC and USE_FENCE_SYNC are incompatible"
-#endif
-const bool GLConsumer::sUseNativeFenceSync = true;
-#else
-const bool GLConsumer::sUseNativeFenceSync = false;
-#endif
-
-// This compile option makes GLConsumer use the EGL_KHR_wait_sync
-// extension to insert server-side waits into the GLES command stream. This
-// feature requires the EGL_ANDROID_native_fence_sync and
-// EGL_KHR_wait_sync extensions.
-#ifdef USE_WAIT_SYNC
-static const bool useWaitSync = true;
-#else
-static const bool useWaitSync = false;
-#endif
-
// Macros for including the GLConsumer name in log messages
#define ST_LOGV(x, ...) ALOGV("[%s] "x, mName.string(), ##__VA_ARGS__)
#define ST_LOGD(x, ...) ALOGD("[%s] "x, mName.string(), ##__VA_ARGS__)
@@ -97,18 +74,6 @@ static float mtxRot90[16] = {
0, 0, 1, 0,
1, 0, 0, 1,
};
-static float mtxRot180[16] = {
- -1, 0, 0, 0,
- 0, -1, 0, 0,
- 0, 0, 1, 0,
- 1, 1, 0, 1,
-};
-static float mtxRot270[16] = {
- 0, -1, 0, 0,
- 1, 0, 0, 0,
- 0, 0, 1, 0,
- 0, 1, 0, 1,
-};
static void mtxMul(float out[16], const float a[16], const float b[16]);
@@ -121,11 +86,7 @@ GLConsumer::GLConsumer(GLuint tex, bool allowSynchronousMode,
mCurrentTimestamp(0),
mFilteringEnabled(true),
mTexName(tex),
-#ifdef USE_FENCE_SYNC
mUseFenceSync(useFenceSync),
-#else
- mUseFenceSync(false),
-#endif
mTexTarget(texTarget),
mEglDisplay(EGL_NO_DISPLAY),
mEglContext(EGL_NO_CONTEXT),
@@ -522,7 +483,7 @@ status_t GLConsumer::syncForReleaseLocked(EGLDisplay dpy) {
ST_LOGV("syncForReleaseLocked");
if (mCurrentTexture != BufferQueue::INVALID_BUFFER_SLOT) {
- if (sUseNativeFenceSync) {
+ if (SyncFeatures::getInstance().useNativeFenceSync()) {
EGLSyncKHR sync = eglCreateSyncKHR(dpy,
EGL_SYNC_NATIVE_FENCE_ANDROID, NULL);
if (sync == EGL_NO_SYNC_KHR) {
@@ -545,7 +506,7 @@ status_t GLConsumer::syncForReleaseLocked(EGLDisplay dpy) {
"%s (%d)", strerror(-err), err);
return err;
}
- } else if (mUseFenceSync) {
+ } else if (mUseFenceSync && SyncFeatures::getInstance().useFenceSync()) {
EGLSyncKHR fence = mEglSlots[mCurrentTexture].mEglFence;
if (fence != EGL_NO_SYNC_KHR) {
// There is already a fence for the current slot. We need to
@@ -825,7 +786,7 @@ status_t GLConsumer::doGLFenceWaitLocked() const {
}
if (mCurrentFence->isValid()) {
- if (useWaitSync) {
+ if (SyncFeatures::getInstance().useWaitSync()) {
// Create an EGLSyncKHR from the current fence.
int fenceFd = mCurrentFence->dup();
if (fenceFd == -1) {
diff --git a/libs/gui/GuiConfig.cpp b/libs/gui/GuiConfig.cpp
index bafd21a..bc0c83c 100644
--- a/libs/gui/GuiConfig.cpp
+++ b/libs/gui/GuiConfig.cpp
@@ -22,14 +22,8 @@ void appendGuiConfigString(String8& configStr)
{
static const char* config =
" [libgui"
-#ifdef USE_FENCE_SYNC
- " USE_FENCE_SYNC"
-#endif
-#ifdef USE_NATIVE_FENCE_SYNC
- " USE_NATIVE_FENCE_SYNC"
-#endif
-#ifdef USE_WAIT_SYNC
- " USE_WAIT_SYNC"
+#ifdef DONT_USE_FENCE_SYNC
+ " DONT_USE_FENCE_SYNC"
#endif
"]";
configStr.append(config);
diff --git a/libs/gui/SyncFeatures.cpp b/libs/gui/SyncFeatures.cpp
new file mode 100644
index 0000000..e5804a7
--- /dev/null
+++ b/libs/gui/SyncFeatures.cpp
@@ -0,0 +1,94 @@
+/*
+ ** Copyright 2013, The Android Open Source Project
+ **
+ ** Licensed under the Apache License, Version 2.0 (the "License");
+ ** you may not use this file except in compliance with the License.
+ ** You may obtain a copy of the License at
+ **
+ ** http://www.apache.org/licenses/LICENSE-2.0
+ **
+ ** Unless required by applicable law or agreed to in writing, software
+ ** distributed under the License is distributed on an "AS IS" BASIS,
+ ** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ** See the License for the specific language governing permissions and
+ ** limitations under the License.
+ */
+
+#define LOG_TAG "GLConsumer"
+
+#define GL_GLEXT_PROTOTYPES
+#define EGL_EGLEXT_PROTOTYPES
+
+#include <EGL/egl.h>
+#include <EGL/eglext.h>
+
+#include <utils/Log.h>
+#include <utils/Singleton.h>
+#include <utils/String8.h>
+
+#include <private/gui/SyncFeatures.h>
+
+EGLAPI const char* eglQueryStringImplementationANDROID(EGLDisplay dpy, EGLint name);
+
+namespace android {
+
+ANDROID_SINGLETON_STATIC_INSTANCE(SyncFeatures);
+
+SyncFeatures::SyncFeatures() : Singleton<SyncFeatures>(),
+ mHasNativeFenceSync(false),
+ mHasFenceSync(false),
+ mHasWaitSync(false) {
+ EGLDisplay dpy = eglGetDisplay(EGL_DEFAULT_DISPLAY);
+ // This can only be called after EGL has been initialized; otherwise the
+ // check below will abort.
+ const char* exts = eglQueryStringImplementationANDROID(dpy, EGL_EXTENSIONS);
+ LOG_ALWAYS_FATAL_IF(exts == NULL, "eglQueryStringImplementationANDROID failed");
+ if (strstr(exts, "EGL_ANDROID_native_fence_sync")) {
+ // This makes GLConsumer use the EGL_ANDROID_native_fence_sync
+ // extension to create Android native fences to signal when all
+ // GLES reads for a given buffer have completed.
+ mHasNativeFenceSync = true;
+ }
+ if (strstr(exts, "EGL_KHR_fence_sync")) {
+ mHasFenceSync = true;
+ }
+ if (strstr(exts, "EGL_KHR_wait_sync")) {
+ mHasWaitSync = true;
+ }
+ mString.append("[using:");
+ if (useNativeFenceSync()) {
+ mString.append(" EGL_ANDROID_native_fence_sync");
+ }
+ if (useFenceSync()) {
+ mString.append(" EGL_KHR_fence_sync");
+ }
+ if (useWaitSync()) {
+ mString.append(" EGL_KHR_wait_sync");
+ }
+ mString.append("]");
+}
+
+bool SyncFeatures::useNativeFenceSync() const {
+ // EGL_ANDROID_native_fence_sync is not compatible with using the
+ // EGL_KHR_fence_sync extension for the same purpose.
+ return mHasNativeFenceSync;
+}
+bool SyncFeatures::useFenceSync() const {
+#ifdef DONT_USE_FENCE_SYNC
+ // on some devices it's better to not use EGL_KHR_fence_sync
+ // even if they have it
+ return false;
+#endif
+ // currently we shall only attempt to use EGL_KHR_fence_sync if
+ // USE_FENCE_SYNC is set in our makefile
+ return !mHasNativeFenceSync && mHasFenceSync;
+}
+bool SyncFeatures::useWaitSync() const {
+ return (useNativeFenceSync() || useFenceSync()) && mHasWaitSync;
+}
+
+String8 SyncFeatures::toString() const {
+ return mString;
+}
+
+} // namespace android
diff --git a/opengl/libs/EGL/eglApi.cpp b/opengl/libs/EGL/eglApi.cpp
index 50b08b0..1be4961 100644
--- a/opengl/libs/EGL/eglApi.cpp
+++ b/opengl/libs/EGL/eglApi.cpp
@@ -52,8 +52,6 @@ using namespace android;
// ----------------------------------------------------------------------------
-#define EGL_VERSION_HW_ANDROID 0x3143
-
namespace android {
struct extention_map_t {
@@ -1021,12 +1019,29 @@ const char* eglQueryString(EGLDisplay dpy, EGLint name)
return dp->getExtensionString();
case EGL_CLIENT_APIS:
return dp->getClientApiString();
- case EGL_VERSION_HW_ANDROID:
- return dp->disp.queryString.version;
}
return setError(EGL_BAD_PARAMETER, (const char *)0);
}
+EGLAPI const char* eglQueryStringImplementationANDROID(EGLDisplay dpy, EGLint name)
+{
+ clearError();
+
+ const egl_display_ptr dp = validate_display(dpy);
+ if (!dp) return (const char *) NULL;
+
+ switch (name) {
+ case EGL_VENDOR:
+ return dp->disp.queryString.vendor;
+ case EGL_VERSION:
+ return dp->disp.queryString.version;
+ case EGL_EXTENSIONS:
+ return dp->disp.queryString.extensions;
+ case EGL_CLIENT_APIS:
+ return dp->disp.queryString.clientApi;
+ }
+ return setError(EGL_BAD_PARAMETER, (const char *)0);
+}
// ----------------------------------------------------------------------------
// EGL 1.1
diff --git a/services/surfaceflinger/GLExtensions.cpp b/services/surfaceflinger/GLExtensions.cpp
index 0cbf4b1..e5fb083 100644
--- a/services/surfaceflinger/GLExtensions.cpp
+++ b/services/surfaceflinger/GLExtensions.cpp
@@ -80,7 +80,7 @@ void GLExtensions::initWithGLStrings(
mHaveDirectTexture = true;
}
#else
-#warning "EGL_ANDROID_image_native_buffer not supported"
+#error "EGL_ANDROID_image_native_buffer not supported"
#endif
if (hasExtension("GL_ARB_texture_non_power_of_two")) {
diff --git a/services/surfaceflinger/SurfaceFlinger.cpp b/services/surfaceflinger/SurfaceFlinger.cpp
index 0a210f7..3ed8b1b 100644
--- a/services/surfaceflinger/SurfaceFlinger.cpp
+++ b/services/surfaceflinger/SurfaceFlinger.cpp
@@ -53,6 +53,7 @@
#include <utils/Trace.h>
#include <private/android_filesystem_config.h>
+#include <private/gui/SyncFeatures.h>
#include "clz.h"
#include "DdmConnection.h"
@@ -68,11 +69,10 @@
#include "DisplayHardware/HWComposer.h"
#include "DisplayHardware/VirtualDisplaySurface.h"
-
-#define EGL_VERSION_HW_ANDROID 0x3143
-
#define DISPLAY_COUNT 1
+EGLAPI const char* eglQueryStringImplementationANDROID(EGLDisplay dpy, EGLint name);
+
namespace android {
// ---------------------------------------------------------------------------
@@ -2280,6 +2280,10 @@ void SurfaceFlinger::dumpAllLocked(
appendGuiConfigString(result);
result.append("\n");
+ result.append("Sync configuration: ");
+ result.append(SyncFeatures::getInstance().toString());
+ result.append("\n");
+
/*
* Dump the visible layer list
*/
@@ -2313,17 +2317,20 @@ void SurfaceFlinger::dumpAllLocked(
HWComposer& hwc(getHwComposer());
sp<const DisplayDevice> hw(getDefaultDisplayDevice());
const GLExtensions& extensions(GLExtensions::getInstance());
+
+ snprintf(buffer, SIZE, "EGL implementation : %s\n",
+ eglQueryStringImplementationANDROID(mEGLDisplay, EGL_VERSION));
+ result.append(buffer);
+ snprintf(buffer, SIZE, "%s\n",
+ eglQueryStringImplementationANDROID(mEGLDisplay, EGL_EXTENSIONS));
+ result.append(buffer);
+
snprintf(buffer, SIZE, "GLES: %s, %s, %s\n",
extensions.getVendor(),
extensions.getRenderer(),
extensions.getVersion());
result.append(buffer);
-
- snprintf(buffer, SIZE, "EGL : %s\n",
- eglQueryString(mEGLDisplay, EGL_VERSION_HW_ANDROID));
- result.append(buffer);
-
- snprintf(buffer, SIZE, "EXTS: %s\n", extensions.getExtension());
+ snprintf(buffer, SIZE, "%s\n", extensions.getExtension());
result.append(buffer);
hw->undefinedRegion.dump(result, "undefinedRegion");
diff --git a/services/surfaceflinger/SurfaceFlingerConsumer.cpp b/services/surfaceflinger/SurfaceFlingerConsumer.cpp
index e427072..2869250 100644
--- a/services/surfaceflinger/SurfaceFlingerConsumer.cpp
+++ b/services/surfaceflinger/SurfaceFlingerConsumer.cpp
@@ -19,10 +19,11 @@
#include "SurfaceFlingerConsumer.h"
+#include <private/gui/SyncFeatures.h>
+
#include <utils/Trace.h>
#include <utils/Errors.h>
-
namespace android {
// ---------------------------------------------------------------------------
@@ -78,7 +79,7 @@ status_t SurfaceFlingerConsumer::updateTexImage(BufferRejecter* rejecter)
return err;
}
- if (!sUseNativeFenceSync) {
+ if (!SyncFeatures::getInstance().useNativeFenceSync()) {
// Bind the new buffer to the GL texture.
//
// Older devices require the "implicit" synchronization provided