Bug 1610775 [wpt PR 21336] - Update urllib3 to 1.25.8, a=testonly
[gecko.git] / dom / canvas / WebGLContext.h
blobf2c0e4dfe2ae531ad12ba32d58a38606c879a1d3
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* This Source Code Form is subject to the terms of the Mozilla Public
3 * License, v. 2.0. If a copy of the MPL was not distributed with this
4 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6 #ifndef WEBGLCONTEXT_H_
7 #define WEBGLCONTEXT_H_
9 #include <memory>
10 #include <stdarg.h>
12 #include "GLContextTypes.h"
13 #include "GLDefs.h"
14 #include "mozilla/Attributes.h"
15 #include "mozilla/CheckedInt.h"
16 #include "mozilla/dom/BindingDeclarations.h"
17 #include "mozilla/dom/HTMLCanvasElement.h"
18 #include "mozilla/dom/Nullable.h"
19 #include "mozilla/dom/TypedArray.h"
20 #include "mozilla/EnumeratedArray.h"
21 #include "mozilla/ErrorResult.h"
22 #include "mozilla/gfx/2D.h"
23 #include "mozilla/Mutex.h"
24 #include "mozilla/UniquePtr.h"
25 #include "mozilla/WeakPtr.h"
26 #include "nsICanvasRenderingContextInternal.h"
27 #include "nsLayoutUtils.h"
28 #include "nsTArray.h"
29 #include "SurfaceTypes.h"
30 #include "ScopedGLHelpers.h"
31 #include "TexUnpackBlob.h"
32 #include "mozilla/WeakPtr.h"
34 // Local
35 #include "CacheInvalidator.h"
36 #include "WebGLContextLossHandler.h"
37 #include "WebGLExtensions.h"
38 #include "WebGLObjectModel.h"
39 #include "WebGLStrongTypes.h"
40 #include "WebGLTypes.h"
42 // Generated
43 #include "nsICanvasRenderingContextInternal.h"
44 #include "mozilla/dom/HTMLCanvasElement.h"
45 #include "nsLayoutUtils.h"
46 #include "mozilla/dom/WebGLRenderingContextBinding.h"
47 #include "mozilla/dom/WebGL2RenderingContextBinding.h"
49 #include <list>
51 class nsIDocShell;
53 // WebGL-only GLenums
54 // clang-format off
55 #define LOCAL_GL_BROWSER_DEFAULT_WEBGL 0x9244
56 #define LOCAL_GL_CONTEXT_LOST_WEBGL 0x9242
57 #define LOCAL_GL_MAX_CLIENT_WAIT_TIMEOUT_WEBGL 0x9247
58 #define LOCAL_GL_UNPACK_COLORSPACE_CONVERSION_WEBGL 0x9243
59 #define LOCAL_GL_UNPACK_FLIP_Y_WEBGL 0x9240
60 #define LOCAL_GL_UNPACK_PREMULTIPLY_ALPHA_WEBGL 0x9241
61 // clang-format on
63 namespace mozilla {
64 class HostWebGLContext;
65 class ScopedCopyTexImageSource;
66 class ScopedDrawCallWrapper;
67 class ScopedResolveTexturesForDraw;
68 class ScopedUnpackReset;
69 class WebGLBuffer;
70 class WebGLExtensionBase;
71 class WebGLFramebuffer;
72 class WebGLProgram;
73 class WebGLQuery;
74 class WebGLRenderbuffer;
75 class WebGLSampler;
76 class WebGLShader;
77 class WebGLSync;
78 class WebGLTexture;
79 class WebGLTransformFeedback;
80 class WebGLVertexArray;
82 namespace dom {
83 class Document;
84 class Element;
85 class ImageData;
86 class OwningHTMLCanvasElementOrOffscreenCanvas;
87 struct WebGLContextAttributes;
88 } // namespace dom
90 namespace gfx {
91 class SourceSurface;
92 class VRLayerChild;
93 } // namespace gfx
95 namespace gl {
96 class GLScreenBuffer;
97 class MozFramebuffer;
98 } // namespace gl
100 namespace layers {
101 class CompositableHost;
104 namespace webgl {
105 class AvailabilityRunnable;
106 struct CachedDrawFetchLimits;
107 struct FbAttachInfo;
108 struct FormatInfo;
109 class FormatUsageAuthority;
110 struct FormatUsageInfo;
111 struct ImageInfo;
112 struct LinkedProgramInfo;
113 struct SamplerUniformInfo;
114 struct SamplingState;
115 class ScopedPrepForResourceClear;
116 class ShaderValidator;
117 class TexUnpackBlob;
118 struct UniformInfo;
119 struct UniformBlockInfo;
120 } // namespace webgl
122 struct WebGLTexImageData {
123 TexImageTarget mTarget;
124 int32_t mRowLength;
125 uint32_t mWidth;
126 uint32_t mHeight;
127 uint32_t mDepth;
128 gfxAlphaType mSrcAlphaType;
131 struct WebGLTexPboOffset {
132 TexImageTarget mTarget;
133 uint32_t mWidth;
134 uint32_t mHeight;
135 uint32_t mDepth;
136 WebGLsizeiptr mPboOffset;
137 bool mHasExpectedImageSize;
138 GLsizei mExpectedImageSize;
141 WebGLTexelFormat GetWebGLTexelFormat(TexInternalFormat format);
143 void AssertUintParamCorrect(gl::GLContext* gl, GLenum pname, GLuint shadow);
145 // From WebGLContextUtils
146 TexTarget TexImageTargetToTexTarget(TexImageTarget texImageTarget);
148 struct WebGLIntOrFloat {
149 const enum { Int, Float, Uint } mType;
151 union {
152 GLint i;
153 GLfloat f;
154 GLuint u;
155 } mValue;
157 explicit WebGLIntOrFloat(GLint i) : mType(Int) { mValue.i = i; }
158 explicit WebGLIntOrFloat(GLfloat f) : mType(Float) { mValue.f = f; }
160 GLint AsInt() const {
161 return (mType == Int) ? mValue.i : NS_lroundf(mValue.f);
163 GLfloat AsFloat() const {
164 return (mType == Float) ? mValue.f : GLfloat(mValue.i);
168 struct IndexedBufferBinding {
169 RefPtr<WebGLBuffer> mBufferBinding;
170 uint64_t mRangeStart;
171 uint64_t mRangeSize;
173 IndexedBufferBinding();
175 uint64_t ByteCount() const;
178 ////////////////////////////////////
180 namespace webgl {
182 class AvailabilityRunnable final : public Runnable {
183 public:
184 const RefPtr<WebGLContext> mWebGL; // Prevent CC
185 std::vector<RefPtr<WebGLQuery>> mQueries;
186 std::vector<RefPtr<WebGLSync>> mSyncs;
188 explicit AvailabilityRunnable(WebGLContext* webgl);
189 ~AvailabilityRunnable();
191 NS_IMETHOD Run() override;
194 struct BufferAndIndex final {
195 const WebGLBuffer* buffer = nullptr;
196 uint32_t id = -1;
199 // -
201 class DynDGpuManager final {
202 static constexpr uint32_t TICK_MS = 3000;
204 enum class State {
205 Inactive,
206 Primed,
207 Active,
210 Mutex mMutex;
211 bool mActivityThisTick = false;
212 State mState = State::Inactive;
213 RefPtr<gl::GLContext> mDGpuContext;
215 public:
216 static std::shared_ptr<DynDGpuManager> Get();
218 DynDGpuManager();
219 ~DynDGpuManager();
221 void ReportActivity(const std::shared_ptr<DynDGpuManager>& strong);
223 private:
224 void SetState(const MutexAutoLock&, State);
225 void Tick(const std::shared_ptr<DynDGpuManager>& strong);
226 void DispatchTick(const std::shared_ptr<DynDGpuManager>& strong);
229 } // namespace webgl
231 ////////////////////////////////////////////////////////////////////////////////
233 class WebGLContext : public VRefCounted, public SupportsWeakPtr<WebGLContext> {
234 friend class ScopedDrawCallWrapper;
235 friend class ScopedDrawWithTransformFeedback;
236 friend class ScopedFakeVertexAttrib0;
237 friend class ScopedFBRebinder;
238 friend class WebGL2Context;
239 friend class WebGLContextUserData;
240 friend class WebGLExtensionCompressedTextureASTC;
241 friend class WebGLExtensionCompressedTextureBPTC;
242 friend class WebGLExtensionCompressedTextureES3;
243 friend class WebGLExtensionCompressedTextureETC1;
244 friend class WebGLExtensionCompressedTexturePVRTC;
245 friend class WebGLExtensionCompressedTextureRGTC;
246 friend class WebGLExtensionCompressedTextureS3TC;
247 friend class WebGLExtensionCompressedTextureS3TC_SRGB;
248 friend class WebGLExtensionDepthTexture;
249 friend class WebGLExtensionDisjointTimerQuery;
250 friend class WebGLExtensionDrawBuffers;
251 friend class WebGLExtensionLoseContext;
252 friend class WebGLExtensionMOZDebug;
253 friend class WebGLExtensionVertexArray;
254 friend class WebGLMemoryTracker;
255 friend class webgl::AvailabilityRunnable;
256 friend struct webgl::LinkedProgramInfo;
257 friend struct webgl::SamplerUniformInfo;
258 friend class webgl::ScopedPrepForResourceClear;
259 friend struct webgl::UniformBlockInfo;
261 friend const webgl::CachedDrawFetchLimits* ValidateDraw(WebGLContext*, GLenum,
262 uint32_t);
263 friend RefPtr<const webgl::LinkedProgramInfo> QueryProgramInfo(
264 WebGLProgram* prog, gl::GLContext* gl);
266 MOZ_DECLARE_REFCOUNTED_VIRTUAL_TYPENAME(WebGLContext, override)
268 enum {
269 UNPACK_FLIP_Y_WEBGL = 0x9240,
270 UNPACK_PREMULTIPLY_ALPHA_WEBGL = 0x9241,
271 // We throw InvalidOperation in TexImage if we fail to use GPU fast-path
272 // for texture copy when it is set to true, only for debug purpose.
273 UNPACK_REQUIRE_FASTPATH = 0x10001,
274 CONTEXT_LOST_WEBGL = 0x9242,
275 UNPACK_COLORSPACE_CONVERSION_WEBGL = 0x9243,
276 BROWSER_DEFAULT_WEBGL = 0x9244,
277 UNMASKED_VENDOR_WEBGL = 0x9245,
278 UNMASKED_RENDERER_WEBGL = 0x9246
281 private:
282 class LruPosition final {
283 std::list<WebGLContext*>::iterator mItr;
285 void reset();
287 public:
288 LruPosition();
289 explicit LruPosition(WebGLContext&);
291 LruPosition& operator=(LruPosition&& rhs) {
292 reset();
293 std::swap(mItr, rhs.mItr);
294 return *this;
297 ~LruPosition() { reset(); }
300 LruPosition mLruPosition;
302 public:
303 void BumpLru() {
304 LruPosition next{*this};
305 mLruPosition = std::move(next);
308 void LoseLruContextIfLimitExceeded();
310 // -
312 // We've had issues in the past with nulling `gl` without actually releasing
313 // all of our resources. This construction ensures that we are aware that we
314 // should only null `gl` in DestroyResourcesAndContext.
315 RefPtr<gl::GLContext> mGL_OnlyClearInDestroyResourcesAndContext;
317 public:
318 // Grab a const reference so we can see changes, but can't make changes.
319 const decltype(mGL_OnlyClearInDestroyResourcesAndContext)& gl;
321 private:
322 std::shared_ptr<webgl::DynDGpuManager> mDynDGpuManager;
324 void ReportActivity() const {
325 if (mDynDGpuManager) {
326 mDynDGpuManager->ReportActivity(mDynDGpuManager);
330 public:
331 void CheckForInactivity();
333 protected:
334 const WeakPtr<HostWebGLContext> mHost;
335 const bool mResistFingerprinting;
336 WebGLContextOptions mOptions;
337 const uint32_t mPrincipalKey;
338 Maybe<webgl::Limits> mLimits;
340 bool mIsContextLost = false;
341 const uint32_t mMaxPerfWarnings;
342 mutable uint64_t mNumPerfWarnings = 0;
343 const uint32_t mMaxAcceptableFBStatusInvals;
345 uint64_t mNextFenceId = 1;
346 uint64_t mCompletedFenceId = 0;
348 public:
349 class FuncScope;
351 private:
352 mutable FuncScope* mFuncScope = nullptr;
354 public:
355 MOZ_DECLARE_WEAKREFERENCE_TYPENAME(WebGLContext)
357 static RefPtr<WebGLContext> Create(HostWebGLContext&,
358 const webgl::InitContextDesc&,
359 webgl::InitContextResult* out);
361 private:
362 void FinishInit();
364 protected:
365 WebGLContext(HostWebGLContext&, const webgl::InitContextDesc&);
366 virtual ~WebGLContext();
368 RefPtr<layers::CompositableHost> mCompositableHost;
370 layers::LayersBackend mBackend = layers::LayersBackend::LAYERS_NONE;
372 public:
373 void Resize(uvec2 size);
375 void SetCompositableHost(RefPtr<layers::CompositableHost>& aCompositableHost);
377 RefPtr<mozilla::gfx::SourceSurface> GetSurfaceSnapshot(
378 gfxAlphaType* out_alphaType);
381 * An abstract base class to be implemented by callers wanting to be notified
382 * that a refresh has occurred. Callers must ensure an observer is removed
383 * before it is destroyed.
385 virtual void DidRefresh();
387 void OnMemoryPressure();
389 // -
393 Here are the bind calls that are supposed to be fully-validated client side,
394 so that client's binding state doesn't diverge:
395 * AttachShader
396 * DetachShader
397 * BindFramebuffer
398 * FramebufferAttach
399 * BindBuffer
400 * BindBufferRange
401 * BindTexture
402 * UseProgram
403 * BindSampler
404 * BindTransformFeedback
405 * BindVertexArray
406 * BeginQuery
407 * EndQuery
408 * ActiveTexture
412 const auto& CurFuncScope() const { return *mFuncScope; }
413 const char* FuncName() const;
415 class FuncScope final {
416 public:
417 const WebGLContext& mWebGL;
418 const char* const mFuncName;
419 bool mBindFailureGuard = false;
421 public:
422 FuncScope(const WebGLContext& webgl, const char* funcName);
423 ~FuncScope();
426 void GenerateErrorImpl(const GLenum err, const nsACString& text) const {
427 GenerateErrorImpl(err, std::string(text.BeginReading()));
429 void GenerateErrorImpl(const GLenum err, const std::string& text) const;
431 template <typename... Args>
432 void GenerateError(const GLenum err, const char* const fmt,
433 const Args&... args) const {
434 MOZ_ASSERT(FuncName());
436 nsCString text;
437 text.AppendPrintf("WebGL warning: %s: ", FuncName());
439 #ifdef __clang__
440 # pragma clang diagnostic push
441 # pragma clang diagnostic ignored "-Wformat-security"
442 #endif
443 text.AppendPrintf(fmt, args...);
444 #ifdef __clang__
445 # pragma clang diagnostic pop
446 #endif
448 GenerateErrorImpl(err, text);
451 template <typename... Args>
452 void ErrorInvalidEnum(const char* const fmt, const Args&... args) const {
453 GenerateError(LOCAL_GL_INVALID_ENUM, fmt, args...);
455 template <typename... Args>
456 void ErrorInvalidOperation(const char* const fmt, const Args&... args) const {
457 GenerateError(LOCAL_GL_INVALID_OPERATION, fmt, args...);
459 template <typename... Args>
460 void ErrorInvalidValue(const char* const fmt, const Args&... args) const {
461 GenerateError(LOCAL_GL_INVALID_VALUE, fmt, args...);
463 template <typename... Args>
464 void ErrorInvalidFramebufferOperation(const char* const fmt,
465 const Args&... args) const {
466 GenerateError(LOCAL_GL_INVALID_FRAMEBUFFER_OPERATION, fmt, args...);
468 template <typename... Args>
469 void ErrorOutOfMemory(const char* const fmt, const Args&... args) const {
470 GenerateError(LOCAL_GL_OUT_OF_MEMORY, fmt, args...);
473 template <typename... Args>
474 void ErrorImplementationBug(const char* const fmt,
475 const Args&... args) const {
476 const nsPrintfCString newFmt(
477 "Implementation bug, please file at %s! %s",
478 "https://bugzilla.mozilla.org/"
479 "enter_bug.cgi?product=Core&component=Canvas%3A+WebGL",
480 fmt);
481 GenerateError(LOCAL_GL_OUT_OF_MEMORY, newFmt.BeginReading(), args...);
482 MOZ_ASSERT(false, "WebGLContext::ErrorImplementationBug");
483 NS_ERROR("WebGLContext::ErrorImplementationBug");
486 void ErrorInvalidEnumInfo(const char* info, GLenum enumValue) const;
487 void ErrorInvalidEnumArg(const char* argName, GLenum val) const;
489 static const char* ErrorName(GLenum error);
492 * Return displayable name for GLenum.
493 * This version is like gl::GLenumToStr but with out the GL_ prefix to
494 * keep consistency with how errors are reported from WebGL.
495 * Returns hex formatted version of glenum if glenum is unknown.
497 static void EnumName(GLenum val, nsCString* out_name);
499 void DummyReadFramebufferOperation();
501 WebGLTexture* GetActiveTex(const GLenum texTarget) const;
503 already_AddRefed<layers::Layer> GetCanvasLayer(nsDisplayListBuilder* builder,
504 layers::Layer* oldLayer,
505 layers::LayerManager* manager);
507 Maybe<ICRData> InitializeCanvasRenderer(layers::LayersBackend backend);
509 gl::GLContext* GL() const { return gl; }
511 bool IsPremultAlpha() const { return mOptions.premultipliedAlpha; }
513 bool IsPreservingDrawingBuffer() const {
514 return mOptions.preserveDrawingBuffer;
517 // Prepare the context for capture before compositing
518 bool PresentScreenBuffer(gl::GLScreenBuffer* const screen = nullptr);
520 // Present to compositor
521 bool Present();
523 void RunContextLossTimer();
524 void CheckForContextLoss();
526 bool TryToRestoreContext();
528 void AssertCachedBindings() const;
529 void AssertCachedGlobalState() const;
531 // WebIDL WebGLRenderingContext API
532 void Commit();
534 uvec2 DrawingBufferSize();
536 public:
537 void GetContextAttributes(dom::Nullable<dom::WebGLContextAttributes>& retval);
539 // This is the entrypoint. Don't test against it directly.
540 bool IsContextLost() const { return mIsContextLost; }
542 // -
544 RefPtr<WebGLBuffer> CreateBuffer();
545 RefPtr<WebGLFramebuffer> CreateFramebuffer();
546 RefPtr<WebGLProgram> CreateProgram();
547 RefPtr<WebGLQuery> CreateQuery();
548 RefPtr<WebGLRenderbuffer> CreateRenderbuffer();
549 RefPtr<WebGLShader> CreateShader(GLenum type);
550 RefPtr<WebGLTexture> CreateTexture();
551 RefPtr<WebGLVertexArray> CreateVertexArray();
553 // -
555 void AttachShader(WebGLProgram& prog, WebGLShader& shader);
556 void BindAttribLocation(WebGLProgram& prog, GLuint location,
557 const std::string& name) const;
558 void BindFramebuffer(GLenum target, WebGLFramebuffer* fb);
559 void BindRenderbuffer(GLenum target, WebGLRenderbuffer* fb);
560 void BindVertexArray(WebGLVertexArray* vao);
561 void BlendColor(GLclampf r, GLclampf g, GLclampf b, GLclampf a);
562 void BlendEquationSeparate(GLenum modeRGB, GLenum modeAlpha);
563 void BlendFuncSeparate(GLenum srcRGB, GLenum dstRGB, GLenum srcAlpha,
564 GLenum dstAlpha);
565 GLenum CheckFramebufferStatus(GLenum target);
566 void Clear(GLbitfield mask);
567 void ClearColor(GLclampf r, GLclampf g, GLclampf b, GLclampf a);
568 void ClearDepth(GLclampf v);
569 void ClearStencil(GLint v);
570 void ColorMask(WebGLboolean r, WebGLboolean g, WebGLboolean b,
571 WebGLboolean a);
572 void CompileShader(WebGLShader& shader);
574 private:
575 void CompileShaderANGLE(WebGLShader* shader);
576 void CompileShaderBypass(WebGLShader* shader, const nsCString& shaderSource);
578 public:
579 void CullFace(GLenum face);
580 void DepthFunc(GLenum func);
581 void DepthMask(WebGLboolean b);
582 void DepthRange(GLclampf zNear, GLclampf zFar);
583 void DetachShader(WebGLProgram& prog, const WebGLShader& shader);
584 void DrawBuffers(const std::vector<GLenum>& buffers);
585 void Flush();
586 void Finish();
588 void FramebufferAttach(GLenum target, GLenum attachSlot,
589 GLenum bindImageTarget,
590 const webgl::FbAttachInfo& toAttach);
592 void FrontFace(GLenum mode);
594 Maybe<double> GetBufferParameter(GLenum target, GLenum pname);
595 webgl::CompileResult GetCompileResult(const WebGLShader&) const;
596 GLenum GetError();
597 GLint GetFragDataLocation(const WebGLProgram&, const std::string& name) const;
599 Maybe<double> GetFramebufferAttachmentParameter(WebGLFramebuffer*,
600 GLenum attachment,
601 GLenum pname) const;
603 Maybe<double> GetRenderbufferParameter(const WebGLRenderbuffer&,
604 GLenum pname) const;
605 webgl::LinkResult GetLinkResult(const WebGLProgram&) const;
607 Maybe<webgl::ShaderPrecisionFormat> GetShaderPrecisionFormat(
608 GLenum shadertype, GLenum precisiontype) const;
610 webgl::GetUniformData GetUniform(const WebGLProgram&, uint32_t loc) const;
612 void Hint(GLenum target, GLenum mode);
614 void LineWidth(GLfloat width);
615 void LinkProgram(WebGLProgram& prog);
616 void PixelStorei(GLenum pname, GLint param);
617 void PolygonOffset(GLfloat factor, GLfloat units);
619 RefPtr<layers::SharedSurfaceTextureClient> GetVRFrame();
620 void ClearVRFrame();
621 void EnsureVRReady();
623 ////
625 webgl::PackingInfo ValidImplementationColorReadPI(
626 const webgl::FormatUsageInfo* usage) const;
628 protected:
629 void ReadPixelsImpl(GLint x, GLint y, GLsizei width, GLsizei height,
630 GLenum format, GLenum type, uintptr_t data,
631 uint64_t dataLen);
632 bool DoReadPixelsAndConvert(const webgl::FormatInfo* srcFormat, GLint x,
633 GLint y, GLsizei width, GLsizei height,
634 GLenum format, GLenum destType, uintptr_t dest,
635 uint64_t dataLen, uint32_t rowStride);
637 public:
638 void ReadPixelsPbo(GLint x, GLint y, GLsizei width, GLsizei height,
639 GLenum format, GLenum type, uint64_t offset);
641 void ReadPixels(GLint x, GLint y, GLsizei width, GLsizei height,
642 GLenum format, GLenum type, const Range<uint8_t>& dest);
644 ////
646 void RenderbufferStorageMultisample(WebGLRenderbuffer&, uint32_t samples,
647 GLenum internalformat, uint32_t width,
648 uint32_t height) const;
650 public:
651 void SampleCoverage(GLclampf value, WebGLboolean invert);
652 void Scissor(GLint x, GLint y, GLsizei width, GLsizei height);
653 void ShaderSource(WebGLShader& shader, const std::string& source) const;
654 void StencilFuncSeparate(GLenum face, GLenum func, GLint ref, GLuint mask);
655 void StencilMaskSeparate(GLenum face, GLuint mask);
656 void StencilOpSeparate(GLenum face, GLenum sfail, GLenum dpfail,
657 GLenum dppass);
659 //////////////////////////
661 void UniformData(uint32_t loc, bool transpose,
662 const Range<const uint8_t>& data) const;
664 ////////////////////////////////////
666 void UseProgram(WebGLProgram* prog);
668 bool ValidateAttribArraySetter(uint32_t count, uint32_t arrayLength);
669 bool ValidateProgram(const WebGLProgram& prog) const;
670 void Viewport(GLint x, GLint y, GLsizei width, GLsizei height);
672 // -----------------------------------------------------------------------------
673 // Buffer Objects (WebGLContextBuffers.cpp)
674 void BindBuffer(GLenum target, WebGLBuffer* buffer);
675 void BindBufferRange(GLenum target, GLuint index, WebGLBuffer* buf,
676 uint64_t offset, uint64_t size);
678 void BufferData(GLenum target, uint64_t dataLen, const uint8_t* data,
679 GLenum usage) const;
680 void BufferSubData(GLenum target, uint64_t dstByteOffset, uint64_t srcDataLen,
681 const uint8_t* srcData) const;
683 protected:
684 // bound buffer state
685 RefPtr<WebGLBuffer> mBoundArrayBuffer;
686 RefPtr<WebGLBuffer> mBoundCopyReadBuffer;
687 RefPtr<WebGLBuffer> mBoundCopyWriteBuffer;
688 RefPtr<WebGLBuffer> mBoundPixelPackBuffer;
689 RefPtr<WebGLBuffer> mBoundPixelUnpackBuffer;
690 RefPtr<WebGLBuffer> mBoundTransformFeedbackBuffer;
691 RefPtr<WebGLBuffer> mBoundUniformBuffer;
693 std::vector<IndexedBufferBinding> mIndexedUniformBufferBindings;
695 RefPtr<WebGLBuffer>& GetBufferSlotByTarget(GLenum target);
696 RefPtr<WebGLBuffer>& GetBufferSlotByTargetIndexed(GLenum target,
697 GLuint index);
699 // -
701 void GenErrorIllegalUse(GLenum useTarget, uint32_t useId, GLenum boundTarget,
702 uint32_t boundId) const;
704 bool ValidateBufferForNonTf(const WebGLBuffer&, GLenum nonTfTarget,
705 uint32_t nonTfId) const;
707 bool ValidateBufferForNonTf(const WebGLBuffer* const nonTfBuffer,
708 const GLenum nonTfTarget,
709 const uint32_t nonTfId = -1) const {
710 if (!nonTfBuffer) return true;
711 return ValidateBufferForNonTf(*nonTfBuffer, nonTfTarget, nonTfId);
714 bool ValidateBuffersForTf(const WebGLTransformFeedback&,
715 const webgl::LinkedProgramInfo&) const;
716 bool ValidateBuffersForTf(
717 const std::vector<webgl::BufferAndIndex>& tfBuffers) const;
719 // -----------------------------------------------------------------------------
720 // Queries (WebGL2ContextQueries.cpp)
721 protected:
722 RefPtr<WebGLQuery> mQuerySlot_SamplesPassed;
723 RefPtr<WebGLQuery> mQuerySlot_TFPrimsWritten;
724 RefPtr<WebGLQuery> mQuerySlot_TimeElapsed;
726 RefPtr<WebGLQuery>* ValidateQuerySlotByTarget(GLenum target);
728 public:
729 void BeginQuery(GLenum target, WebGLQuery& query);
730 void EndQuery(GLenum target);
731 Maybe<double> GetQueryParameter(const WebGLQuery& query, GLenum pname) const;
732 void QueryCounter(WebGLQuery&) const;
734 // -----------------------------------------------------------------------------
735 // State and State Requests (WebGLContextState.cpp)
736 private:
737 void SetEnabled(const char* funcName, GLenum cap, bool enabled);
739 public:
740 void Disable(GLenum cap) { SetEnabled("disabled", cap, false); }
741 void Enable(GLenum cap) { SetEnabled("enabled", cap, true); }
742 bool GetStencilBits(GLint* const out_stencilBits) const;
744 virtual Maybe<double> GetParameter(GLenum pname);
745 Maybe<std::string> GetString(GLenum pname) const;
747 bool IsEnabled(GLenum cap);
749 private:
750 // State tracking slots
751 realGLboolean mDitherEnabled = 1;
752 realGLboolean mRasterizerDiscardEnabled = 0;
753 realGLboolean mScissorTestEnabled = 0;
754 realGLboolean mDepthTestEnabled = 0;
755 realGLboolean mStencilTestEnabled = 0;
756 realGLboolean mBlendEnabled = 0;
757 GLenum mGenerateMipmapHint = 0;
759 struct ScissorRect final {
760 GLint x;
761 GLint y;
762 GLsizei w;
763 GLsizei h;
765 void Apply(gl::GLContext&) const;
767 ScissorRect mScissorRect = {};
769 bool ValidateCapabilityEnum(GLenum cap);
770 realGLboolean* GetStateTrackingSlot(GLenum cap);
772 // Allocation debugging variables
773 mutable uint64_t mDataAllocGLCallCount = 0;
775 void OnDataAllocCall() const { mDataAllocGLCallCount++; }
777 uint64_t GetNumGLDataAllocCalls() const { return mDataAllocGLCallCount; }
779 void OnEndOfFrame();
781 // -----------------------------------------------------------------------------
782 // Texture funcions (WebGLContextTextures.cpp)
783 public:
784 void ActiveTexture(uint32_t texUnit);
785 void BindTexture(GLenum texTarget, WebGLTexture* tex);
786 void GenerateMipmap(GLenum texTarget);
788 Maybe<double> GetTexParameter(const WebGLTexture&, GLenum pname) const;
789 void TexParameter_base(GLenum texTarget, GLenum pname,
790 const FloatOrInt& param);
792 virtual bool IsTexParamValid(GLenum pname) const;
794 ////////////////////////////////////
795 // Uploads
797 // CompressedTexSubImage if `sub`
798 void CompressedTexImage(bool sub, GLenum imageTarget, uint32_t level,
799 GLenum format, uvec3 offset, uvec3 size,
800 const Range<const uint8_t>& src,
801 const uint32_t pboImageSize,
802 const Maybe<uint64_t>& pboOffset) const;
804 // CopyTexSubImage if `!respectFormat`
805 void CopyTexImage(GLenum imageTarget, uint32_t level, GLenum respecFormat,
806 uvec3 dstOffset, const ivec2& srcOffset,
807 const uvec2& size) const;
809 // TexSubImage if `!respectFormat`
810 void TexImage(GLenum imageTarget, uint32_t level, GLenum respecFormat,
811 uvec3 offset, uvec3 size, const webgl::PackingInfo& pi,
812 const TexImageSource& src,
813 const dom::HTMLCanvasElement& canvas) const;
815 void TexStorage(GLenum texTarget, uint32_t levels, GLenum sizedFormat,
816 uvec3 size) const;
818 UniquePtr<webgl::TexUnpackBlob> ToTexUnpackBytes(
819 const WebGLTexImageData& imageData);
821 UniquePtr<webgl::TexUnpackBytes> ToTexUnpackBytes(WebGLTexPboOffset& aPbo);
823 ////////////////////////////////////
824 // WebGLTextureUpload.cpp
825 protected:
826 bool ValidateTexImageSpecification(uint8_t funcDims, GLenum texImageTarget,
827 GLint level, GLsizei width, GLsizei height,
828 GLsizei depth, GLint border,
829 TexImageTarget* const out_target,
830 WebGLTexture** const out_texture,
831 webgl::ImageInfo** const out_imageInfo);
832 bool ValidateTexImageSelection(uint8_t funcDims, GLenum texImageTarget,
833 GLint level, GLint xOffset, GLint yOffset,
834 GLint zOffset, GLsizei width, GLsizei height,
835 GLsizei depth,
836 TexImageTarget* const out_target,
837 WebGLTexture** const out_texture,
838 webgl::ImageInfo** const out_imageInfo);
839 bool ValidateUnpackInfo(bool usePBOs, GLenum format, GLenum type,
840 webgl::PackingInfo* const out);
842 // -----------------------------------------------------------------------------
843 // Vertices Feature (WebGLContextVertices.cpp)
844 GLenum mPrimRestartTypeBytes = 0;
846 public:
847 void DrawArraysInstanced(GLenum mode, GLint first, GLsizei vertexCount,
848 GLsizei instanceCount);
849 void DrawElementsInstanced(GLenum mode, GLsizei vertexCount, GLenum type,
850 WebGLintptr byteOffset, GLsizei instanceCount);
852 void EnableVertexAttribArray(GLuint index);
853 void DisableVertexAttribArray(GLuint index);
855 Maybe<double> GetVertexAttrib(GLuint index, GLenum pname);
857 ////
859 void VertexAttrib4T(GLuint index, const webgl::TypedQuad&);
861 ////
863 void VertexAttribPointer(bool isFuncInt, GLuint index, GLint size,
864 GLenum type, bool normalized, uint32_t stride,
865 uint64_t byteOffset);
867 public:
868 void VertexAttribDivisor(GLuint index, GLuint divisor);
870 private:
871 WebGLBuffer* DrawElements_check(GLsizei indexCount, GLenum type,
872 WebGLintptr byteOffset,
873 GLsizei instanceCount);
874 void Draw_cleanup();
876 void VertexAttrib1fv_base(GLuint index, uint32_t arrayLength,
877 const GLfloat* ptr);
878 void VertexAttrib2fv_base(GLuint index, uint32_t arrayLength,
879 const GLfloat* ptr);
880 void VertexAttrib3fv_base(GLuint index, uint32_t arrayLength,
881 const GLfloat* ptr);
882 void VertexAttrib4fv_base(GLuint index, uint32_t arrayLength,
883 const GLfloat* ptr);
885 bool BindArrayAttribToLocation0(WebGLProgram* prog);
887 // -----------------------------------------------------------------------------
888 // PROTECTED
889 protected:
890 WebGLVertexAttrib0Status WhatDoesVertexAttrib0Need() const;
891 bool DoFakeVertexAttrib0(uint64_t vertexCount);
892 void UndoFakeVertexAttrib0();
894 bool mResetLayer = true;
895 bool mOptionsFrozen = false;
896 bool mIsMesa = false;
897 bool mLoseContextOnMemoryPressure = false;
898 bool mCanLoseContextInForeground = true;
899 bool mShouldPresent = false;
900 bool mDisableFragHighP = false;
901 bool mVRReady = false;
903 template <typename WebGLObjectType>
904 void DeleteWebGLObjectsArray(nsTArray<WebGLObjectType>& array);
906 GLuint mActiveTexture = 0;
907 GLenum mDefaultFB_DrawBuffer0 = 0;
908 GLenum mDefaultFB_ReadBuffer = 0;
910 mutable GLenum mWebGLError = 0;
912 std::unique_ptr<webgl::ShaderValidator> CreateShaderValidator(
913 GLenum shaderType) const;
915 // some GL constants
916 uint32_t mGLMaxFragmentUniformVectors = 0;
917 uint32_t mGLMaxVertexUniformVectors = 0;
918 uint32_t mGLMaxVertexOutputVectors = 0;
919 uint32_t mGLMaxFragmentInputVectors = 0;
921 uint32_t mGLMaxVertexTextureImageUnits = 0;
922 uint32_t mGLMaxFragmentTextureImageUnits = 0;
923 uint32_t mGLMaxCombinedTextureImageUnits = 0;
925 // ES3:
926 uint32_t mGLMinProgramTexelOffset = 0;
927 uint32_t mGLMaxProgramTexelOffset = 0;
929 public:
930 auto GLMaxDrawBuffers() const { return mLimits->maxColorDrawBuffers; }
932 uint32_t MaxValidDrawBuffers() const {
933 if (IsWebGL2() ||
934 IsExtensionEnabled(WebGLExtensionID::WEBGL_draw_buffers)) {
935 return GLMaxDrawBuffers();
937 return 1;
940 GLenum LastColorAttachmentEnum() const {
941 return LOCAL_GL_COLOR_ATTACHMENT0 + MaxValidDrawBuffers() - 1;
944 const auto& Options() const { return mOptions; }
946 protected:
947 uint32_t mGLMaxRenderbufferSize = 0;
949 public:
950 const auto& Limits() const { return *mLimits; }
951 auto MaxVertexAttribs() const { return mLimits->maxVertexAttribs; }
952 auto GLMaxTextureUnits() const { return mLimits->maxTexUnits; }
954 bool IsFormatValidForFB(TexInternalFormat format) const;
956 protected:
957 // -------------------------------------------------------------------------
958 // WebGL extensions (implemented in WebGLContextExtensions.cpp)
960 EnumeratedArray<WebGLExtensionID, WebGLExtensionID::Max,
961 std::unique_ptr<WebGLExtensionBase>>
962 mExtensions;
964 public:
965 void RequestExtension(WebGLExtensionID, bool explicitly = true);
967 // returns true if the extension has been enabled by calling getExtension.
968 bool IsExtensionEnabled(const WebGLExtensionID id) const {
969 return bool(mExtensions[id]);
972 bool IsExtensionExplicit(WebGLExtensionID) const;
973 void WarnIfImplicit(WebGLExtensionID) const;
975 bool IsExtensionSupported(WebGLExtensionID) const;
977 // -------------------------------------------------------------------------
978 // WebGL 2 specifics (implemented in WebGL2Context.cpp)
979 public:
980 virtual bool IsWebGL2() const { return false; }
982 struct FailureReason {
983 nsCString key; // For reporting.
984 nsCString info;
986 FailureReason() {}
988 template <typename A, typename B>
989 FailureReason(const A& _key, const B& _info)
990 : key(nsCString(_key)), info(nsCString(_info)) {}
993 protected:
994 bool InitWebGL2(FailureReason* const out_failReason);
996 bool CreateAndInitGL(bool forceEnabled,
997 std::vector<FailureReason>* const out_failReasons);
999 // -------------------------------------------------------------------------
1000 // Validation functions (implemented in WebGLContextValidate.cpp)
1001 bool InitAndValidateGL(FailureReason* const out_failReason);
1003 bool ValidateBlendEquationEnum(GLenum cap, const char* info);
1004 bool ValidateBlendFuncEnumsCompatibility(GLenum sfactor, GLenum dfactor,
1005 const char* info);
1006 bool ValidateStencilOpEnum(GLenum action, const char* info);
1007 bool ValidateFaceEnum(GLenum face);
1008 bool ValidateTexInputData(GLenum type, js::Scalar::Type jsArrayType,
1009 WebGLTexImageFunc func, WebGLTexDimensions dims);
1010 bool ValidateAttribPointer(bool integerMode, GLuint index, GLint size,
1011 GLenum type, WebGLboolean normalized,
1012 GLsizei stride, WebGLintptr byteOffset,
1013 const char* info);
1014 bool ValidateStencilParamsForDrawCall() const;
1016 bool ValidateCopyTexImage(TexInternalFormat srcFormat,
1017 TexInternalFormat dstformat, WebGLTexImageFunc func,
1018 WebGLTexDimensions dims);
1020 bool ValidateTexImage(TexImageTarget texImageTarget, GLint level,
1021 GLenum internalFormat, GLint xoffset, GLint yoffset,
1022 GLint zoffset, GLint width, GLint height, GLint depth,
1023 GLint border, GLenum format, GLenum type,
1024 WebGLTexImageFunc func, WebGLTexDimensions dims);
1025 bool ValidateTexImageFormat(GLenum internalFormat, WebGLTexImageFunc func,
1026 WebGLTexDimensions dims);
1027 bool ValidateTexImageType(GLenum type, WebGLTexImageFunc func,
1028 WebGLTexDimensions dims);
1029 bool ValidateTexImageFormatAndType(GLenum format, GLenum type,
1030 WebGLTexImageFunc func,
1031 WebGLTexDimensions dims);
1032 bool ValidateCompTexImageInternalFormat(GLenum format, WebGLTexImageFunc func,
1033 WebGLTexDimensions dims);
1034 bool ValidateCopyTexImageInternalFormat(GLenum format, WebGLTexImageFunc func,
1035 WebGLTexDimensions dims);
1036 bool ValidateTexImageSize(TexImageTarget texImageTarget, GLint level,
1037 GLint width, GLint height, GLint depth,
1038 WebGLTexImageFunc func, WebGLTexDimensions dims);
1039 bool ValidateTexSubImageSize(GLint x, GLint y, GLint z, GLsizei width,
1040 GLsizei height, GLsizei depth, GLsizei baseWidth,
1041 GLsizei baseHeight, GLsizei baseDepth,
1042 WebGLTexImageFunc func, WebGLTexDimensions dims);
1043 bool ValidateCompTexImageSize(GLint level, GLenum internalFormat,
1044 GLint xoffset, GLint yoffset, GLsizei width,
1045 GLsizei height, GLsizei levelWidth,
1046 GLsizei levelHeight, WebGLTexImageFunc func,
1047 WebGLTexDimensions dims);
1048 bool ValidateCompTexImageDataSize(GLint level, GLenum internalFormat,
1049 GLsizei width, GLsizei height,
1050 uint32_t byteLength, WebGLTexImageFunc func,
1051 WebGLTexDimensions dims);
1053 bool HasDrawBuffers() const {
1054 return IsWebGL2() ||
1055 IsExtensionEnabled(WebGLExtensionID::WEBGL_draw_buffers);
1058 RefPtr<WebGLBuffer>* ValidateBufferSlot(GLenum target);
1060 public:
1061 WebGLBuffer* ValidateBufferSelection(GLenum target) const;
1063 protected:
1064 IndexedBufferBinding* ValidateIndexedBufferSlot(GLenum target, GLuint index);
1066 bool ValidateIndexedBufferBinding(
1067 GLenum target, GLuint index,
1068 RefPtr<WebGLBuffer>** const out_genericBinding,
1069 IndexedBufferBinding** const out_indexedBinding);
1071 public:
1072 bool ValidateNonNegative(const char* argName, int64_t val) const {
1073 if (MOZ_UNLIKELY(val < 0)) {
1074 ErrorInvalidValue("`%s` must be non-negative.", argName);
1075 return false;
1077 return true;
1080 template <typename T>
1081 bool ValidateNonNull(const char* const argName,
1082 const dom::Nullable<T>& maybe) const {
1083 if (maybe.IsNull()) {
1084 ErrorInvalidValue("%s: Cannot be null.", argName);
1085 return false;
1087 return true;
1090 ////
1092 protected:
1093 void DestroyResourcesAndContext();
1095 // helpers
1097 bool ConvertImage(size_t width, size_t height, size_t srcStride,
1098 size_t dstStride, const uint8_t* src, uint8_t* dst,
1099 WebGLTexelFormat srcFormat, bool srcPremultiplied,
1100 WebGLTexelFormat dstFormat, bool dstPremultiplied,
1101 size_t dstTexelSize);
1103 //////
1104 public:
1105 template <typename T>
1106 bool ValidateObject(const char* const argName, const T& object) const {
1107 // Todo: Remove all callers.
1108 return true;
1111 template <typename T>
1112 bool ValidateObject(const char* const argName, const T* const object) const {
1113 // Todo: Remove most (all?) callers.
1114 if (!object) {
1115 ErrorInvalidOperation(
1116 "%s: Object argument cannot have been marked for"
1117 " deletion.",
1118 argName);
1119 return false;
1121 return true;
1124 ////
1126 public:
1127 void LoseContext(
1128 webgl::ContextLossReason reason = webgl::ContextLossReason::None);
1129 const WebGLPixelStore GetPixelStore() const { return mPixelStore; }
1131 protected:
1132 nsTArray<RefPtr<WebGLTexture>> mBound2DTextures;
1133 nsTArray<RefPtr<WebGLTexture>> mBoundCubeMapTextures;
1134 nsTArray<RefPtr<WebGLTexture>> mBound3DTextures;
1135 nsTArray<RefPtr<WebGLTexture>> mBound2DArrayTextures;
1136 nsTArray<RefPtr<WebGLSampler>> mBoundSamplers;
1138 void ResolveTexturesForDraw() const;
1140 RefPtr<WebGLProgram> mCurrentProgram;
1141 RefPtr<const webgl::LinkedProgramInfo> mActiveProgramLinkInfo;
1143 bool ValidateFramebufferTarget(GLenum target) const;
1144 bool ValidateInvalidateFramebuffer(GLenum target,
1145 const Range<const GLenum>& attachments,
1146 std::vector<GLenum>* const scopedVector,
1147 GLsizei* const out_glNumAttachments,
1148 const GLenum** const out_glAttachments);
1150 RefPtr<WebGLFramebuffer> mBoundDrawFramebuffer;
1151 RefPtr<WebGLFramebuffer> mBoundReadFramebuffer;
1152 RefPtr<WebGLTransformFeedback> mBoundTransformFeedback;
1153 RefPtr<WebGLVertexArray> mBoundVertexArray;
1155 public:
1156 const auto& BoundReadFb() const { return mBoundReadFramebuffer; }
1158 protected:
1159 RefPtr<WebGLTransformFeedback> mDefaultTransformFeedback;
1160 RefPtr<WebGLVertexArray> mDefaultVertexArray;
1162 WebGLPixelStore mPixelStore;
1164 CheckedUint32 GetUnpackSize(bool isFunc3D, uint32_t width, uint32_t height,
1165 uint32_t depth, uint8_t bytesPerPixel);
1167 bool ValidatePackSize(uint32_t width, uint32_t height, uint8_t bytesPerPixel,
1168 uint32_t* const out_rowStride,
1169 uint32_t* const out_endOffset);
1171 UniquePtr<webgl::TexUnpackBlob> FromDomElem(
1172 const dom::HTMLCanvasElement& canvas, TexImageTarget target, uvec3 size,
1173 const dom::Element& elem, ErrorResult* const out_error) const;
1175 UniquePtr<webgl::TexUnpackBlob> From(
1176 const dom::HTMLCanvasElement& canvas, TexImageTarget target,
1177 const uvec3& size, const TexImageSource& src,
1178 dom::Uint8ClampedArray* const scopedArr) const;
1180 ////////////////////////////////////
1182 protected:
1183 GLuint mEmptyTFO = 0;
1185 // Generic Vertex Attributes
1186 // Though CURRENT_VERTEX_ATTRIB is listed under "Vertex Shader State" in the
1187 // spec state tables, this isn't vertex shader /object/ state. This array is
1188 // merely state useful to vertex shaders, but is global state.
1189 std::vector<webgl::AttribBaseType> mGenericVertexAttribTypes;
1190 CacheInvalidator mGenericVertexAttribTypeInvalidator;
1192 GLuint mFakeVertexAttrib0BufferObject = 0;
1193 size_t mFakeVertexAttrib0BufferObjectSize = 0;
1194 bool mFakeVertexAttrib0DataDefined = false;
1195 alignas(alignof(float)) uint8_t
1196 mGenericVertexAttrib0Data[sizeof(float) * 4] = {};
1197 alignas(alignof(float)) uint8_t
1198 mFakeVertexAttrib0Data[sizeof(float) * 4] = {};
1200 GLint mStencilRefFront = 0;
1201 GLint mStencilRefBack = 0;
1202 GLuint mStencilValueMaskFront = 0;
1203 GLuint mStencilValueMaskBack = 0;
1204 GLuint mStencilWriteMaskFront = 0;
1205 GLuint mStencilWriteMaskBack = 0;
1206 uint8_t mColorWriteMask = 0; // bitmask
1207 realGLboolean mDepthWriteMask = 0;
1208 GLfloat mColorClearValue[4];
1209 GLint mStencilClearValue = 0;
1210 GLfloat mDepthClearValue = 0.0;
1212 GLint mViewportX = 0;
1213 GLint mViewportY = 0;
1214 GLsizei mViewportWidth = 0;
1215 GLsizei mViewportHeight = 0;
1216 bool mAlreadyWarnedAboutViewportLargerThanDest = false;
1218 GLfloat mLineWidth = 0.0;
1220 WebGLContextLossHandler mContextLossHandler;
1222 // Used for some hardware (particularly Tegra 2 and 4) that likes to
1223 // be Flushed while doing hundreds of draw calls.
1224 int mDrawCallsSinceLastFlush = 0;
1226 mutable uint64_t mWarningCount = 0;
1227 const uint64_t mMaxWarnings;
1228 bool mAlreadyWarnedAboutFakeVertexAttrib0 = false;
1230 bool ShouldGenerateWarnings() const { return mWarningCount < mMaxWarnings; }
1232 bool ShouldGeneratePerfWarnings() const {
1233 return mNumPerfWarnings < mMaxPerfWarnings;
1236 bool mNeedsFakeNoAlpha = false;
1237 bool mNeedsFakeNoDepth = false;
1238 bool mNeedsFakeNoStencil = false;
1239 bool mNeedsFakeNoStencil_UserFBs = false;
1241 mutable uint8_t mDriverColorMask = 0;
1242 bool mDriverDepthTest = false;
1243 bool mDriverStencilTest = false;
1245 bool mNeedsIndexValidation = false;
1247 const bool mAllowFBInvalidation;
1248 #if defined(MOZ_WIDGET_ANDROID)
1249 UniquePtr<gl::GLScreenBuffer> mVRScreen;
1250 #endif
1252 bool Has64BitTimestamps() const;
1254 // --
1256 const uint8_t mMsaaSamples;
1257 mutable uvec2 mRequestedSize;
1258 mutable UniquePtr<gl::MozFramebuffer> mDefaultFB;
1259 mutable bool mDefaultFB_IsInvalid = false;
1260 mutable UniquePtr<gl::MozFramebuffer> mResolvedDefaultFB;
1262 // --
1264 bool EnsureDefaultFB();
1265 bool ValidateAndInitFB(
1266 const WebGLFramebuffer* fb,
1267 GLenum incompleteFbError = LOCAL_GL_INVALID_FRAMEBUFFER_OPERATION);
1268 void DoBindFB(const WebGLFramebuffer* fb,
1269 GLenum target = LOCAL_GL_FRAMEBUFFER) const;
1271 bool BindCurFBForDraw();
1272 bool BindCurFBForColorRead(
1273 const webgl::FormatUsageInfo** out_format, uint32_t* out_width,
1274 uint32_t* out_height,
1275 GLenum incompleteFbError = LOCAL_GL_INVALID_FRAMEBUFFER_OPERATION);
1276 void DoColorMask(uint8_t bitmask) const;
1277 void BlitBackbufferToCurDriverFB() const;
1278 bool BindDefaultFBForRead();
1280 // --
1282 public:
1283 // console logging helpers
1284 template <typename... Args>
1285 void GenerateWarning(const char* const fmt, const Args&... args) const {
1286 GenerateError(0, fmt, args...);
1289 template <typename... Args>
1290 void GeneratePerfWarning(const char* const fmt, const Args&... args) const {
1291 if (!ShouldGeneratePerfWarnings()) return;
1293 const auto funcName = FuncName();
1294 nsCString msg;
1295 msg.AppendPrintf("WebGL perf warning: %s: ", funcName);
1297 #ifdef __clang__
1298 # pragma clang diagnostic push
1299 # pragma clang diagnostic ignored "-Wformat-security"
1300 #endif
1301 msg.AppendPrintf(fmt, args...);
1302 #ifdef __clang__
1303 # pragma clang diagnostic pop
1304 #endif
1306 GenerateErrorImpl(0, msg);
1308 mNumPerfWarnings++;
1309 if (!ShouldGeneratePerfWarnings()) {
1310 GenerateWarning(
1311 "After reporting %u, no further WebGL perf warnings will"
1312 " be reported for this WebGL context.",
1313 uint32_t(mNumPerfWarnings));
1317 public:
1318 UniquePtr<webgl::FormatUsageAuthority> mFormatUsage;
1320 virtual UniquePtr<webgl::FormatUsageAuthority> CreateFormatUsage(
1321 gl::GLContext* gl) const;
1323 const decltype(mBound2DTextures)* TexListForElemType(GLenum elemType) const;
1325 // --
1326 private:
1327 webgl::AvailabilityRunnable* mAvailabilityRunnable = nullptr;
1329 public:
1330 webgl::AvailabilityRunnable* EnsureAvailabilityRunnable();
1332 // -
1334 // Friend list
1335 friend class ScopedCopyTexImageSource;
1336 friend class ScopedResolveTexturesForDraw;
1337 friend class ScopedUnpackReset;
1338 friend class webgl::TexUnpackBlob;
1339 friend class webgl::TexUnpackBytes;
1340 friend class webgl::TexUnpackImage;
1341 friend class webgl::TexUnpackSurface;
1342 friend struct webgl::UniformInfo;
1343 friend class WebGLTexture;
1344 friend class WebGLFBAttachPoint;
1345 friend class WebGLFramebuffer;
1346 friend class WebGLRenderbuffer;
1347 friend class WebGLProgram;
1348 friend class WebGLQuery;
1349 friend class WebGLBuffer;
1350 friend class WebGLSampler;
1351 friend class WebGLShader;
1352 friend class WebGLSync;
1353 friend class WebGLTransformFeedback;
1354 friend class WebGLVertexArray;
1355 friend class WebGLVertexArrayFake;
1356 friend class WebGLVertexArrayGL;
1359 // Returns `value` rounded to the next highest multiple of `multiple`.
1360 // AKA PadToAlignment, StrideForAlignment.
1361 template <typename V, typename M>
1362 V RoundUpToMultipleOf(const V& value, const M& multiple) {
1363 return ((value + multiple - 1) / multiple) * multiple;
1366 const char* GetEnumName(GLenum val, const char* defaultRet = "<unknown>");
1367 std::string EnumString(GLenum val);
1369 class ScopedUnpackReset final {
1370 private:
1371 const WebGLContext* const mWebGL;
1373 public:
1374 explicit ScopedUnpackReset(const WebGLContext* webgl);
1375 ~ScopedUnpackReset();
1378 class ScopedFBRebinder final {
1379 private:
1380 const WebGLContext* const mWebGL;
1382 public:
1383 explicit ScopedFBRebinder(const WebGLContext* const webgl) : mWebGL(webgl) {}
1384 ~ScopedFBRebinder();
1387 class ScopedLazyBind final {
1388 private:
1389 gl::GLContext* const mGL;
1390 const GLenum mTarget;
1392 public:
1393 ScopedLazyBind(gl::GLContext* gl, GLenum target, const WebGLBuffer* buf);
1394 ~ScopedLazyBind();
1397 ////
1399 bool Intersect(int32_t srcSize, int32_t read0, int32_t readSize,
1400 int32_t* out_intRead0, int32_t* out_intWrite0,
1401 int32_t* out_intSize);
1403 uint64_t AvailGroups(uint64_t totalAvailItems, uint64_t firstItemOffset,
1404 uint32_t groupSize, uint32_t groupStride);
1406 ////
1408 class ScopedDrawCallWrapper final {
1409 public:
1410 WebGLContext& mWebGL;
1412 explicit ScopedDrawCallWrapper(WebGLContext& webgl);
1413 ~ScopedDrawCallWrapper();
1416 namespace webgl {
1418 class ScopedPrepForResourceClear final {
1419 const WebGLContext& webgl;
1421 public:
1422 explicit ScopedPrepForResourceClear(const WebGLContext&);
1423 ~ScopedPrepForResourceClear();
1426 struct IndexedName final {
1427 std::string name;
1428 uint64_t index;
1430 Maybe<IndexedName> ParseIndexed(const std::string& str);
1432 } // namespace webgl
1434 webgl::LinkActiveInfo GetLinkActiveInfo(
1435 gl::GLContext& gl, const GLuint prog, const bool webgl2,
1436 const std::unordered_map<std::string, std::string>& nameUnmap);
1438 } // namespace mozilla
1440 #endif