From dff8e58d47ede6e748c0b02e128ca33b42a4f362 Mon Sep 17 00:00:00 2001 From: Mathias Agopian Date: Mon, 4 May 2009 14:17:04 -0700 Subject: update surfaceflinger, libui and libagl to the new gralloc api - Currently the lock/unlock path is naive and is done for each drawing operation (glDrawElements and glDrawArrays). this should be improved eventually. - factor all the lock/unlock code in SurfaceBuffer. - fixed "showupdate" so it works even when we don't have preserving eglSwapBuffers(). - improved the situation with the dirty-region and fixed a problem that caused GL apps to not update. - make use of LightRefBase() where needed, instead of duplicating its implementation - add LightRefBase::getStrongCount() - renamed EGLNativeWindowSurface.cpp to FramebufferNativeWindow.cpp - disabled copybits test, since it clashes with the new gralloc api - Camera/Video will be fixed later when we rework the overlay apis --- libs/ui/FramebufferNativeWindow.cpp | 214 ++++++++++++++++++++++++++++++++++++ 1 file changed, 214 insertions(+) create mode 100644 libs/ui/FramebufferNativeWindow.cpp (limited to 'libs/ui/FramebufferNativeWindow.cpp') diff --git a/libs/ui/FramebufferNativeWindow.cpp b/libs/ui/FramebufferNativeWindow.cpp new file mode 100644 index 000000000000..407d6f4f2b19 --- /dev/null +++ b/libs/ui/FramebufferNativeWindow.cpp @@ -0,0 +1,214 @@ +/* +** +** Copyright 2007 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 "FramebufferNativeWindow" + +#include +#include +#include +#include + +#include +#include +#include + +#include +#include +#include + +#include + +#include +#include + +#include +#include + +// ---------------------------------------------------------------------------- +namespace android { +// ---------------------------------------------------------------------------- + +/* + * This implements the (main) framebuffer management. This class is used + * mostly by SurfaceFlinger, but also by command line GL application. + * + * In fact this is an implementation of android_native_window_t on top of + * the framebuffer. + * + * Currently it is pretty simple, it manages only two buffers (the front and + * back buffer). + * + */ + +FramebufferNativeWindow::FramebufferNativeWindow() + : BASE(), fbDev(0), grDev(0) +{ + hw_module_t const* module; + if (hw_get_module(GRALLOC_HARDWARE_MODULE_ID, &module) == 0) { + int stride; + framebuffer_open(module, &fbDev); + gralloc_open(module, &grDev); + int err; + + + // initialize the buffer FIFO + mNumBuffers = 2; + mNumFreeBuffers = 2; + mBufferHead = mNumBuffers-1; + buffers[0] = new NativeBuffer( + fbDev->width, fbDev->height, fbDev->format, GRALLOC_USAGE_HW_FB); + buffers[1] = new NativeBuffer( + fbDev->width, fbDev->height, fbDev->format, GRALLOC_USAGE_HW_FB); + + err = grDev->alloc(grDev, + fbDev->width, fbDev->height, fbDev->format, + GRALLOC_USAGE_HW_FB, &buffers[0]->handle, &buffers[0]->stride); + + LOGE_IF(err, "fb buffer 0 allocation failed w=%d, h=%d, err=%s", + fbDev->width, fbDev->height, strerror(-err)); + + err = grDev->alloc(grDev, + fbDev->width, fbDev->height, fbDev->format, + GRALLOC_USAGE_HW_FB, &buffers[1]->handle, &buffers[1]->stride); + + LOGE_IF(err, "fb buffer 1 allocation failed w=%d, h=%d, err=%s", + fbDev->width, fbDev->height, strerror(-err)); + } + + uint32_t flags = fbDev->flags & SURFACE_FLAG_MAPPED; + + /* + * FIXME: SURFACE_FLAG_PRESERVE_CONTENT + * how to implement this, there is no concept of preserve content in + * the framebuffer, which just "posts" buffer. + * + * It looks like what we need is a way to know if the posted buffer can + * be reused. But if so, why allocating 2 buffers?... + * + * should the lock/unlock calls take care of the copy-back? + * + * + * In the end, the client wants to know if the backbuffer is preserved + * though... it's complicated. + * + */ + + //flags |= SURFACE_FLAG_PRESERVE_CONTENT; + + + const_cast(android_native_window_t::flags) = flags; + const_cast(android_native_window_t::xdpi) = fbDev->xdpi; + const_cast(android_native_window_t::ydpi) = fbDev->ydpi; + const_cast(android_native_window_t::minSwapInterval) = + fbDev->minSwapInterval; + const_cast(android_native_window_t::maxSwapInterval) = + fbDev->maxSwapInterval; + + android_native_window_t::setSwapInterval = setSwapInterval; + android_native_window_t::dequeueBuffer = dequeueBuffer; + android_native_window_t::lockBuffer = lockBuffer; + android_native_window_t::queueBuffer = queueBuffer; +} + +FramebufferNativeWindow::~FramebufferNativeWindow() { + grDev->free(grDev, buffers[0]->handle); + grDev->free(grDev, buffers[1]->handle); + gralloc_close(grDev); + framebuffer_close(fbDev); +} + +void FramebufferNativeWindow::connect(android_native_window_t* window) +{ +} + +void FramebufferNativeWindow::disconnect(android_native_window_t* window) +{ +} + +int FramebufferNativeWindow::setSwapInterval( + android_native_window_t* window, int interval) +{ + framebuffer_device_t* fb = getSelf(window)->fbDev; + return fb->setSwapInterval(fb, interval); +} + +void FramebufferNativeWindow::setSwapRectangle(const Rect& dirty) +{ + Mutex::Autolock _l(mutex); + mDirty = dirty; +} + +int FramebufferNativeWindow::dequeueBuffer(android_native_window_t* window, + android_native_buffer_t** buffer) +{ + FramebufferNativeWindow* self = getSelf(window); + Mutex::Autolock _l(self->mutex); + framebuffer_device_t* fb = self->fbDev; + + // wait for a free buffer + while (!self->mNumFreeBuffers) { + self->mCondition.wait(self->mutex); + } + // get this buffer + self->mNumFreeBuffers--; + int index = self->mBufferHead++; + if (self->mBufferHead >= self->mNumBuffers) + self->mBufferHead = 0; + + *buffer = self->buffers[index].get(); + + return 0; +} + +int FramebufferNativeWindow::lockBuffer(android_native_window_t* window, + android_native_buffer_t* buffer) +{ + FramebufferNativeWindow* self = getSelf(window); + Mutex::Autolock _l(self->mutex); + + // wait that the buffer we're locking is not front anymore + while (self->front == buffer) { + self->mCondition.wait(self->mutex); + } + + return NO_ERROR; +} + +int FramebufferNativeWindow::queueBuffer(android_native_window_t* window, + android_native_buffer_t* buffer) +{ + FramebufferNativeWindow* self = getSelf(window); + Mutex::Autolock _l(self->mutex); + framebuffer_device_t* fb = self->fbDev; + buffer_handle_t handle = static_cast(buffer)->handle; + int res = fb->post(fb, handle); + self->front = static_cast(buffer); + self->mNumFreeBuffers++; + self->mCondition.broadcast(); + return res; +} + +// ---------------------------------------------------------------------------- +}; // namespace android +// ---------------------------------------------------------------------------- + + +EGLNativeWindowType android_createDisplaySurface(void) +{ + return new android::FramebufferNativeWindow(); +} + -- cgit v1.2.3-59-g8ed1b From 6279619e4279daf77feff0c76e089b26ad66124f Mon Sep 17 00:00:00 2001 From: Mathias Agopian Date: Mon, 4 May 2009 19:38:43 -0700 Subject: minor clean-up in FramebufferNativeWindow --- include/ui/FramebufferNativeWindow.h | 6 ------ libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp | 11 ++++------- libs/surfaceflinger/DisplayHardware/DisplayHardware.h | 1 - libs/ui/FramebufferNativeWindow.cpp | 14 -------------- 4 files changed, 4 insertions(+), 28 deletions(-) (limited to 'libs/ui/FramebufferNativeWindow.cpp') diff --git a/include/ui/FramebufferNativeWindow.h b/include/ui/FramebufferNativeWindow.h index 1d49cca401ae..4b281db84433 100644 --- a/include/ui/FramebufferNativeWindow.h +++ b/include/ui/FramebufferNativeWindow.h @@ -76,13 +76,9 @@ public: framebuffer_device_t const * getDevice() const { return fbDev; } - void setSwapRectangle(const Rect& dirty); - private: friend class LightRefBase; ~FramebufferNativeWindow(); // this class cannot be overloaded - static void connect(android_native_window_t* window); - static void disconnect(android_native_window_t* window); static int setSwapInterval(android_native_window_t* window, int interval); static int dequeueBuffer(android_native_window_t* window, android_native_buffer_t** buffer); static int lockBuffer(android_native_window_t* window, android_native_buffer_t* buffer); @@ -94,8 +90,6 @@ private: sp buffers[2]; sp front; - Rect mDirty; - mutable Mutex mutex; Condition mCondition; int32_t mNumBuffers; diff --git a/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp b/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp index 83ebd7a617d3..ca96e140ff7f 100644 --- a/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp +++ b/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp @@ -305,16 +305,13 @@ void DisplayHardware::flip(const Region& dirty) const EGLDisplay dpy = mDisplay; EGLSurface surface = mSurface; - Region newDirty(dirty); - newDirty.andSelf(Rect(mWidth, mHeight)); - if (mFlags & BUFFER_PRESERVED) { - mDirty = newDirty; + Region newDirty(dirty); + newDirty.andSelf(Rect(mWidth, mHeight)); + const Rect& b(newDirty.bounds()); + //mNativeWindow->setSwapRectangle(b); } - const Rect& b(newDirty.bounds()); - mNativeWindow->setSwapRectangle(b); - mPageFlipCount++; eglSwapBuffers(dpy, surface); checkEGLErrors("eglSwapBuffers"); diff --git a/libs/surfaceflinger/DisplayHardware/DisplayHardware.h b/libs/surfaceflinger/DisplayHardware/DisplayHardware.h index 97a68a53b424..c9c75e27744b 100644 --- a/libs/surfaceflinger/DisplayHardware/DisplayHardware.h +++ b/libs/surfaceflinger/DisplayHardware/DisplayHardware.h @@ -102,7 +102,6 @@ private: int mHeight; PixelFormat mFormat; uint32_t mFlags; - mutable Region mDirty; mutable uint32_t mPageFlipCount; sp mNativeWindow; diff --git a/libs/ui/FramebufferNativeWindow.cpp b/libs/ui/FramebufferNativeWindow.cpp index 407d6f4f2b19..f235cb44a546 100644 --- a/libs/ui/FramebufferNativeWindow.cpp +++ b/libs/ui/FramebufferNativeWindow.cpp @@ -131,14 +131,6 @@ FramebufferNativeWindow::~FramebufferNativeWindow() { framebuffer_close(fbDev); } -void FramebufferNativeWindow::connect(android_native_window_t* window) -{ -} - -void FramebufferNativeWindow::disconnect(android_native_window_t* window) -{ -} - int FramebufferNativeWindow::setSwapInterval( android_native_window_t* window, int interval) { @@ -146,12 +138,6 @@ int FramebufferNativeWindow::setSwapInterval( return fb->setSwapInterval(fb, interval); } -void FramebufferNativeWindow::setSwapRectangle(const Rect& dirty) -{ - Mutex::Autolock _l(mutex); - mDirty = dirty; -} - int FramebufferNativeWindow::dequeueBuffer(android_native_window_t* window, android_native_buffer_t** buffer) { -- cgit v1.2.3-59-g8ed1b From ac2523b161df2bb507cc88906bb070878266770d Mon Sep 17 00:00:00 2001 From: Mathias Agopian Date: Tue, 5 May 2009 18:11:11 -0700 Subject: move opengl/include/EGL/android_natives.h to include/ui/egl/android_natives.h and don't include it from egl.h the android_native_ types are just forward declared in egl.h --- include/private/ui/SurfaceBuffer.h | 76 +++++++ include/ui/FramebufferNativeWindow.h | 23 +- include/ui/ISurface.h | 2 - include/ui/Surface.h | 40 +--- include/ui/egl/android_natives.h | 240 ++++++++++++++++++++ .../DisplayHardware/DisplayHardware.cpp | 1 - libs/surfaceflinger/LayerBitmap.h | 4 +- libs/ui/BufferMapper.cpp | 2 - libs/ui/FramebufferNativeWindow.cpp | 19 ++ libs/ui/ISurface.cpp | 1 + libs/ui/Surface.cpp | 5 +- opengl/include/EGL/android_natives.h | 241 --------------------- opengl/include/EGL/eglplatform.h | 4 +- opengl/libagl/TextureObjectManager.cpp | 2 + opengl/libagl/TextureObjectManager.h | 2 +- opengl/libagl/egl.cpp | 3 +- opengl/libagl/texture.cpp | 2 +- 17 files changed, 352 insertions(+), 315 deletions(-) create mode 100644 include/private/ui/SurfaceBuffer.h create mode 100644 include/ui/egl/android_natives.h delete mode 100644 opengl/include/EGL/android_natives.h (limited to 'libs/ui/FramebufferNativeWindow.cpp') diff --git a/include/private/ui/SurfaceBuffer.h b/include/private/ui/SurfaceBuffer.h new file mode 100644 index 000000000000..a6db50f4cf69 --- /dev/null +++ b/include/private/ui/SurfaceBuffer.h @@ -0,0 +1,76 @@ +/* + * Copyright (C) 2007 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_UI_PRIVATE_SURFACE_BUFFER_H +#define ANDROID_UI_PRIVATE_SURFACE_BUFFER_H + +#include +#include + +#include + +#include + +namespace android { + +// --------------------------------------------------------------------------- + +class BufferMapper; +class Rect; +class Surface; +class SurfaceBuffer; + +// --------------------------------------------------------------------------- + +class SurfaceBuffer + : public EGLNativeBase< + android_native_buffer_t, + SurfaceBuffer, + LightRefBase > +{ +public: + status_t lock(uint32_t usage, void** vaddr); + status_t lock(uint32_t usage, const Rect& rect, void** vaddr); + status_t unlock(); + +protected: + SurfaceBuffer(); + SurfaceBuffer(const Parcel& reply); + virtual ~SurfaceBuffer(); + bool mOwner; + + inline const BufferMapper& getBufferMapper() const { return mBufferMapper; } + inline BufferMapper& getBufferMapper() { return mBufferMapper; } + +private: + friend class Surface; + friend class BpSurface; + friend class BnSurface; + friend class LightRefBase; + + SurfaceBuffer& operator = (const SurfaceBuffer& rhs); + const SurfaceBuffer& operator = (const SurfaceBuffer& rhs) const; + + static status_t writeToParcel(Parcel* reply, + android_native_buffer_t const* buffer); + + BufferMapper& mBufferMapper; +}; + +}; // namespace android + +#endif // ANDROID_UI_PRIVATE_SURFACE_BUFFER_H + diff --git a/include/ui/FramebufferNativeWindow.h b/include/ui/FramebufferNativeWindow.h index 0db245af44dd..aad39a2a6b8b 100644 --- a/include/ui/FramebufferNativeWindow.h +++ b/include/ui/FramebufferNativeWindow.h @@ -21,13 +21,14 @@ #include #include -#include #include #include #include +#include + extern "C" EGLNativeWindowType android_createDisplaySurface(void); @@ -36,25 +37,7 @@ namespace android { // --------------------------------------------------------------------------- class Surface; - - -class NativeBuffer - : public EGLNativeBase< - android_native_buffer_t, - NativeBuffer, - LightRefBase > -{ -public: - NativeBuffer(int w, int h, int f, int u) : BASE() { - android_native_buffer_t::width = w; - android_native_buffer_t::height = h; - android_native_buffer_t::format = f; - android_native_buffer_t::usage = u; - } -private: - friend class LightRefBase; - ~NativeBuffer() { }; // this class cannot be overloaded -}; +class NativeBuffer; // --------------------------------------------------------------------------- diff --git a/include/ui/ISurface.h b/include/ui/ISurface.h index 1a788720dbcd..e47b75362775 100644 --- a/include/ui/ISurface.h +++ b/include/ui/ISurface.h @@ -20,8 +20,6 @@ #include #include -#include - #include #include #include diff --git a/include/ui/Surface.h b/include/ui/Surface.h index e9bb1b3f473d..8c4f63ddfec0 100644 --- a/include/ui/Surface.h +++ b/include/ui/Surface.h @@ -28,7 +28,7 @@ #include #include -#include +#include namespace android { @@ -43,44 +43,6 @@ struct layer_cblk_t; // --------------------------------------------------------------------------- -class SurfaceBuffer - : public EGLNativeBase< - android_native_buffer_t, - SurfaceBuffer, - LightRefBase > -{ -public: - status_t lock(uint32_t usage, void** vaddr); - status_t lock(uint32_t usage, const Rect& rect, void** vaddr); - status_t unlock(); - -protected: - SurfaceBuffer(); - SurfaceBuffer(const Parcel& reply); - virtual ~SurfaceBuffer(); - bool mOwner; - - inline const BufferMapper& getBufferMapper() const { return mBufferMapper; } - inline BufferMapper& getBufferMapper() { return mBufferMapper; } - -private: - friend class Surface; - friend class BpSurface; - friend class BnSurface; - friend class LightRefBase; - - SurfaceBuffer& operator = (const SurfaceBuffer& rhs); - const SurfaceBuffer& operator = (const SurfaceBuffer& rhs) const; - - static status_t writeToParcel(Parcel* reply, - android_native_buffer_t const* buffer); - - BufferMapper& mBufferMapper; -}; - -// --------------------------------------------------------------------------- -class Surface; - class SurfaceControl : public RefBase { public: diff --git a/include/ui/egl/android_natives.h b/include/ui/egl/android_natives.h new file mode 100644 index 000000000000..5842ee72ce7f --- /dev/null +++ b/include/ui/egl/android_natives.h @@ -0,0 +1,240 @@ +/* + * Copyright (C) 2009 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_ANDROID_NATIVES_H +#define ANDROID_ANDROID_NATIVES_H + +#include +#include + +#include + +#ifdef __cplusplus +extern "C" { +#endif + +/*****************************************************************************/ + +#define ANDROID_NATIVE_MAKE_CONSTANT(a,b,c,d) \ + (((unsigned)(a)<<24)|((unsigned)(b)<<16)|((unsigned)(c)<<8)|(unsigned)(d)) + +#define ANDROID_NATIVE_WINDOW_MAGIC \ + ANDROID_NATIVE_MAKE_CONSTANT('_','w','n','d') + +#define ANDROID_NATIVE_BUFFER_MAGIC \ + ANDROID_NATIVE_MAKE_CONSTANT('_','b','f','r') + +// --------------------------------------------------------------------------- + +struct android_native_buffer_t; + +enum { + /* attributes of this surface or its updater */ + SURFACE_FLAG_PRESERVE_CONTENT = FRAMEBUFFER_RESERVED0, + SURFACE_FLAG_MAPPED = FRAMEBUFFER_FLAG_MAPPED, +}; + +// --------------------------------------------------------------------------- + +struct android_native_base_t +{ + /* a magic value defined by the actual EGL native type */ + int magic; + + /* the sizeof() of the actual EGL native type */ + int version; + + void* reserved[4]; + + /* reference-counting interface */ + void (*incRef)(struct android_native_base_t* base); + void (*decRef)(struct android_native_base_t* base); +}; + + +struct android_native_window_t +{ +#ifdef __cplusplus + android_native_window_t() + : flags(0), minSwapInterval(0), maxSwapInterval(0), xdpi(0), ydpi(0) + { + common.magic = ANDROID_NATIVE_WINDOW_MAGIC; + common.version = sizeof(android_native_window_t); + memset(common.reserved, 0, sizeof(common.reserved)); + } +#endif + + struct android_native_base_t common; + + /* flags describing some attributes of this surface or its updater */ + const uint32_t flags; + + /* min swap interval supported by this updated */ + const int minSwapInterval; + + /* max swap interval supported by this updated */ + const int maxSwapInterval; + + /* horizontal and vertical resolution in DPI */ + const float xdpi; + const float ydpi; + + /* Some storage reserved for the OEM's driver. */ + intptr_t oem[4]; + + + /* + * Set the swap interval for this surface. + * + * Returns 0 on success or -errno on error. + */ + int (*setSwapInterval)(struct android_native_window_t* window, + int interval); + + /* + * hook called by EGL to acquire a buffer. After this call, the buffer + * is not locked, so its content cannot be modified. + * this call may block if no buffers are available. + * + * Returns 0 on success or -errno on error. + */ + int (*dequeueBuffer)(struct android_native_window_t* window, + struct android_native_buffer_t** buffer); + + /* + * hook called by EGL to lock a buffer. This MUST be called before modifying + * the content of a buffer. The buffer must have been acquired with + * dequeueBuffer first. + * + * Returns 0 on success or -errno on error. + */ + int (*lockBuffer)(struct android_native_window_t* window, + struct android_native_buffer_t* buffer); + /* + * hook called by EGL when modifications to the render buffer are done. + * This unlocks and post the buffer. + * + * Buffers MUST be queued in the same order than they were dequeued. + * + * Returns 0 on success or -errno on error. + */ + int (*queueBuffer)(struct android_native_window_t* window, + struct android_native_buffer_t* buffer); + + + void* reserved_proc[5]; +}; + + +struct android_native_buffer_t +{ +#ifdef __cplusplus + android_native_buffer_t() { + common.magic = ANDROID_NATIVE_BUFFER_MAGIC; + common.version = sizeof(android_native_buffer_t); + memset(common.reserved, 0, sizeof(common.reserved)); + } +#endif + + struct android_native_base_t common; + + int width; + int height; + int stride; + int format; + int usage; + + void* reserved[2]; + + buffer_handle_t handle; + + void* reserved_proc[8]; +}; + + +/* FIXME: this is legacy for pixmaps */ +struct egl_native_pixmap_t +{ + int32_t version; /* must be 32 */ + int32_t width; + int32_t height; + int32_t stride; + uint8_t* data; + uint8_t format; + uint8_t rfu[3]; + union { + uint32_t compressedFormat; + int32_t vstride; + }; + int32_t reserved; +}; + +/*****************************************************************************/ + +#ifdef __cplusplus +} +#endif + + +/*****************************************************************************/ + +#ifdef __cplusplus + +#include + +namespace android { + +/* + * This helper class turns an EGL android_native_xxx type into a C++ + * reference-counted object; with proper type conversions. + */ +template +class EGLNativeBase : public NATIVE_TYPE, public REF +{ +protected: + typedef EGLNativeBase BASE; + EGLNativeBase() : NATIVE_TYPE(), REF() { + NATIVE_TYPE::common.incRef = incRef; + NATIVE_TYPE::common.decRef = decRef; + } + static inline TYPE* getSelf(NATIVE_TYPE* self) { + return static_cast(self); + } + static inline TYPE const* getSelf(NATIVE_TYPE const* self) { + return static_cast(self); + } + static inline TYPE* getSelf(android_native_base_t* base) { + return getSelf(reinterpret_cast(base)); + } + static inline TYPE const * getSelf(android_native_base_t const* base) { + return getSelf(reinterpret_cast(base)); + } + static void incRef(android_native_base_t* base) { + EGLNativeBase* self = getSelf(base); + self->incStrong(self); + } + static void decRef(android_native_base_t* base) { + EGLNativeBase* self = getSelf(base); + self->decStrong(self); + } +}; + +} // namespace android +#endif // __cplusplus + +/*****************************************************************************/ + +#endif /* ANDROID_ANDROID_NATIVES_H */ diff --git a/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp b/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp index ca96e140ff7f..374f2e2c8b65 100644 --- a/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp +++ b/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp @@ -30,7 +30,6 @@ #include #include #include -#include #include diff --git a/libs/surfaceflinger/LayerBitmap.h b/libs/surfaceflinger/LayerBitmap.h index 6e136a2ae764..824e0f2b311b 100644 --- a/libs/surfaceflinger/LayerBitmap.h +++ b/libs/surfaceflinger/LayerBitmap.h @@ -28,12 +28,10 @@ #include #include -#include - #include #include - +#include class copybit_image_t; struct android_native_buffer_t; diff --git a/libs/ui/BufferMapper.cpp b/libs/ui/BufferMapper.cpp index 1a75c5d9acdf..92a9a86bb0f2 100644 --- a/libs/ui/BufferMapper.cpp +++ b/libs/ui/BufferMapper.cpp @@ -25,8 +25,6 @@ #include #include -#include - #include diff --git a/libs/ui/FramebufferNativeWindow.cpp b/libs/ui/FramebufferNativeWindow.cpp index f235cb44a546..5e69cff985c7 100644 --- a/libs/ui/FramebufferNativeWindow.cpp +++ b/libs/ui/FramebufferNativeWindow.cpp @@ -42,6 +42,25 @@ namespace android { // ---------------------------------------------------------------------------- +class NativeBuffer + : public EGLNativeBase< + android_native_buffer_t, + NativeBuffer, + LightRefBase > +{ +public: + NativeBuffer(int w, int h, int f, int u) : BASE() { + android_native_buffer_t::width = w; + android_native_buffer_t::height = h; + android_native_buffer_t::format = f; + android_native_buffer_t::usage = u; + } +private: + friend class LightRefBase; + ~NativeBuffer() { }; // this class cannot be overloaded +}; + + /* * This implements the (main) framebuffer management. This class is used * mostly by SurfaceFlinger, but also by command line GL application. diff --git a/libs/ui/ISurface.cpp b/libs/ui/ISurface.cpp index fcea8ec70121..ec922d0cf1b2 100644 --- a/libs/ui/ISurface.cpp +++ b/libs/ui/ISurface.cpp @@ -27,6 +27,7 @@ #include #include +#include namespace android { diff --git a/libs/ui/Surface.cpp b/libs/ui/Surface.cpp index 782eac46beb8..6437619b20e2 100644 --- a/libs/ui/Surface.cpp +++ b/libs/ui/Surface.cpp @@ -36,12 +36,11 @@ #include #include -#include +#include #include #include - -#include +#include namespace android { diff --git a/opengl/include/EGL/android_natives.h b/opengl/include/EGL/android_natives.h deleted file mode 100644 index b8465d580228..000000000000 --- a/opengl/include/EGL/android_natives.h +++ /dev/null @@ -1,241 +0,0 @@ -/* - * Copyright (C) 2009 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_ANDROID_NATIVES_H -#define ANDROID_ANDROID_NATIVES_H - -#include -#include - -#include - -#ifdef __cplusplus -extern "C" { -#endif - -/*****************************************************************************/ - -#define ANDROID_NATIVE_MAKE_CONSTANT(a,b,c,d) \ - (((unsigned)(a)<<24)|((unsigned)(b)<<16)|((unsigned)(c)<<8)|(unsigned)(d)) - -#define ANDROID_NATIVE_WINDOW_MAGIC \ - ANDROID_NATIVE_MAKE_CONSTANT('_','w','n','d') - -#define ANDROID_NATIVE_BUFFER_MAGIC \ - ANDROID_NATIVE_MAKE_CONSTANT('_','b','f','r') - -// --------------------------------------------------------------------------- - -struct android_native_buffer_t; - -enum { - /* attributes of this surface or its updater */ - SURFACE_FLAG_PRESERVE_CONTENT = FRAMEBUFFER_RESERVED0, - SURFACE_FLAG_MAPPED = FRAMEBUFFER_FLAG_MAPPED, -}; - - -// --------------------------------------------------------------------------- - -struct android_native_base_t -{ - /* a magic value defined by the actual EGL native type */ - int magic; - - /* the sizeof() of the actual EGL native type */ - int version; - - void* reserved[4]; - - /* reference-counting interface */ - void (*incRef)(struct android_native_base_t* base); - void (*decRef)(struct android_native_base_t* base); -}; - - -struct android_native_window_t -{ -#ifdef __cplusplus - android_native_window_t() - : flags(0), minSwapInterval(0), maxSwapInterval(0), xdpi(0), ydpi(0) - { - common.magic = ANDROID_NATIVE_WINDOW_MAGIC; - common.version = sizeof(android_native_window_t); - memset(common.reserved, 0, sizeof(common.reserved)); - } -#endif - - struct android_native_base_t common; - - /* flags describing some attributes of this surface or its updater */ - const uint32_t flags; - - /* min swap interval supported by this updated */ - const int minSwapInterval; - - /* max swap interval supported by this updated */ - const int maxSwapInterval; - - /* horizontal and vertical resolution in DPI */ - const float xdpi; - const float ydpi; - - /* Some storage reserved for the OEM's driver. */ - intptr_t oem[4]; - - - /* - * Set the swap interval for this surface. - * - * Returns 0 on success or -errno on error. - */ - int (*setSwapInterval)(struct android_native_window_t* window, - int interval); - - /* - * hook called by EGL to acquire a buffer. After this call, the buffer - * is not locked, so its content cannot be modified. - * this call may block if no buffers are available. - * - * Returns 0 on success or -errno on error. - */ - int (*dequeueBuffer)(struct android_native_window_t* window, - struct android_native_buffer_t** buffer); - - /* - * hook called by EGL to lock a buffer. This MUST be called before modifying - * the content of a buffer. The buffer must have been acquired with - * dequeueBuffer first. - * - * Returns 0 on success or -errno on error. - */ - int (*lockBuffer)(struct android_native_window_t* window, - struct android_native_buffer_t* buffer); - /* - * hook called by EGL when modifications to the render buffer are done. - * This unlocks and post the buffer. - * - * Buffers MUST be queued in the same order than they were dequeued. - * - * Returns 0 on success or -errno on error. - */ - int (*queueBuffer)(struct android_native_window_t* window, - struct android_native_buffer_t* buffer); - - - void* reserved_proc[5]; -}; - - -struct android_native_buffer_t -{ -#ifdef __cplusplus - android_native_buffer_t() { - common.magic = ANDROID_NATIVE_BUFFER_MAGIC; - common.version = sizeof(android_native_buffer_t); - memset(common.reserved, 0, sizeof(common.reserved)); - } -#endif - - struct android_native_base_t common; - - int width; - int height; - int stride; - int format; - int usage; - - void* reserved[2]; - - buffer_handle_t handle; - - void* reserved_proc[8]; -}; - - -/* FIXME: this is legacy for pixmaps */ -struct egl_native_pixmap_t -{ - int32_t version; /* must be 32 */ - int32_t width; - int32_t height; - int32_t stride; - uint8_t* data; - uint8_t format; - uint8_t rfu[3]; - union { - uint32_t compressedFormat; - int32_t vstride; - }; - int32_t reserved; -}; - -/*****************************************************************************/ - -#ifdef __cplusplus -} -#endif - - -/*****************************************************************************/ - -#ifdef __cplusplus - -#include - -namespace android { - -/* - * This helper class turns an EGL android_native_xxx type into a C++ - * reference-counted object; with proper type conversions. - */ -template -class EGLNativeBase : public NATIVE_TYPE, public REF -{ -protected: - typedef EGLNativeBase BASE; - EGLNativeBase() : NATIVE_TYPE(), REF() { - NATIVE_TYPE::common.incRef = incRef; - NATIVE_TYPE::common.decRef = decRef; - } - static inline TYPE* getSelf(NATIVE_TYPE* self) { - return static_cast(self); - } - static inline TYPE const* getSelf(NATIVE_TYPE const* self) { - return static_cast(self); - } - static inline TYPE* getSelf(android_native_base_t* base) { - return getSelf(reinterpret_cast(base)); - } - static inline TYPE const * getSelf(android_native_base_t const* base) { - return getSelf(reinterpret_cast(base)); - } - static void incRef(android_native_base_t* base) { - EGLNativeBase* self = getSelf(base); - self->incStrong(self); - } - static void decRef(android_native_base_t* base) { - EGLNativeBase* self = getSelf(base); - self->decStrong(self); - } -}; - -} // namespace android -#endif // __cplusplus - -/*****************************************************************************/ - -#endif /* ANDROID_ANDROID_NATIVES_H */ diff --git a/opengl/include/EGL/eglplatform.h b/opengl/include/EGL/eglplatform.h index d42808704dd6..956149091d81 100644 --- a/opengl/include/EGL/eglplatform.h +++ b/opengl/include/EGL/eglplatform.h @@ -89,7 +89,8 @@ typedef Window EGLNativeWindowType; #elif defined(ANDROID) -#include +struct android_native_window_t; +struct egl_native_pixmap_t; typedef struct android_native_window_t* EGLNativeWindowType; typedef struct egl_native_pixmap_t* EGLNativePixmapType; @@ -97,6 +98,7 @@ typedef void* EGLNativeDisplayType; #ifndef EGL_ANDROID_image_native_buffer #define EGL_ANDROID_image_native_buffer 1 +struct android_native_buffer_t; #define EGL_NATIVE_BUFFER_ANDROID 0x6000 /* eglCreateImageKHR target */ #endif diff --git a/opengl/libagl/TextureObjectManager.cpp b/opengl/libagl/TextureObjectManager.cpp index 9eb99f0bc231..e5d4ed2b6f97 100644 --- a/opengl/libagl/TextureObjectManager.cpp +++ b/opengl/libagl/TextureObjectManager.cpp @@ -19,6 +19,8 @@ #include "context.h" #include "TextureObjectManager.h" +#include + namespace android { // ---------------------------------------------------------------------------- diff --git a/opengl/libagl/TextureObjectManager.h b/opengl/libagl/TextureObjectManager.h index 29d50370eb41..e0eadf147959 100644 --- a/opengl/libagl/TextureObjectManager.h +++ b/opengl/libagl/TextureObjectManager.h @@ -30,7 +30,7 @@ #include #include -#include +#include #include "Tokenizer.h" #include "TokenManager.h" diff --git a/opengl/libagl/egl.cpp b/opengl/libagl/egl.cpp index 720ba0bdaff3..0950f3ea2666 100644 --- a/opengl/libagl/egl.cpp +++ b/opengl/libagl/egl.cpp @@ -33,13 +33,14 @@ #include #include -#include #include #include #include #include +#include + #include "context.h" #include "state.h" #include "texture.h" diff --git a/opengl/libagl/texture.cpp b/opengl/libagl/texture.cpp index 118964340f48..0211208e2f4a 100644 --- a/opengl/libagl/texture.cpp +++ b/opengl/libagl/texture.cpp @@ -23,7 +23,7 @@ #include "texture.h" #include "TextureObjectManager.h" -#include +#include #ifdef LIBAGL_USE_GRALLOC_COPYBITS #include "copybit.h" -- cgit v1.2.3-59-g8ed1b From b51e18d59b6f8e44a5d3516fc3359c54fa913331 Mon Sep 17 00:00:00 2001 From: Mathias Agopian Date: Tue, 5 May 2009 18:21:32 -0700 Subject: move android_native_buffer_t declaration into its own private/ui/android_native_priv.h header, since user code should never have access to it. --- include/private/ui/SurfaceBuffer.h | 2 +- include/private/ui/android_natives_priv.h | 62 +++++++++++++++++++++++++++++++ include/ui/egl/android_natives.h | 26 ------------- libs/ui/FramebufferNativeWindow.cpp | 2 + opengl/libagl/TextureObjectManager.cpp | 2 +- opengl/libagl/egl.cpp | 2 +- opengl/libagl/texture.cpp | 2 +- 7 files changed, 68 insertions(+), 30 deletions(-) create mode 100644 include/private/ui/android_natives_priv.h (limited to 'libs/ui/FramebufferNativeWindow.cpp') diff --git a/include/private/ui/SurfaceBuffer.h b/include/private/ui/SurfaceBuffer.h index a6db50f4cf69..c45abeb73c25 100644 --- a/include/private/ui/SurfaceBuffer.h +++ b/include/private/ui/SurfaceBuffer.h @@ -22,7 +22,7 @@ #include -#include +#include namespace android { diff --git a/include/private/ui/android_natives_priv.h b/include/private/ui/android_natives_priv.h new file mode 100644 index 000000000000..ee843e928100 --- /dev/null +++ b/include/private/ui/android_natives_priv.h @@ -0,0 +1,62 @@ +/* + * Copyright (C) 2009 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_ANDROID_NATIVES_PRIV_H +#define ANDROID_ANDROID_NATIVES_PRIV_H + +#include + +#ifdef __cplusplus +extern "C" { +#endif + +/*****************************************************************************/ + +struct android_native_buffer_t +{ +#ifdef __cplusplus + android_native_buffer_t() { + common.magic = ANDROID_NATIVE_BUFFER_MAGIC; + common.version = sizeof(android_native_buffer_t); + memset(common.reserved, 0, sizeof(common.reserved)); + } +#endif + + struct android_native_base_t common; + + int width; + int height; + int stride; + int format; + int usage; + + void* reserved[2]; + + buffer_handle_t handle; + + void* reserved_proc[8]; +}; + + +/*****************************************************************************/ + +#ifdef __cplusplus +} +#endif + +/*****************************************************************************/ + +#endif /* ANDROID_ANDROID_NATIVES_PRIV_H */ diff --git a/include/ui/egl/android_natives.h b/include/ui/egl/android_natives.h index 5842ee72ce7f..fa3b7a0dc78d 100644 --- a/include/ui/egl/android_natives.h +++ b/include/ui/egl/android_natives.h @@ -139,32 +139,6 @@ struct android_native_window_t }; -struct android_native_buffer_t -{ -#ifdef __cplusplus - android_native_buffer_t() { - common.magic = ANDROID_NATIVE_BUFFER_MAGIC; - common.version = sizeof(android_native_buffer_t); - memset(common.reserved, 0, sizeof(common.reserved)); - } -#endif - - struct android_native_base_t common; - - int width; - int height; - int stride; - int format; - int usage; - - void* reserved[2]; - - buffer_handle_t handle; - - void* reserved_proc[8]; -}; - - /* FIXME: this is legacy for pixmaps */ struct egl_native_pixmap_t { diff --git a/libs/ui/FramebufferNativeWindow.cpp b/libs/ui/FramebufferNativeWindow.cpp index 5e69cff985c7..4e692e2c27a1 100644 --- a/libs/ui/FramebufferNativeWindow.cpp +++ b/libs/ui/FramebufferNativeWindow.cpp @@ -38,6 +38,8 @@ #include #include +#include + // ---------------------------------------------------------------------------- namespace android { // ---------------------------------------------------------------------------- diff --git a/opengl/libagl/TextureObjectManager.cpp b/opengl/libagl/TextureObjectManager.cpp index e5d4ed2b6f97..9deb2cf9eea4 100644 --- a/opengl/libagl/TextureObjectManager.cpp +++ b/opengl/libagl/TextureObjectManager.cpp @@ -19,7 +19,7 @@ #include "context.h" #include "TextureObjectManager.h" -#include +#include namespace android { // ---------------------------------------------------------------------------- diff --git a/opengl/libagl/egl.cpp b/opengl/libagl/egl.cpp index 0950f3ea2666..1a774f59db22 100644 --- a/opengl/libagl/egl.cpp +++ b/opengl/libagl/egl.cpp @@ -39,7 +39,7 @@ #include #include -#include +#include #include "context.h" #include "state.h" diff --git a/opengl/libagl/texture.cpp b/opengl/libagl/texture.cpp index 0211208e2f4a..d675107ca0b1 100644 --- a/opengl/libagl/texture.cpp +++ b/opengl/libagl/texture.cpp @@ -23,7 +23,7 @@ #include "texture.h" #include "TextureObjectManager.h" -#include +#include #ifdef LIBAGL_USE_GRALLOC_COPYBITS #include "copybit.h" -- cgit v1.2.3-59-g8ed1b From 9bd5da4db97fec7cdbe6e07870411c1fcaff4365 Mon Sep 17 00:00:00 2001 From: Mathias Agopian Date: Tue, 5 May 2009 18:29:35 -0700 Subject: get rid off unneeded flags --- include/ui/egl/android_natives.h | 8 ++------ libs/ui/FramebufferNativeWindow.cpp | 23 +---------------------- 2 files changed, 3 insertions(+), 28 deletions(-) (limited to 'libs/ui/FramebufferNativeWindow.cpp') diff --git a/include/ui/egl/android_natives.h b/include/ui/egl/android_natives.h index fa3b7a0dc78d..0398ea7eb7c1 100644 --- a/include/ui/egl/android_natives.h +++ b/include/ui/egl/android_natives.h @@ -41,12 +41,6 @@ extern "C" { struct android_native_buffer_t; -enum { - /* attributes of this surface or its updater */ - SURFACE_FLAG_PRESERVE_CONTENT = FRAMEBUFFER_RESERVED0, - SURFACE_FLAG_MAPPED = FRAMEBUFFER_FLAG_MAPPED, -}; - // --------------------------------------------------------------------------- struct android_native_base_t @@ -64,6 +58,7 @@ struct android_native_base_t void (*decRef)(struct android_native_base_t* base); }; +// --------------------------------------------------------------------------- struct android_native_window_t { @@ -138,6 +133,7 @@ struct android_native_window_t void* reserved_proc[5]; }; +// --------------------------------------------------------------------------- /* FIXME: this is legacy for pixmaps */ struct egl_native_pixmap_t diff --git a/libs/ui/FramebufferNativeWindow.cpp b/libs/ui/FramebufferNativeWindow.cpp index 4e692e2c27a1..83b333f7e0e1 100644 --- a/libs/ui/FramebufferNativeWindow.cpp +++ b/libs/ui/FramebufferNativeWindow.cpp @@ -110,28 +110,7 @@ FramebufferNativeWindow::FramebufferNativeWindow() fbDev->width, fbDev->height, strerror(-err)); } - uint32_t flags = fbDev->flags & SURFACE_FLAG_MAPPED; - - /* - * FIXME: SURFACE_FLAG_PRESERVE_CONTENT - * how to implement this, there is no concept of preserve content in - * the framebuffer, which just "posts" buffer. - * - * It looks like what we need is a way to know if the posted buffer can - * be reused. But if so, why allocating 2 buffers?... - * - * should the lock/unlock calls take care of the copy-back? - * - * - * In the end, the client wants to know if the backbuffer is preserved - * though... it's complicated. - * - */ - - //flags |= SURFACE_FLAG_PRESERVE_CONTENT; - - - const_cast(android_native_window_t::flags) = flags; + const_cast(android_native_window_t::flags) = fbDev->flags; const_cast(android_native_window_t::xdpi) = fbDev->xdpi; const_cast(android_native_window_t::ydpi) = fbDev->ydpi; const_cast(android_native_window_t::minSwapInterval) = -- cgit v1.2.3-59-g8ed1b From 97b8056c3182a973c67d3c1b196150d4b9e30f3a Mon Sep 17 00:00:00 2001 From: Mathias Agopian Date: Thu, 7 May 2009 17:40:23 -0700 Subject: add support for update-on-demand in SurfaceFlinger --- include/ui/FramebufferNativeWindow.h | 4 ++++ libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp | 12 +++++++++--- libs/ui/FramebufferNativeWindow.cpp | 12 +++++++++++- 3 files changed, 24 insertions(+), 4 deletions(-) (limited to 'libs/ui/FramebufferNativeWindow.cpp') diff --git a/include/ui/FramebufferNativeWindow.h b/include/ui/FramebufferNativeWindow.h index aad39a2a6b8b..a7804728c4ea 100644 --- a/include/ui/FramebufferNativeWindow.h +++ b/include/ui/FramebufferNativeWindow.h @@ -52,6 +52,9 @@ public: framebuffer_device_t const * getDevice() const { return fbDev; } + bool isUpdateOnDemand() const { return mUpdateOnDemand; } + status_t setUpdateRectangle(const Rect& updateRect); + private: friend class LightRefBase; ~FramebufferNativeWindow(); // this class cannot be overloaded @@ -71,6 +74,7 @@ private: int32_t mNumBuffers; int32_t mNumFreeBuffers; int32_t mBufferHead; + bool mUpdateOnDemand; }; // --------------------------------------------------------------------------- diff --git a/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp b/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp index 31db31f9abb5..25e351c10f86 100644 --- a/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp +++ b/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp @@ -183,9 +183,11 @@ void DisplayHardware::init(uint32_t dpy) LOGI("extensions: %s", egl_extensions); LOGI("Client API: %s", eglQueryString(display, EGL_CLIENT_APIS)?:"Not Supported"); - // TODO: get the real "update_on_demand" behavior (probably should be HAL module) - // FIXME: mFlags |= UPDATE_ON_DEMAND; + if (mNativeWindow->isUpdateOnDemand()) { + mFlags |= UPDATE_ON_DEMAND; + } + if (eglGetConfigAttrib(display, config, EGL_CONFIG_CAVEAT, &dummy) == EGL_TRUE) { if (dummy == EGL_SLOW_CONFIG) mFlags |= SLOW_CONFIG; @@ -210,7 +212,7 @@ void DisplayHardware::init(uint32_t dpy) mDpiX = mNativeWindow->xdpi; mDpiX = mNativeWindow->ydpi; - mRefreshRate = mNativeWindow->getDevice()->fps; + mRefreshRate = fbDev->fps; char property[PROPERTY_VALUE_MAX]; if (property_get("ro.sf.lcd_density", property, NULL) <= 0) { @@ -314,6 +316,10 @@ void DisplayHardware::flip(const Region& dirty) const b.left, b.top, b.width(), b.height()); } + if (mFlags & UPDATE_ON_DEMAND) { + mNativeWindow->setUpdateRectangle(dirty.bounds()); + } + mPageFlipCount++; eglSwapBuffers(dpy, surface); checkEGLErrors("eglSwapBuffers"); diff --git a/libs/ui/FramebufferNativeWindow.cpp b/libs/ui/FramebufferNativeWindow.cpp index 83b333f7e0e1..8c8fd6bb0f9d 100644 --- a/libs/ui/FramebufferNativeWindow.cpp +++ b/libs/ui/FramebufferNativeWindow.cpp @@ -76,7 +76,7 @@ private: */ FramebufferNativeWindow::FramebufferNativeWindow() - : BASE(), fbDev(0), grDev(0) + : BASE(), fbDev(0), grDev(0), mUpdateOnDemand(false) { hw_module_t const* module; if (hw_get_module(GRALLOC_HARDWARE_MODULE_ID, &module) == 0) { @@ -86,6 +86,8 @@ FramebufferNativeWindow::FramebufferNativeWindow() int err; + mUpdateOnDemand = (fbDev->setUpdateRect != 0); + // initialize the buffer FIFO mNumBuffers = 2; mNumFreeBuffers = 2; @@ -131,6 +133,14 @@ FramebufferNativeWindow::~FramebufferNativeWindow() { framebuffer_close(fbDev); } +status_t FramebufferNativeWindow::setUpdateRectangle(const Rect& r) +{ + if (!mUpdateOnDemand) { + return INVALID_OPERATION; + } + return fbDev->setUpdateRect(fbDev, r.left, r.top, r.width(), r.height()); +} + int FramebufferNativeWindow::setSwapInterval( android_native_window_t* window, int interval) { -- cgit v1.2.3-59-g8ed1b From cbc4c9f8d56317b2fe8964c15c9785ebeef98ca7 Mon Sep 17 00:00:00 2001 From: Mathias Agopian Date: Tue, 23 Jun 2009 21:11:43 -0700 Subject: hack copybit back in for video playback on msm7k. we have h/w accelerated video again --- include/ui/FramebufferNativeWindow.h | 8 +- .../DisplayHardware/DisplayHardware.cpp | 7 +- .../DisplayHardware/DisplayHardware.h | 6 +- libs/surfaceflinger/LayerBuffer.cpp | 124 ++++++++++++++++++++- libs/surfaceflinger/LayerBuffer.h | 3 + libs/ui/FramebufferNativeWindow.cpp | 6 + 6 files changed, 142 insertions(+), 12 deletions(-) (limited to 'libs/ui/FramebufferNativeWindow.cpp') diff --git a/include/ui/FramebufferNativeWindow.h b/include/ui/FramebufferNativeWindow.h index a7804728c4ea..03d064cb36b8 100644 --- a/include/ui/FramebufferNativeWindow.h +++ b/include/ui/FramebufferNativeWindow.h @@ -55,6 +55,9 @@ public: bool isUpdateOnDemand() const { return mUpdateOnDemand; } status_t setUpdateRectangle(const Rect& updateRect); + // FIXME: needed for copybit hack in LayerBuffer + android_native_buffer_t const* getBackbuffer() const; + private: friend class LightRefBase; ~FramebufferNativeWindow(); // this class cannot be overloaded @@ -75,8 +78,11 @@ private: int32_t mNumFreeBuffers; int32_t mBufferHead; bool mUpdateOnDemand; -}; + // FIXME: for getBackbuffer + int32_t mLastDequeued; +}; + // --------------------------------------------------------------------------- }; // namespace android // --------------------------------------------------------------------------- diff --git a/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp b/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp index 784dfa585f55..925f5cc7a7a5 100644 --- a/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp +++ b/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp @@ -349,10 +349,7 @@ void DisplayHardware::makeCurrent() const eglMakeCurrent(mDisplay, mSurface, mSurface, mContext); } -void DisplayHardware::copyFrontToImage(const copybit_image_t& front) const { - // FIXME: we need to get rid of this +sp DisplayHardware::getFb() const { + return mNativeWindow; } -void DisplayHardware::copyBackToImage(const copybit_image_t& front) const { - // FIXME: we need to get rid of this -} diff --git a/libs/surfaceflinger/DisplayHardware/DisplayHardware.h b/libs/surfaceflinger/DisplayHardware/DisplayHardware.h index c3dbff178f29..240c5d148e35 100644 --- a/libs/surfaceflinger/DisplayHardware/DisplayHardware.h +++ b/libs/surfaceflinger/DisplayHardware/DisplayHardware.h @@ -80,13 +80,13 @@ public: EGLDisplay getEGLDisplay() const { return mDisplay; } overlay_control_device_t* getOverlayEngine() const { return mOverlayEngine; } - void copyFrontToImage(const copybit_image_t& front) const; - void copyBackToImage(const copybit_image_t& front) const; - Rect bounds() const { return Rect(mWidth, mHeight); } + // FIXME: needed in LayerBuffer for msm7k/copybit hack + sp getFb() const; + private: void init(uint32_t displayIndex) __attribute__((noinline)); void fini() __attribute__((noinline)); diff --git a/libs/surfaceflinger/LayerBuffer.cpp b/libs/surfaceflinger/LayerBuffer.cpp index 22fd4994d5a6..1baf720b1e7b 100644 --- a/libs/surfaceflinger/LayerBuffer.cpp +++ b/libs/surfaceflinger/LayerBuffer.cpp @@ -24,6 +24,9 @@ #include #include +#include + +#include #include "LayerBuffer.h" #include "SurfaceFlinger.h" @@ -316,7 +319,12 @@ LayerBuffer::BufferSource::BufferSource(LayerBuffer& layer, mLayer.setNeedsBlending((info.h_alpha - info.l_alpha) > 0); mBufferSize = info.getScanlineSize(buffers.hor_stride)*buffers.ver_stride; mLayer.forceVisibilityTransaction(); - + + hw_module_t const* module; + mBlitEngine = NULL; + if (hw_get_module(COPYBIT_HARDWARE_MODULE_ID, &module) == 0) { + copybit_open(module, &mBlitEngine); + } } LayerBuffer::BufferSource::~BufferSource() @@ -387,9 +395,119 @@ void LayerBuffer::BufferSource::onDraw(const Region& clip) const return; } - const NativeBuffer& src( ourBuffer->getBuffer() ); + status_t err = NO_ERROR; + NativeBuffer src(ourBuffer->getBuffer()); + const Rect& transformedBounds = mLayer.getTransformedBounds(); + copybit_device_t* copybit = mBlitEngine; + + if (copybit) { + const int src_width = src.crop.r - src.crop.l; + const int src_height = src.crop.b - src.crop.t; + int W = transformedBounds.width(); + int H = transformedBounds.height(); + if (mLayer.getOrientation() & Transform::ROT_90) { + int t(W); W=H; H=t; + } + +#if 0 + /* With LayerBuffer, it is likely that we'll have to rescale the + * surface, because this is often used for video playback or + * camera-preview. Since we want these operation as fast as possible + * we make sure we can use the 2D H/W even if it doesn't support + * the requested scale factor, in which case we perform the scaling + * in several passes. */ + + const float min = copybit->get(copybit, COPYBIT_MINIFICATION_LIMIT); + const float mag = copybit->get(copybit, COPYBIT_MAGNIFICATION_LIMIT); + + float xscale = 1.0f; + if (src_width > W*min) xscale = 1.0f / min; + else if (src_width*mag < W) xscale = mag; + + float yscale = 1.0f; + if (src_height > H*min) yscale = 1.0f / min; + else if (src_height*mag < H) yscale = mag; + + if (UNLIKELY(xscale!=1.0f || yscale!=1.0f)) { + if (UNLIKELY(mTemporaryDealer == 0)) { + // allocate a memory-dealer for this the first time + mTemporaryDealer = mLayer.mFlinger->getSurfaceHeapManager() + ->createHeap(ISurfaceComposer::eHardware); + mTempBitmap.init(mTemporaryDealer); + } + + const int tmp_w = floorf(src_width * xscale); + const int tmp_h = floorf(src_height * yscale); + err = mTempBitmap.setBits(tmp_w, tmp_h, 1, src.img.format); + + if (LIKELY(err == NO_ERROR)) { + NativeBuffer tmp; + mTempBitmap.getBitmapSurface(&tmp.img); + tmp.crop.l = 0; + tmp.crop.t = 0; + tmp.crop.r = tmp.img.w; + tmp.crop.b = tmp.img.h; + + region_iterator tmp_it(Region(Rect(tmp.crop.r, tmp.crop.b))); + copybit->set_parameter(copybit, COPYBIT_TRANSFORM, 0); + copybit->set_parameter(copybit, COPYBIT_PLANE_ALPHA, 0xFF); + copybit->set_parameter(copybit, COPYBIT_DITHER, COPYBIT_DISABLE); + err = copybit->stretch(copybit, + &tmp.img, &src.img, &tmp.crop, &src.crop, &tmp_it); + src = tmp; + } + } +#endif + + copybit_image_t dst; + const DisplayHardware& hw(mLayer.graphicPlane(0).displayHardware()); + sp fbw = hw.getFb(); + android_native_buffer_t const* nb = fbw->getBackbuffer(); + native_handle_t const* hnd = nb->handle; + + if (hnd->data[1] != 0x3141592) { + LOGE("buffer not compatible with copybit"); + err = -1; + } else { + + dst.w = 320; + dst.h = 480; + dst.format = 4; + dst.offset = hnd->data[4]; + dst.base = 0; + dst.fd = hnd->data[0]; + + const Rect& transformedBounds = mLayer.getTransformedBounds(); + const copybit_rect_t& drect + = reinterpret_cast(transformedBounds); + const State& s(mLayer.drawingState()); + region_iterator it(clip); + + // pick the right orientation for this buffer + int orientation = mLayer.getOrientation(); + if (UNLIKELY(mBufferHeap.transform)) { + Transform rot90; + GraphicPlane::orientationToTransfrom( + ISurfaceComposer::eOrientation90, 0, 0, &rot90); + const Transform& planeTransform(mLayer.graphicPlane(0).transform()); + const Layer::State& s(mLayer.drawingState()); + Transform tr(planeTransform * s.transform * rot90); + orientation = tr.getOrientation(); + } + + copybit->set_parameter(copybit, COPYBIT_TRANSFORM, orientation); + copybit->set_parameter(copybit, COPYBIT_PLANE_ALPHA, s.alpha); + copybit->set_parameter(copybit, COPYBIT_DITHER, COPYBIT_ENABLE); + + err = copybit->stretch(copybit, + &dst, &src.img, &drect, &src.crop, &it); + if (err != NO_ERROR) { + LOGE("copybit failed (%s)", strerror(err)); + } + } + } - //if (!can_use_copybit || err) + if (!copybit || err) { // OpenGL fall-back if (UNLIKELY(mTexture.name == -1LU)) { diff --git a/libs/surfaceflinger/LayerBuffer.h b/libs/surfaceflinger/LayerBuffer.h index e1b3cf8bfe70..cd541a513024 100644 --- a/libs/surfaceflinger/LayerBuffer.h +++ b/libs/surfaceflinger/LayerBuffer.h @@ -26,6 +26,8 @@ #include "LayerBase.h" #include "LayerBitmap.h" +struct copybit_device_t; + namespace android { // --------------------------------------------------------------------------- @@ -128,6 +130,7 @@ private: size_t mBufferSize; mutable sp mTempBitmap; mutable LayerBase::Texture mTexture; + copybit_device_t* mBlitEngine; }; class OverlaySource : public Source { diff --git a/libs/ui/FramebufferNativeWindow.cpp b/libs/ui/FramebufferNativeWindow.cpp index 8c8fd6bb0f9d..406c0725c063 100644 --- a/libs/ui/FramebufferNativeWindow.cpp +++ b/libs/ui/FramebufferNativeWindow.cpp @@ -63,6 +63,11 @@ private: }; +android_native_buffer_t const* FramebufferNativeWindow::getBackbuffer() const { + return static_cast(buffers[mLastDequeued].get()); +} + + /* * This implements the (main) framebuffer management. This class is used * mostly by SurfaceFlinger, but also by command line GL application. @@ -165,6 +170,7 @@ int FramebufferNativeWindow::dequeueBuffer(android_native_window_t* window, if (self->mBufferHead >= self->mNumBuffers) self->mBufferHead = 0; + self->mLastDequeued = index; *buffer = self->buffers[index].get(); return 0; -- cgit v1.2.3-59-g8ed1b From 26c28b16f3464eeb98b091b915ccf494ac31c35f Mon Sep 17 00:00:00 2001 From: Mathias Agopian Date: Wed, 24 Jun 2009 22:39:26 -0700 Subject: make use of new eglGetRenderBufferANDROID extension to clean-up a bit a few hacks added recently --- include/ui/FramebufferNativeWindow.h | 6 -- .../DisplayHardware/DisplayHardware.cpp | 5 -- .../DisplayHardware/DisplayHardware.h | 3 - libs/surfaceflinger/LayerBuffer.cpp | 79 ++++++++++++---------- libs/ui/FramebufferNativeWindow.cpp | 6 -- 5 files changed, 42 insertions(+), 57 deletions(-) (limited to 'libs/ui/FramebufferNativeWindow.cpp') diff --git a/include/ui/FramebufferNativeWindow.h b/include/ui/FramebufferNativeWindow.h index 03d064cb36b8..e72357a60190 100644 --- a/include/ui/FramebufferNativeWindow.h +++ b/include/ui/FramebufferNativeWindow.h @@ -55,9 +55,6 @@ public: bool isUpdateOnDemand() const { return mUpdateOnDemand; } status_t setUpdateRectangle(const Rect& updateRect); - // FIXME: needed for copybit hack in LayerBuffer - android_native_buffer_t const* getBackbuffer() const; - private: friend class LightRefBase; ~FramebufferNativeWindow(); // this class cannot be overloaded @@ -78,9 +75,6 @@ private: int32_t mNumFreeBuffers; int32_t mBufferHead; bool mUpdateOnDemand; - - // FIXME: for getBackbuffer - int32_t mLastDequeued; }; // --------------------------------------------------------------------------- diff --git a/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp b/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp index 925f5cc7a7a5..1719b7443b63 100644 --- a/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp +++ b/libs/surfaceflinger/DisplayHardware/DisplayHardware.cpp @@ -348,8 +348,3 @@ void DisplayHardware::makeCurrent() const { eglMakeCurrent(mDisplay, mSurface, mSurface, mContext); } - -sp DisplayHardware::getFb() const { - return mNativeWindow; -} - diff --git a/libs/surfaceflinger/DisplayHardware/DisplayHardware.h b/libs/surfaceflinger/DisplayHardware/DisplayHardware.h index 240c5d148e35..8972d513fdaa 100644 --- a/libs/surfaceflinger/DisplayHardware/DisplayHardware.h +++ b/libs/surfaceflinger/DisplayHardware/DisplayHardware.h @@ -84,9 +84,6 @@ public: return Rect(mWidth, mHeight); } - // FIXME: needed in LayerBuffer for msm7k/copybit hack - sp getFb() const; - private: void init(uint32_t displayIndex) __attribute__((noinline)); void fini() __attribute__((noinline)); diff --git a/libs/surfaceflinger/LayerBuffer.cpp b/libs/surfaceflinger/LayerBuffer.cpp index 58bba44a0459..d70a71f4568c 100644 --- a/libs/surfaceflinger/LayerBuffer.cpp +++ b/libs/surfaceflinger/LayerBuffer.cpp @@ -468,47 +468,52 @@ void LayerBuffer::BufferSource::onDraw(const Region& clip) const } #endif - copybit_image_t dst; - const DisplayHardware& hw(mLayer.graphicPlane(0).displayHardware()); - sp fbw = hw.getFb(); - android_native_buffer_t const* nb = fbw->getBackbuffer(); - native_handle_t const* hnd = nb->handle; - - dst.w = 320; - dst.h = 480; - dst.format = 4; - dst.base = 0; - dst.handle = (native_handle_t *)nb->handle; - - const Rect& transformedBounds = mLayer.getTransformedBounds(); - const copybit_rect_t& drect - = reinterpret_cast(transformedBounds); - const State& s(mLayer.drawingState()); - region_iterator it(clip); - - // pick the right orientation for this buffer - int orientation = mLayer.getOrientation(); - if (UNLIKELY(mBufferHeap.transform)) { - Transform rot90; - GraphicPlane::orientationToTransfrom( - ISurfaceComposer::eOrientation90, 0, 0, &rot90); - const Transform& planeTransform(mLayer.graphicPlane(0).transform()); - const Layer::State& s(mLayer.drawingState()); - Transform tr(planeTransform * s.transform * rot90); - orientation = tr.getOrientation(); - } +#ifdef EGL_ANDROID_get_render_buffer + EGLDisplay dpy = eglGetCurrentDisplay(); + EGLSurface draw = eglGetCurrentSurface(EGL_DRAW); + EGLClientBuffer clientBuf = eglGetRenderBufferANDROID(dpy, draw); + android_native_buffer_t* nb = (android_native_buffer_t*)clientBuf; + if (nb == 0) { + err = BAD_VALUE; + } else { + copybit_image_t dst; + dst.w = nb->width; + dst.h = nb->height; + dst.format = nb->format; + dst.base = NULL; // unused by copybit on msm7k + dst.handle = (native_handle_t *)nb->handle; + + const Rect& transformedBounds = mLayer.getTransformedBounds(); + const copybit_rect_t& drect + = reinterpret_cast(transformedBounds); + const State& s(mLayer.drawingState()); + region_iterator it(clip); + + // pick the right orientation for this buffer + int orientation = mLayer.getOrientation(); + if (UNLIKELY(mBufferHeap.transform)) { + Transform rot90; + GraphicPlane::orientationToTransfrom( + ISurfaceComposer::eOrientation90, 0, 0, &rot90); + const Transform& planeTransform(mLayer.graphicPlane(0).transform()); + const Layer::State& s(mLayer.drawingState()); + Transform tr(planeTransform * s.transform * rot90); + orientation = tr.getOrientation(); + } - copybit->set_parameter(copybit, COPYBIT_TRANSFORM, orientation); - copybit->set_parameter(copybit, COPYBIT_PLANE_ALPHA, s.alpha); - copybit->set_parameter(copybit, COPYBIT_DITHER, COPYBIT_ENABLE); + copybit->set_parameter(copybit, COPYBIT_TRANSFORM, orientation); + copybit->set_parameter(copybit, COPYBIT_PLANE_ALPHA, s.alpha); + copybit->set_parameter(copybit, COPYBIT_DITHER, COPYBIT_ENABLE); - err = copybit->stretch(copybit, - &dst, &src.img, &drect, &src.crop, &it); - if (err != NO_ERROR) { - LOGE("copybit failed (%s)", strerror(err)); + err = copybit->stretch(copybit, + &dst, &src.img, &drect, &src.crop, &it); + if (err != NO_ERROR) { + LOGE("copybit failed (%s)", strerror(err)); + } } } - +#endif + if (!copybit || err) { // OpenGL fall-back diff --git a/libs/ui/FramebufferNativeWindow.cpp b/libs/ui/FramebufferNativeWindow.cpp index 406c0725c063..8c8fd6bb0f9d 100644 --- a/libs/ui/FramebufferNativeWindow.cpp +++ b/libs/ui/FramebufferNativeWindow.cpp @@ -63,11 +63,6 @@ private: }; -android_native_buffer_t const* FramebufferNativeWindow::getBackbuffer() const { - return static_cast(buffers[mLastDequeued].get()); -} - - /* * This implements the (main) framebuffer management. This class is used * mostly by SurfaceFlinger, but also by command line GL application. @@ -170,7 +165,6 @@ int FramebufferNativeWindow::dequeueBuffer(android_native_window_t* window, if (self->mBufferHead >= self->mNumBuffers) self->mBufferHead = 0; - self->mLastDequeued = index; *buffer = self->buffers[index].get(); return 0; -- cgit v1.2.3-59-g8ed1b