diff options
author | Teng-Hui Zhu <ztenghui@google.com> | 2011-06-17 09:00:47 -0700 |
---|---|---|
committer | Android (Google) Code Review <android-gerrit@google.com> | 2011-06-17 09:00:47 -0700 |
commit | 00196945f3d5ad4a36965abb046955e99e092ef3 (patch) | |
tree | 905bf1979b723c38d42871532ab4b79039defa07 | |
parent | 032e76714e4ef7e4560c86a6d17ae89c88897144 (diff) | |
parent | 1ff2b9b9ba1fd8da776f2b114f371d2299aae835 (diff) | |
download | external_webkit-00196945f3d5ad4a36965abb046955e99e092ef3.zip external_webkit-00196945f3d5ad4a36965abb046955e99e092ef3.tar.gz external_webkit-00196945f3d5ad4a36965abb046955e99e092ef3.tar.bz2 |
Merge "Interface clean up for porting Surface Texture, no functional change."
8 files changed, 176 insertions, 76 deletions
diff --git a/Source/WebCore/platform/graphics/android/BackedDoubleBufferedTexture.cpp b/Source/WebCore/platform/graphics/android/BackedDoubleBufferedTexture.cpp index 964422a..b24c806 100644 --- a/Source/WebCore/platform/graphics/android/BackedDoubleBufferedTexture.cpp +++ b/Source/WebCore/platform/graphics/android/BackedDoubleBufferedTexture.cpp @@ -41,7 +41,7 @@ namespace WebCore { BackedDoubleBufferedTexture::BackedDoubleBufferedTexture(uint32_t w, uint32_t h, SkBitmap* bitmap, SkBitmap::Config config) - : DoubleBufferedTexture(eglGetCurrentContext()) + : DoubleBufferedTexture(eglGetCurrentContext(), EglImageMode) , m_usedLevel(-1) , m_config(config) , m_owner(0) @@ -82,7 +82,7 @@ BackedDoubleBufferedTexture::~BackedDoubleBufferedTexture() if (!m_sharedBitmap) delete m_bitmap; delete m_canvas; - SharedTexture* textures[3] = { &m_textureA, &m_textureB, 0 }; + SharedTexture* textures[3] = { m_textureA, m_textureB, 0 }; destroyTextures(textures); #ifdef DEBUG_COUNT ClassTracker::instance()->decrement("BackedDoubleBufferedTexture"); diff --git a/Source/WebCore/platform/graphics/android/DoubleBufferedTexture.cpp b/Source/WebCore/platform/graphics/android/DoubleBufferedTexture.cpp index 395bb2b..569f987 100644 --- a/Source/WebCore/platform/graphics/android/DoubleBufferedTexture.cpp +++ b/Source/WebCore/platform/graphics/android/DoubleBufferedTexture.cpp @@ -35,12 +35,20 @@ namespace WebCore { -DoubleBufferedTexture::DoubleBufferedTexture(EGLContext sharedContext) +DoubleBufferedTexture::DoubleBufferedTexture(EGLContext sharedContext, SharedTextureMode mode) { + m_sharedTextureMode = mode; + + m_textureA = new SharedTexture(m_sharedTextureMode); + if (m_sharedTextureMode == EglImageMode) + m_textureB = new SharedTexture(m_sharedTextureMode); + else + m_textureB = 0; + m_display = eglGetCurrentDisplay(); m_pContext = EGL_NO_CONTEXT; m_cContext = sharedContext; - m_writeableTexture = &m_textureA; + m_writeableTexture = m_textureA; m_lockedConsumerTexture = GL_NO_TEXTURE; m_supportsEGLImage = GLUtils::isEGLImageSupported(); #ifdef DEBUG_COUNT @@ -53,17 +61,23 @@ DoubleBufferedTexture::~DoubleBufferedTexture() #ifdef DEBUG_COUNT ClassTracker::instance()->decrement("DoubleBufferedTexture"); #endif + delete m_textureA; + delete m_textureB; } SharedTexture* DoubleBufferedTexture::getWriteableTexture() { + if (m_sharedTextureMode == SurfaceTextureMode) + return m_textureA; return reinterpret_cast<SharedTexture*>( android_atomic_release_load((int32_t*)&m_writeableTexture)); } SharedTexture* DoubleBufferedTexture::getReadableTexture() { - return (getWriteableTexture() != &m_textureA) ? &m_textureA : &m_textureB; + if (m_sharedTextureMode == SurfaceTextureMode) + return m_textureA; + return (getWriteableTexture() != m_textureA) ? m_textureA : m_textureB; } EGLContext DoubleBufferedTexture::producerAcquireContext() @@ -89,41 +103,61 @@ EGLContext DoubleBufferedTexture::producerAcquireContext() } // initialize the producer's textures - m_textureA.lock(); - m_textureB.lock(); - m_textureA.initSourceTexture(); - m_textureB.initSourceTexture(); - LOGV("Initialized Textures A/B (%d:%d)", m_textureA.getSourceTextureId(), - m_textureB.getSourceTextureId()); - m_textureA.unlock(); - m_textureB.unlock(); + m_textureA->lock(); + if (m_sharedTextureMode == EglImageMode) + m_textureB->lock(); + + m_textureA->initSourceTexture(); + LOGV("Initialized Textures A (%d)", m_textureA->getSourceTextureId()); + if (m_sharedTextureMode == EglImageMode) { + m_textureB->initSourceTexture(); + LOGV("Initialized Textures B (%d)", m_textureB->getSourceTextureId()); + } + + m_textureA->unlock(); + if (m_sharedTextureMode == EglImageMode) + m_textureB->unlock(); m_pContext = context; return context; } +// For MediaTexture only void DoubleBufferedTexture::producerDeleteTextures() { - m_textureA.lock(); - m_textureB.lock(); - LOGV("Deleting Producer Textures A/B (%d:%d)", m_textureA.getSourceTextureId(), - m_textureB.getSourceTextureId()); - m_textureA.deleteSourceTexture(); - m_textureB.deleteSourceTexture(); - m_textureA.unlock(); - m_textureB.unlock(); + m_textureA->lock(); + if (m_sharedTextureMode == EglImageMode) + m_textureB->lock(); + + LOGV("Deleting Producer Textures A (%d)", m_textureA->getSourceTextureId()); + m_textureA->deleteSourceTexture(); + if (m_sharedTextureMode == EglImageMode){ + LOGV("Deleting Producer Textures B (%d)", m_textureB->getSourceTextureId()); + m_textureB->deleteSourceTexture(); + } + + m_textureA->unlock(); + if (m_sharedTextureMode == EglImageMode) + m_textureB->unlock(); } +// For MediaTexture only void DoubleBufferedTexture::consumerDeleteTextures() { - m_textureA.lock(); - m_textureB.lock(); - LOGV("Deleting Consumer Textures A/B (%d:%d)", m_textureA.getTargetTextureId(), - m_textureB.getTargetTextureId()); - m_textureA.deleteTargetTexture(); - m_textureB.deleteTargetTexture(); - m_textureA.unlock(); - m_textureB.unlock(); + m_textureA->lock(); + if (m_sharedTextureMode == EglImageMode) + m_textureB->lock(); + + LOGV("Deleting Consumer Textures A (%d)", m_textureA->getTargetTextureId()); + m_textureA->deleteTargetTexture(); + if (m_sharedTextureMode == EglImageMode) { + LOGV("Deleting Consumer Textures B (%d)", m_textureB->getTargetTextureId()); + m_textureB->deleteTargetTexture(); + } + + m_textureA->unlock(); + if (m_sharedTextureMode == EglImageMode) + m_textureB->unlock(); } TextureInfo* DoubleBufferedTexture::producerLock() @@ -148,9 +182,10 @@ void DoubleBufferedTexture::producerRelease() void DoubleBufferedTexture::producerReleaseAndSwap() { producerRelease(); - - // swap the front and back buffers using an atomic op for the memory barrier - android_atomic_acquire_store((int32_t)getReadableTexture(), (int32_t*)&m_writeableTexture); + if (m_sharedTextureMode == EglImageMode) { + // swap the front and back buffers using an atomic op for the memory barrier + android_atomic_acquire_store((int32_t)getReadableTexture(), (int32_t*)&m_writeableTexture); + } } TextureInfo* DoubleBufferedTexture::consumerLock() diff --git a/Source/WebCore/platform/graphics/android/DoubleBufferedTexture.h b/Source/WebCore/platform/graphics/android/DoubleBufferedTexture.h index ba56c0e..57935d3 100644 --- a/Source/WebCore/platform/graphics/android/DoubleBufferedTexture.h +++ b/Source/WebCore/platform/graphics/android/DoubleBufferedTexture.h @@ -34,7 +34,7 @@ namespace WebCore { class DoubleBufferedTexture { public: // consumer thread functions - DoubleBufferedTexture(EGLContext sharedContext); + DoubleBufferedTexture(EGLContext sharedContext, SharedTextureMode mode); virtual ~DoubleBufferedTexture(); // provider thread functions @@ -53,8 +53,8 @@ protected: SharedTexture* getReadableTexture(); SharedTexture* getWriteableTexture(); - SharedTexture m_textureA; - SharedTexture m_textureB; + SharedTexture* m_textureA; + SharedTexture* m_textureB; private: @@ -66,6 +66,8 @@ private: EGLContext m_cContext; bool m_supportsEGLImage; + + SharedTextureMode m_sharedTextureMode; }; } // namespace WebCore diff --git a/Source/WebCore/platform/graphics/android/MediaTexture.cpp b/Source/WebCore/platform/graphics/android/MediaTexture.cpp index 14f0c20..d8dc960 100644 --- a/Source/WebCore/platform/graphics/android/MediaTexture.cpp +++ b/Source/WebCore/platform/graphics/android/MediaTexture.cpp @@ -48,7 +48,7 @@ namespace WebCore { -MediaTexture::MediaTexture(EGLContext sharedContext) : DoubleBufferedTexture(sharedContext) +MediaTexture::MediaTexture(EGLContext sharedContext) : DoubleBufferedTexture(sharedContext, EglImageMode) { m_producerRefCount = 0; m_consumerRefCount = 0; diff --git a/Source/WebCore/platform/graphics/android/SharedTexture.cpp b/Source/WebCore/platform/graphics/android/SharedTexture.cpp index 829cdcf..6df37a0 100644 --- a/Source/WebCore/platform/graphics/android/SharedTexture.cpp +++ b/Source/WebCore/platform/graphics/android/SharedTexture.cpp @@ -27,6 +27,7 @@ #include "SharedTexture.h" #include "GLUtils.h" +#include <gui/SurfaceTexture.h> #define LOG_NDEBUG 1 #define LOG_TAG "SharedTexture.cpp" @@ -34,18 +35,26 @@ namespace WebCore { -SharedTexture::SharedTexture() +SharedTexture::SharedTexture(SharedTextureMode mode) { - m_eglImage = EGL_NO_IMAGE_KHR; - m_isNewImage = true; - m_syncObject = EGL_NO_SYNC_KHR; - - // Defer initialization of these values until we initialize the source - // texture. This ensures that this initialization happens in the appropriate - // thread. - m_display = 0; - m_supportsEGLImage = false; - m_supportsEGLFenceSyncKHR = false; + m_sharedTextureMode = mode; + + m_sourceTexture = new TextureInfo(m_sharedTextureMode); + m_targetTexture = 0; + + if (m_sharedTextureMode == EglImageMode) { + m_targetTexture = new TextureInfo(m_sharedTextureMode); + m_eglImage = EGL_NO_IMAGE_KHR; + m_isNewImage = true; + m_syncObject = EGL_NO_SYNC_KHR; + + // Defer initialization of these values until we initialize the source + // texture. This ensures that this initialization happens in the appropriate + // thread. + m_display = 0; + m_supportsEGLImage = false; + m_supportsEGLFenceSyncKHR = false; + } } // called by the consumer when it no longer wants to consume and after it has @@ -53,11 +62,18 @@ SharedTexture::SharedTexture() // source texture and EGLImage is the responsibility of the caller. SharedTexture::~SharedTexture() { - deleteTargetTexture(); + if (m_sharedTextureMode == EglImageMode) + deleteTargetTexture(); + + delete m_sourceTexture; + delete m_targetTexture; } + void SharedTexture::initSourceTexture() { + if (m_sharedTextureMode == SurfaceTextureMode) + return; m_display = eglGetCurrentDisplay(); m_supportsEGLImage = GLUtils::isEGLImageSupported(); @@ -69,18 +85,21 @@ void SharedTexture::initSourceTexture() LOGI("imageEGL: %d syncKHR: %d", m_supportsEGLImage, m_supportsEGLFenceSyncKHR); - glGenTextures(1, &m_sourceTexture.m_textureId); -} + glGenTextures(1, &m_sourceTexture->m_textureId); +} +// For MediaTexture only void SharedTexture::deleteSourceTexture() { + if (m_sharedTextureMode == SurfaceTextureMode) + return; // We need to delete the source texture and EGLImage in the thread in which // it was created. In theory we should be able to delete the EGLImage // from either thread, but it currently throws an error if not deleted // in the same EGLContext from which it was created. if (m_supportsEGLImage) { - GLUtils::deleteTexture(&m_sourceTexture.m_textureId); + GLUtils::deleteTexture(&m_sourceTexture->m_textureId); if (m_eglImage != EGL_NO_IMAGE_KHR) { eglDestroyImageKHR(eglGetCurrentDisplay(), m_eglImage); m_eglImage = EGL_NO_IMAGE_KHR; @@ -90,16 +109,23 @@ void SharedTexture::deleteSourceTexture() } } +// For MediaTexture only void SharedTexture::deleteTargetTexture() { + if (m_sharedTextureMode == SurfaceTextureMode) + return; + if (m_supportsEGLImage) - GLUtils::deleteTexture(&m_targetTexture.m_textureId); + GLUtils::deleteTexture(&m_targetTexture->m_textureId); else - GLUtils::deleteTexture(&m_sourceTexture.m_textureId); + GLUtils::deleteTexture(&m_sourceTexture->m_textureId); } TextureInfo* SharedTexture::lockSource() { + if (m_sharedTextureMode == SurfaceTextureMode) + return m_sourceTexture; + m_lock.lock(); if (m_supportsEGLFenceSyncKHR && m_syncObject != EGL_NO_SYNC_KHR) { @@ -107,33 +133,35 @@ TextureInfo* SharedTexture::lockSource() EGLint status = eglClientWaitSyncKHR(m_display, m_syncObject, 0, 1000000); if (status == EGL_TIMEOUT_EXPIRED_KHR) - LOGE("Sync timeout for shared texture (%d)", m_sourceTexture.m_textureId); + LOGE("Sync timeout for shared texture (%d)", m_sourceTexture->m_textureId); eglDestroySyncKHR(m_display, m_syncObject); m_syncObject = EGL_NO_SYNC_KHR; } - - return &m_sourceTexture; + return m_sourceTexture; } void SharedTexture::releaseSource() { + if (m_sharedTextureMode == SurfaceTextureMode) + return; + if (m_supportsEGLImage) { // delete the existing image if needed - if (!m_sourceTexture.equalsAttributes(&m_targetTexture)) { + if (!m_sourceTexture->equalsAttributes(m_targetTexture)) { if (m_eglImage != EGL_NO_IMAGE_KHR) { eglDestroyImageKHR(m_display, m_eglImage); m_eglImage = EGL_NO_IMAGE_KHR; m_isNewImage = true; } - m_targetTexture.copyAttributes(&m_sourceTexture); + m_targetTexture->copyAttributes(m_sourceTexture); } // create an image from the texture, only when the texture is valid - if (m_eglImage == EGL_NO_IMAGE_KHR && m_sourceTexture.m_width - && m_sourceTexture.m_height) { - GLUtils::createEGLImageFromTexture(m_sourceTexture.m_textureId, &m_eglImage); - LOGV("Generating Image (%d) 0x%x", m_sourceTexture.m_textureId, m_eglImage); + if (m_eglImage == EGL_NO_IMAGE_KHR && m_sourceTexture->m_width + && m_sourceTexture->m_height) { + GLUtils::createEGLImageFromTexture(m_sourceTexture->m_textureId, &m_eglImage); + LOGV("Generating Image (%d) 0x%x", m_sourceTexture->m_textureId, m_eglImage); glFinish(); // ensures the texture is ready to be used by the consumer } @@ -153,28 +181,33 @@ void SharedTexture::releaseSource() TextureInfo* SharedTexture::lockTarget() { + // Note that the source and targe are the same when using Surface Texture. + if (m_sharedTextureMode == SurfaceTextureMode) + return m_sourceTexture; + m_lock.lock(); - if ((!m_supportsEGLImage && m_targetTexture.m_textureId == GL_NO_TEXTURE) + if ((!m_supportsEGLImage && m_targetTexture->m_textureId == GL_NO_TEXTURE) || (m_supportsEGLImage && m_eglImage == EGL_NO_IMAGE_KHR)) { m_lock.unlock(); return 0; } - if (m_supportsEGLImage && (m_isNewImage || m_targetTexture.m_textureId == GL_NO_TEXTURE)) { - if (m_targetTexture.m_textureId == GL_NO_TEXTURE) - glGenTextures(1, &m_targetTexture.m_textureId); + if (m_supportsEGLImage && (m_isNewImage || m_targetTexture->m_textureId == GL_NO_TEXTURE)) { + if (m_targetTexture->m_textureId == GL_NO_TEXTURE) + glGenTextures(1, &m_targetTexture->m_textureId); - GLUtils::createTextureFromEGLImage(m_targetTexture.m_textureId, m_eglImage); + GLUtils::createTextureFromEGLImage(m_targetTexture->m_textureId, m_eglImage); LOGV("Generating Consumer Texture from 0x%x", m_eglImage); m_isNewImage = false; } - - return &m_targetTexture; + return m_targetTexture; } void SharedTexture::releaseTarget() { + if (m_sharedTextureMode == SurfaceTextureMode) + return; if (m_supportsEGLFenceSyncKHR) { if (m_syncObject != EGL_NO_SYNC_KHR) diff --git a/Source/WebCore/platform/graphics/android/SharedTexture.h b/Source/WebCore/platform/graphics/android/SharedTexture.h index 376eeb3..305a442 100644 --- a/Source/WebCore/platform/graphics/android/SharedTexture.h +++ b/Source/WebCore/platform/graphics/android/SharedTexture.h @@ -45,7 +45,7 @@ namespace WebCore { class SharedTexture { public: // consumer thread functions - SharedTexture(); + SharedTexture(SharedTextureMode mode); ~SharedTexture(); TextureInfo* lockSource(); @@ -61,8 +61,8 @@ public: void initSourceTexture(); // producer thread only void deleteSourceTexture(); // producer thread only void deleteTargetTexture(); // consumer thread only - GLuint getSourceTextureId() { return m_sourceTexture.m_textureId; } - GLuint getTargetTextureId() { return m_targetTexture.m_textureId; } + GLuint getSourceTextureId() { return m_sourceTexture->m_textureId; } + GLuint getTargetTextureId() { return m_targetTexture->m_textureId; } EGLImageKHR getEGLImage() { return m_eglImage; } private: @@ -78,13 +78,13 @@ private: * metadata is used to track changes to the texture that would orphan the * target texture and require a new EGLImage to be constructed. */ - TextureInfo m_sourceTexture; + TextureInfo* m_sourceTexture; /** * The target texture stores the id and metadata of the texture that is to be * used by the consumer. In the case where EGLImages are supported this hold * the current eglImage target. */ - TextureInfo m_targetTexture; + TextureInfo* m_targetTexture; /** * The EGLImage is used to share the texture between EGLContexts on two * different threads. This serves as an alternative to sharing the contexts @@ -109,6 +109,8 @@ private: bool m_supportsEGLImage; bool m_supportsEGLFenceSyncKHR; + + SharedTextureMode m_sharedTextureMode; }; } // namespace WebCore diff --git a/Source/WebCore/platform/graphics/android/TextureInfo.cpp b/Source/WebCore/platform/graphics/android/TextureInfo.cpp index 2db1667..ce132c8 100644 --- a/Source/WebCore/platform/graphics/android/TextureInfo.cpp +++ b/Source/WebCore/platform/graphics/android/TextureInfo.cpp @@ -23,16 +23,24 @@ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ +#include "config.h" #include "TextureInfo.h" +#include "WebCoreJni.h" + +#include <JNIUtility.h> +#include <android/native_window.h> +#include <gui/SurfaceTexture.h> +#include <gui/SurfaceTextureClient.h> namespace WebCore { -TextureInfo::TextureInfo() +TextureInfo::TextureInfo(SharedTextureMode mode) { m_textureId = GL_NO_TEXTURE; m_width = 0; m_height = 0; m_internalFormat = 0; + m_sharedTextureMode = mode; } bool TextureInfo::equalsAttributes(const TextureInfo* otherTexture) diff --git a/Source/WebCore/platform/graphics/android/TextureInfo.h b/Source/WebCore/platform/graphics/android/TextureInfo.h index 9ed6719..4a9ce30 100644 --- a/Source/WebCore/platform/graphics/android/TextureInfo.h +++ b/Source/WebCore/platform/graphics/android/TextureInfo.h @@ -27,6 +27,15 @@ #define TextureInfo_h #include <GLES2/gl2.h> +#include <jni.h> +#include <ui/GraphicBuffer.h> +#include <utils/RefBase.h> + +using android::sp; + +namespace android { + class SurfaceTexture; +} namespace WebCore { @@ -35,10 +44,15 @@ static const GLuint GL_NO_TEXTURE = 0; * TextureInfo is a class that stores both the texture and metadata about the * texture. */ +enum SharedTextureMode { + EglImageMode, + SurfaceTextureMode +}; + class TextureInfo { public: - TextureInfo(); + TextureInfo(SharedTextureMode mode); bool equalsAttributes(const TextureInfo* otherTexture); void copyAttributes(const TextureInfo* sourceTexture); @@ -50,6 +64,12 @@ public: int32_t m_height; GLenum m_internalFormat; + // Surface Texture specific data + sp<android::SurfaceTexture> m_surfaceTexture; + sp<ANativeWindow> m_ANW; + +private: + SharedTextureMode m_sharedTextureMode; }; } // namespace WebCore |