Bug 1891710: part 2) Enable <Element-outerHTML.html> WPT for Trusted Types. r=smaug
[gecko.git] / gfx / layers / composite / TextureHost.h
blob343ba6f6008c1644d3fc864e8aa46ab52338cb83
1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* vim: set ts=8 sts=2 et sw=2 tw=80: */
3 /* This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
7 #ifndef MOZILLA_GFX_TEXTUREHOST_H
8 #define MOZILLA_GFX_TEXTUREHOST_H
10 #include <stddef.h> // for size_t
11 #include <stdint.h> // for uint64_t, uint32_t, uint8_t
12 #include "mozilla/Assertions.h" // for MOZ_ASSERT, etc
13 #include "mozilla/Attributes.h" // for override
14 #include "mozilla/RefPtr.h" // for RefPtr, already_AddRefed, etc
15 #include "mozilla/dom/ipc/IdType.h"
16 #include "mozilla/gfx/Logging.h"
17 #include "mozilla/gfx/Matrix.h"
18 #include "mozilla/gfx/Point.h" // for IntSize, IntPoint
19 #include "mozilla/gfx/Rect.h"
20 #include "mozilla/gfx/Types.h" // for SurfaceFormat, etc
21 #include "mozilla/ipc/FileDescriptor.h"
22 #include "mozilla/layers/CompositorTypes.h" // for TextureFlags, etc
23 #include "mozilla/layers/LayersTypes.h" // for LayerRenderState, etc
24 #include "mozilla/layers/LayersMessages.h"
25 #include "mozilla/layers/LayersSurfaces.h"
26 #include "mozilla/layers/TextureSourceProvider.h"
27 #include "mozilla/mozalloc.h" // for operator delete
28 #include "mozilla/Range.h"
29 #include "mozilla/UniquePtr.h" // for UniquePtr
30 #include "mozilla/webrender/WebRenderTypes.h"
31 #include "nsCOMPtr.h" // for already_AddRefed
32 #include "nsDebug.h" // for NS_WARNING
33 #include "nsISupportsImpl.h" // for MOZ_COUNT_CTOR, etc
34 #include "nsRect.h"
35 #include "nsRegion.h" // for nsIntRegion
36 #include "nsTraceRefcnt.h" // for MOZ_COUNT_CTOR, etc
37 #include "nscore.h" // for nsACString
38 #include "mozilla/layers/AtomicRefCountedWithFinalize.h"
40 class MacIOSurface;
41 namespace mozilla {
42 namespace gfx {
43 class DataSourceSurface;
46 namespace ipc {
47 class Shmem;
48 } // namespace ipc
50 namespace wr {
51 class DisplayListBuilder;
52 class TransactionBuilder;
53 } // namespace wr
55 namespace layers {
57 class AndroidHardwareBuffer;
58 class AndroidHardwareBufferTextureHost;
59 class BufferDescriptor;
60 class BufferTextureHost;
61 class Compositor;
62 class CompositableParentManager;
63 class ReadLockDescriptor;
64 class CompositorBridgeParent;
65 class SurfaceDescriptor;
66 class HostIPCAllocator;
67 class ISurfaceAllocator;
68 class MacIOSurfaceTextureHostOGL;
69 class ShmemTextureHost;
70 class SurfaceTextureHost;
71 class TextureHostOGL;
72 class TextureReadLock;
73 class TextureSourceOGL;
74 class TextureSourceD3D11;
75 class DataTextureSource;
76 class PTextureParent;
77 class RemoteTextureHostWrapper;
78 class TextureParent;
79 class WebRenderTextureHost;
80 class WrappingTextureSourceYCbCrBasic;
81 class TextureHostWrapperD3D11;
83 /**
84 * A view on a TextureHost where the texture is internally represented as tiles
85 * (contrast with a tiled buffer, where each texture is a tile). For iteration
86 * by the texture's buffer host. This is only useful when the underlying surface
87 * is too big to fit in one device texture, which forces us to split it in
88 * smaller parts. Tiled Compositable is a different thing.
90 class BigImageIterator {
91 public:
92 virtual void BeginBigImageIteration() = 0;
93 virtual void EndBigImageIteration(){};
94 virtual gfx::IntRect GetTileRect() = 0;
95 virtual size_t GetTileCount() = 0;
96 virtual bool NextTile() = 0;
99 /**
100 * TextureSource is the interface for texture objects that can be composited
101 * by a given compositor backend. Since the drawing APIs are different
102 * between backends, the TextureSource interface is split into different
103 * interfaces (TextureSourceOGL, etc.), and TextureSource mostly provide
104 * access to these interfaces.
106 * This class is used on the compositor side.
108 class TextureSource : public RefCounted<TextureSource> {
109 public:
110 MOZ_DECLARE_REFCOUNTED_VIRTUAL_TYPENAME(TextureSource)
112 TextureSource();
114 virtual ~TextureSource();
116 virtual const char* Name() const = 0;
119 * Should be overridden in order to deallocate the data that is associated
120 * with the rendering backend, such as GL textures.
122 virtual void DeallocateDeviceData() {}
125 * Return the size of the texture in texels.
126 * If this is a tile iterator, GetSize must return the size of the current
127 * tile.
129 virtual gfx::IntSize GetSize() const = 0;
132 * Return the pixel format of this texture
134 virtual gfx::SurfaceFormat GetFormat() const {
135 return gfx::SurfaceFormat::UNKNOWN;
139 * Cast to a TextureSource for for each backend..
141 virtual TextureSourceOGL* AsSourceOGL() {
142 gfxCriticalNote << "Failed to cast " << Name()
143 << " into a TextureSourceOGL";
144 return nullptr;
146 virtual TextureSourceD3D11* AsSourceD3D11() { return nullptr; }
148 * Cast to a DataTextureSurce.
150 virtual DataTextureSource* AsDataTextureSource() { return nullptr; }
153 * Overload this if the TextureSource supports big textures that don't fit in
154 * one device texture and must be tiled internally.
156 virtual BigImageIterator* AsBigImageIterator() { return nullptr; }
158 virtual void Unbind() {}
160 void SetNextSibling(TextureSource* aTexture) { mNextSibling = aTexture; }
162 TextureSource* GetNextSibling() const { return mNextSibling; }
165 * In some rare cases we currently need to consider a group of textures as one
166 * TextureSource, that can be split in sub-TextureSources.
168 TextureSource* GetSubSource(int index) {
169 switch (index) {
170 case 0:
171 return this;
172 case 1:
173 return GetNextSibling();
174 case 2:
175 return GetNextSibling() ? GetNextSibling()->GetNextSibling() : nullptr;
177 return nullptr;
180 void AddCompositableRef() { ++mCompositableCount; }
182 void ReleaseCompositableRef() {
183 --mCompositableCount;
184 MOZ_ASSERT(mCompositableCount >= 0);
187 // When iterating as a BigImage, this creates temporary TextureSources
188 // wrapping individual tiles.
189 virtual RefPtr<TextureSource> ExtractCurrentTile() {
190 NS_WARNING("Implementation does not expose tile sources");
191 return nullptr;
194 int NumCompositableRefs() const { return mCompositableCount; }
196 // The direct-map cpu buffer should be alive when gpu uses it. And it
197 // should not be updated while gpu reads it. This Sync() function
198 // implements this synchronized behavior by allowing us to check if
199 // the GPU is done with the texture, and block on it if aBlocking is
200 // true.
201 virtual bool Sync(bool aBlocking) { return true; }
203 protected:
204 RefPtr<TextureSource> mNextSibling;
205 int mCompositableCount;
208 /// Equivalent of a RefPtr<TextureSource>, that calls AddCompositableRef and
209 /// ReleaseCompositableRef in addition to the usual AddRef and Release.
211 /// The semantoics of these CompositableTextureRefs are important because they
212 /// are used both as a synchronization/safety mechanism, and as an optimization
213 /// mechanism. They are also tricky and subtle because we use them in a very
214 /// implicit way (assigning to a CompositableTextureRef is less visible than
215 /// explicitly calling a method or whatnot).
216 /// It is Therefore important to be careful about the way we use this tool.
218 /// CompositableTextureRef is a mechanism that lets us count how many
219 /// compositables are using a given texture (for TextureSource and TextureHost).
220 /// We use it to run specific code when a texture is not used anymore, and also
221 /// we trigger fast paths on some operations when we can see that the texture's
222 /// CompositableTextureRef counter is equal to 1 (the texture is not shared
223 /// between compositables).
224 /// This means that it is important to observe the following rules:
225 /// * CompositableHosts that receive UseTexture and similar messages *must*
226 /// store all of the TextureHosts they receive in CompositableTextureRef slots
227 /// for as long as they may be using them.
228 /// * CompositableHosts must store each texture in a *single*
229 /// CompositableTextureRef slot to ensure that the counter properly reflects how
230 /// many compositables are using the texture. If a compositable needs to hold
231 /// two references to a given texture (for example to have a pointer to the
232 /// current texture in a list of textures that may be used), it can hold its
233 /// extra references with RefPtr or whichever pointer type makes sense.
234 template <typename T>
235 class CompositableTextureRef {
236 public:
237 CompositableTextureRef() = default;
239 explicit CompositableTextureRef(const CompositableTextureRef& aOther) {
240 *this = aOther;
243 explicit CompositableTextureRef(T* aOther) { *this = aOther; }
245 ~CompositableTextureRef() {
246 if (mRef) {
247 mRef->ReleaseCompositableRef();
251 CompositableTextureRef& operator=(const CompositableTextureRef& aOther) {
252 if (aOther.get()) {
253 aOther->AddCompositableRef();
255 if (mRef) {
256 mRef->ReleaseCompositableRef();
258 mRef = aOther.get();
259 return *this;
262 CompositableTextureRef& operator=(T* aOther) {
263 if (aOther) {
264 aOther->AddCompositableRef();
266 if (mRef) {
267 mRef->ReleaseCompositableRef();
269 mRef = aOther;
270 return *this;
273 T* get() const { return mRef; }
274 operator T*() const { return mRef; }
275 T* operator->() const { return mRef; }
276 T& operator*() const { return *mRef; }
278 private:
279 RefPtr<T> mRef;
282 typedef CompositableTextureRef<TextureSource> CompositableTextureSourceRef;
283 typedef CompositableTextureRef<TextureHost> CompositableTextureHostRef;
286 * Interface for TextureSources that can be updated from a DataSourceSurface.
288 * All backend should implement at least one DataTextureSource.
290 class DataTextureSource : public TextureSource {
291 public:
292 DataTextureSource() : mOwner(0), mUpdateSerial(0) {}
294 const char* Name() const override { return "DataTextureSource"; }
296 DataTextureSource* AsDataTextureSource() override { return this; }
299 * Upload a (portion of) surface to the TextureSource.
301 * The DataTextureSource doesn't own aSurface, although it owns and manage
302 * the device texture it uploads to internally.
304 virtual bool Update(gfx::DataSourceSurface* aSurface,
305 nsIntRegion* aDestRegion = nullptr,
306 gfx::IntPoint* aSrcOffset = nullptr,
307 gfx::IntPoint* aDstOffset = nullptr) = 0;
310 * A facility to avoid reuploading when it is not necessary.
311 * The caller of Update can use GetUpdateSerial to see if the number has
312 * changed since last update, and call SetUpdateSerial after each successful
313 * update. The caller is responsible for managing the update serial except
314 * when the texture data is deallocated in which case the TextureSource should
315 * always reset the update serial to zero.
317 uint32_t GetUpdateSerial() const { return mUpdateSerial; }
318 void SetUpdateSerial(uint32_t aValue) { mUpdateSerial = aValue; }
320 // By default at least set the update serial to zero.
321 // overloaded versions should do that too.
322 void DeallocateDeviceData() override { SetUpdateSerial(0); }
324 #ifdef DEBUG
326 * Provide read access to the data as a DataSourceSurface.
328 * This is expected to be very slow and should be used for mostly debugging.
329 * XXX - implement everywhere and make it pure virtual.
331 virtual already_AddRefed<gfx::DataSourceSurface> ReadBack() {
332 return nullptr;
334 #endif
336 void SetOwner(TextureHost* aOwner) {
337 auto newOwner = (uintptr_t)aOwner;
338 if (newOwner != mOwner) {
339 mOwner = newOwner;
340 SetUpdateSerial(0);
344 bool IsOwnedBy(TextureHost* aOwner) const {
345 return mOwner == (uintptr_t)aOwner;
348 bool HasOwner() const { return !IsOwnedBy(nullptr); }
350 private:
351 // We store mOwner as an integer rather than as a pointer to make it clear
352 // it is not intended to be dereferenced.
353 uintptr_t mOwner;
354 uint32_t mUpdateSerial;
357 enum class TextureHostType : int8_t {
358 Unknown = 0,
359 Buffer,
360 DXGI,
361 DXGIYCbCr,
362 DcompSurface,
363 DMABUF,
364 MacIOSurface,
365 AndroidSurfaceTexture,
366 AndroidHardwareBuffer,
367 EGLImage,
368 GLTexture,
369 Last
373 * TextureHost is a thin abstraction over texture data that need to be shared
374 * between the content process and the compositor process. It is the
375 * compositor-side half of a TextureClient/TextureHost pair. A corresponding
376 * TextureClient lives on the content-side.
378 * TextureHost only knows how to deserialize or synchronize generic image data
379 * (SurfaceDescriptor) and provide access to one or more TextureSource objects
380 * (these provide the necessary APIs for compositor backends to composite the
381 * image).
383 * A TextureHost implementation corresponds to one SurfaceDescriptor type, as
384 * opposed to TextureSource that corresponds to device textures.
385 * This means that for YCbCr planes, even though they are represented as
386 * 3 textures internally (3 TextureSources), we use 1 TextureHost and not 3,
387 * because the 3 planes are stored in the same buffer of shared memory, before
388 * they are uploaded separately.
390 * There is always one and only one TextureHost per TextureClient, and the
391 * TextureClient/Host pair only owns one buffer of image data through its
392 * lifetime. This means that the lifetime of the underlying shared data
393 * matches the lifetime of the TextureClient/Host pair. It also means
394 * TextureClient/Host do not implement double buffering, which is the
395 * reponsibility of the compositable (which would use two Texture pairs).
397 * The Lock/Unlock mecanism here mirrors Lock/Unlock in TextureClient.
400 class TextureHost : public AtomicRefCountedWithFinalize<TextureHost> {
402 * Called once, just before the destructor.
404 * Here goes the shut-down code that uses virtual methods.
405 * Must only be called by Release().
407 void Finalize();
409 friend class AtomicRefCountedWithFinalize<TextureHost>;
411 public:
412 TextureHost(TextureHostType aType, TextureFlags aFlags);
414 protected:
415 virtual ~TextureHost();
417 public:
419 * Factory method.
421 static already_AddRefed<TextureHost> Create(
422 const SurfaceDescriptor& aDesc, ReadLockDescriptor&& aReadLock,
423 HostIPCAllocator* aDeallocator, LayersBackend aBackend,
424 TextureFlags aFlags, wr::MaybeExternalImageId& aExternalImageId);
427 * Lock the texture host for compositing without using compositor.
429 virtual bool LockWithoutCompositor() { return true; }
431 * Similar to Unlock(), but it should be called with LockWithoutCompositor().
433 virtual void UnlockWithoutCompositor() {}
436 * Note that the texture host format can be different from its corresponding
437 * texture source's. For example a ShmemTextureHost can have the ycbcr
438 * format and produce 3 "alpha" textures sources.
440 virtual gfx::SurfaceFormat GetFormat() const = 0;
442 * Return the format used for reading the texture.
443 * Apple's YCBCR_422 is R8G8B8X8.
445 virtual gfx::SurfaceFormat GetReadFormat() const { return GetFormat(); }
447 virtual gfx::YUVColorSpace GetYUVColorSpace() const {
448 return gfx::YUVColorSpace::Identity;
452 * Return the color depth of the image. Used with YUV textures.
454 virtual gfx::ColorDepth GetColorDepth() const {
455 return gfx::ColorDepth::COLOR_8;
459 * Return true if using full range values (0-255 if 8 bits YUV). Used with YUV
460 * textures.
462 virtual gfx::ColorRange GetColorRange() const {
463 return gfx::ColorRange::LIMITED;
467 * Called when another TextureHost will take over.
469 virtual void UnbindTextureSource();
471 virtual bool IsValid() { return true; }
474 * Should be overridden in order to deallocate the data that is associated
475 * with the rendering backend, such as GL textures.
477 virtual void DeallocateDeviceData() {}
480 * Should be overridden in order to deallocate the data that is shared with
481 * the content side, such as shared memory.
483 virtual void DeallocateSharedData() {}
486 * Should be overridden in order to force the TextureHost to drop all
487 * references to it's shared data.
489 * This is important to ensure the correctness of the deallocation protocol.
491 virtual void ForgetSharedData() {}
493 virtual gfx::IntSize GetSize() const = 0;
496 * Should be overridden if TextureHost supports crop rect.
498 virtual void SetCropRect(nsIntRect aCropRect) {}
501 * Debug facility.
502 * XXX - cool kids use Moz2D. See bug 882113.
504 virtual already_AddRefed<gfx::DataSourceSurface> GetAsSurface() = 0;
507 * XXX - Flags should only be set at creation time, this will be removed.
509 void SetFlags(TextureFlags aFlags) { mFlags = aFlags; }
512 * XXX - Flags should only be set at creation time, this will be removed.
514 void AddFlag(TextureFlags aFlag) { mFlags |= aFlag; }
516 TextureFlags GetFlags() { return mFlags; }
518 wr::MaybeExternalImageId GetMaybeExternalImageId() const {
519 return mExternalImageId;
523 * Allocate and deallocate a TextureParent actor.
525 * TextureParent< is an implementation detail of TextureHost that is not
526 * exposed to the rest of the code base. CreateIPDLActor and DestroyIPDLActor
527 * are for use with the managing IPDL protocols only (so that they can
528 * implement AllocPTextureParent and DeallocPTextureParent).
530 static PTextureParent* CreateIPDLActor(
531 HostIPCAllocator* aAllocator, const SurfaceDescriptor& aSharedData,
532 ReadLockDescriptor&& aDescriptor, LayersBackend aLayersBackend,
533 TextureFlags aFlags, const dom::ContentParentId& aContentId,
534 uint64_t aSerial, const wr::MaybeExternalImageId& aExternalImageId);
535 static bool DestroyIPDLActor(PTextureParent* actor);
538 * Destroy the TextureChild/Parent pair.
540 static bool SendDeleteIPDLActor(PTextureParent* actor);
542 static void ReceivedDestroy(PTextureParent* actor);
545 * Get the TextureHost corresponding to the actor passed in parameter.
547 static TextureHost* AsTextureHost(PTextureParent* actor);
549 static uint64_t GetTextureSerial(PTextureParent* actor);
551 static dom::ContentParentId GetTextureContentId(PTextureParent* actor);
554 * Return a pointer to the IPDLActor.
556 * This is to be used with IPDL messages only. Do not store the returned
557 * pointer.
559 PTextureParent* GetIPDLActor();
561 // If a texture host holds a reference to shmem, it should override this
562 // method to forget about the shmem _without_ releasing it.
563 virtual void OnShutdown() {}
565 // Forget buffer actor. Used only for hacky fix for bug 966446.
566 virtual void ForgetBufferActor() {}
568 virtual const char* Name() { return "TextureHost"; }
571 * Returns true if the TextureHost can be released before the rendering is
572 * completed, otherwise returns false.
574 virtual bool NeedsDeferredDeletion() const { return true; }
576 void AddCompositableRef() {
577 ++mCompositableCount;
578 if (mCompositableCount == 1) {
579 PrepareForUse();
583 void ReleaseCompositableRef() {
584 --mCompositableCount;
585 MOZ_ASSERT(mCompositableCount >= 0);
586 if (mCompositableCount == 0) {
587 UnbindTextureSource();
588 // Send mFwdTransactionId to client side if necessary.
589 NotifyNotUsed();
593 int NumCompositableRefs() const { return mCompositableCount; }
595 void SetLastFwdTransactionId(uint64_t aTransactionId);
597 void DeserializeReadLock(ReadLockDescriptor&& aDesc,
598 ISurfaceAllocator* aAllocator);
599 void SetReadLocked();
601 TextureReadLock* GetReadLock() { return mReadLock; }
603 virtual BufferTextureHost* AsBufferTextureHost() { return nullptr; }
604 virtual ShmemTextureHost* AsShmemTextureHost() { return nullptr; }
605 virtual MacIOSurfaceTextureHostOGL* AsMacIOSurfaceTextureHost() {
606 return nullptr;
608 virtual WebRenderTextureHost* AsWebRenderTextureHost() { return nullptr; }
609 virtual SurfaceTextureHost* AsSurfaceTextureHost() { return nullptr; }
610 virtual AndroidHardwareBufferTextureHost*
611 AsAndroidHardwareBufferTextureHost() {
612 return nullptr;
614 virtual RemoteTextureHostWrapper* AsRemoteTextureHostWrapper() {
615 return nullptr;
618 virtual TextureHostWrapperD3D11* AsTextureHostWrapperD3D11() {
619 return nullptr;
622 virtual bool IsWrappingSurfaceTextureHost() { return false; }
624 // Create the corresponding RenderTextureHost type of this texture, and
625 // register the RenderTextureHost into render thread.
626 virtual void CreateRenderTexture(
627 const wr::ExternalImageId& aExternalImageId) {
628 MOZ_RELEASE_ASSERT(
629 false,
630 "No CreateRenderTexture() implementation for this TextureHost type.");
633 void EnsureRenderTexture(const wr::MaybeExternalImageId& aExternalImageId);
635 // Destroy RenderTextureHost when it was created by the TextureHost.
636 // It is called in TextureHost::Finalize().
637 virtual void MaybeDestroyRenderTexture();
639 static void DestroyRenderTexture(const wr::ExternalImageId& aExternalImageId);
641 /// Returns the number of actual textures that will be used to render this.
642 /// For example in a lot of YUV cases it will be 3
643 virtual uint32_t NumSubTextures() { return 1; }
645 enum ResourceUpdateOp {
646 ADD_IMAGE,
647 UPDATE_IMAGE,
650 // Add all necessary TextureHost informations to the resource update queue.
651 virtual void PushResourceUpdates(wr::TransactionBuilder& aResources,
652 ResourceUpdateOp aOp,
653 const Range<wr::ImageKey>& aImageKeys,
654 const wr::ExternalImageId& aExtID) {
655 MOZ_ASSERT_UNREACHABLE("Unimplemented");
658 enum class PushDisplayItemFlag {
659 // Passed if the caller wants these display items to be promoted
660 // to compositor surfaces if possible.
661 PREFER_COMPOSITOR_SURFACE,
663 // Passed in the RenderCompositor supports BufferTextureHosts
664 // being used directly as external compositor surfaces.
665 SUPPORTS_EXTERNAL_BUFFER_TEXTURES,
667 using PushDisplayItemFlagSet = EnumSet<PushDisplayItemFlag>;
669 // Put all necessary WR commands into DisplayListBuilder for this textureHost
670 // rendering.
671 virtual void PushDisplayItems(wr::DisplayListBuilder& aBuilder,
672 const wr::LayoutRect& aBounds,
673 const wr::LayoutRect& aClip,
674 wr::ImageRendering aFilter,
675 const Range<wr::ImageKey>& aKeys,
676 PushDisplayItemFlagSet aFlags) {
677 MOZ_ASSERT_UNREACHABLE(
678 "No PushDisplayItems() implementation for this TextureHost type.");
682 * Some API's can use the cross-process IOSurface directly, such as OpenVR
684 virtual MacIOSurface* GetMacIOSurface() { return nullptr; }
686 virtual bool NeedsYFlip() const;
688 virtual void SetAcquireFence(mozilla::ipc::FileDescriptor&& aFenceFd) {}
690 virtual void SetReleaseFence(mozilla::ipc::FileDescriptor&& aFenceFd) {}
692 virtual mozilla::ipc::FileDescriptor GetAndResetReleaseFence() {
693 return mozilla::ipc::FileDescriptor();
696 virtual AndroidHardwareBuffer* GetAndroidHardwareBuffer() const {
697 return nullptr;
700 virtual bool SupportsExternalCompositing(WebRenderBackend aBackend) {
701 return false;
704 virtual TextureHostType GetTextureHostType() { return mTextureHostType; }
706 // Our WebRender backend may impose restrictions on whether textures are
707 // prepared as native textures or not, or it may have no restriction at
708 // all. This enumerates those possibilities.
709 enum NativeTexturePolicy {
710 REQUIRE,
711 FORBID,
712 DONT_CARE,
715 static NativeTexturePolicy BackendNativeTexturePolicy(
716 layers::WebRenderBackend aBackend, gfx::IntSize aSize) {
717 static const int32_t SWGL_DIMENSION_MAX = 1 << 15;
718 if (aBackend == WebRenderBackend::SOFTWARE) {
719 return (aSize.width <= SWGL_DIMENSION_MAX &&
720 aSize.height <= SWGL_DIMENSION_MAX)
721 ? REQUIRE
722 : FORBID;
724 return DONT_CARE;
727 void SetDestroyedCallback(std::function<void()>&& aDestroyedCallback) {
728 MOZ_ASSERT(!mDestroyedCallback);
729 mDestroyedCallback = std::move(aDestroyedCallback);
732 protected:
733 virtual void ReadUnlock();
735 void RecycleTexture(TextureFlags aFlags);
738 * Called when mCompositableCount becomes from 0 to 1.
740 virtual void PrepareForUse();
743 * Called when mCompositableCount becomes 0.
745 virtual void NotifyNotUsed();
747 // for Compositor.
748 void CallNotifyNotUsed();
750 TextureHostType mTextureHostType;
751 PTextureParent* mActor;
752 RefPtr<TextureReadLock> mReadLock;
753 TextureFlags mFlags;
754 int mCompositableCount;
755 uint64_t mFwdTransactionId;
756 bool mReadLocked;
757 wr::MaybeExternalImageId mExternalImageId;
759 std::function<void()> mDestroyedCallback;
761 friend class Compositor;
762 friend class RemoteTextureHostWrapper;
763 friend class TextureParent;
764 friend class TextureSourceProvider;
765 friend class GPUVideoTextureHost;
766 friend class WebRenderTextureHost;
767 friend class TextureHostWrapperD3D11;
771 * TextureHost that wraps a random access buffer such as a Shmem or some raw
772 * memory.
774 * This TextureHost is backend-independent and the backend-specific bits are
775 * in the TextureSource.
776 * This class must be inherited to implement GetBuffer and DeallocSharedData
777 * (see ShmemTextureHost and MemoryTextureHost)
779 * Uploads happen when Lock is called.
781 * BufferTextureHost supports YCbCr and flavours of RGBA images (RGBX, A, etc.).
783 class BufferTextureHost : public TextureHost {
784 public:
785 BufferTextureHost(const BufferDescriptor& aDescriptor, TextureFlags aFlags);
787 virtual ~BufferTextureHost();
789 virtual uint8_t* GetBuffer() = 0;
791 virtual size_t GetBufferSize() = 0;
793 void UnbindTextureSource() override;
795 void DeallocateDeviceData() override;
798 * Return the format that is exposed to the compositor when calling
799 * BindTextureSource.
801 * If the shared format is YCbCr and the compositor does not support it,
802 * GetFormat will be RGB32 (even though mFormat is SurfaceFormat::YUV).
804 gfx::SurfaceFormat GetFormat() const override;
806 gfx::YUVColorSpace GetYUVColorSpace() const override;
808 gfx::ColorDepth GetColorDepth() const override;
810 gfx::ColorRange GetColorRange() const override;
812 gfx::ChromaSubsampling GetChromaSubsampling() const;
814 gfx::IntSize GetSize() const override { return mSize; }
816 already_AddRefed<gfx::DataSourceSurface> GetAsSurface() override;
818 bool NeedsDeferredDeletion() const override {
819 return TextureHost::NeedsDeferredDeletion() || UseExternalTextures();
822 BufferTextureHost* AsBufferTextureHost() override { return this; }
824 const BufferDescriptor& GetBufferDescriptor() const { return mDescriptor; }
826 void CreateRenderTexture(
827 const wr::ExternalImageId& aExternalImageId) override;
829 uint32_t NumSubTextures() override;
831 void PushResourceUpdates(wr::TransactionBuilder& aResources,
832 ResourceUpdateOp aOp,
833 const Range<wr::ImageKey>& aImageKeys,
834 const wr::ExternalImageId& aExtID) override;
836 void PushDisplayItems(wr::DisplayListBuilder& aBuilder,
837 const wr::LayoutRect& aBounds,
838 const wr::LayoutRect& aClip, wr::ImageRendering aFilter,
839 const Range<wr::ImageKey>& aImageKeys,
840 PushDisplayItemFlagSet aFlags) override;
842 uint8_t* GetYChannel();
843 uint8_t* GetCbChannel();
844 uint8_t* GetCrChannel();
845 int32_t GetYStride() const;
846 int32_t GetCbCrStride() const;
848 protected:
849 bool UseExternalTextures() const { return mUseExternalTextures; }
851 BufferDescriptor mDescriptor;
852 RefPtr<Compositor> mCompositor;
853 gfx::IntSize mSize;
854 gfx::SurfaceFormat mFormat;
855 bool mLocked;
856 bool mUseExternalTextures;
858 class DataTextureSourceYCbCrBasic;
862 * TextureHost that wraps shared memory.
863 * the corresponding texture on the client side is ShmemTextureClient.
864 * This TextureHost is backend-independent.
866 class ShmemTextureHost : public BufferTextureHost {
867 public:
868 ShmemTextureHost(const mozilla::ipc::Shmem& aShmem,
869 const BufferDescriptor& aDesc,
870 ISurfaceAllocator* aDeallocator, TextureFlags aFlags);
872 protected:
873 ~ShmemTextureHost();
875 public:
876 void DeallocateSharedData() override;
878 void ForgetSharedData() override;
880 uint8_t* GetBuffer() override;
882 size_t GetBufferSize() override;
884 const char* Name() override { return "ShmemTextureHost"; }
886 void OnShutdown() override;
888 ShmemTextureHost* AsShmemTextureHost() override { return this; }
890 protected:
891 UniquePtr<mozilla::ipc::Shmem> mShmem;
892 RefPtr<ISurfaceAllocator> mDeallocator;
896 * TextureHost that wraps raw memory.
897 * The corresponding texture on the client side is MemoryTextureClient.
898 * Can obviously not be used in a cross process setup.
899 * This TextureHost is backend-independent.
901 class MemoryTextureHost : public BufferTextureHost {
902 public:
903 MemoryTextureHost(uint8_t* aBuffer, const BufferDescriptor& aDesc,
904 TextureFlags aFlags);
906 protected:
907 ~MemoryTextureHost();
909 public:
910 void DeallocateSharedData() override;
912 void ForgetSharedData() override;
914 uint8_t* GetBuffer() override;
916 size_t GetBufferSize() override;
918 const char* Name() override { return "MemoryTextureHost"; }
920 protected:
921 uint8_t* mBuffer;
924 class MOZ_STACK_CLASS AutoLockTextureHostWithoutCompositor {
925 public:
926 explicit AutoLockTextureHostWithoutCompositor(TextureHost* aTexture)
927 : mTexture(aTexture) {
928 mLocked = mTexture ? mTexture->LockWithoutCompositor() : false;
931 ~AutoLockTextureHostWithoutCompositor() {
932 if (mTexture && mLocked) {
933 mTexture->UnlockWithoutCompositor();
937 bool Failed() { return mTexture && !mLocked; }
939 private:
940 RefPtr<TextureHost> mTexture;
941 bool mLocked;
945 * This can be used as an offscreen rendering target by the compositor, and
946 * subsequently can be used as a source by the compositor.
948 class CompositingRenderTarget : public TextureSource {
949 public:
950 explicit CompositingRenderTarget(const gfx::IntPoint& aOrigin)
951 : mClearOnBind(false),
952 mOrigin(aOrigin),
953 mZNear(0),
954 mZFar(0),
955 mHasComplexProjection(false),
956 mEnableDepthBuffer(false) {}
957 virtual ~CompositingRenderTarget() = default;
959 const char* Name() const override { return "CompositingRenderTarget"; }
961 #ifdef MOZ_DUMP_PAINTING
962 virtual already_AddRefed<gfx::DataSourceSurface> Dump(
963 Compositor* aCompositor) {
964 return nullptr;
966 #endif
969 * Perform a clear when recycling a non opaque surface.
970 * The clear is deferred to when the render target is bound.
972 void ClearOnBind() { mClearOnBind = true; }
974 const gfx::IntPoint& GetOrigin() const { return mOrigin; }
975 gfx::IntRect GetRect() { return gfx::IntRect(GetOrigin(), GetSize()); }
978 * If a Projection matrix is set, then it is used for rendering to
979 * this render target instead of generating one. If no explicit
980 * projection is set, Compositors are expected to generate an
981 * orthogonal maaping that maps 0..1 to the full size of the render
982 * target.
984 bool HasComplexProjection() const { return mHasComplexProjection; }
985 void ClearProjection() { mHasComplexProjection = false; }
986 void SetProjection(const gfx::Matrix4x4& aNewMatrix, bool aEnableDepthBuffer,
987 float aZNear, float aZFar) {
988 mProjectionMatrix = aNewMatrix;
989 mEnableDepthBuffer = aEnableDepthBuffer;
990 mZNear = aZNear;
991 mZFar = aZFar;
992 mHasComplexProjection = true;
994 void GetProjection(gfx::Matrix4x4& aMatrix, bool& aEnableDepth, float& aZNear,
995 float& aZFar) {
996 MOZ_ASSERT(mHasComplexProjection);
997 aMatrix = mProjectionMatrix;
998 aEnableDepth = mEnableDepthBuffer;
999 aZNear = mZNear;
1000 aZFar = mZFar;
1003 protected:
1004 bool mClearOnBind;
1006 private:
1007 gfx::IntPoint mOrigin;
1009 gfx::Matrix4x4 mProjectionMatrix;
1010 float mZNear, mZFar;
1011 bool mHasComplexProjection;
1012 bool mEnableDepthBuffer;
1016 * Creates a TextureHost that can be used with any of the existing backends
1017 * Not all SurfaceDescriptor types are supported
1019 already_AddRefed<TextureHost> CreateBackendIndependentTextureHost(
1020 const SurfaceDescriptor& aDesc, ISurfaceAllocator* aDeallocator,
1021 LayersBackend aBackend, TextureFlags aFlags);
1023 } // namespace layers
1024 } // namespace mozilla
1026 #endif