mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-11-23 21:01:08 +00:00
Bug 1742052 - Remove unused code around TextureHost r=gfx-reviewers,nical
Differential Revision: https://phabricator.services.mozilla.com/D131701
This commit is contained in:
parent
368a8a1650
commit
44ff20fb9f
@ -68,7 +68,7 @@ Compositor::Compositor(widget::CompositorWidget* aWidget)
|
||||
{
|
||||
}
|
||||
|
||||
Compositor::~Compositor() { ReadUnlockTextures(); }
|
||||
Compositor::~Compositor() {}
|
||||
|
||||
void Compositor::Destroy() {
|
||||
mWidget = nullptr;
|
||||
@ -77,10 +77,7 @@ void Compositor::Destroy() {
|
||||
mIsDestroyed = true;
|
||||
}
|
||||
|
||||
void Compositor::EndFrame() {
|
||||
ReadUnlockTextures();
|
||||
mLastCompositionEndTime = TimeStamp::Now();
|
||||
}
|
||||
void Compositor::EndFrame() { mLastCompositionEndTime = TimeStamp::Now(); }
|
||||
|
||||
nsTArray<TexturedVertex> TexturedTrianglesToVertexArray(
|
||||
const nsTArray<gfx::TexturedTriangle>& aTriangles) {
|
||||
@ -236,23 +233,6 @@ size_t DecomposeIntoNoRepeatRects(const gfx::Rect& aRect,
|
||||
return 4;
|
||||
}
|
||||
|
||||
void Compositor::UnlockAfterComposition(TextureHost* aTexture) {
|
||||
TextureSourceProvider::UnlockAfterComposition(aTexture);
|
||||
|
||||
// If this is being called after we shutdown the compositor, we must finish
|
||||
// read unlocking now to prevent a cycle.
|
||||
if (IsDestroyed()) {
|
||||
ReadUnlockTextures();
|
||||
}
|
||||
}
|
||||
|
||||
bool Compositor::NotifyNotUsedAfterComposition(TextureHost* aTextureHost) {
|
||||
if (IsDestroyed() || AsBasicCompositor()) {
|
||||
return false;
|
||||
}
|
||||
return TextureSourceProvider::NotifyNotUsedAfterComposition(aTextureHost);
|
||||
}
|
||||
|
||||
already_AddRefed<RecordedFrame> Compositor::RecordFrame(
|
||||
const TimeStamp& aTimeStamp) {
|
||||
RefPtr<CompositingRenderTarget> renderTarget = GetWindowRenderTarget();
|
||||
|
@ -130,7 +130,6 @@ class CompositorBridgeParent;
|
||||
class NativeLayer;
|
||||
class CompositorOGL;
|
||||
class CompositorD3D11;
|
||||
class BasicCompositor;
|
||||
class TextureReadLock;
|
||||
struct GPUStats;
|
||||
class AsyncReadbackBuffer;
|
||||
@ -290,7 +289,7 @@ class Compositor : public TextureSourceProvider {
|
||||
*/
|
||||
virtual void EndFrame();
|
||||
|
||||
virtual void CancelFrame(bool aNeedFlush = true) { ReadUnlockTextures(); }
|
||||
virtual void CancelFrame(bool aNeedFlush = true) {}
|
||||
|
||||
#ifdef MOZ_DUMP_PAINTING
|
||||
virtual const char* Name() const = 0;
|
||||
@ -304,9 +303,6 @@ class Compositor : public TextureSourceProvider {
|
||||
return mLastCompositionEndTime;
|
||||
}
|
||||
|
||||
void UnlockAfterComposition(TextureHost* aTexture) override;
|
||||
bool NotifyNotUsedAfterComposition(TextureHost* aTextureHost) override;
|
||||
|
||||
/**
|
||||
* Notify the compositor that composition is being paused. This allows the
|
||||
* compositor to temporarily release any resources.
|
||||
|
@ -15,74 +15,9 @@
|
||||
namespace mozilla {
|
||||
namespace layers {
|
||||
|
||||
TextureSourceProvider::~TextureSourceProvider() { ReadUnlockTextures(); }
|
||||
TextureSourceProvider::~TextureSourceProvider() {}
|
||||
|
||||
void TextureSourceProvider::ReadUnlockTextures() {
|
||||
#ifdef XP_DARWIN
|
||||
nsClassHashtable<nsUint32HashKey, nsTArray<uint64_t>>
|
||||
texturesIdsToUnlockByPid;
|
||||
for (auto& texture : mUnlockAfterComposition) {
|
||||
auto bufferTexture = texture->AsBufferTextureHost();
|
||||
if (bufferTexture && bufferTexture->IsDirectMap()) {
|
||||
texture->ReadUnlock();
|
||||
auto actor = texture->GetIPDLActor();
|
||||
if (actor) {
|
||||
base::ProcessId pid = actor->OtherPid();
|
||||
nsTArray<uint64_t>* textureIds =
|
||||
texturesIdsToUnlockByPid.GetOrInsertNew(pid);
|
||||
textureIds->AppendElement(TextureHost::GetTextureSerial(actor));
|
||||
}
|
||||
} else {
|
||||
texture->ReadUnlock();
|
||||
}
|
||||
}
|
||||
for (const auto& entry : texturesIdsToUnlockByPid) {
|
||||
TextureSync::SetTexturesUnlocked(entry.GetKey(), *entry.GetWeak());
|
||||
}
|
||||
#else
|
||||
for (auto& texture : mUnlockAfterComposition) {
|
||||
texture->ReadUnlock();
|
||||
}
|
||||
#endif
|
||||
mUnlockAfterComposition.Clear();
|
||||
}
|
||||
|
||||
void TextureSourceProvider::UnlockAfterComposition(TextureHost* aTexture) {
|
||||
mUnlockAfterComposition.AppendElement(aTexture);
|
||||
}
|
||||
|
||||
bool TextureSourceProvider::NotifyNotUsedAfterComposition(
|
||||
TextureHost* aTextureHost) {
|
||||
mNotifyNotUsedAfterComposition.AppendElement(aTextureHost);
|
||||
|
||||
// If Compositor holds many TextureHosts without compositing,
|
||||
// the TextureHosts should be flushed to reduce memory consumption.
|
||||
const int thresholdCount = 5;
|
||||
const double thresholdSec = 2.0f;
|
||||
if (mNotifyNotUsedAfterComposition.Length() > thresholdCount) {
|
||||
TimeStamp lastCompositionEndTime = GetLastCompositionEndTime();
|
||||
TimeDuration duration = lastCompositionEndTime
|
||||
? TimeStamp::Now() - lastCompositionEndTime
|
||||
: TimeDuration();
|
||||
// Check if we could flush
|
||||
if (duration.ToSeconds() > thresholdSec) {
|
||||
FlushPendingNotifyNotUsed();
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void TextureSourceProvider::FlushPendingNotifyNotUsed() {
|
||||
for (auto& textureHost : mNotifyNotUsedAfterComposition) {
|
||||
textureHost->CallNotifyNotUsed();
|
||||
}
|
||||
mNotifyNotUsedAfterComposition.Clear();
|
||||
}
|
||||
|
||||
void TextureSourceProvider::Destroy() {
|
||||
ReadUnlockTextures();
|
||||
FlushPendingNotifyNotUsed();
|
||||
}
|
||||
void TextureSourceProvider::Destroy() {}
|
||||
|
||||
} // namespace layers
|
||||
} // namespace mozilla
|
||||
|
@ -25,7 +25,6 @@ namespace layers {
|
||||
|
||||
class TextureHost;
|
||||
class DataTextureSource;
|
||||
class BasicCompositor;
|
||||
class Compositor;
|
||||
class CompositorOGL;
|
||||
|
||||
@ -38,59 +37,17 @@ class TextureSourceProvider {
|
||||
virtual already_AddRefed<DataTextureSource> CreateDataTextureSource(
|
||||
TextureFlags aFlags = TextureFlags::NO_FLAGS) = 0;
|
||||
|
||||
virtual already_AddRefed<DataTextureSource> CreateDataTextureSourceAround(
|
||||
gfx::DataSourceSurface* aSurface) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
virtual already_AddRefed<DataTextureSource>
|
||||
CreateDataTextureSourceAroundYCbCr(TextureHost* aTexture) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
virtual TimeStamp GetLastCompositionEndTime() const = 0;
|
||||
|
||||
// Return true if the effect type is supported.
|
||||
//
|
||||
// By default Compositor implementations should support all effects but in
|
||||
// some rare cases it is not possible to support an effect efficiently.
|
||||
// This is the case for BasicCompositor with EffectYCbCr.
|
||||
virtual bool SupportsEffect(EffectTypes aEffect) { return true; }
|
||||
|
||||
/// Most compositor backends operate asynchronously under the hood. This
|
||||
/// means that when a layer stops using a texture it is often desirable to
|
||||
/// wait for the end of the next composition before releasing the texture's
|
||||
/// ReadLock.
|
||||
/// This function provides a convenient way to do this delayed unlocking, if
|
||||
/// the texture itself requires it.
|
||||
virtual void UnlockAfterComposition(TextureHost* aTexture);
|
||||
|
||||
/// Most compositor backends operate asynchronously under the hood. This
|
||||
/// means that when a layer stops using a texture it is often desirable to
|
||||
/// wait for the end of the next composition before NotifyNotUsed() call.
|
||||
/// This function provides a convenient way to do this delayed NotifyNotUsed()
|
||||
/// call, if the texture itself requires it.
|
||||
/// See bug 1260611 and bug 1252835
|
||||
///
|
||||
/// Returns true if notified, false otherwise.
|
||||
virtual bool NotifyNotUsedAfterComposition(TextureHost* aTextureHost);
|
||||
|
||||
virtual void MaybeUnlockBeforeNextComposition(TextureHost* aTextureHost) {}
|
||||
virtual void TryUnlockTextures() {}
|
||||
|
||||
// If overridden, make sure to call the base function.
|
||||
virtual void Destroy();
|
||||
|
||||
void FlushPendingNotifyNotUsed();
|
||||
|
||||
// If this provider is also a Compositor, return the compositor. Otherwise
|
||||
// return null.
|
||||
virtual Compositor* AsCompositor() { return nullptr; }
|
||||
|
||||
// If this provider is also a BasicCompositor, return the compositor.
|
||||
// Otherwise return nullptr.
|
||||
virtual BasicCompositor* AsBasicCompositor() { return nullptr; }
|
||||
|
||||
// If this provider is also a CompositorOGL, return the compositor. Otherwise
|
||||
// return nullptr.
|
||||
virtual CompositorOGL* AsCompositorOGL() { return nullptr; }
|
||||
@ -109,30 +66,8 @@ class TextureSourceProvider {
|
||||
// used to composite).
|
||||
virtual bool IsValid() const = 0;
|
||||
|
||||
public:
|
||||
class MOZ_STACK_CLASS AutoReadUnlockTextures final {
|
||||
public:
|
||||
explicit AutoReadUnlockTextures(TextureSourceProvider* aProvider)
|
||||
: mProvider(aProvider) {}
|
||||
~AutoReadUnlockTextures() { mProvider->ReadUnlockTextures(); }
|
||||
|
||||
private:
|
||||
RefPtr<TextureSourceProvider> mProvider;
|
||||
};
|
||||
|
||||
protected:
|
||||
// Should be called at the end of each composition.
|
||||
void ReadUnlockTextures();
|
||||
|
||||
virtual ~TextureSourceProvider();
|
||||
|
||||
private:
|
||||
// An array of locks that will need to be unlocked after the next composition.
|
||||
nsTArray<RefPtr<TextureHost>> mUnlockAfterComposition;
|
||||
|
||||
// An array of TextureHosts that will need to call NotifyNotUsed() after the
|
||||
// next composition.
|
||||
nsTArray<RefPtr<TextureHost>> mNotifyNotUsedAfterComposition;
|
||||
};
|
||||
|
||||
} // namespace layers
|
||||
|
@ -75,75 +75,17 @@ TextureHost* GPUVideoTextureHost::EnsureWrappedTextureHost() {
|
||||
texture.forget());
|
||||
}
|
||||
|
||||
if (mPendingSourceProvider) {
|
||||
RefPtr<TextureSourceProvider> provider = mPendingSourceProvider.forget();
|
||||
mWrappedTextureHost->SetTextureSourceProvider(provider);
|
||||
}
|
||||
if (mPendingUpdatedInternal) {
|
||||
mWrappedTextureHost->UpdatedInternal(mPendingIntRegion.ptrOr(nullptr));
|
||||
mPendingIntRegion.reset();
|
||||
mPendingUpdatedInternal = false;
|
||||
}
|
||||
if (mPendingPrepareTextureSource) {
|
||||
mWrappedTextureHost->PrepareTextureSource(*mPendingPrepareTextureSource);
|
||||
mPendingPrepareTextureSource.reset();
|
||||
}
|
||||
|
||||
return mWrappedTextureHost;
|
||||
}
|
||||
|
||||
bool GPUVideoTextureHost::IsValid() { return !!EnsureWrappedTextureHost(); }
|
||||
|
||||
bool GPUVideoTextureHost::Lock() {
|
||||
if (!EnsureWrappedTextureHost()) {
|
||||
return false;
|
||||
}
|
||||
return EnsureWrappedTextureHost()->Lock();
|
||||
}
|
||||
|
||||
void GPUVideoTextureHost::Unlock() {
|
||||
if (!EnsureWrappedTextureHost()) {
|
||||
return;
|
||||
}
|
||||
EnsureWrappedTextureHost()->Unlock();
|
||||
}
|
||||
|
||||
void GPUVideoTextureHost::PrepareTextureSource(
|
||||
CompositableTextureSourceRef& aTexture) {
|
||||
if (!EnsureWrappedTextureHost()) {
|
||||
mPendingPrepareTextureSource = Some(aTexture);
|
||||
return;
|
||||
}
|
||||
EnsureWrappedTextureHost()->PrepareTextureSource(aTexture);
|
||||
}
|
||||
|
||||
bool GPUVideoTextureHost::BindTextureSource(
|
||||
CompositableTextureSourceRef& aTexture) {
|
||||
MOZ_ASSERT(EnsureWrappedTextureHost(), "Image isn't valid yet");
|
||||
if (!EnsureWrappedTextureHost()) {
|
||||
return false;
|
||||
}
|
||||
return EnsureWrappedTextureHost()->BindTextureSource(aTexture);
|
||||
}
|
||||
|
||||
bool GPUVideoTextureHost::AcquireTextureSource(
|
||||
CompositableTextureSourceRef& aTexture) {
|
||||
MOZ_ASSERT(EnsureWrappedTextureHost(), "Image isn't valid yet");
|
||||
if (!EnsureWrappedTextureHost()) {
|
||||
return false;
|
||||
}
|
||||
return EnsureWrappedTextureHost()->AcquireTextureSource(aTexture);
|
||||
}
|
||||
|
||||
void GPUVideoTextureHost::SetTextureSourceProvider(
|
||||
TextureSourceProvider* aProvider) {
|
||||
if (!EnsureWrappedTextureHost()) {
|
||||
mPendingSourceProvider = aProvider;
|
||||
return;
|
||||
}
|
||||
EnsureWrappedTextureHost()->SetTextureSourceProvider(aProvider);
|
||||
}
|
||||
|
||||
gfx::YUVColorSpace GPUVideoTextureHost::GetYUVColorSpace() const {
|
||||
MOZ_ASSERT(mWrappedTextureHost, "Image isn't valid yet");
|
||||
if (!mWrappedTextureHost) {
|
||||
@ -277,14 +219,6 @@ bool GPUVideoTextureHost::SupportsExternalCompositing(
|
||||
return EnsureWrappedTextureHost()->SupportsExternalCompositing(aBackend);
|
||||
}
|
||||
|
||||
void GPUVideoTextureHost::UnbindTextureSource() {
|
||||
if (EnsureWrappedTextureHost()) {
|
||||
EnsureWrappedTextureHost()->UnbindTextureSource();
|
||||
}
|
||||
// Handle read unlock
|
||||
TextureHost::UnbindTextureSource();
|
||||
}
|
||||
|
||||
void GPUVideoTextureHost::NotifyNotUsed() {
|
||||
if (EnsureWrappedTextureHost()) {
|
||||
EnsureWrappedTextureHost()->NotifyNotUsed();
|
||||
|
@ -21,20 +21,8 @@ class GPUVideoTextureHost : public TextureHost {
|
||||
|
||||
void DeallocateDeviceData() override {}
|
||||
|
||||
virtual void SetTextureSourceProvider(
|
||||
TextureSourceProvider* aProvider) override;
|
||||
|
||||
bool Lock() override;
|
||||
|
||||
void Unlock() override;
|
||||
|
||||
gfx::SurfaceFormat GetFormat() const override;
|
||||
|
||||
void PrepareTextureSource(CompositableTextureSourceRef& aTexture) override;
|
||||
|
||||
bool BindTextureSource(CompositableTextureSourceRef& aTexture) override;
|
||||
bool AcquireTextureSource(CompositableTextureSourceRef& aTexture) override;
|
||||
|
||||
already_AddRefed<gfx::DataSourceSurface> GetAsSurface() override {
|
||||
return nullptr; // XXX - implement this (for MOZ_DUMP_PAINTING)
|
||||
}
|
||||
@ -73,7 +61,6 @@ class GPUVideoTextureHost : public TextureHost {
|
||||
|
||||
bool SupportsExternalCompositing(WebRenderBackend aBackend) override;
|
||||
|
||||
void UnbindTextureSource() override;
|
||||
void NotifyNotUsed() override;
|
||||
|
||||
protected:
|
||||
@ -85,10 +72,8 @@ class GPUVideoTextureHost : public TextureHost {
|
||||
void UpdatedInternal(const nsIntRegion* Region) override;
|
||||
|
||||
RefPtr<TextureHost> mWrappedTextureHost;
|
||||
RefPtr<TextureSourceProvider> mPendingSourceProvider;
|
||||
bool mPendingUpdatedInternal = false;
|
||||
Maybe<nsIntRegion> mPendingIntRegion;
|
||||
Maybe<CompositableTextureSourceRef> mPendingPrepareTextureSource;
|
||||
SurfaceDescriptorGPUVideo mDescriptor;
|
||||
};
|
||||
|
||||
|
@ -166,7 +166,6 @@ const ImageComposite::TimedImage* ImageComposite::ChooseImage() {
|
||||
void ImageComposite::RemoveImagesWithTextureHost(TextureHost* aTexture) {
|
||||
for (int32_t i = mImages.Length() - 1; i >= 0; --i) {
|
||||
if (mImages[i].mTextureHost == aTexture) {
|
||||
aTexture->UnbindTextureSource();
|
||||
mImages.RemoveElementAt(i);
|
||||
}
|
||||
}
|
||||
|
@ -367,24 +367,6 @@ void TextureHost::Finalize() {
|
||||
}
|
||||
}
|
||||
|
||||
void TextureHost::UnbindTextureSource() {
|
||||
if (mReadLocked) {
|
||||
// This TextureHost is not used anymore. Since most compositor backends are
|
||||
// working asynchronously under the hood a compositor could still be using
|
||||
// this texture, so it is generally best to wait until the end of the next
|
||||
// composition before calling ReadUnlock. We ask the compositor to take care
|
||||
// of that for us.
|
||||
if (mProvider) {
|
||||
mProvider->UnlockAfterComposition(this);
|
||||
} else {
|
||||
// GetCompositor returned null which means no compositor can be using this
|
||||
// texture. We can ReadUnlock right away.
|
||||
ReadUnlock();
|
||||
MaybeNotifyUnlocked();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void TextureHost::RecycleTexture(TextureFlags aFlags) {
|
||||
MOZ_ASSERT(GetFlags() & TextureFlags::RECYCLE);
|
||||
MOZ_ASSERT(aFlags & TextureFlags::RECYCLE);
|
||||
@ -403,17 +385,7 @@ void TextureHost::NotifyNotUsed() {
|
||||
return;
|
||||
}
|
||||
|
||||
// The following cases do not need to defer NotifyNotUsed until next
|
||||
// Composite.
|
||||
// - TextureHost does not have Compositor.
|
||||
// - Compositor is BasicCompositor.
|
||||
// - TextureHost has intermediate buffer.
|
||||
// end of buffer usage.
|
||||
if (!mProvider || HasIntermediateBuffer() ||
|
||||
!mProvider->NotifyNotUsedAfterComposition(this)) {
|
||||
static_cast<TextureParent*>(mActor)->NotifyNotUsed(mFwdTransactionId);
|
||||
return;
|
||||
}
|
||||
static_cast<TextureParent*>(mActor)->NotifyNotUsed(mFwdTransactionId);
|
||||
}
|
||||
|
||||
void TextureHost::CallNotifyNotUsed() {
|
||||
@ -530,61 +502,7 @@ void BufferTextureHost::UpdatedInternal(const nsIntRegion* aRegion) {
|
||||
}
|
||||
}
|
||||
|
||||
void BufferTextureHost::SetTextureSourceProvider(
|
||||
TextureSourceProvider* aProvider) {
|
||||
if (mProvider == aProvider) {
|
||||
return;
|
||||
}
|
||||
if (mFirstSource && mFirstSource->IsOwnedBy(this)) {
|
||||
mFirstSource->SetOwner(nullptr);
|
||||
}
|
||||
if (mFirstSource) {
|
||||
mFirstSource = nullptr;
|
||||
mNeedsFullUpdate = true;
|
||||
}
|
||||
mProvider = aProvider;
|
||||
}
|
||||
|
||||
void BufferTextureHost::DeallocateDeviceData() {
|
||||
if (mFirstSource && mFirstSource->NumCompositableRefs() > 0) {
|
||||
// WrappingTextureSourceYCbCrBasic wraps YUV format BufferTextureHost.
|
||||
// When BufferTextureHost is destroyed, data of
|
||||
// WrappingTextureSourceYCbCrBasic becomes invalid.
|
||||
if (mFirstSource->AsWrappingTextureSourceYCbCrBasic() &&
|
||||
mFirstSource->IsOwnedBy(this)) {
|
||||
mFirstSource->SetOwner(nullptr);
|
||||
mFirstSource->DeallocateDeviceData();
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
if (!mFirstSource || !mFirstSource->IsOwnedBy(this)) {
|
||||
mFirstSource = nullptr;
|
||||
return;
|
||||
}
|
||||
|
||||
mFirstSource->SetOwner(nullptr);
|
||||
|
||||
RefPtr<TextureSource> it = mFirstSource;
|
||||
while (it) {
|
||||
it->DeallocateDeviceData();
|
||||
it = it->GetNextSibling();
|
||||
}
|
||||
}
|
||||
|
||||
bool BufferTextureHost::Lock() {
|
||||
MOZ_ASSERT(!mLocked);
|
||||
if (!UploadIfNeeded()) {
|
||||
return false;
|
||||
}
|
||||
mLocked = !!mFirstSource;
|
||||
return mLocked;
|
||||
}
|
||||
|
||||
void BufferTextureHost::Unlock() {
|
||||
MOZ_ASSERT(mLocked);
|
||||
mLocked = false;
|
||||
}
|
||||
void BufferTextureHost::DeallocateDeviceData() {}
|
||||
|
||||
void BufferTextureHost::CreateRenderTexture(
|
||||
const wr::ExternalImageId& aExternalImageId) {
|
||||
@ -698,9 +616,6 @@ void TextureHost::SetReadLocked() {
|
||||
// lock again!
|
||||
MOZ_ASSERT(!mReadLocked);
|
||||
mReadLocked = true;
|
||||
if (mProvider) {
|
||||
mProvider->MaybeUnlockBeforeNextComposition(this);
|
||||
}
|
||||
}
|
||||
|
||||
void TextureHost::ReadUnlock() {
|
||||
@ -714,171 +629,6 @@ bool TextureHost::NeedsYFlip() const {
|
||||
return bool(mFlags & TextureFlags::ORIGIN_BOTTOM_LEFT);
|
||||
}
|
||||
|
||||
bool BufferTextureHost::EnsureWrappingTextureSource() {
|
||||
MOZ_ASSERT(!mHasIntermediateBuffer);
|
||||
|
||||
if (mFirstSource && mFirstSource->IsOwnedBy(this)) {
|
||||
return true;
|
||||
}
|
||||
// We don't own it, apparently.
|
||||
if (mFirstSource) {
|
||||
mNeedsFullUpdate = true;
|
||||
mFirstSource = nullptr;
|
||||
}
|
||||
|
||||
if (!mProvider) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (mFormat == gfx::SurfaceFormat::YUV) {
|
||||
mFirstSource = mProvider->CreateDataTextureSourceAroundYCbCr(this);
|
||||
} else {
|
||||
uint8_t* data = GetBuffer();
|
||||
if (!data) {
|
||||
return false;
|
||||
}
|
||||
RefPtr<gfx::DataSourceSurface> surf =
|
||||
gfx::Factory::CreateWrappingDataSourceSurface(
|
||||
data, ImageDataSerializer::ComputeRGBStride(mFormat, mSize.width),
|
||||
mSize, mFormat);
|
||||
if (!surf) {
|
||||
return false;
|
||||
}
|
||||
mFirstSource = mProvider->CreateDataTextureSourceAround(surf);
|
||||
}
|
||||
|
||||
if (!mFirstSource) {
|
||||
// BasicCompositor::CreateDataTextureSourceAround never returns null
|
||||
// and we don't expect to take this branch if we are using another backend.
|
||||
// Returning false is fine but if we get into this situation it probably
|
||||
// means something fishy is going on, like a texture being used with
|
||||
// several compositor backends.
|
||||
NS_WARNING("Failed to use a BufferTextureHost without intermediate buffer");
|
||||
return false;
|
||||
}
|
||||
|
||||
mFirstSource->SetUpdateSerial(mUpdateSerial);
|
||||
mFirstSource->SetOwner(this);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool IsCompatibleTextureSource(TextureSource* aTexture,
|
||||
const BufferDescriptor& aDescriptor,
|
||||
TextureSourceProvider* aProvider) {
|
||||
if (!aProvider) {
|
||||
return false;
|
||||
}
|
||||
|
||||
switch (aDescriptor.type()) {
|
||||
case BufferDescriptor::TYCbCrDescriptor: {
|
||||
const YCbCrDescriptor& ycbcr = aDescriptor.get_YCbCrDescriptor();
|
||||
|
||||
if (!aProvider->SupportsEffect(EffectTypes::YCBCR)) {
|
||||
return aTexture->GetFormat() == gfx::SurfaceFormat::B8G8R8X8 &&
|
||||
aTexture->GetSize() == ycbcr.ySize();
|
||||
}
|
||||
|
||||
if (aTexture->GetFormat() != gfx::SurfaceFormat::A8 ||
|
||||
aTexture->GetSize() != ycbcr.ySize()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
auto cbTexture = aTexture->GetSubSource(1);
|
||||
if (!cbTexture || cbTexture->GetFormat() != gfx::SurfaceFormat::A8 ||
|
||||
cbTexture->GetSize() != ycbcr.cbCrSize()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
auto crTexture = aTexture->GetSubSource(2);
|
||||
if (!crTexture || crTexture->GetFormat() != gfx::SurfaceFormat::A8 ||
|
||||
crTexture->GetSize() != ycbcr.cbCrSize()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
case BufferDescriptor::TRGBDescriptor: {
|
||||
const RGBDescriptor& rgb = aDescriptor.get_RGBDescriptor();
|
||||
return aTexture->GetFormat() == rgb.format() &&
|
||||
aTexture->GetSize() == rgb.size();
|
||||
}
|
||||
default: {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void BufferTextureHost::PrepareTextureSource(
|
||||
CompositableTextureSourceRef& aTexture) {
|
||||
if (!mHasIntermediateBuffer) {
|
||||
EnsureWrappingTextureSource();
|
||||
}
|
||||
|
||||
if (mFirstSource && mFirstSource->IsOwnedBy(this)) {
|
||||
// We are already attached to a TextureSource, nothing to do except tell
|
||||
// the compositable to use it.
|
||||
aTexture = mFirstSource.get();
|
||||
return;
|
||||
}
|
||||
|
||||
// We don't own it, apparently.
|
||||
if (mFirstSource) {
|
||||
mNeedsFullUpdate = true;
|
||||
mFirstSource = nullptr;
|
||||
}
|
||||
|
||||
DataTextureSource* texture =
|
||||
aTexture.get() ? aTexture->AsDataTextureSource() : nullptr;
|
||||
|
||||
bool compatibleFormats =
|
||||
texture && IsCompatibleTextureSource(texture, mDescriptor, mProvider);
|
||||
|
||||
bool shouldCreateTexture = !compatibleFormats ||
|
||||
texture->NumCompositableRefs() > 1 ||
|
||||
texture->HasOwner();
|
||||
|
||||
if (!shouldCreateTexture) {
|
||||
mFirstSource = texture;
|
||||
mFirstSource->SetOwner(this);
|
||||
mNeedsFullUpdate = true;
|
||||
|
||||
// It's possible that texture belonged to a different compositor,
|
||||
// so make sure we update it (and all of its siblings) to the
|
||||
// current one.
|
||||
RefPtr<TextureSource> it = mFirstSource;
|
||||
while (it) {
|
||||
it->SetTextureSourceProvider(mProvider);
|
||||
it = it->GetNextSibling();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bool BufferTextureHost::BindTextureSource(
|
||||
CompositableTextureSourceRef& aTexture) {
|
||||
MOZ_ASSERT(mLocked);
|
||||
MOZ_ASSERT(mFirstSource);
|
||||
aTexture = mFirstSource;
|
||||
return !!aTexture;
|
||||
}
|
||||
|
||||
bool BufferTextureHost::AcquireTextureSource(
|
||||
CompositableTextureSourceRef& aTexture) {
|
||||
if (!UploadIfNeeded()) {
|
||||
return false;
|
||||
}
|
||||
aTexture = mFirstSource;
|
||||
return !!mFirstSource;
|
||||
}
|
||||
|
||||
void BufferTextureHost::ReadUnlock() {
|
||||
if (mFirstSource) {
|
||||
mFirstSource->Sync(true);
|
||||
}
|
||||
|
||||
TextureHost::ReadUnlock();
|
||||
}
|
||||
|
||||
void BufferTextureHost::MaybeNotifyUnlocked() {
|
||||
#ifdef XP_DARWIN
|
||||
auto actor = GetIPDLActor();
|
||||
@ -890,34 +640,7 @@ void BufferTextureHost::MaybeNotifyUnlocked() {
|
||||
#endif
|
||||
}
|
||||
|
||||
void BufferTextureHost::UnbindTextureSource() {
|
||||
if (mFirstSource && mFirstSource->IsOwnedBy(this)) {
|
||||
mFirstSource->Unbind();
|
||||
}
|
||||
|
||||
// This texture is not used by any layer anymore.
|
||||
// If the texture doesn't have an intermediate buffer, it means we are
|
||||
// compositing synchronously on the CPU, so we don't need to wait until
|
||||
// the end of the next composition to ReadUnlock (which other textures do
|
||||
// by default).
|
||||
// If the texture has an intermediate buffer we don't care either because
|
||||
// texture uploads are also performed synchronously for BufferTextureHost.
|
||||
ReadUnlock();
|
||||
MaybeNotifyUnlocked();
|
||||
}
|
||||
|
||||
gfx::SurfaceFormat BufferTextureHost::GetFormat() const {
|
||||
// mFormat is the format of the data that we share with the content process.
|
||||
// GetFormat, on the other hand, expects the format that we present to the
|
||||
// Compositor (it is used to choose the effect type).
|
||||
// if the compositor does not support YCbCr effects, we give it a RGBX texture
|
||||
// instead (see BufferTextureHost::Upload)
|
||||
if (mFormat == gfx::SurfaceFormat::YUV && mProvider &&
|
||||
!mProvider->SupportsEffect(EffectTypes::YCBCR)) {
|
||||
return gfx::SurfaceFormat::R8G8B8X8;
|
||||
}
|
||||
return mFormat;
|
||||
}
|
||||
gfx::SurfaceFormat BufferTextureHost::GetFormat() const { return mFormat; }
|
||||
|
||||
gfx::YUVColorSpace BufferTextureHost::GetYUVColorSpace() const {
|
||||
if (mFormat == gfx::SurfaceFormat::YUV) {
|
||||
@ -948,156 +671,11 @@ bool BufferTextureHost::UploadIfNeeded() {
|
||||
}
|
||||
|
||||
bool BufferTextureHost::MaybeUpload(nsIntRegion* aRegion) {
|
||||
auto serial = mFirstSource ? mFirstSource->GetUpdateSerial() : 0;
|
||||
|
||||
if (serial == mUpdateSerial) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (serial == 0) {
|
||||
// 0 means the source has no valid content
|
||||
aRegion = nullptr;
|
||||
}
|
||||
|
||||
if (!Upload(aRegion)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (mHasIntermediateBuffer) {
|
||||
// We just did the texture upload, the content side can now freely write
|
||||
// into the shared buffer.
|
||||
ReadUnlock();
|
||||
MaybeNotifyUnlocked();
|
||||
}
|
||||
|
||||
// We no longer have an invalid region.
|
||||
mNeedsFullUpdate = false;
|
||||
mMaybeUpdatedRegion.SetEmpty();
|
||||
|
||||
// If upload returns true we know mFirstSource is not null
|
||||
mFirstSource->SetUpdateSerial(mUpdateSerial);
|
||||
return true;
|
||||
MOZ_ASSERT(!aRegion);
|
||||
return false;
|
||||
}
|
||||
|
||||
bool BufferTextureHost::Upload(nsIntRegion* aRegion) {
|
||||
uint8_t* buf = GetBuffer();
|
||||
if (!buf) {
|
||||
// We don't have a buffer; a possible cause is that the IPDL actor
|
||||
// is already dead. This inevitably happens as IPDL actors can die
|
||||
// at any time, so we want to silently return in this case.
|
||||
// another possible cause is that IPDL failed to map the shmem when
|
||||
// deserializing it.
|
||||
return false;
|
||||
}
|
||||
if (!mProvider) {
|
||||
// This can happen if we send textures to a compositable that isn't yet
|
||||
// attached to a layer.
|
||||
return false;
|
||||
}
|
||||
if (!mHasIntermediateBuffer && EnsureWrappingTextureSource()) {
|
||||
if (!mFirstSource || !mFirstSource->IsDirectMap()) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
if (mFormat == gfx::SurfaceFormat::UNKNOWN) {
|
||||
NS_WARNING("BufferTextureHost: unsupported format!");
|
||||
return false;
|
||||
} else if (mFormat == gfx::SurfaceFormat::YUV) {
|
||||
const YCbCrDescriptor& desc = mDescriptor.get_YCbCrDescriptor();
|
||||
|
||||
if (!mProvider->SupportsEffect(EffectTypes::YCBCR)) {
|
||||
RefPtr<gfx::DataSourceSurface> surf =
|
||||
ImageDataSerializer::DataSourceSurfaceFromYCbCrDescriptor(
|
||||
buf, mDescriptor.get_YCbCrDescriptor());
|
||||
if (NS_WARN_IF(!surf)) {
|
||||
return false;
|
||||
}
|
||||
if (!mFirstSource) {
|
||||
mFirstSource = mProvider->CreateDataTextureSource(
|
||||
mFlags | TextureFlags::RGB_FROM_YCBCR);
|
||||
mFirstSource->SetOwner(this);
|
||||
}
|
||||
return mFirstSource->Update(surf, aRegion);
|
||||
}
|
||||
|
||||
RefPtr<DataTextureSource> srcY;
|
||||
RefPtr<DataTextureSource> srcU;
|
||||
RefPtr<DataTextureSource> srcV;
|
||||
if (!mFirstSource) {
|
||||
// We don't support BigImages for YCbCr compositing.
|
||||
srcY = mProvider->CreateDataTextureSource(
|
||||
mFlags | TextureFlags::DISALLOW_BIGIMAGE);
|
||||
srcU = mProvider->CreateDataTextureSource(
|
||||
mFlags | TextureFlags::DISALLOW_BIGIMAGE);
|
||||
srcV = mProvider->CreateDataTextureSource(
|
||||
mFlags | TextureFlags::DISALLOW_BIGIMAGE);
|
||||
mFirstSource = srcY;
|
||||
mFirstSource->SetOwner(this);
|
||||
srcY->SetNextSibling(srcU);
|
||||
srcU->SetNextSibling(srcV);
|
||||
} else {
|
||||
// mFormat never changes so if this was created as a YCbCr host and
|
||||
// already contains a source it should already have 3 sources.
|
||||
// BufferTextureHost only uses DataTextureSources so it is safe to assume
|
||||
// all 3 sources are DataTextureSource.
|
||||
MOZ_ASSERT(mFirstSource->GetNextSibling());
|
||||
MOZ_ASSERT(mFirstSource->GetNextSibling()->GetNextSibling());
|
||||
srcY = mFirstSource;
|
||||
srcU = mFirstSource->GetNextSibling()->AsDataTextureSource();
|
||||
srcV = mFirstSource->GetNextSibling()
|
||||
->GetNextSibling()
|
||||
->AsDataTextureSource();
|
||||
}
|
||||
|
||||
RefPtr<gfx::DataSourceSurface> tempY =
|
||||
gfx::Factory::CreateWrappingDataSourceSurface(
|
||||
ImageDataSerializer::GetYChannel(buf, desc), desc.yStride(),
|
||||
desc.ySize(), SurfaceFormatForColorDepth(desc.colorDepth()));
|
||||
RefPtr<gfx::DataSourceSurface> tempCb =
|
||||
gfx::Factory::CreateWrappingDataSourceSurface(
|
||||
ImageDataSerializer::GetCbChannel(buf, desc), desc.cbCrStride(),
|
||||
desc.cbCrSize(), SurfaceFormatForColorDepth(desc.colorDepth()));
|
||||
RefPtr<gfx::DataSourceSurface> tempCr =
|
||||
gfx::Factory::CreateWrappingDataSourceSurface(
|
||||
ImageDataSerializer::GetCrChannel(buf, desc), desc.cbCrStride(),
|
||||
desc.cbCrSize(), SurfaceFormatForColorDepth(desc.colorDepth()));
|
||||
// We don't support partial updates for Y U V textures
|
||||
NS_ASSERTION(!aRegion, "Unsupported partial updates for YCbCr textures");
|
||||
if (!tempY || !tempCb || !tempCr || !srcY->Update(tempY) ||
|
||||
!srcU->Update(tempCb) || !srcV->Update(tempCr)) {
|
||||
NS_WARNING("failed to update the DataTextureSource");
|
||||
return false;
|
||||
}
|
||||
} else {
|
||||
// non-YCbCr case
|
||||
nsIntRegion* regionToUpdate = aRegion;
|
||||
if (!mFirstSource) {
|
||||
mFirstSource = mProvider->CreateDataTextureSource(mFlags);
|
||||
mFirstSource->SetOwner(this);
|
||||
if (mFlags & TextureFlags::COMPONENT_ALPHA) {
|
||||
// Update the full region the first time for component alpha textures.
|
||||
regionToUpdate = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
RefPtr<gfx::DataSourceSurface> surf =
|
||||
gfx::Factory::CreateWrappingDataSourceSurface(
|
||||
GetBuffer(),
|
||||
ImageDataSerializer::ComputeRGBStride(mFormat, mSize.width), mSize,
|
||||
mFormat);
|
||||
if (!surf) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!mFirstSource->Update(surf.get(), regionToUpdate)) {
|
||||
NS_WARNING("failed to update the DataTextureSource");
|
||||
return false;
|
||||
}
|
||||
}
|
||||
MOZ_ASSERT(mFirstSource);
|
||||
return true;
|
||||
}
|
||||
bool BufferTextureHost::Upload(nsIntRegion* aRegion) { return false; }
|
||||
|
||||
already_AddRefed<gfx::DataSourceSurface> BufferTextureHost::GetAsSurface() {
|
||||
RefPtr<gfx::DataSourceSurface> result;
|
||||
|
@ -69,7 +69,6 @@ class TextureHostOGL;
|
||||
class TextureReadLock;
|
||||
class TextureSourceOGL;
|
||||
class TextureSourceD3D11;
|
||||
class TextureSourceBasic;
|
||||
class DataTextureSource;
|
||||
class PTextureParent;
|
||||
class TextureParent;
|
||||
@ -140,14 +139,10 @@ class TextureSource : public RefCounted<TextureSource> {
|
||||
return nullptr;
|
||||
}
|
||||
virtual TextureSourceD3D11* AsSourceD3D11() { return nullptr; }
|
||||
virtual TextureSourceBasic* AsSourceBasic() { return nullptr; }
|
||||
/**
|
||||
* Cast to a DataTextureSurce.
|
||||
*/
|
||||
virtual DataTextureSource* AsDataTextureSource() { return nullptr; }
|
||||
virtual WrappingTextureSourceYCbCrBasic* AsWrappingTextureSourceYCbCrBasic() {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
/**
|
||||
* Overload this if the TextureSource supports big textures that don't fit in
|
||||
@ -155,8 +150,6 @@ class TextureSource : public RefCounted<TextureSource> {
|
||||
*/
|
||||
virtual BigImageIterator* AsBigImageIterator() { return nullptr; }
|
||||
|
||||
virtual void SetTextureSourceProvider(TextureSourceProvider* aProvider) {}
|
||||
|
||||
virtual void Unbind() {}
|
||||
|
||||
void SetNextSibling(TextureSource* aTexture) { mNextSibling = aTexture; }
|
||||
@ -195,9 +188,6 @@ class TextureSource : public RefCounted<TextureSource> {
|
||||
|
||||
int NumCompositableRefs() const { return mCompositableCount; }
|
||||
|
||||
// Some texture sources could wrap the cpu buffer to gpu directly. Then,
|
||||
// we could get better performance of texture uploading.
|
||||
virtual bool IsDirectMap() { return false; }
|
||||
// The direct-map cpu buffer should be alive when gpu uses it. And it
|
||||
// should not be updated while gpu reads it. This Sync() function
|
||||
// implements this synchronized behavior by allowing us to check if
|
||||
@ -413,16 +403,6 @@ class TextureHost : public AtomicRefCountedWithFinalize<TextureHost> {
|
||||
ISurfaceAllocator* aDeallocator, LayersBackend aBackend,
|
||||
TextureFlags aFlags, wr::MaybeExternalImageId& aExternalImageId);
|
||||
|
||||
/**
|
||||
* Lock the texture host for compositing.
|
||||
*/
|
||||
virtual bool Lock() { return true; }
|
||||
/**
|
||||
* Unlock the texture host after compositing. Lock() and Unlock() should be
|
||||
* called in pair.
|
||||
*/
|
||||
virtual void Unlock() {}
|
||||
|
||||
/**
|
||||
* Lock the texture host for compositing without using compositor.
|
||||
*/
|
||||
@ -463,35 +443,6 @@ class TextureHost : public AtomicRefCountedWithFinalize<TextureHost> {
|
||||
return gfx::ColorRange::LIMITED;
|
||||
}
|
||||
|
||||
/**
|
||||
* Called during the transaction. The TextureSource may or may not be
|
||||
* composited.
|
||||
*
|
||||
* Note that this is called outside of lock/unlock.
|
||||
*/
|
||||
virtual void PrepareTextureSource(CompositableTextureSourceRef& aTexture) {}
|
||||
|
||||
/**
|
||||
* Called at composition time, just before compositing the TextureSource
|
||||
* composited.
|
||||
*
|
||||
* Note that this is called only withing lock/unlock.
|
||||
*/
|
||||
virtual bool BindTextureSource(CompositableTextureSourceRef& aTexture) = 0;
|
||||
|
||||
/**
|
||||
* Called when preparing the rendering pipeline for advanced-layers. This is
|
||||
* a lockless version of BindTextureSource.
|
||||
*/
|
||||
virtual bool AcquireTextureSource(CompositableTextureSourceRef& aTexture) {
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when another TextureHost will take over.
|
||||
*/
|
||||
virtual void UnbindTextureSource();
|
||||
|
||||
virtual bool IsValid() { return true; }
|
||||
|
||||
/**
|
||||
@ -505,17 +456,6 @@ class TextureHost : public AtomicRefCountedWithFinalize<TextureHost> {
|
||||
*/
|
||||
void Updated(const nsIntRegion* aRegion = nullptr);
|
||||
|
||||
/**
|
||||
* Sets this TextureHost's compositor. A TextureHost can change compositor
|
||||
* on certain occasions, in particular if it belongs to an async Compositable.
|
||||
* aCompositor can be null, in which case the TextureHost must cleanup all
|
||||
* of its device textures.
|
||||
*
|
||||
* Setting mProvider from this callback implicitly causes the texture to
|
||||
* be locked for an extra frame after being detached from a compositable.
|
||||
*/
|
||||
virtual void SetTextureSourceProvider(TextureSourceProvider* aProvider) {}
|
||||
|
||||
/**
|
||||
* Should be overridden in order to deallocate the data that is associated
|
||||
* with the rendering backend, such as GL textures.
|
||||
@ -633,7 +573,6 @@ class TextureHost : public AtomicRefCountedWithFinalize<TextureHost> {
|
||||
--mCompositableCount;
|
||||
MOZ_ASSERT(mCompositableCount >= 0);
|
||||
if (mCompositableCount == 0) {
|
||||
UnbindTextureSource();
|
||||
// Send mFwdTransactionId to client side if necessary.
|
||||
NotifyNotUsed();
|
||||
}
|
||||
@ -722,12 +661,8 @@ class TextureHost : public AtomicRefCountedWithFinalize<TextureHost> {
|
||||
*/
|
||||
virtual MacIOSurface* GetMacIOSurface() { return nullptr; }
|
||||
|
||||
virtual bool IsDirectMap() { return false; }
|
||||
|
||||
virtual bool NeedsYFlip() const;
|
||||
|
||||
TextureSourceProvider* GetProvider() const { return mProvider; }
|
||||
|
||||
virtual void SetAcquireFence(mozilla::ipc::FileDescriptor&& aFenceFd) {}
|
||||
|
||||
virtual void SetReleaseFence(mozilla::ipc::FileDescriptor&& aFenceFd) {}
|
||||
@ -788,7 +723,6 @@ class TextureHost : public AtomicRefCountedWithFinalize<TextureHost> {
|
||||
void CallNotifyNotUsed();
|
||||
|
||||
PTextureParent* mActor;
|
||||
RefPtr<TextureSourceProvider> mProvider;
|
||||
RefPtr<TextureReadLock> mReadLock;
|
||||
TextureFlags mFlags;
|
||||
int mCompositableCount;
|
||||
@ -826,21 +760,8 @@ class BufferTextureHost : public TextureHost {
|
||||
|
||||
virtual size_t GetBufferSize() = 0;
|
||||
|
||||
bool Lock() override;
|
||||
|
||||
void Unlock() override;
|
||||
|
||||
void PrepareTextureSource(CompositableTextureSourceRef& aTexture) override;
|
||||
|
||||
bool BindTextureSource(CompositableTextureSourceRef& aTexture) override;
|
||||
bool AcquireTextureSource(CompositableTextureSourceRef& aTexture) override;
|
||||
|
||||
void UnbindTextureSource() override;
|
||||
|
||||
void DeallocateDeviceData() override;
|
||||
|
||||
void SetTextureSourceProvider(TextureSourceProvider* aProvider) override;
|
||||
|
||||
/**
|
||||
* Return the format that is exposed to the compositor when calling
|
||||
* BindTextureSource.
|
||||
@ -886,12 +807,6 @@ class BufferTextureHost : public TextureHost {
|
||||
const Range<wr::ImageKey>& aImageKeys,
|
||||
PushDisplayItemFlagSet aFlags) override;
|
||||
|
||||
void ReadUnlock() override;
|
||||
bool IsDirectMap() override {
|
||||
return mFirstSource && mFirstSource->IsDirectMap();
|
||||
};
|
||||
|
||||
bool CanUnlock() { return !mFirstSource || mFirstSource->Sync(false); }
|
||||
void DisableExternalTextures() { mUseExternalTextures = false; }
|
||||
|
||||
protected:
|
||||
@ -899,14 +814,12 @@ class BufferTextureHost : public TextureHost {
|
||||
bool Upload(nsIntRegion* aRegion = nullptr);
|
||||
bool UploadIfNeeded();
|
||||
bool MaybeUpload(nsIntRegion* aRegion);
|
||||
bool EnsureWrappingTextureSource();
|
||||
|
||||
void UpdatedInternal(const nsIntRegion* aRegion = nullptr) override;
|
||||
void MaybeNotifyUnlocked() override;
|
||||
|
||||
BufferDescriptor mDescriptor;
|
||||
RefPtr<Compositor> mCompositor;
|
||||
RefPtr<DataTextureSource> mFirstSource;
|
||||
nsIntRegion mMaybeUpdatedRegion;
|
||||
gfx::IntSize mSize;
|
||||
gfx::SurfaceFormat mFormat;
|
||||
@ -980,25 +893,6 @@ class MemoryTextureHost : public BufferTextureHost {
|
||||
uint8_t* mBuffer;
|
||||
};
|
||||
|
||||
class MOZ_STACK_CLASS AutoLockTextureHost {
|
||||
public:
|
||||
explicit AutoLockTextureHost(TextureHost* aTexture) : mTexture(aTexture) {
|
||||
mLocked = mTexture ? mTexture->Lock() : false;
|
||||
}
|
||||
|
||||
~AutoLockTextureHost() {
|
||||
if (mTexture && mLocked) {
|
||||
mTexture->Unlock();
|
||||
}
|
||||
}
|
||||
|
||||
bool Failed() { return mTexture && !mLocked; }
|
||||
|
||||
private:
|
||||
RefPtr<TextureHost> mTexture;
|
||||
bool mLocked;
|
||||
};
|
||||
|
||||
class MOZ_STACK_CLASS AutoLockTextureHostWithoutCompositor {
|
||||
public:
|
||||
explicit AutoLockTextureHostWithoutCompositor(TextureHost* aTexture)
|
||||
|
@ -816,13 +816,10 @@ Maybe<IntRect> CompositorD3D11::BeginFrame(const nsIntRegion& aInvalidRegion,
|
||||
if (mWidget->IsHidden()) {
|
||||
// We are not going to render, and not going to call EndFrame so we have to
|
||||
// read-unlock our textures to prevent them from accumulating.
|
||||
ReadUnlockTextures();
|
||||
return Nothing();
|
||||
}
|
||||
|
||||
if (mDevice->GetDeviceRemovedReason() != S_OK) {
|
||||
ReadUnlockTextures();
|
||||
|
||||
if (!mAttachments->IsDeviceReset()) {
|
||||
gfxCriticalNote << "GFX: D3D11 skip BeginFrame with device-removed.";
|
||||
|
||||
@ -876,7 +873,6 @@ Maybe<IntRect> CompositorD3D11::BeginFrame(const nsIntRegion& aInvalidRegion,
|
||||
// Failed to create a render target or the view.
|
||||
if (!UpdateRenderTarget() || !mDefaultRT || !mDefaultRT->mRTView ||
|
||||
mSize.width <= 0 || mSize.height <= 0) {
|
||||
ReadUnlockTextures();
|
||||
return Nothing();
|
||||
}
|
||||
|
||||
@ -1066,7 +1062,6 @@ void CompositorD3D11::Present() {
|
||||
}
|
||||
|
||||
void CompositorD3D11::CancelFrame(bool aNeedFlush) {
|
||||
ReadUnlockTextures();
|
||||
// Flush the context, otherwise the driver might hold some resources alive
|
||||
// until the next flush or present.
|
||||
if (aNeedFlush) {
|
||||
|
@ -819,61 +819,16 @@ RefPtr<ID3D11Device> DXGITextureHostD3D11::GetDevice() {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
if (mProvider) {
|
||||
return mProvider->GetD3D11Device();
|
||||
} else {
|
||||
return mDevice;
|
||||
}
|
||||
}
|
||||
|
||||
void DXGITextureHostD3D11::SetTextureSourceProvider(
|
||||
TextureSourceProvider* aProvider) {
|
||||
if (!aProvider || !aProvider->GetD3D11Device()) {
|
||||
mDevice = nullptr;
|
||||
mProvider = nullptr;
|
||||
mTextureSource = nullptr;
|
||||
return;
|
||||
}
|
||||
|
||||
if (mDevice && (aProvider->GetD3D11Device() != mDevice)) {
|
||||
if (mTextureSource) {
|
||||
mTextureSource->Reset();
|
||||
}
|
||||
mTextureSource = nullptr;
|
||||
return;
|
||||
}
|
||||
|
||||
mProvider = aProvider;
|
||||
mDevice = aProvider->GetD3D11Device();
|
||||
|
||||
if (mTextureSource) {
|
||||
mTextureSource->SetTextureSourceProvider(aProvider);
|
||||
}
|
||||
}
|
||||
|
||||
bool DXGITextureHostD3D11::Lock() {
|
||||
if (!mProvider) {
|
||||
// Make an early return here if we call SetTextureSourceProvider() with an
|
||||
// incompatible compositor. This check tries to prevent the problem where we
|
||||
// use that incompatible compositor to compose this texture.
|
||||
return false;
|
||||
}
|
||||
|
||||
return LockInternal();
|
||||
return mDevice;
|
||||
}
|
||||
|
||||
bool DXGITextureHostD3D11::LockWithoutCompositor() {
|
||||
// Unlike the normal Lock() function, this function may be called when
|
||||
// mProvider is nullptr such as during WebVR frame submission. So, there is
|
||||
// no 'mProvider' checking here.
|
||||
if (!mDevice) {
|
||||
mDevice = DeviceManagerDx::Get()->GetCompositorDevice();
|
||||
}
|
||||
return LockInternal();
|
||||
}
|
||||
|
||||
void DXGITextureHostD3D11::Unlock() { UnlockInternal(); }
|
||||
|
||||
void DXGITextureHostD3D11::UnlockWithoutCompositor() { UnlockInternal(); }
|
||||
|
||||
bool DXGITextureHostD3D11::LockInternal() {
|
||||
@ -961,14 +916,7 @@ bool DXGITextureHostD3D11::EnsureTextureSource() {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (mProvider) {
|
||||
if (!mProvider->IsValid()) {
|
||||
return false;
|
||||
}
|
||||
mTextureSource = new DataTextureSourceD3D11(mFormat, mProvider, mTexture);
|
||||
} else {
|
||||
mTextureSource = new DataTextureSourceD3D11(mDevice, mFormat, mTexture);
|
||||
}
|
||||
mTextureSource = new DataTextureSourceD3D11(mDevice, mFormat, mTexture);
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -976,23 +924,6 @@ void DXGITextureHostD3D11::UnlockInternal() {
|
||||
UnlockD3DTexture(mTextureSource->GetD3D11Texture());
|
||||
}
|
||||
|
||||
bool DXGITextureHostD3D11::BindTextureSource(
|
||||
CompositableTextureSourceRef& aTexture) {
|
||||
MOZ_ASSERT(mIsLocked);
|
||||
// If Lock was successful we must have a valid TextureSource.
|
||||
MOZ_ASSERT(mTextureSource);
|
||||
return AcquireTextureSource(aTexture);
|
||||
}
|
||||
|
||||
bool DXGITextureHostD3D11::AcquireTextureSource(
|
||||
CompositableTextureSourceRef& aTexture) {
|
||||
if (!EnsureTextureSource()) {
|
||||
return false;
|
||||
}
|
||||
aTexture = mTextureSource;
|
||||
return true;
|
||||
}
|
||||
|
||||
void DXGITextureHostD3D11::CreateRenderTexture(
|
||||
const wr::ExternalImageId& aExternalImageId) {
|
||||
RefPtr<wr::RenderTextureHost> texture = new wr::RenderDXGITextureHost(
|
||||
@ -1211,88 +1142,9 @@ bool DXGIYCbCrTextureHostD3D11::EnsureTexture() {
|
||||
return true;
|
||||
}
|
||||
|
||||
RefPtr<ID3D11Device> DXGIYCbCrTextureHostD3D11::GetDevice() {
|
||||
if (mFlags & TextureFlags::INVALID_COMPOSITOR) {
|
||||
return nullptr;
|
||||
}
|
||||
RefPtr<ID3D11Device> DXGIYCbCrTextureHostD3D11::GetDevice() { return nullptr; }
|
||||
|
||||
return mProvider->GetD3D11Device();
|
||||
}
|
||||
|
||||
void DXGIYCbCrTextureHostD3D11::SetTextureSourceProvider(
|
||||
TextureSourceProvider* aProvider) {
|
||||
if (!aProvider || !aProvider->GetD3D11Device()) {
|
||||
mProvider = nullptr;
|
||||
mTextureSources[0] = nullptr;
|
||||
mTextureSources[1] = nullptr;
|
||||
mTextureSources[2] = nullptr;
|
||||
return;
|
||||
}
|
||||
|
||||
mProvider = aProvider;
|
||||
|
||||
if (mTextureSources[0]) {
|
||||
mTextureSources[0]->SetTextureSourceProvider(aProvider);
|
||||
}
|
||||
}
|
||||
|
||||
bool DXGIYCbCrTextureHostD3D11::Lock() {
|
||||
if (!EnsureTextureSource()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
mIsLocked = LockD3DTexture(mTextureSources[0]->GetD3D11Texture()) &&
|
||||
LockD3DTexture(mTextureSources[1]->GetD3D11Texture()) &&
|
||||
LockD3DTexture(mTextureSources[2]->GetD3D11Texture());
|
||||
|
||||
return mIsLocked;
|
||||
}
|
||||
|
||||
bool DXGIYCbCrTextureHostD3D11::EnsureTextureSource() {
|
||||
if (!mProvider) {
|
||||
NS_WARNING("no suitable compositor");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!GetDevice()) {
|
||||
NS_WARNING("trying to lock a TextureHost without a D3D device");
|
||||
return false;
|
||||
}
|
||||
if (!mTextureSources[0]) {
|
||||
if (!EnsureTexture()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
MOZ_ASSERT(mTextures[1] && mTextures[2]);
|
||||
|
||||
mTextureSources[0] =
|
||||
new DataTextureSourceD3D11(SurfaceFormat::A8, mProvider, mTextures[0]);
|
||||
mTextureSources[1] =
|
||||
new DataTextureSourceD3D11(SurfaceFormat::A8, mProvider, mTextures[1]);
|
||||
mTextureSources[2] =
|
||||
new DataTextureSourceD3D11(SurfaceFormat::A8, mProvider, mTextures[2]);
|
||||
mTextureSources[0]->SetNextSibling(mTextureSources[1]);
|
||||
mTextureSources[1]->SetNextSibling(mTextureSources[2]);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void DXGIYCbCrTextureHostD3D11::Unlock() {
|
||||
MOZ_ASSERT(mIsLocked);
|
||||
UnlockD3DTexture(mTextureSources[0]->GetD3D11Texture());
|
||||
UnlockD3DTexture(mTextureSources[1]->GetD3D11Texture());
|
||||
UnlockD3DTexture(mTextureSources[2]->GetD3D11Texture());
|
||||
mIsLocked = false;
|
||||
}
|
||||
|
||||
bool DXGIYCbCrTextureHostD3D11::BindTextureSource(
|
||||
CompositableTextureSourceRef& aTexture) {
|
||||
MOZ_ASSERT(mIsLocked);
|
||||
// If Lock was successful we must have a valid TextureSource.
|
||||
MOZ_ASSERT(mTextureSources[0] && mTextureSources[1] && mTextureSources[2]);
|
||||
aTexture = mTextureSources[0].get();
|
||||
return !!aTexture;
|
||||
}
|
||||
bool DXGIYCbCrTextureHostD3D11::EnsureTextureSource() { return false; }
|
||||
|
||||
void DXGIYCbCrTextureHostD3D11::CreateRenderTexture(
|
||||
const wr::ExternalImageId& aExternalImageId) {
|
||||
@ -1373,15 +1225,6 @@ bool DXGIYCbCrTextureHostD3D11::SupportsExternalCompositing(
|
||||
return aBackend == WebRenderBackend::SOFTWARE;
|
||||
}
|
||||
|
||||
bool DXGIYCbCrTextureHostD3D11::AcquireTextureSource(
|
||||
CompositableTextureSourceRef& aTexture) {
|
||||
if (!EnsureTextureSource()) {
|
||||
return false;
|
||||
}
|
||||
aTexture = mTextureSources[0].get();
|
||||
return !!aTexture;
|
||||
}
|
||||
|
||||
bool DataTextureSourceD3D11::Update(DataSourceSurface* aSurface,
|
||||
nsIntRegion* aDestRegion,
|
||||
IntPoint* aSrcOffset,
|
||||
|
@ -326,18 +326,10 @@ class DXGITextureHostD3D11 : public TextureHost {
|
||||
DXGITextureHostD3D11(TextureFlags aFlags,
|
||||
const SurfaceDescriptorD3D10& aDescriptor);
|
||||
|
||||
bool BindTextureSource(CompositableTextureSourceRef& aTexture) override;
|
||||
bool AcquireTextureSource(CompositableTextureSourceRef& aTexture) override;
|
||||
|
||||
void DeallocateDeviceData() override {}
|
||||
|
||||
void SetTextureSourceProvider(TextureSourceProvider* aProvider) override;
|
||||
|
||||
gfx::SurfaceFormat GetFormat() const override { return mFormat; }
|
||||
|
||||
bool Lock() override;
|
||||
void Unlock() override;
|
||||
|
||||
bool LockWithoutCompositor() override;
|
||||
void UnlockWithoutCompositor() override;
|
||||
|
||||
@ -393,13 +385,8 @@ class DXGIYCbCrTextureHostD3D11 : public TextureHost {
|
||||
DXGIYCbCrTextureHostD3D11(TextureFlags aFlags,
|
||||
const SurfaceDescriptorDXGIYCbCr& aDescriptor);
|
||||
|
||||
bool BindTextureSource(CompositableTextureSourceRef& aTexture) override;
|
||||
bool AcquireTextureSource(CompositableTextureSourceRef& aTexture) override;
|
||||
|
||||
void DeallocateDeviceData() override {}
|
||||
|
||||
void SetTextureSourceProvider(TextureSourceProvider* aProvider) override;
|
||||
|
||||
gfx::SurfaceFormat GetFormat() const override {
|
||||
return gfx::SurfaceFormat::YUV;
|
||||
}
|
||||
@ -410,10 +397,6 @@ class DXGIYCbCrTextureHostD3D11 : public TextureHost {
|
||||
}
|
||||
gfx::ColorRange GetColorRange() const override { return mColorRange; }
|
||||
|
||||
bool Lock() override;
|
||||
|
||||
void Unlock() override;
|
||||
|
||||
gfx::IntSize GetSize() const override { return mSize; }
|
||||
|
||||
already_AddRefed<gfx::DataSourceSurface> GetAsSurface() override {
|
||||
|
@ -422,12 +422,6 @@ void ImageBridgeParent::NotifyNotUsed(PTextureParent* aTexture,
|
||||
MOZ_ASSERT(texture->GetFlags() & TextureFlags::RECYCLE);
|
||||
|
||||
Maybe<FileDescriptor> fenceFd = Some(FileDescriptor());
|
||||
auto* compositor = texture->GetProvider()
|
||||
? texture->GetProvider()->AsCompositorOGL()
|
||||
: nullptr;
|
||||
if (compositor) {
|
||||
fenceFd = Some(compositor->GetReleaseFence());
|
||||
}
|
||||
|
||||
auto* wrTexture = texture->AsWebRenderTextureHost();
|
||||
if (wrTexture) {
|
||||
@ -476,13 +470,7 @@ void ImageBridgeParent::NotifyBufferNotUsedOfCompositorBridge(
|
||||
MOZ_ASSERT(aTexture->GetAndroidHardwareBuffer());
|
||||
|
||||
#ifdef MOZ_WIDGET_ANDROID
|
||||
auto* compositor = aTexture->GetProvider()
|
||||
? aTexture->GetProvider()->AsCompositorOGL()
|
||||
: nullptr;
|
||||
Maybe<FileDescriptor> fenceFd = Some(FileDescriptor());
|
||||
if (compositor) {
|
||||
fenceFd = Some(compositor->GetReleaseFence());
|
||||
}
|
||||
|
||||
auto* wrTexture = aTexture->AsWebRenderTextureHost();
|
||||
if (wrTexture) {
|
||||
|
@ -250,10 +250,6 @@ void CompositorOGL::Destroy() {
|
||||
mTexturePool = nullptr;
|
||||
}
|
||||
|
||||
#ifdef XP_DARWIN
|
||||
mMaybeUnlockBeforeNextComposition.Clear();
|
||||
#endif
|
||||
|
||||
if (!mDestroyed) {
|
||||
mDestroyed = true;
|
||||
CleanupResources();
|
||||
@ -1631,97 +1627,6 @@ already_AddRefed<DataTextureSource> CompositorOGL::CreateDataTextureSource(
|
||||
return MakeAndAddRef<TextureImageTextureSourceOGL>(this, aFlags);
|
||||
}
|
||||
|
||||
already_AddRefed<DataTextureSource>
|
||||
CompositorOGL::CreateDataTextureSourceAroundYCbCr(TextureHost* aTexture) {
|
||||
if (!gl()) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
BufferTextureHost* bufferTexture = aTexture->AsBufferTextureHost();
|
||||
MOZ_ASSERT(bufferTexture);
|
||||
|
||||
if (!bufferTexture) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
uint8_t* buf = bufferTexture->GetBuffer();
|
||||
const BufferDescriptor& buffDesc = bufferTexture->GetBufferDescriptor();
|
||||
const YCbCrDescriptor& desc = buffDesc.get_YCbCrDescriptor();
|
||||
|
||||
RefPtr<gfx::DataSourceSurface> tempY =
|
||||
gfx::Factory::CreateWrappingDataSourceSurface(
|
||||
ImageDataSerializer::GetYChannel(buf, desc), desc.yStride(),
|
||||
desc.ySize(), SurfaceFormatForColorDepth(desc.colorDepth()));
|
||||
if (!tempY) {
|
||||
return nullptr;
|
||||
}
|
||||
RefPtr<gfx::DataSourceSurface> tempCb =
|
||||
gfx::Factory::CreateWrappingDataSourceSurface(
|
||||
ImageDataSerializer::GetCbChannel(buf, desc), desc.cbCrStride(),
|
||||
desc.cbCrSize(), SurfaceFormatForColorDepth(desc.colorDepth()));
|
||||
if (!tempCb) {
|
||||
return nullptr;
|
||||
}
|
||||
RefPtr<gfx::DataSourceSurface> tempCr =
|
||||
gfx::Factory::CreateWrappingDataSourceSurface(
|
||||
ImageDataSerializer::GetCrChannel(buf, desc), desc.cbCrStride(),
|
||||
desc.cbCrSize(), SurfaceFormatForColorDepth(desc.colorDepth()));
|
||||
if (!tempCr) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
RefPtr<DirectMapTextureSource> srcY = new DirectMapTextureSource(this, tempY);
|
||||
RefPtr<DirectMapTextureSource> srcU =
|
||||
new DirectMapTextureSource(this, tempCb);
|
||||
RefPtr<DirectMapTextureSource> srcV =
|
||||
new DirectMapTextureSource(this, tempCr);
|
||||
|
||||
srcY->SetNextSibling(srcU);
|
||||
srcU->SetNextSibling(srcV);
|
||||
|
||||
return srcY.forget();
|
||||
}
|
||||
|
||||
#ifdef XP_DARWIN
|
||||
void CompositorOGL::MaybeUnlockBeforeNextComposition(
|
||||
TextureHost* aTextureHost) {
|
||||
auto bufferTexture = aTextureHost->AsBufferTextureHost();
|
||||
if (bufferTexture) {
|
||||
mMaybeUnlockBeforeNextComposition.AppendElement(bufferTexture);
|
||||
}
|
||||
}
|
||||
|
||||
void CompositorOGL::TryUnlockTextures() {
|
||||
nsClassHashtable<nsUint32HashKey, nsTArray<uint64_t>>
|
||||
texturesIdsToUnlockByPid;
|
||||
for (auto& texture : mMaybeUnlockBeforeNextComposition) {
|
||||
if (texture->IsDirectMap() && texture->CanUnlock()) {
|
||||
texture->ReadUnlock();
|
||||
auto actor = texture->GetIPDLActor();
|
||||
if (actor) {
|
||||
base::ProcessId pid = actor->OtherPid();
|
||||
nsTArray<uint64_t>* textureIds =
|
||||
texturesIdsToUnlockByPid.GetOrInsertNew(pid);
|
||||
textureIds->AppendElement(TextureHost::GetTextureSerial(actor));
|
||||
}
|
||||
}
|
||||
}
|
||||
mMaybeUnlockBeforeNextComposition.Clear();
|
||||
for (const auto& entry : texturesIdsToUnlockByPid) {
|
||||
TextureSync::SetTexturesUnlocked(entry.GetKey(), *entry.GetWeak());
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
already_AddRefed<DataTextureSource>
|
||||
CompositorOGL::CreateDataTextureSourceAround(gfx::DataSourceSurface* aSurface) {
|
||||
if (!gl()) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
return MakeAndAddRef<DirectMapTextureSource>(this, aSurface);
|
||||
}
|
||||
|
||||
int32_t CompositorOGL::GetMaxTextureSize() const {
|
||||
MOZ_ASSERT(mGLContext);
|
||||
GLint texSize = 0;
|
||||
|
@ -124,12 +124,6 @@ class CompositorOGL final : public Compositor {
|
||||
already_AddRefed<DataTextureSource> CreateDataTextureSource(
|
||||
TextureFlags aFlags = TextureFlags::NO_FLAGS) override;
|
||||
|
||||
already_AddRefed<DataTextureSource> CreateDataTextureSourceAroundYCbCr(
|
||||
TextureHost* aTexture) override;
|
||||
|
||||
already_AddRefed<DataTextureSource> CreateDataTextureSourceAround(
|
||||
gfx::DataSourceSurface* aSurface) override;
|
||||
|
||||
bool Initialize(GLContext* aGLContext,
|
||||
RefPtr<ShaderProgramOGLsHolder> aProgramsHolder,
|
||||
nsCString* const out_failureReason);
|
||||
@ -192,11 +186,6 @@ class CompositorOGL final : public Compositor {
|
||||
GLContext* gl() const { return mGLContext; }
|
||||
GLContext* GetGLContext() const override { return mGLContext; }
|
||||
|
||||
#ifdef XP_DARWIN
|
||||
void MaybeUnlockBeforeNextComposition(TextureHost* aTextureHost) override;
|
||||
void TryUnlockTextures() override;
|
||||
#endif
|
||||
|
||||
/**
|
||||
* Clear the program state. This must be called
|
||||
* before operating on the GLContext directly. */
|
||||
@ -255,10 +244,6 @@ class CompositorOGL final : public Compositor {
|
||||
gfx::Matrix4x4 mProjMatrix;
|
||||
bool mCanRenderToDefaultFramebuffer = true;
|
||||
|
||||
#ifdef XP_DARWIN
|
||||
nsTArray<RefPtr<BufferTextureHost>> mMaybeUnlockBeforeNextComposition;
|
||||
#endif
|
||||
|
||||
/** The size of the surface we are rendering to */
|
||||
gfx::IntSize mSurfaceSize;
|
||||
|
||||
|
@ -28,63 +28,6 @@ DMABUFTextureHostOGL::~DMABUFTextureHostOGL() {
|
||||
MOZ_COUNT_DTOR(DMABUFTextureHostOGL);
|
||||
}
|
||||
|
||||
GLTextureSource* DMABUFTextureHostOGL::CreateTextureSourceForPlane(
|
||||
size_t aPlane) {
|
||||
if (!mSurface) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
if (!mSurface->GetTexture(aPlane)) {
|
||||
if (!mSurface->CreateTexture(gl(), aPlane)) {
|
||||
return nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
return new GLTextureSource(
|
||||
mProvider, mSurface->GetTexture(aPlane), LOCAL_GL_TEXTURE_2D,
|
||||
gfx::IntSize(mSurface->GetWidth(aPlane), mSurface->GetHeight(aPlane)),
|
||||
// XXX: This isn't really correct (but isn't used), we should be using the
|
||||
// format of the individual plane, not of the whole buffer.
|
||||
mSurface->GetFormatGL());
|
||||
}
|
||||
|
||||
bool DMABUFTextureHostOGL::Lock() {
|
||||
if (!gl() || !gl()->MakeCurrent() || !mSurface) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!mTextureSource) {
|
||||
mTextureSource = CreateTextureSourceForPlane(0);
|
||||
|
||||
RefPtr<TextureSource> prev = mTextureSource;
|
||||
for (int i = 1; i < mSurface->GetTextureCount(); i++) {
|
||||
RefPtr<TextureSource> next = CreateTextureSourceForPlane(i);
|
||||
prev->SetNextSibling(next);
|
||||
prev = next;
|
||||
}
|
||||
}
|
||||
|
||||
mSurface->FenceWait();
|
||||
return true;
|
||||
}
|
||||
|
||||
void DMABUFTextureHostOGL::Unlock() {}
|
||||
|
||||
void DMABUFTextureHostOGL::SetTextureSourceProvider(
|
||||
TextureSourceProvider* aProvider) {
|
||||
if (!aProvider || !aProvider->GetGLContext()) {
|
||||
mTextureSource = nullptr;
|
||||
mProvider = nullptr;
|
||||
return;
|
||||
}
|
||||
|
||||
mProvider = aProvider;
|
||||
|
||||
if (mTextureSource) {
|
||||
mTextureSource->SetTextureSourceProvider(aProvider);
|
||||
}
|
||||
}
|
||||
|
||||
gfx::SurfaceFormat DMABUFTextureHostOGL::GetFormat() const {
|
||||
if (!mSurface) {
|
||||
return gfx::SurfaceFormat::UNKNOWN;
|
||||
@ -118,9 +61,7 @@ gfx::IntSize DMABUFTextureHostOGL::GetSize() const {
|
||||
return gfx::IntSize(mSurface->GetWidth(), mSurface->GetHeight());
|
||||
}
|
||||
|
||||
gl::GLContext* DMABUFTextureHostOGL::gl() const {
|
||||
return mProvider ? mProvider->GetGLContext() : nullptr;
|
||||
}
|
||||
gl::GLContext* DMABUFTextureHostOGL::gl() const { return nullptr; }
|
||||
|
||||
void DMABUFTextureHostOGL::CreateRenderTexture(
|
||||
const wr::ExternalImageId& aExternalImageId) {
|
||||
|
@ -24,19 +24,10 @@ class DMABUFTextureHostOGL : public TextureHost {
|
||||
DMABUFTextureHostOGL(TextureFlags aFlags, const SurfaceDescriptor& aDesc);
|
||||
virtual ~DMABUFTextureHostOGL();
|
||||
|
||||
void SetTextureSourceProvider(TextureSourceProvider* aProvider) override;
|
||||
|
||||
bool Lock() override;
|
||||
void Unlock() override;
|
||||
bool IsValid() override { return !!mSurface; }
|
||||
|
||||
gfx::SurfaceFormat GetFormat() const override;
|
||||
|
||||
bool BindTextureSource(CompositableTextureSourceRef& aTexture) override {
|
||||
aTexture = mTextureSource;
|
||||
return !!aTexture;
|
||||
}
|
||||
|
||||
already_AddRefed<gfx::DataSourceSurface> GetAsSurface() override {
|
||||
return nullptr; // XXX - implement this (for MOZ_DUMP_PAINTING)
|
||||
}
|
||||
@ -67,9 +58,6 @@ class DMABUFTextureHostOGL : public TextureHost {
|
||||
const Range<wr::ImageKey>& aImageKeys,
|
||||
PushDisplayItemFlagSet aFlags) override;
|
||||
|
||||
private:
|
||||
GLTextureSource* CreateTextureSourceForPlane(size_t aPlane);
|
||||
|
||||
protected:
|
||||
RefPtr<GLTextureSource> mTextureSource;
|
||||
RefPtr<DMABufSurface> mSurface;
|
||||
|
@ -31,66 +31,6 @@ MacIOSurfaceTextureHostOGL::~MacIOSurfaceTextureHostOGL() {
|
||||
MOZ_COUNT_DTOR(MacIOSurfaceTextureHostOGL);
|
||||
}
|
||||
|
||||
GLTextureSource* MacIOSurfaceTextureHostOGL::CreateTextureSourceForPlane(
|
||||
size_t aPlane) {
|
||||
MOZ_ASSERT(mSurface);
|
||||
|
||||
GLuint textureHandle;
|
||||
gl::GLContext* gl = mProvider->GetGLContext();
|
||||
gl->fGenTextures(1, &textureHandle);
|
||||
gl->fBindTexture(LOCAL_GL_TEXTURE_RECTANGLE_ARB, textureHandle);
|
||||
gl->fTexParameteri(LOCAL_GL_TEXTURE_RECTANGLE_ARB, LOCAL_GL_TEXTURE_WRAP_T,
|
||||
LOCAL_GL_CLAMP_TO_EDGE);
|
||||
gl->fTexParameteri(LOCAL_GL_TEXTURE_RECTANGLE_ARB, LOCAL_GL_TEXTURE_WRAP_S,
|
||||
LOCAL_GL_CLAMP_TO_EDGE);
|
||||
|
||||
gfx::SurfaceFormat readFormat = gfx::SurfaceFormat::UNKNOWN;
|
||||
mSurface->CGLTexImageIOSurface2D(
|
||||
gl, gl::GLContextCGL::Cast(gl)->GetCGLContext(), aPlane, &readFormat);
|
||||
// With compositorOGL, we doesn't support the yuv interleaving format yet.
|
||||
MOZ_ASSERT(readFormat != gfx::SurfaceFormat::YUV422);
|
||||
|
||||
return new GLTextureSource(
|
||||
mProvider, textureHandle, LOCAL_GL_TEXTURE_RECTANGLE_ARB,
|
||||
gfx::IntSize(mSurface->GetDevicePixelWidth(aPlane),
|
||||
mSurface->GetDevicePixelHeight(aPlane)),
|
||||
readFormat);
|
||||
}
|
||||
|
||||
bool MacIOSurfaceTextureHostOGL::Lock() {
|
||||
if (!gl() || !gl()->MakeCurrent() || !mSurface) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!mTextureSource) {
|
||||
mTextureSource = CreateTextureSourceForPlane(0);
|
||||
|
||||
RefPtr<TextureSource> prev = mTextureSource;
|
||||
for (size_t i = 1; i < mSurface->GetPlaneCount(); i++) {
|
||||
RefPtr<TextureSource> next = CreateTextureSourceForPlane(i);
|
||||
prev->SetNextSibling(next);
|
||||
prev = next;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void MacIOSurfaceTextureHostOGL::SetTextureSourceProvider(
|
||||
TextureSourceProvider* aProvider) {
|
||||
if (!aProvider || !aProvider->GetGLContext()) {
|
||||
mTextureSource = nullptr;
|
||||
mProvider = nullptr;
|
||||
return;
|
||||
}
|
||||
|
||||
if (mProvider != aProvider) {
|
||||
// Cannot share GL texture identifiers across compositors.
|
||||
mTextureSource = nullptr;
|
||||
}
|
||||
|
||||
mProvider = aProvider;
|
||||
}
|
||||
|
||||
gfx::SurfaceFormat MacIOSurfaceTextureHostOGL::GetFormat() const {
|
||||
if (!mSurface) {
|
||||
return gfx::SurfaceFormat::UNKNOWN;
|
||||
@ -113,9 +53,7 @@ gfx::IntSize MacIOSurfaceTextureHostOGL::GetSize() const {
|
||||
mSurface->GetDevicePixelHeight());
|
||||
}
|
||||
|
||||
gl::GLContext* MacIOSurfaceTextureHostOGL::gl() const {
|
||||
return mProvider ? mProvider->GetGLContext() : nullptr;
|
||||
}
|
||||
gl::GLContext* MacIOSurfaceTextureHostOGL::gl() const { return nullptr; }
|
||||
|
||||
gfx::YUVColorSpace MacIOSurfaceTextureHostOGL::GetYUVColorSpace() const {
|
||||
if (!mSurface) {
|
||||
|
@ -31,18 +31,9 @@ class MacIOSurfaceTextureHostOGL : public TextureHost {
|
||||
// MacIOSurfaceTextureSourceOGL doesn't own any GL texture
|
||||
void DeallocateDeviceData() override {}
|
||||
|
||||
void SetTextureSourceProvider(TextureSourceProvider* aProvider) override;
|
||||
|
||||
bool Lock() override;
|
||||
|
||||
gfx::SurfaceFormat GetFormat() const override;
|
||||
gfx::SurfaceFormat GetReadFormat() const override;
|
||||
|
||||
bool BindTextureSource(CompositableTextureSourceRef& aTexture) override {
|
||||
aTexture = mTextureSource;
|
||||
return !!aTexture;
|
||||
}
|
||||
|
||||
already_AddRefed<gfx::DataSourceSurface> GetAsSurface() override {
|
||||
RefPtr<gfx::SourceSurface> surf =
|
||||
CreateSourceSurfaceFromMacIOSurface(GetMacIOSurface());
|
||||
@ -83,8 +74,6 @@ class MacIOSurfaceTextureHostOGL : public TextureHost {
|
||||
gfx::ColorRange GetColorRange() const override;
|
||||
|
||||
protected:
|
||||
GLTextureSource* CreateTextureSourceForPlane(size_t aPlane);
|
||||
|
||||
RefPtr<GLTextureSource> mTextureSource;
|
||||
RefPtr<MacIOSurface> mSurface;
|
||||
};
|
||||
|
@ -228,27 +228,6 @@ void TextureImageTextureSourceOGL::EnsureBuffer(const IntSize& aSize,
|
||||
mTexImage->Resize(aSize);
|
||||
}
|
||||
|
||||
void TextureImageTextureSourceOGL::SetTextureSourceProvider(
|
||||
TextureSourceProvider* aProvider) {
|
||||
GLContext* newGL = aProvider ? aProvider->GetGLContext() : nullptr;
|
||||
if (!newGL || mGL != newGL) {
|
||||
DeallocateDeviceData();
|
||||
}
|
||||
mGL = newGL;
|
||||
|
||||
CompositorOGL* compositor =
|
||||
aProvider ? aProvider->AsCompositorOGL() : nullptr;
|
||||
if (mCompositor != compositor) {
|
||||
if (mCompositor) {
|
||||
mCompositor->UnregisterTextureSource(this);
|
||||
}
|
||||
if (compositor) {
|
||||
compositor->RegisterTextureSource(this);
|
||||
}
|
||||
mCompositor = compositor;
|
||||
}
|
||||
}
|
||||
|
||||
gfx::IntSize TextureImageTextureSourceOGL::GetSize() const {
|
||||
if (mTexImage) {
|
||||
if (mIterating) {
|
||||
@ -328,21 +307,6 @@ void GLTextureSource::BindTexture(GLenum aTextureUnit,
|
||||
ApplySamplingFilterToBoundTexture(gl, aSamplingFilter, mTextureTarget);
|
||||
}
|
||||
|
||||
void GLTextureSource::SetTextureSourceProvider(
|
||||
TextureSourceProvider* aProvider) {
|
||||
GLContext* newGL = aProvider ? aProvider->GetGLContext() : nullptr;
|
||||
if (!newGL) {
|
||||
mGL = newGL;
|
||||
} else if (mGL != newGL) {
|
||||
gfxCriticalError()
|
||||
<< "GLTextureSource does not support changing compositors";
|
||||
}
|
||||
|
||||
if (mNextSibling) {
|
||||
mNextSibling->SetTextureSourceProvider(aProvider);
|
||||
}
|
||||
}
|
||||
|
||||
bool GLTextureSource::IsValid() const { return !!gl() && mTextureHandle != 0; }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
@ -497,17 +461,6 @@ void SurfaceTextureSource::BindTexture(GLenum aTextureUnit,
|
||||
ApplySamplingFilterToBoundTexture(gl, aSamplingFilter, mTextureTarget);
|
||||
}
|
||||
|
||||
void SurfaceTextureSource::SetTextureSourceProvider(
|
||||
TextureSourceProvider* aProvider) {
|
||||
GLContext* newGL = aProvider->GetGLContext();
|
||||
if (!newGL || mGL != newGL) {
|
||||
DeallocateDeviceData();
|
||||
return;
|
||||
}
|
||||
|
||||
mGL = newGL;
|
||||
}
|
||||
|
||||
bool SurfaceTextureSource::IsValid() const { return !!gl(); }
|
||||
|
||||
gfx::Matrix4x4 SurfaceTextureSource::GetTextureTransform() {
|
||||
@ -559,24 +512,7 @@ SurfaceTextureHost::~SurfaceTextureHost() {
|
||||
}
|
||||
}
|
||||
|
||||
void SurfaceTextureHost::PrepareTextureSource(
|
||||
CompositableTextureSourceRef& aTexture) {
|
||||
if (!mContinuousUpdate && mSurfTex) {
|
||||
if (!EnsureAttached()) {
|
||||
return;
|
||||
}
|
||||
|
||||
// UpdateTexImage() advances the internal buffer queue, so we only want to
|
||||
// call this once per transactionwhen we are not in continuous mode (as we
|
||||
// are here). Otherwise, the SurfaceTexture content will be de-synced from
|
||||
// the rest of the page in subsequent compositor passes.
|
||||
mSurfTex->UpdateTexImage();
|
||||
}
|
||||
}
|
||||
|
||||
gl::GLContext* SurfaceTextureHost::gl() const {
|
||||
return mProvider ? mProvider->GetGLContext() : nullptr;
|
||||
}
|
||||
gl::GLContext* SurfaceTextureHost::gl() const { return nullptr; }
|
||||
|
||||
bool SurfaceTextureHost::EnsureAttached() {
|
||||
GLContext* gl = this->gl();
|
||||
@ -599,42 +535,6 @@ bool SurfaceTextureHost::EnsureAttached() {
|
||||
return true;
|
||||
}
|
||||
|
||||
bool SurfaceTextureHost::Lock() {
|
||||
if (!EnsureAttached()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (mContinuousUpdate) {
|
||||
mSurfTex->UpdateTexImage();
|
||||
}
|
||||
|
||||
if (!mTextureSource) {
|
||||
GLenum target =
|
||||
LOCAL_GL_TEXTURE_EXTERNAL; // This is required by SurfaceTexture
|
||||
GLenum wrapMode = LOCAL_GL_CLAMP_TO_EDGE;
|
||||
mTextureSource =
|
||||
new SurfaceTextureSource(mProvider, mSurfTex, mFormat, target, wrapMode,
|
||||
mSize, mIgnoreTransform);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void SurfaceTextureHost::SetTextureSourceProvider(
|
||||
TextureSourceProvider* aProvider) {
|
||||
if (mProvider != aProvider) {
|
||||
if (!aProvider || !aProvider->GetGLContext()) {
|
||||
DeallocateDeviceData();
|
||||
return;
|
||||
}
|
||||
mProvider = aProvider;
|
||||
}
|
||||
|
||||
if (mTextureSource) {
|
||||
mTextureSource->SetTextureSourceProvider(aProvider);
|
||||
}
|
||||
}
|
||||
|
||||
void SurfaceTextureHost::NotifyNotUsed() {
|
||||
if (mSurfTex && mSurfTex->IsSingleBuffer()) {
|
||||
if (!EnsureAttached()) {
|
||||
@ -779,149 +679,7 @@ void AndroidHardwareBufferTextureHost::DestroyEGLImage() {
|
||||
}
|
||||
}
|
||||
|
||||
void AndroidHardwareBufferTextureHost::PrepareTextureSource(
|
||||
CompositableTextureSourceRef& aTextureSource) {
|
||||
MOZ_ASSERT(mAndroidHardwareBuffer);
|
||||
|
||||
if (!mAndroidHardwareBuffer) {
|
||||
mTextureSource = nullptr;
|
||||
return;
|
||||
}
|
||||
|
||||
if (mTextureSource) {
|
||||
// We are already attached to a TextureSource, nothing to do except tell
|
||||
// the compositable to use it.
|
||||
aTextureSource = mTextureSource;
|
||||
return;
|
||||
}
|
||||
|
||||
if (!gl() || !gl()->MakeCurrent()) {
|
||||
mTextureSource = nullptr;
|
||||
return;
|
||||
}
|
||||
|
||||
if (!mEGLImage) {
|
||||
// XXX add crop handling for video
|
||||
// Should only happen the first time.
|
||||
const auto& gle = gl::GLContextEGL::Cast(gl());
|
||||
const auto& egl = gle->mEgl;
|
||||
|
||||
const EGLint attrs[] = {
|
||||
LOCAL_EGL_IMAGE_PRESERVED,
|
||||
LOCAL_EGL_TRUE,
|
||||
LOCAL_EGL_NONE,
|
||||
LOCAL_EGL_NONE,
|
||||
};
|
||||
|
||||
EGLClientBuffer clientBuffer = egl->mLib->fGetNativeClientBufferANDROID(
|
||||
mAndroidHardwareBuffer->GetNativeBuffer());
|
||||
mEGLImage = egl->fCreateImage(
|
||||
EGL_NO_CONTEXT, LOCAL_EGL_NATIVE_BUFFER_ANDROID, clientBuffer, attrs);
|
||||
}
|
||||
|
||||
GLenum textureTarget = LOCAL_GL_TEXTURE_EXTERNAL;
|
||||
GLTextureSource* glSource =
|
||||
aTextureSource ? aTextureSource->AsSourceOGL()->AsGLTextureSource()
|
||||
: nullptr;
|
||||
|
||||
bool shouldCreateTextureSource =
|
||||
!glSource || !glSource->IsValid() ||
|
||||
glSource->NumCompositableRefs() > 1 ||
|
||||
glSource->GetTextureTarget() != textureTarget;
|
||||
|
||||
if (shouldCreateTextureSource) {
|
||||
GLuint textureHandle;
|
||||
gl()->fGenTextures(1, &textureHandle);
|
||||
gl()->fBindTexture(textureTarget, textureHandle);
|
||||
gl()->fTexParameteri(textureTarget, LOCAL_GL_TEXTURE_WRAP_T,
|
||||
LOCAL_GL_CLAMP_TO_EDGE);
|
||||
gl()->fTexParameteri(textureTarget, LOCAL_GL_TEXTURE_WRAP_S,
|
||||
LOCAL_GL_CLAMP_TO_EDGE);
|
||||
gl()->fEGLImageTargetTexture2D(textureTarget, mEGLImage);
|
||||
|
||||
mTextureSource = new GLTextureSource(mProvider, textureHandle,
|
||||
textureTarget, GetSize(), GetFormat());
|
||||
aTextureSource = mTextureSource;
|
||||
} else {
|
||||
gl()->fBindTexture(textureTarget, glSource->GetTextureHandle());
|
||||
gl()->fEGLImageTargetTexture2D(textureTarget, mEGLImage);
|
||||
glSource->SetSize(GetSize());
|
||||
glSource->SetFormat(GetFormat());
|
||||
mTextureSource = glSource;
|
||||
}
|
||||
}
|
||||
|
||||
bool AndroidHardwareBufferTextureHost::BindTextureSource(
|
||||
CompositableTextureSourceRef& aTextureSource) {
|
||||
// This happens at composition time.
|
||||
|
||||
// If mTextureSource is null it means PrepareTextureSource failed.
|
||||
if (!mTextureSource) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// If Prepare didn't fail, we expect our TextureSource to be the same as
|
||||
// aTextureSource, otherwise it means something has fiddled with the
|
||||
// TextureSource between Prepare and now.
|
||||
MOZ_ASSERT(mTextureSource == aTextureSource);
|
||||
aTextureSource = mTextureSource;
|
||||
|
||||
// XXX Acquire Fence Handling
|
||||
return true;
|
||||
}
|
||||
|
||||
gl::GLContext* AndroidHardwareBufferTextureHost::gl() const {
|
||||
return mProvider ? mProvider->GetGLContext() : nullptr;
|
||||
}
|
||||
|
||||
bool AndroidHardwareBufferTextureHost::Lock() {
|
||||
if (!mAndroidHardwareBuffer) {
|
||||
return false;
|
||||
}
|
||||
|
||||
auto fenceFd = mAndroidHardwareBuffer->GetAndResetAcquireFence();
|
||||
if (fenceFd.IsValid()) {
|
||||
const auto& gle = gl::GLContextEGL::Cast(gl());
|
||||
const auto& egl = gle->mEgl;
|
||||
|
||||
auto rawFD = fenceFd.TakePlatformHandle();
|
||||
const EGLint attribs[] = {LOCAL_EGL_SYNC_NATIVE_FENCE_FD_ANDROID,
|
||||
rawFD.get(), LOCAL_EGL_NONE};
|
||||
|
||||
EGLSync sync =
|
||||
egl->fCreateSync(LOCAL_EGL_SYNC_NATIVE_FENCE_ANDROID, attribs);
|
||||
if (sync) {
|
||||
// Release fd here, since it is owned by EGLSync
|
||||
Unused << rawFD.release();
|
||||
|
||||
if (egl->IsExtensionSupported(gl::EGLExtension::KHR_wait_sync)) {
|
||||
egl->fWaitSync(sync, 0);
|
||||
} else {
|
||||
egl->fClientWaitSync(sync, 0, LOCAL_EGL_FOREVER);
|
||||
}
|
||||
egl->fDestroySync(sync);
|
||||
} else {
|
||||
gfxCriticalNote << "Failed to create EGLSync from acquire fence fd";
|
||||
}
|
||||
}
|
||||
|
||||
return mTextureSource && mTextureSource->IsValid();
|
||||
}
|
||||
|
||||
void AndroidHardwareBufferTextureHost::SetTextureSourceProvider(
|
||||
TextureSourceProvider* aProvider) {
|
||||
if (mProvider != aProvider) {
|
||||
if (!aProvider || !aProvider->GetGLContext()) {
|
||||
DeallocateDeviceData();
|
||||
return;
|
||||
}
|
||||
mProvider = aProvider;
|
||||
}
|
||||
|
||||
if (mTextureSource) {
|
||||
mTextureSource->SetTextureSourceProvider(aProvider);
|
||||
}
|
||||
}
|
||||
gl::GLContext* AndroidHardwareBufferTextureHost::gl() const { return nullptr; }
|
||||
|
||||
void AndroidHardwareBufferTextureHost::NotifyNotUsed() {
|
||||
// XXX Add android fence handling
|
||||
@ -1055,7 +813,6 @@ EGLImageTextureSource::EGLImageTextureSource(TextureSourceProvider* aProvider,
|
||||
mSize(aSize) {
|
||||
MOZ_ASSERT(mTextureTarget == LOCAL_GL_TEXTURE_2D ||
|
||||
mTextureTarget == LOCAL_GL_TEXTURE_EXTERNAL);
|
||||
SetTextureSourceProvider(aProvider);
|
||||
}
|
||||
|
||||
void EGLImageTextureSource::BindTexture(GLenum aTextureUnit,
|
||||
@ -1088,24 +845,6 @@ void EGLImageTextureSource::BindTexture(GLenum aTextureUnit,
|
||||
ApplySamplingFilterToBoundTexture(gl, aSamplingFilter, mTextureTarget);
|
||||
}
|
||||
|
||||
void EGLImageTextureSource::SetTextureSourceProvider(
|
||||
TextureSourceProvider* aProvider) {
|
||||
if (mCompositor == aProvider) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!aProvider) {
|
||||
mGL = nullptr;
|
||||
mCompositor = nullptr;
|
||||
return;
|
||||
}
|
||||
|
||||
mGL = aProvider->GetGLContext();
|
||||
if (Compositor* compositor = aProvider->AsCompositor()) {
|
||||
mCompositor = compositor->AsCompositorOGL();
|
||||
}
|
||||
}
|
||||
|
||||
bool EGLImageTextureSource::IsValid() const { return !!gl(); }
|
||||
|
||||
gfx::Matrix4x4 EGLImageTextureSource::GetTextureTransform() {
|
||||
@ -1126,62 +865,7 @@ EGLImageTextureHost::EGLImageTextureHost(TextureFlags aFlags, EGLImage aImage,
|
||||
|
||||
EGLImageTextureHost::~EGLImageTextureHost() = default;
|
||||
|
||||
gl::GLContext* EGLImageTextureHost::gl() const {
|
||||
return mProvider ? mProvider->GetGLContext() : nullptr;
|
||||
}
|
||||
|
||||
bool EGLImageTextureHost::Lock() {
|
||||
GLContext* gl = this->gl();
|
||||
if (!gl || !gl->MakeCurrent()) {
|
||||
return false;
|
||||
}
|
||||
const auto& gle = GLContextEGL::Cast(gl);
|
||||
const auto& egl = gle->mEgl;
|
||||
|
||||
EGLint status = LOCAL_EGL_CONDITION_SATISFIED;
|
||||
|
||||
if (mSync) {
|
||||
MOZ_ASSERT(egl->IsExtensionSupported(EGLExtension::KHR_fence_sync));
|
||||
// XXX eglWaitSyncKHR() is better api. Bug 1660434 is going to fix it.
|
||||
status = egl->fClientWaitSync(mSync, 0, LOCAL_EGL_FOREVER);
|
||||
}
|
||||
|
||||
if (status != LOCAL_EGL_CONDITION_SATISFIED) {
|
||||
MOZ_ASSERT(
|
||||
status != 0,
|
||||
"ClientWaitSync generated an error. Has mSync already been destroyed?");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!mTextureSource) {
|
||||
gfx::SurfaceFormat format =
|
||||
mHasAlpha ? gfx::SurfaceFormat::R8G8B8A8 : gfx::SurfaceFormat::R8G8B8X8;
|
||||
GLenum target = gl->GetPreferredEGLImageTextureTarget();
|
||||
GLenum wrapMode = LOCAL_GL_CLAMP_TO_EDGE;
|
||||
mTextureSource = new EGLImageTextureSource(mProvider, mImage, format,
|
||||
target, wrapMode, mSize);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void EGLImageTextureHost::Unlock() {}
|
||||
|
||||
void EGLImageTextureHost::SetTextureSourceProvider(
|
||||
TextureSourceProvider* aProvider) {
|
||||
if (mProvider != aProvider) {
|
||||
if (!aProvider || !aProvider->GetGLContext()) {
|
||||
mProvider = nullptr;
|
||||
mTextureSource = nullptr;
|
||||
return;
|
||||
}
|
||||
mProvider = aProvider;
|
||||
}
|
||||
|
||||
if (mTextureSource) {
|
||||
mTextureSource->SetTextureSourceProvider(aProvider);
|
||||
}
|
||||
}
|
||||
gl::GLContext* EGLImageTextureHost::gl() const { return nullptr; }
|
||||
|
||||
gfx::SurfaceFormat EGLImageTextureHost::GetFormat() const {
|
||||
MOZ_ASSERT(mTextureSource);
|
||||
@ -1245,49 +929,7 @@ GLTextureHost::GLTextureHost(TextureFlags aFlags, GLuint aTextureHandle,
|
||||
|
||||
GLTextureHost::~GLTextureHost() = default;
|
||||
|
||||
gl::GLContext* GLTextureHost::gl() const {
|
||||
return mProvider ? mProvider->GetGLContext() : nullptr;
|
||||
}
|
||||
|
||||
bool GLTextureHost::Lock() {
|
||||
GLContext* gl = this->gl();
|
||||
if (!gl || !gl->MakeCurrent()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (mSync) {
|
||||
if (!gl->MakeCurrent()) {
|
||||
return false;
|
||||
}
|
||||
gl->fWaitSync(mSync, 0, LOCAL_GL_TIMEOUT_IGNORED);
|
||||
gl->fDeleteSync(mSync);
|
||||
mSync = 0;
|
||||
}
|
||||
|
||||
if (!mTextureSource) {
|
||||
gfx::SurfaceFormat format =
|
||||
mHasAlpha ? gfx::SurfaceFormat::R8G8B8A8 : gfx::SurfaceFormat::R8G8B8X8;
|
||||
mTextureSource =
|
||||
new GLTextureSource(mProvider, mTexture, mTarget, mSize, format);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void GLTextureHost::SetTextureSourceProvider(TextureSourceProvider* aProvider) {
|
||||
if (mProvider != aProvider) {
|
||||
if (!aProvider || !aProvider->GetGLContext()) {
|
||||
mProvider = nullptr;
|
||||
mTextureSource = nullptr;
|
||||
return;
|
||||
}
|
||||
mProvider = aProvider;
|
||||
}
|
||||
|
||||
if (mTextureSource) {
|
||||
mTextureSource->SetTextureSourceProvider(aProvider);
|
||||
}
|
||||
}
|
||||
gl::GLContext* GLTextureHost::gl() const { return nullptr; }
|
||||
|
||||
gfx::SurfaceFormat GLTextureHost::GetFormat() const {
|
||||
MOZ_ASSERT(mTextureSource);
|
||||
|
@ -175,8 +175,6 @@ class TextureImageTextureSourceOGL final : public DataTextureSource,
|
||||
|
||||
bool IsValid() const override { return !!mTexImage; }
|
||||
|
||||
void SetTextureSourceProvider(TextureSourceProvider* aProvider) override;
|
||||
|
||||
GLenum GetWrapMode() const override { return mTexImage->GetWrapMode(); }
|
||||
|
||||
// BigImageIterator
|
||||
@ -248,8 +246,6 @@ class GLTextureSource : public DataTextureSource, public TextureSourceOGL {
|
||||
|
||||
void DeallocateDeviceData() override;
|
||||
|
||||
void SetTextureSourceProvider(TextureSourceProvider* aProvider) override;
|
||||
|
||||
void SetSize(gfx::IntSize aSize) { mSize = aSize; }
|
||||
|
||||
void SetFormat(gfx::SurfaceFormat aFormat) { mFormat = aFormat; }
|
||||
@ -294,8 +290,6 @@ class DirectMapTextureSource : public GLTextureSource {
|
||||
gfx::IntPoint* aSrcOffset = nullptr,
|
||||
gfx::IntPoint* aDstOffset = nullptr) override;
|
||||
|
||||
bool IsDirectMap() override { return true; }
|
||||
|
||||
// If aBlocking is false, check if this texture is no longer being used
|
||||
// by the GPU - if aBlocking is true, this will block until the GPU is
|
||||
// done with it.
|
||||
@ -321,19 +315,8 @@ class GLTextureHost : public TextureHost {
|
||||
// We don't own anything.
|
||||
void DeallocateDeviceData() override {}
|
||||
|
||||
void SetTextureSourceProvider(TextureSourceProvider* aProvider) override;
|
||||
|
||||
bool Lock() override;
|
||||
|
||||
void Unlock() override {}
|
||||
|
||||
gfx::SurfaceFormat GetFormat() const override;
|
||||
|
||||
bool BindTextureSource(CompositableTextureSourceRef& aTexture) override {
|
||||
aTexture = mTextureSource;
|
||||
return !!aTexture;
|
||||
}
|
||||
|
||||
already_AddRefed<gfx::DataSourceSurface> GetAsSurface() override {
|
||||
return nullptr; // XXX - implement this (for MOZ_DUMP_PAINTING)
|
||||
}
|
||||
@ -387,8 +370,6 @@ class SurfaceTextureSource : public TextureSource, public TextureSourceOGL {
|
||||
|
||||
void DeallocateDeviceData() override;
|
||||
|
||||
void SetTextureSourceProvider(TextureSourceProvider* aProvider) override;
|
||||
|
||||
gl::GLContext* gl() const { return mGL; }
|
||||
|
||||
protected:
|
||||
@ -410,23 +391,12 @@ class SurfaceTextureHost : public TextureHost {
|
||||
|
||||
virtual ~SurfaceTextureHost();
|
||||
|
||||
void PrepareTextureSource(CompositableTextureSourceRef& aTexture) override;
|
||||
|
||||
void DeallocateDeviceData() override;
|
||||
|
||||
void SetTextureSourceProvider(TextureSourceProvider* aProvider) override;
|
||||
|
||||
bool Lock() override;
|
||||
|
||||
gfx::SurfaceFormat GetFormat() const override;
|
||||
|
||||
void NotifyNotUsed() override;
|
||||
|
||||
bool BindTextureSource(CompositableTextureSourceRef& aTexture) override {
|
||||
aTexture = mTextureSource;
|
||||
return !!aTexture;
|
||||
}
|
||||
|
||||
already_AddRefed<gfx::DataSourceSurface> GetAsSurface() override {
|
||||
return nullptr; // XXX - implement this (for MOZ_DUMP_PAINTING)
|
||||
}
|
||||
@ -484,17 +454,8 @@ class AndroidHardwareBufferTextureHost : public TextureHost {
|
||||
|
||||
virtual ~AndroidHardwareBufferTextureHost();
|
||||
|
||||
void PrepareTextureSource(
|
||||
CompositableTextureSourceRef& aTextureSource) override;
|
||||
|
||||
bool BindTextureSource(CompositableTextureSourceRef& aTexture) override;
|
||||
|
||||
void DeallocateDeviceData() override;
|
||||
|
||||
void SetTextureSourceProvider(TextureSourceProvider* aProvider) override;
|
||||
|
||||
bool Lock() override;
|
||||
|
||||
gfx::SurfaceFormat GetFormat() const override;
|
||||
|
||||
gfx::IntSize GetSize() const override;
|
||||
@ -585,8 +546,6 @@ class EGLImageTextureSource : public TextureSource, public TextureSourceOGL {
|
||||
// We don't own anything.
|
||||
void DeallocateDeviceData() override {}
|
||||
|
||||
void SetTextureSourceProvider(TextureSourceProvider* aProvider) override;
|
||||
|
||||
gl::GLContext* gl() const { return mGL; }
|
||||
|
||||
protected:
|
||||
@ -609,19 +568,8 @@ class EGLImageTextureHost final : public TextureHost {
|
||||
// We don't own anything.
|
||||
void DeallocateDeviceData() override {}
|
||||
|
||||
void SetTextureSourceProvider(TextureSourceProvider* aProvider) override;
|
||||
|
||||
bool Lock() override;
|
||||
|
||||
void Unlock() override;
|
||||
|
||||
gfx::SurfaceFormat GetFormat() const override;
|
||||
|
||||
bool BindTextureSource(CompositableTextureSourceRef& aTexture) override {
|
||||
aTexture = mTextureSource;
|
||||
return !!aTexture;
|
||||
}
|
||||
|
||||
already_AddRefed<gfx::DataSourceSurface> GetAsSurface() override {
|
||||
return nullptr; // XXX - implement this (for MOZ_DUMP_PAINTING)
|
||||
}
|
||||
|
@ -67,61 +67,6 @@ wr::ExternalImageId WebRenderTextureHost::GetExternalImageKey() {
|
||||
|
||||
bool WebRenderTextureHost::IsValid() { return mWrappedTextureHost->IsValid(); }
|
||||
|
||||
bool WebRenderTextureHost::Lock() {
|
||||
MOZ_ASSERT(mWrappedTextureHost->AsBufferTextureHost());
|
||||
|
||||
if (mWrappedTextureHost->AsBufferTextureHost()) {
|
||||
return mWrappedTextureHost->Lock();
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void WebRenderTextureHost::Unlock() {
|
||||
MOZ_ASSERT(mWrappedTextureHost->AsBufferTextureHost());
|
||||
|
||||
if (mWrappedTextureHost->AsBufferTextureHost()) {
|
||||
mWrappedTextureHost->Unlock();
|
||||
}
|
||||
}
|
||||
|
||||
void WebRenderTextureHost::PrepareTextureSource(
|
||||
CompositableTextureSourceRef& aTexture) {
|
||||
MOZ_ASSERT(mWrappedTextureHost->AsBufferTextureHost());
|
||||
|
||||
if (mWrappedTextureHost->AsBufferTextureHost()) {
|
||||
mWrappedTextureHost->PrepareTextureSource(aTexture);
|
||||
}
|
||||
}
|
||||
|
||||
bool WebRenderTextureHost::BindTextureSource(
|
||||
CompositableTextureSourceRef& aTexture) {
|
||||
MOZ_ASSERT(mWrappedTextureHost->AsBufferTextureHost());
|
||||
|
||||
if (mWrappedTextureHost->AsBufferTextureHost()) {
|
||||
return mWrappedTextureHost->BindTextureSource(aTexture);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void WebRenderTextureHost::UnbindTextureSource() {
|
||||
if (mWrappedTextureHost->AsBufferTextureHost()) {
|
||||
mWrappedTextureHost->UnbindTextureSource();
|
||||
}
|
||||
// Handle read unlock
|
||||
TextureHost::UnbindTextureSource();
|
||||
}
|
||||
|
||||
void WebRenderTextureHost::SetTextureSourceProvider(
|
||||
TextureSourceProvider* aProvider) {
|
||||
// During using WebRender, only BasicCompositor could exist
|
||||
MOZ_ASSERT(!aProvider || aProvider->AsBasicCompositor());
|
||||
MOZ_ASSERT(mWrappedTextureHost->AsBufferTextureHost());
|
||||
|
||||
if (mWrappedTextureHost->AsBufferTextureHost()) {
|
||||
mWrappedTextureHost->SetTextureSourceProvider(aProvider);
|
||||
}
|
||||
}
|
||||
|
||||
already_AddRefed<gfx::DataSourceSurface> WebRenderTextureHost::GetAsSurface() {
|
||||
return mWrappedTextureHost->GetAsSurface();
|
||||
}
|
||||
|
@ -30,15 +30,6 @@ class WebRenderTextureHost : public TextureHost {
|
||||
|
||||
void DeallocateDeviceData() override {}
|
||||
|
||||
bool Lock() override;
|
||||
|
||||
void Unlock() override;
|
||||
|
||||
void PrepareTextureSource(CompositableTextureSourceRef& aTexture) override;
|
||||
bool BindTextureSource(CompositableTextureSourceRef& aTexture) override;
|
||||
void UnbindTextureSource() override;
|
||||
void SetTextureSourceProvider(TextureSourceProvider* aProvider) override;
|
||||
|
||||
gfx::SurfaceFormat GetFormat() const override;
|
||||
|
||||
virtual void NotifyNotUsed() override;
|
||||
|
@ -153,24 +153,6 @@ void TestTextureClientSurface(TextureClient* texture,
|
||||
|
||||
ASSERT_TRUE(host.get() != nullptr);
|
||||
ASSERT_EQ(host->GetFlags(), texture->GetFlags());
|
||||
|
||||
// host read
|
||||
|
||||
// XXX - this can fail because lock tries to upload the texture but it needs a
|
||||
// Compositor to do that. We could add a DummyComposior for testing but I am
|
||||
// not sure it'll be worth it. Maybe always test against a BasicCompositor,
|
||||
// but the latter needs a widget...
|
||||
if (host->Lock()) {
|
||||
RefPtr<mozilla::gfx::DataSourceSurface> hostDataSurface =
|
||||
host->GetAsSurface();
|
||||
|
||||
DataSourceSurface::ScopedMap map(hostDataSurface, DataSourceSurface::READ);
|
||||
RefPtr<gfxImageSurface> hostSurface = new gfxImageSurface(
|
||||
map.GetData(), hostDataSurface->GetSize(), map.GetStride(),
|
||||
SurfaceFormatToImageFormat(hostDataSurface->GetFormat()));
|
||||
AssertSurfacesEqual(surface, hostSurface.get());
|
||||
host->Unlock();
|
||||
}
|
||||
}
|
||||
|
||||
// Same as above, for YCbCr surfaces
|
||||
@ -201,14 +183,6 @@ void TestTextureClientYCbCr(TextureClient* client, PlanarYCbCrData& ycbcrData) {
|
||||
|
||||
ASSERT_TRUE(host.get() != nullptr);
|
||||
ASSERT_EQ(host->GetFlags(), client->GetFlags());
|
||||
|
||||
// host read
|
||||
|
||||
if (host->Lock()) {
|
||||
// This will work iff the compositor is not BasicCompositor
|
||||
ASSERT_EQ(host->GetFormat(), mozilla::gfx::SurfaceFormat::YUV);
|
||||
host->Unlock();
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace layers
|
||||
|
Loading…
Reference in New Issue
Block a user