gfx/layers/opengl/TextureHostOGL.cpp

changeset 0
6474c204b198
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/gfx/layers/opengl/TextureHostOGL.cpp	Wed Dec 31 06:09:35 2014 +0100
     1.3 @@ -0,0 +1,668 @@
     1.4 +/* -*- Mode: C++; tab-width: 20; indent-tabs-mode: nil; c-basic-offset: 2 -*-
     1.5 +* This Source Code Form is subject to the terms of the Mozilla Public
     1.6 +* License, v. 2.0. If a copy of the MPL was not distributed with this
     1.7 +* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
     1.8 +
     1.9 +#include "TextureHostOGL.h"
    1.10 +#include "GLContext.h"                  // for GLContext, etc
    1.11 +#include "GLSharedHandleHelpers.h"
    1.12 +#include "GLUploadHelpers.h"
    1.13 +#include "GLReadTexImageHelper.h"
    1.14 +#include "SharedSurface.h"              // for SharedSurface
    1.15 +#include "SharedSurfaceEGL.h"           // for SharedSurface_EGLImage
    1.16 +#include "SharedSurfaceGL.h"            // for SharedSurface_GLTexture, etc
    1.17 +#include "SurfaceStream.h"              // for SurfaceStream
    1.18 +#include "SurfaceTypes.h"               // for SharedSurfaceType, etc
    1.19 +#include "gfx2DGlue.h"                  // for ContentForFormat, etc
    1.20 +#include "gfxReusableSurfaceWrapper.h"  // for gfxReusableSurfaceWrapper
    1.21 +#include "mozilla/gfx/2D.h"             // for DataSourceSurface
    1.22 +#include "mozilla/gfx/BaseSize.h"       // for BaseSize
    1.23 +#include "mozilla/layers/CompositorOGL.h"  // for CompositorOGL
    1.24 +#ifdef MOZ_WIDGET_GONK
    1.25 +# include "GrallocImages.h"  // for GrallocImage
    1.26 +# include "EGLImageHelpers.h"
    1.27 +#endif
    1.28 +#include "mozilla/layers/ISurfaceAllocator.h"
    1.29 +#include "mozilla/layers/YCbCrImageDataSerializer.h"
    1.30 +#include "mozilla/layers/GrallocTextureHost.h"
    1.31 +#include "nsPoint.h"                    // for nsIntPoint
    1.32 +#include "nsRegion.h"                   // for nsIntRegion
    1.33 +#include "GfxTexturesReporter.h"        // for GfxTexturesReporter
    1.34 +#include "GLBlitTextureImageHelper.h"
    1.35 +#ifdef XP_MACOSX
    1.36 +#include "SharedSurfaceIO.h"
    1.37 +#include "mozilla/layers/MacIOSurfaceTextureHostOGL.h"
    1.38 +#endif
    1.39 +#include "GeckoProfiler.h"
    1.40 +
    1.41 +using namespace mozilla::gl;
    1.42 +using namespace mozilla::gfx;
    1.43 +
    1.44 +namespace mozilla {
    1.45 +namespace layers {
    1.46 +
    1.47 +class Compositor;
    1.48 +
    1.49 +TemporaryRef<CompositableBackendSpecificData>
    1.50 +CreateCompositableBackendSpecificDataOGL()
    1.51 +{
    1.52 +#ifdef MOZ_WIDGET_GONK
    1.53 +  return new CompositableDataGonkOGL();
    1.54 +#else
    1.55 +  return nullptr;
    1.56 +#endif
    1.57 +}
    1.58 +
    1.59 +TemporaryRef<TextureHost>
    1.60 +CreateTextureHostOGL(const SurfaceDescriptor& aDesc,
    1.61 +                     ISurfaceAllocator* aDeallocator,
    1.62 +                     TextureFlags aFlags)
    1.63 +{
    1.64 +  RefPtr<TextureHost> result;
    1.65 +  switch (aDesc.type()) {
    1.66 +    case SurfaceDescriptor::TSurfaceDescriptorShmem:
    1.67 +    case SurfaceDescriptor::TSurfaceDescriptorMemory: {
    1.68 +      result = CreateBackendIndependentTextureHost(aDesc,
    1.69 +                                                   aDeallocator, aFlags);
    1.70 +      break;
    1.71 +    }
    1.72 +    case SurfaceDescriptor::TSharedTextureDescriptor: {
    1.73 +      const SharedTextureDescriptor& desc = aDesc.get_SharedTextureDescriptor();
    1.74 +      result = new SharedTextureHostOGL(aFlags,
    1.75 +                                        desc.shareType(),
    1.76 +                                        desc.handle(),
    1.77 +                                        desc.size(),
    1.78 +                                        desc.inverted());
    1.79 +      break;
    1.80 +    }
    1.81 +    case SurfaceDescriptor::TSurfaceStreamDescriptor: {
    1.82 +      const SurfaceStreamDescriptor& desc = aDesc.get_SurfaceStreamDescriptor();
    1.83 +      result = new StreamTextureHostOGL(aFlags, desc);
    1.84 +      break;
    1.85 +    }
    1.86 +#ifdef XP_MACOSX
    1.87 +    case SurfaceDescriptor::TSurfaceDescriptorMacIOSurface: {
    1.88 +      const SurfaceDescriptorMacIOSurface& desc =
    1.89 +        aDesc.get_SurfaceDescriptorMacIOSurface();
    1.90 +      result = new MacIOSurfaceTextureHostOGL(aFlags, desc);
    1.91 +      break;
    1.92 +    }
    1.93 +#endif
    1.94 +#ifdef MOZ_WIDGET_GONK
    1.95 +    case SurfaceDescriptor::TNewSurfaceDescriptorGralloc: {
    1.96 +      const NewSurfaceDescriptorGralloc& desc =
    1.97 +        aDesc.get_NewSurfaceDescriptorGralloc();
    1.98 +      result = new GrallocTextureHostOGL(aFlags, desc);
    1.99 +      break;
   1.100 +    }
   1.101 +#endif
   1.102 +    default: return nullptr;
   1.103 +  }
   1.104 +  return result.forget();
   1.105 +}
   1.106 +
   1.107 +static gl::TextureImage::Flags
   1.108 +FlagsToGLFlags(TextureFlags aFlags)
   1.109 +{
   1.110 +  uint32_t result = TextureImage::NoFlags;
   1.111 +
   1.112 +  if (aFlags & TEXTURE_USE_NEAREST_FILTER)
   1.113 +    result |= TextureImage::UseNearestFilter;
   1.114 +  if (aFlags & TEXTURE_NEEDS_Y_FLIP)
   1.115 +    result |= TextureImage::NeedsYFlip;
   1.116 +  if (aFlags & TEXTURE_DISALLOW_BIGIMAGE)
   1.117 +    result |= TextureImage::DisallowBigImage;
   1.118 +
   1.119 +  return static_cast<gl::TextureImage::Flags>(result);
   1.120 +}
   1.121 +
   1.122 +GLenum
   1.123 +WrapMode(gl::GLContext *aGl, bool aAllowRepeat)
   1.124 +{
   1.125 +  if (aAllowRepeat &&
   1.126 +      (aGl->IsExtensionSupported(GLContext::ARB_texture_non_power_of_two) ||
   1.127 +       aGl->IsExtensionSupported(GLContext::OES_texture_npot))) {
   1.128 +    return LOCAL_GL_REPEAT;
   1.129 +  }
   1.130 +  return LOCAL_GL_CLAMP_TO_EDGE;
   1.131 +}
   1.132 +
   1.133 +CompositableDataGonkOGL::CompositableDataGonkOGL()
   1.134 + : mTexture(0)
   1.135 +{
   1.136 +}
   1.137 +CompositableDataGonkOGL::~CompositableDataGonkOGL()
   1.138 +{
   1.139 +  DeleteTextureIfPresent();
   1.140 +}
   1.141 +
   1.142 +gl::GLContext*
   1.143 +CompositableDataGonkOGL::gl() const
   1.144 +{
   1.145 +  return mCompositor ? mCompositor->gl() : nullptr;
   1.146 +}
   1.147 +
   1.148 +void CompositableDataGonkOGL::SetCompositor(Compositor* aCompositor)
   1.149 +{
   1.150 +  mCompositor = static_cast<CompositorOGL*>(aCompositor);
   1.151 +}
   1.152 +
   1.153 +void CompositableDataGonkOGL::ClearData()
   1.154 +{
   1.155 +  CompositableBackendSpecificData::ClearData();
   1.156 +  DeleteTextureIfPresent();
   1.157 +}
   1.158 +
   1.159 +GLuint CompositableDataGonkOGL::GetTexture()
   1.160 +{
   1.161 +  if (!mTexture) {
   1.162 +    if (gl()->MakeCurrent()) {
   1.163 +      gl()->fGenTextures(1, &mTexture);
   1.164 +    }
   1.165 +  }
   1.166 +  return mTexture;
   1.167 +}
   1.168 +
   1.169 +void
   1.170 +CompositableDataGonkOGL::DeleteTextureIfPresent()
   1.171 +{
   1.172 +  if (mTexture) {
   1.173 +    if (gl()->MakeCurrent()) {
   1.174 +      gl()->fDeleteTextures(1, &mTexture);
   1.175 +    }
   1.176 +    mTexture = 0;
   1.177 +  }
   1.178 +}
   1.179 +
   1.180 +#if defined(MOZ_WIDGET_GONK) && ANDROID_VERSION >= 17
   1.181 +bool
   1.182 +TextureHostOGL::SetReleaseFence(const android::sp<android::Fence>& aReleaseFence)
   1.183 +{
   1.184 +  if (!aReleaseFence.get() || !aReleaseFence->isValid()) {
   1.185 +    // HWC might not provide Fence.
   1.186 +    // In this case, HWC implicitly handles buffer's fence.
   1.187 +    return false;
   1.188 +  }
   1.189 +
   1.190 +  if (!mReleaseFence.get()) {
   1.191 +    mReleaseFence = aReleaseFence;
   1.192 +  } else {
   1.193 +    android::sp<android::Fence> mergedFence = android::Fence::merge(
   1.194 +                  android::String8::format("TextureHostOGL"),
   1.195 +                  mReleaseFence, aReleaseFence);
   1.196 +    if (!mergedFence.get()) {
   1.197 +      // synchronization is broken, the best we can do is hope fences
   1.198 +      // signal in order so the new fence will act like a union.
   1.199 +      // This error handling is same as android::ConsumerBase does.
   1.200 +      mReleaseFence = aReleaseFence;
   1.201 +      return false;
   1.202 +    }
   1.203 +    mReleaseFence = mergedFence;
   1.204 +  }
   1.205 +  return true;
   1.206 +}
   1.207 +
   1.208 +android::sp<android::Fence>
   1.209 +TextureHostOGL::GetAndResetReleaseFence()
   1.210 +{
   1.211 +  // Hold previous ReleaseFence to prevent Fence delivery failure via gecko IPC.
   1.212 +  mPrevReleaseFence = mReleaseFence;
   1.213 +  // Reset current ReleaseFence.
   1.214 +  mReleaseFence = android::Fence::NO_FENCE;
   1.215 +  return mPrevReleaseFence;
   1.216 +}
   1.217 +#endif
   1.218 +
   1.219 +bool
   1.220 +TextureImageTextureSourceOGL::Update(gfx::DataSourceSurface* aSurface,
   1.221 +                                     nsIntRegion* aDestRegion,
   1.222 +                                     gfx::IntPoint* aSrcOffset)
   1.223 +{
   1.224 +  MOZ_ASSERT(mGL);
   1.225 +  if (!mGL) {
   1.226 +    NS_WARNING("trying to update TextureImageTextureSourceOGL without a GLContext");
   1.227 +    return false;
   1.228 +  }
   1.229 +  MOZ_ASSERT(aSurface);
   1.230 +
   1.231 +  IntSize size = aSurface->GetSize();
   1.232 +  if (!mTexImage ||
   1.233 +      (mTexImage->GetSize() != size && !aSrcOffset) ||
   1.234 +      mTexImage->GetContentType() != gfx::ContentForFormat(aSurface->GetFormat())) {
   1.235 +    if (mFlags & TEXTURE_DISALLOW_BIGIMAGE) {
   1.236 +      mTexImage = CreateBasicTextureImage(mGL, size,
   1.237 +                                          gfx::ContentForFormat(aSurface->GetFormat()),
   1.238 +                                          WrapMode(mGL, mFlags & TEXTURE_ALLOW_REPEAT),
   1.239 +                                          FlagsToGLFlags(mFlags),
   1.240 +                                          SurfaceFormatToImageFormat(aSurface->GetFormat()));
   1.241 +    } else {
   1.242 +      // XXX - clarify which size we want to use. IncrementalContentHost will
   1.243 +      // require the size of the destination surface to be different from
   1.244 +      // the size of aSurface.
   1.245 +      // See bug 893300 (tracks the implementation of ContentHost for new textures).
   1.246 +      mTexImage = CreateTextureImage(mGL,
   1.247 +                                     size,
   1.248 +                                     gfx::ContentForFormat(aSurface->GetFormat()),
   1.249 +                                     WrapMode(mGL, mFlags & TEXTURE_ALLOW_REPEAT),
   1.250 +                                     FlagsToGLFlags(mFlags),
   1.251 +                                     SurfaceFormatToImageFormat(aSurface->GetFormat()));
   1.252 +    }
   1.253 +    ClearCachedFilter();
   1.254 +  }
   1.255 +
   1.256 +  mTexImage->UpdateFromDataSource(aSurface, aDestRegion, aSrcOffset);
   1.257 +
   1.258 +  if (mTexImage->InUpdate()) {
   1.259 +    mTexImage->EndUpdate();
   1.260 +  }
   1.261 +  return true;
   1.262 +}
   1.263 +
   1.264 +void
   1.265 +TextureImageTextureSourceOGL::EnsureBuffer(const nsIntSize& aSize,
   1.266 +                                           gfxContentType aContentType)
   1.267 +{
   1.268 +  if (!mTexImage ||
   1.269 +      mTexImage->GetSize() != aSize.ToIntSize() ||
   1.270 +      mTexImage->GetContentType() != aContentType) {
   1.271 +    mTexImage = CreateTextureImage(mGL,
   1.272 +                                   aSize.ToIntSize(),
   1.273 +                                   aContentType,
   1.274 +                                   WrapMode(mGL, mFlags & TEXTURE_ALLOW_REPEAT),
   1.275 +                                   FlagsToGLFlags(mFlags));
   1.276 +  }
   1.277 +  mTexImage->Resize(aSize.ToIntSize());
   1.278 +}
   1.279 +
   1.280 +void
   1.281 +TextureImageTextureSourceOGL::CopyTo(const nsIntRect& aSourceRect,
   1.282 +                                     DataTextureSource *aDest,
   1.283 +                                     const nsIntRect& aDestRect)
   1.284 +{
   1.285 +  MOZ_ASSERT(aDest->AsSourceOGL(), "Incompatible destination type!");
   1.286 +  TextureImageTextureSourceOGL *dest =
   1.287 +    aDest->AsSourceOGL()->AsTextureImageTextureSource();
   1.288 +  MOZ_ASSERT(dest, "Incompatible destination type!");
   1.289 +
   1.290 +  mGL->BlitTextureImageHelper()->BlitTextureImage(mTexImage, aSourceRect,
   1.291 +                                                  dest->mTexImage, aDestRect);
   1.292 +  dest->mTexImage->MarkValid();
   1.293 +}
   1.294 +
   1.295 +void
   1.296 +TextureImageTextureSourceOGL::SetCompositor(Compositor* aCompositor)
   1.297 +{
   1.298 +  CompositorOGL* glCompositor = static_cast<CompositorOGL*>(aCompositor);
   1.299 +
   1.300 +  if (!glCompositor || (mGL != glCompositor->gl())) {
   1.301 +    DeallocateDeviceData();
   1.302 +    mGL = glCompositor ? glCompositor->gl() : nullptr;
   1.303 +  }
   1.304 +}
   1.305 +
   1.306 +gfx::IntSize
   1.307 +TextureImageTextureSourceOGL::GetSize() const
   1.308 +{
   1.309 +  if (mTexImage) {
   1.310 +    if (mIterating) {
   1.311 +      return mTexImage->GetTileRect().Size();
   1.312 +    }
   1.313 +    return mTexImage->GetSize();
   1.314 +  }
   1.315 +  NS_WARNING("Trying to query the size of an empty TextureSource.");
   1.316 +  return gfx::IntSize(0, 0);
   1.317 +}
   1.318 +
   1.319 +gfx::SurfaceFormat
   1.320 +TextureImageTextureSourceOGL::GetFormat() const
   1.321 +{
   1.322 +  if (mTexImage) {
   1.323 +    return mTexImage->GetTextureFormat();
   1.324 +  }
   1.325 +  NS_WARNING("Trying to query the format of an empty TextureSource.");
   1.326 +  return gfx::SurfaceFormat::UNKNOWN;
   1.327 +}
   1.328 +
   1.329 +nsIntRect TextureImageTextureSourceOGL::GetTileRect()
   1.330 +{
   1.331 +  return ThebesIntRect(mTexImage->GetTileRect());
   1.332 +}
   1.333 +
   1.334 +void
   1.335 +TextureImageTextureSourceOGL::BindTexture(GLenum aTextureUnit, gfx::Filter aFilter)
   1.336 +{
   1.337 +  MOZ_ASSERT(mTexImage,
   1.338 +    "Trying to bind a TextureSource that does not have an underlying GL texture.");
   1.339 +  mTexImage->BindTexture(aTextureUnit);
   1.340 +  SetFilter(mGL, aFilter);
   1.341 +}
   1.342 +
   1.343 +SharedTextureSourceOGL::SharedTextureSourceOGL(CompositorOGL* aCompositor,
   1.344 +                                               gl::SharedTextureHandle aHandle,
   1.345 +                                               gfx::SurfaceFormat aFormat,
   1.346 +                                               GLenum aTarget,
   1.347 +                                               GLenum aWrapMode,
   1.348 +                                               SharedTextureShareType aShareType,
   1.349 +                                               gfx::IntSize aSize)
   1.350 +  : mSize(aSize)
   1.351 +  , mCompositor(aCompositor)
   1.352 +  , mSharedHandle(aHandle)
   1.353 +  , mFormat(aFormat)
   1.354 +  , mShareType(aShareType)
   1.355 +  , mTextureTarget(aTarget)
   1.356 +  , mWrapMode(aWrapMode)
   1.357 +{}
   1.358 +
   1.359 +void
   1.360 +SharedTextureSourceOGL::BindTexture(GLenum aTextureUnit, gfx::Filter aFilter)
   1.361 +{
   1.362 +  if (!gl()) {
   1.363 +    NS_WARNING("Trying to bind a texture without a GLContext");
   1.364 +    return;
   1.365 +  }
   1.366 +  GLuint tex = mCompositor->GetTemporaryTexture(GetTextureTarget(), aTextureUnit);
   1.367 +
   1.368 +  gl()->fActiveTexture(aTextureUnit);
   1.369 +  gl()->fBindTexture(mTextureTarget, tex);
   1.370 +  if (!AttachSharedHandle(gl(), mShareType, mSharedHandle)) {
   1.371 +    NS_ERROR("Failed to bind shared texture handle");
   1.372 +    return;
   1.373 +  }
   1.374 +  ApplyFilterToBoundTexture(gl(), aFilter, mTextureTarget);
   1.375 +}
   1.376 +
   1.377 +void
   1.378 +SharedTextureSourceOGL::DetachSharedHandle()
   1.379 +{
   1.380 +  if (!gl()) {
   1.381 +    return;
   1.382 +  }
   1.383 +  gl::DetachSharedHandle(gl(), mShareType, mSharedHandle);
   1.384 +}
   1.385 +
   1.386 +void
   1.387 +SharedTextureSourceOGL::SetCompositor(Compositor* aCompositor)
   1.388 +{
   1.389 +  mCompositor = static_cast<CompositorOGL*>(aCompositor);
   1.390 +}
   1.391 +
   1.392 +bool
   1.393 +SharedTextureSourceOGL::IsValid() const
   1.394 +{
   1.395 +  return !!gl();
   1.396 +}
   1.397 +
   1.398 +gl::GLContext*
   1.399 +SharedTextureSourceOGL::gl() const
   1.400 +{
   1.401 +  return mCompositor ? mCompositor->gl() : nullptr;
   1.402 +}
   1.403 +
   1.404 +gfx::Matrix4x4
   1.405 +SharedTextureSourceOGL::GetTextureTransform()
   1.406 +{
   1.407 +  SharedHandleDetails handleDetails;
   1.408 +  if (!GetSharedHandleDetails(gl(), mShareType, mSharedHandle, handleDetails)) {
   1.409 +    NS_WARNING("Could not get shared handle details");
   1.410 +    return gfx::Matrix4x4();
   1.411 +  }
   1.412 +
   1.413 +  return handleDetails.mTextureTransform;
   1.414 +}
   1.415 +
   1.416 +SharedTextureHostOGL::SharedTextureHostOGL(TextureFlags aFlags,
   1.417 +                                           gl::SharedTextureShareType aShareType,
   1.418 +                                           gl::SharedTextureHandle aSharedHandle,
   1.419 +                                           gfx::IntSize aSize,
   1.420 +                                           bool inverted)
   1.421 +  : TextureHost(aFlags)
   1.422 +  , mSize(aSize)
   1.423 +  , mCompositor(nullptr)
   1.424 +  , mSharedHandle(aSharedHandle)
   1.425 +  , mShareType(aShareType)
   1.426 +{
   1.427 +}
   1.428 +
   1.429 +SharedTextureHostOGL::~SharedTextureHostOGL()
   1.430 +{
   1.431 +  // If need to deallocate textures, call DeallocateSharedData() before
   1.432 +  // the destructor
   1.433 +}
   1.434 +
   1.435 +gl::GLContext*
   1.436 +SharedTextureHostOGL::gl() const
   1.437 +{
   1.438 +  return mCompositor ? mCompositor->gl() : nullptr;
   1.439 +}
   1.440 +
   1.441 +bool
   1.442 +SharedTextureHostOGL::Lock()
   1.443 +{
   1.444 +  if (!mCompositor) {
   1.445 +    return false;
   1.446 +  }
   1.447 +
   1.448 +  if (!mTextureSource) {
   1.449 +    // XXX on android GetSharedHandleDetails can call into Java which we'd
   1.450 +    // rather not do from the compositor
   1.451 +    SharedHandleDetails handleDetails;
   1.452 +    if (!GetSharedHandleDetails(gl(), mShareType, mSharedHandle, handleDetails)) {
   1.453 +      NS_WARNING("Could not get shared handle details");
   1.454 +      return false;
   1.455 +    }
   1.456 +
   1.457 +    GLenum wrapMode = LOCAL_GL_CLAMP_TO_EDGE;
   1.458 +    mTextureSource = new SharedTextureSourceOGL(mCompositor,
   1.459 +                                                mSharedHandle,
   1.460 +                                                handleDetails.mTextureFormat,
   1.461 +                                                handleDetails.mTarget,
   1.462 +                                                wrapMode,
   1.463 +                                                mShareType,
   1.464 +                                                mSize);
   1.465 +  }
   1.466 +  return true;
   1.467 +}
   1.468 +
   1.469 +void
   1.470 +SharedTextureHostOGL::Unlock()
   1.471 +{
   1.472 +  if (!mTextureSource) {
   1.473 +    return;
   1.474 +  }
   1.475 +  mTextureSource->DetachSharedHandle();
   1.476 +}
   1.477 +
   1.478 +void
   1.479 +SharedTextureHostOGL::SetCompositor(Compositor* aCompositor)
   1.480 +{
   1.481 +  CompositorOGL* glCompositor = static_cast<CompositorOGL*>(aCompositor);
   1.482 +  mCompositor = glCompositor;
   1.483 +  if (mTextureSource) {
   1.484 +    mTextureSource->SetCompositor(glCompositor);
   1.485 +  }
   1.486 +}
   1.487 +
   1.488 +gfx::SurfaceFormat
   1.489 +SharedTextureHostOGL::GetFormat() const
   1.490 +{
   1.491 +  MOZ_ASSERT(mTextureSource);
   1.492 +  return mTextureSource->GetFormat();
   1.493 +}
   1.494 +
   1.495 +void
   1.496 +StreamTextureSourceOGL::BindTexture(GLenum activetex, gfx::Filter aFilter)
   1.497 +{
   1.498 +  MOZ_ASSERT(gl());
   1.499 +  gl()->fActiveTexture(activetex);
   1.500 +  gl()->fBindTexture(mTextureTarget, mTextureHandle);
   1.501 +  SetFilter(gl(), aFilter);
   1.502 +}
   1.503 +
   1.504 +bool
   1.505 +StreamTextureSourceOGL::RetrieveTextureFromStream()
   1.506 +{
   1.507 +  gl()->MakeCurrent();
   1.508 +
   1.509 +  SharedSurface* sharedSurf = mStream->SwapConsumer();
   1.510 +  if (!sharedSurf) {
   1.511 +    // We don't have a valid surf to show yet.
   1.512 +    return false;
   1.513 +  }
   1.514 +
   1.515 +  gl()->MakeCurrent();
   1.516 +
   1.517 +  mSize = IntSize(sharedSurf->Size().width, sharedSurf->Size().height);
   1.518 +
   1.519 +  DataSourceSurface* toUpload = nullptr;
   1.520 +  switch (sharedSurf->Type()) {
   1.521 +    case SharedSurfaceType::GLTextureShare: {
   1.522 +      SharedSurface_GLTexture* glTexSurf = SharedSurface_GLTexture::Cast(sharedSurf);
   1.523 +      mTextureHandle = glTexSurf->ConsTexture(gl());
   1.524 +      mTextureTarget = glTexSurf->ConsTextureTarget();
   1.525 +      MOZ_ASSERT(mTextureHandle);
   1.526 +      mFormat = sharedSurf->HasAlpha() ? SurfaceFormat::R8G8B8A8
   1.527 +                                       : SurfaceFormat::R8G8B8X8;
   1.528 +      break;
   1.529 +    }
   1.530 +    case SharedSurfaceType::EGLImageShare: {
   1.531 +      SharedSurface_EGLImage* eglImageSurf =
   1.532 +          SharedSurface_EGLImage::Cast(sharedSurf);
   1.533 +
   1.534 +      eglImageSurf->AcquireConsumerTexture(gl(), &mTextureHandle, &mTextureTarget);
   1.535 +      MOZ_ASSERT(mTextureHandle);
   1.536 +      mFormat = sharedSurf->HasAlpha() ? SurfaceFormat::R8G8B8A8
   1.537 +                                       : SurfaceFormat::R8G8B8X8;
   1.538 +      break;
   1.539 +    }
   1.540 +#ifdef XP_MACOSX
   1.541 +    case SharedSurfaceType::IOSurface: {
   1.542 +      SharedSurface_IOSurface* glTexSurf = SharedSurface_IOSurface::Cast(sharedSurf);
   1.543 +      mTextureHandle = glTexSurf->ConsTexture(gl());
   1.544 +      mTextureTarget = glTexSurf->ConsTextureTarget();
   1.545 +      MOZ_ASSERT(mTextureHandle);
   1.546 +      mFormat = sharedSurf->HasAlpha() ? SurfaceFormat::R8G8B8A8
   1.547 +                                       : SurfaceFormat::R8G8B8X8;
   1.548 +      break;
   1.549 +    }
   1.550 +#endif
   1.551 +    case SharedSurfaceType::Basic: {
   1.552 +      toUpload = SharedSurface_Basic::Cast(sharedSurf)->GetData();
   1.553 +      MOZ_ASSERT(toUpload);
   1.554 +      break;
   1.555 +    }
   1.556 +    default:
   1.557 +      MOZ_CRASH("Invalid SharedSurface type.");
   1.558 +  }
   1.559 +
   1.560 +  if (toUpload) {
   1.561 +    // mBounds seems to end up as (0,0,0,0) a lot, so don't use it?
   1.562 +    nsIntSize size(ThebesIntSize(toUpload->GetSize()));
   1.563 +    nsIntRect rect(nsIntPoint(0,0), size);
   1.564 +    nsIntRegion bounds(rect);
   1.565 +    mFormat = UploadSurfaceToTexture(gl(),
   1.566 +                                     toUpload,
   1.567 +                                     bounds,
   1.568 +                                     mUploadTexture,
   1.569 +                                     true);
   1.570 +    mTextureHandle = mUploadTexture;
   1.571 +    mTextureTarget = LOCAL_GL_TEXTURE_2D;
   1.572 +  }
   1.573 +
   1.574 +  MOZ_ASSERT(mTextureHandle);
   1.575 +  gl()->fBindTexture(mTextureTarget, mTextureHandle);
   1.576 +  gl()->fTexParameteri(mTextureTarget,
   1.577 +                      LOCAL_GL_TEXTURE_WRAP_S,
   1.578 +                      LOCAL_GL_CLAMP_TO_EDGE);
   1.579 +  gl()->fTexParameteri(mTextureTarget,
   1.580 +                      LOCAL_GL_TEXTURE_WRAP_T,
   1.581 +                      LOCAL_GL_CLAMP_TO_EDGE);
   1.582 +
   1.583 +  ClearCachedFilter();
   1.584 +
   1.585 +  return true;
   1.586 +}
   1.587 +
   1.588 +void
   1.589 +StreamTextureSourceOGL::DeallocateDeviceData()
   1.590 +{
   1.591 +  if (mUploadTexture) {
   1.592 +    MOZ_ASSERT(gl());
   1.593 +    gl()->MakeCurrent();
   1.594 +    gl()->fDeleteTextures(1, &mUploadTexture);
   1.595 +    mUploadTexture = 0;
   1.596 +    mTextureHandle = 0;
   1.597 +  }
   1.598 +}
   1.599 +
   1.600 +gl::GLContext*
   1.601 +StreamTextureSourceOGL::gl() const
   1.602 +{
   1.603 +  return mCompositor ? mCompositor->gl() : nullptr;
   1.604 +}
   1.605 +
   1.606 +void
   1.607 +StreamTextureSourceOGL::SetCompositor(Compositor* aCompositor)
   1.608 +{
   1.609 +  mCompositor = static_cast<CompositorOGL*>(aCompositor);
   1.610 +}
   1.611 +
   1.612 +StreamTextureHostOGL::StreamTextureHostOGL(TextureFlags aFlags,
   1.613 +                                           const SurfaceStreamDescriptor& aDesc)
   1.614 +  : TextureHost(aFlags)
   1.615 +{
   1.616 +  mStream = SurfaceStream::FromHandle(aDesc.handle());
   1.617 +  MOZ_ASSERT(mStream);
   1.618 +}
   1.619 +
   1.620 +StreamTextureHostOGL::~StreamTextureHostOGL()
   1.621 +{
   1.622 +  // If need to deallocate textures, call DeallocateSharedData() before
   1.623 +  // the destructor
   1.624 +}
   1.625 +
   1.626 +bool
   1.627 +StreamTextureHostOGL::Lock()
   1.628 +{
   1.629 +  if (!mCompositor) {
   1.630 +    return false;
   1.631 +  }
   1.632 +
   1.633 +  if (!mTextureSource) {
   1.634 +    mTextureSource = new StreamTextureSourceOGL(mCompositor,
   1.635 +                                                mStream);
   1.636 +  }
   1.637 +
   1.638 +  return mTextureSource->RetrieveTextureFromStream();
   1.639 +}
   1.640 +
   1.641 +void
   1.642 +StreamTextureHostOGL::Unlock()
   1.643 +{
   1.644 +}
   1.645 +
   1.646 +void
   1.647 +StreamTextureHostOGL::SetCompositor(Compositor* aCompositor)
   1.648 +{
   1.649 +  CompositorOGL* glCompositor = static_cast<CompositorOGL*>(aCompositor);
   1.650 +  mCompositor = glCompositor;
   1.651 +  if (mTextureSource) {
   1.652 +    mTextureSource->SetCompositor(glCompositor);
   1.653 +  }
   1.654 +}
   1.655 +
   1.656 +gfx::SurfaceFormat
   1.657 +StreamTextureHostOGL::GetFormat() const
   1.658 +{
   1.659 +  MOZ_ASSERT(mTextureSource);
   1.660 +  return mTextureSource->GetFormat();
   1.661 +}
   1.662 +
   1.663 +gfx::IntSize
   1.664 +StreamTextureHostOGL::GetSize() const
   1.665 +{
   1.666 +  MOZ_ASSERT(mTextureSource);
   1.667 +  return mTextureSource->GetSize();
   1.668 +}
   1.669 +
   1.670 +} // namespace
   1.671 +} // namespace

mercurial