зеркало из https://github.com/mozilla/gecko-dev.git
Backed out changeset 57fa22ef0461 (bug 1615751) for multiple build bustages.
DONTBUILD CLOSED TREE
This commit is contained in:
Родитель
739ec46d60
Коммит
fa5241b0f1
|
@ -2120,6 +2120,9 @@ void GLContext::ReportOutstandingNames() {
|
|||
#endif /* DEBUG */
|
||||
|
||||
void GLContext::GuaranteeResolve() {
|
||||
if (mScreen) {
|
||||
mScreen->AssureBlitted();
|
||||
}
|
||||
fFinish();
|
||||
}
|
||||
|
||||
|
@ -2332,6 +2335,21 @@ bool GLContext::Readback(SharedSurface* src, gfx::DataSourceSurface* dest) {
|
|||
return true;
|
||||
}
|
||||
|
||||
// Do whatever tear-down is necessary after drawing to our offscreen FBO,
|
||||
// if it's bound.
|
||||
void GLContext::AfterGLDrawCall() {
|
||||
if (mScreen) {
|
||||
mScreen->AfterDrawCall();
|
||||
}
|
||||
mHeavyGLCallsSinceLastFlush = true;
|
||||
}
|
||||
|
||||
// Do whatever setup is necessary to read from our offscreen FBO, if it's
|
||||
// bound.
|
||||
void GLContext::BeforeGLReadCall() {
|
||||
if (mScreen) mScreen->BeforeReadCall();
|
||||
}
|
||||
|
||||
void GLContext::fBindFramebuffer(GLenum target, GLuint framebuffer) {
|
||||
if (!mScreen) {
|
||||
raw_fBindFramebuffer(target, framebuffer);
|
||||
|
@ -2602,6 +2620,10 @@ bool GLContext::InitOffscreen(const gfx::IntSize& size,
|
|||
return true;
|
||||
}
|
||||
|
||||
bool GLContext::IsDrawingToDefaultFramebuffer() {
|
||||
return Screen()->IsDrawFramebufferDefault();
|
||||
}
|
||||
|
||||
GLuint CreateTexture(GLContext* aGL, GLenum aInternalFormat, GLenum aFormat,
|
||||
GLenum aType, const gfx::IntSize& aSize, bool linear) {
|
||||
GLuint tex = 0;
|
||||
|
|
|
@ -726,11 +726,11 @@ class GLContext : public GenericAtomicRefCounted,
|
|||
|
||||
// Do whatever tear-down is necessary after drawing to our offscreen FBO,
|
||||
// if it's bound.
|
||||
void AfterGLDrawCall() { mHeavyGLCallsSinceLastFlush = true; }
|
||||
void AfterGLDrawCall();
|
||||
|
||||
// Do whatever setup is necessary to read from our offscreen FBO, if it's
|
||||
// bound.
|
||||
void BeforeGLReadCall() {}
|
||||
void BeforeGLReadCall();
|
||||
|
||||
// Do whatever tear-down is necessary after reading from our offscreen FBO,
|
||||
// if it's bound.
|
||||
|
@ -3568,6 +3568,8 @@ class GLContext : public GenericAtomicRefCounted,
|
|||
|
||||
bool WorkAroundDriverBugs() const { return mWorkAroundDriverBugs; }
|
||||
|
||||
bool IsDrawingToDefaultFramebuffer();
|
||||
|
||||
bool IsOffscreenSizeAllowed(const gfx::IntSize& aSize) const;
|
||||
|
||||
virtual bool Init();
|
||||
|
|
|
@ -415,6 +415,15 @@ bool GLContextEGL::ReleaseTexImage() {
|
|||
}
|
||||
|
||||
void GLContextEGL::SetEGLSurfaceOverride(EGLSurface surf) {
|
||||
if (Screen()) {
|
||||
/* Blit `draw` to `read` if we need to, before we potentially juggle
|
||||
* `read` around. If we don't, we might attach a different `read`,
|
||||
* and *then* hit AssureBlitted, which will blit a dirty `draw` onto
|
||||
* the wrong `read`!
|
||||
*/
|
||||
Screen()->AssureBlitted();
|
||||
}
|
||||
|
||||
mSurfaceOverride = surf;
|
||||
DebugOnly<bool> ok = MakeCurrent(true);
|
||||
MOZ_ASSERT(ok);
|
||||
|
|
|
@ -156,6 +156,9 @@ GLScreenBuffer::GLScreenBuffer(GLContext* gl, const SurfaceCaps& caps,
|
|||
: mGL(gl),
|
||||
mCaps(caps),
|
||||
mFactory(std::move(factory)),
|
||||
mNeedsBlit(true),
|
||||
mUserReadBufferMode(LOCAL_GL_BACK),
|
||||
mUserDrawBufferMode(LOCAL_GL_BACK),
|
||||
mUserDrawFB(0),
|
||||
mUserReadFB(0),
|
||||
mInternalDrawFB(0),
|
||||
|
@ -178,6 +181,36 @@ GLScreenBuffer::~GLScreenBuffer() {
|
|||
mBack->Surf()->ProducerRelease();
|
||||
}
|
||||
|
||||
void GLScreenBuffer::BindAsFramebuffer(GLContext* const gl,
|
||||
GLenum target) const {
|
||||
GLuint drawFB = DrawFB();
|
||||
GLuint readFB = ReadFB();
|
||||
|
||||
if (!gl->IsSupported(GLFeature::split_framebuffer)) {
|
||||
MOZ_ASSERT(drawFB == readFB);
|
||||
gl->raw_fBindFramebuffer(target, readFB);
|
||||
return;
|
||||
}
|
||||
|
||||
switch (target) {
|
||||
case LOCAL_GL_FRAMEBUFFER:
|
||||
gl->raw_fBindFramebuffer(LOCAL_GL_DRAW_FRAMEBUFFER_EXT, drawFB);
|
||||
gl->raw_fBindFramebuffer(LOCAL_GL_READ_FRAMEBUFFER_EXT, readFB);
|
||||
break;
|
||||
|
||||
case LOCAL_GL_DRAW_FRAMEBUFFER_EXT:
|
||||
gl->raw_fBindFramebuffer(LOCAL_GL_DRAW_FRAMEBUFFER_EXT, drawFB);
|
||||
break;
|
||||
|
||||
case LOCAL_GL_READ_FRAMEBUFFER_EXT:
|
||||
gl->raw_fBindFramebuffer(LOCAL_GL_READ_FRAMEBUFFER_EXT, readFB);
|
||||
break;
|
||||
|
||||
default:
|
||||
MOZ_CRASH("GFX: Bad `target` for BindFramebuffer.");
|
||||
}
|
||||
}
|
||||
|
||||
void GLScreenBuffer::BindFB(GLuint fb) {
|
||||
GLuint drawFB = DrawFB();
|
||||
GLuint readFB = ReadFB();
|
||||
|
@ -229,6 +262,28 @@ void GLScreenBuffer::BindReadFB(GLuint fb) {
|
|||
#endif
|
||||
}
|
||||
|
||||
void GLScreenBuffer::BindFB_Internal(GLuint fb) {
|
||||
mInternalDrawFB = mUserDrawFB = fb;
|
||||
mInternalReadFB = mUserReadFB = fb;
|
||||
mGL->raw_fBindFramebuffer(LOCAL_GL_FRAMEBUFFER, mInternalDrawFB);
|
||||
|
||||
#ifdef DEBUG
|
||||
mInInternalMode_DrawFB = true;
|
||||
mInInternalMode_ReadFB = true;
|
||||
#endif
|
||||
}
|
||||
|
||||
void GLScreenBuffer::BindDrawFB_Internal(GLuint fb) {
|
||||
MOZ_ASSERT(mGL->IsSupported(GLFeature::split_framebuffer));
|
||||
|
||||
mInternalDrawFB = mUserDrawFB = fb;
|
||||
mGL->raw_fBindFramebuffer(LOCAL_GL_DRAW_FRAMEBUFFER_EXT, mInternalDrawFB);
|
||||
|
||||
#ifdef DEBUG
|
||||
mInInternalMode_DrawFB = true;
|
||||
#endif
|
||||
}
|
||||
|
||||
void GLScreenBuffer::BindReadFB_Internal(GLuint fb) {
|
||||
MOZ_ASSERT(mGL->IsSupported(GLFeature::split_framebuffer));
|
||||
|
||||
|
@ -302,6 +357,18 @@ void GLScreenBuffer::DeletingFB(GLuint fb) {
|
|||
}
|
||||
}
|
||||
|
||||
void GLScreenBuffer::AfterDrawCall() {
|
||||
if (mUserDrawFB != 0) return;
|
||||
|
||||
RequireBlit();
|
||||
}
|
||||
|
||||
void GLScreenBuffer::BeforeReadCall() {
|
||||
if (mUserReadFB != 0) return;
|
||||
|
||||
AssureBlitted();
|
||||
}
|
||||
|
||||
bool GLScreenBuffer::CopyTexImage2D(GLenum target, GLint level,
|
||||
GLenum internalformat, GLint x, GLint y,
|
||||
GLsizei width, GLsizei height,
|
||||
|
@ -340,6 +407,14 @@ bool GLScreenBuffer::ReadPixels(GLint x, GLint y, GLsizei width, GLsizei height,
|
|||
return false;
|
||||
}
|
||||
|
||||
void GLScreenBuffer::RequireBlit() { mNeedsBlit = true; }
|
||||
|
||||
void GLScreenBuffer::AssureBlitted() {
|
||||
if (!mNeedsBlit) return;
|
||||
|
||||
mNeedsBlit = false;
|
||||
}
|
||||
|
||||
void GLScreenBuffer::Morph(UniquePtr<SurfaceFactory> newFactory) {
|
||||
MOZ_RELEASE_ASSERT(newFactory, "newFactory must not be null");
|
||||
mFactory = std::move(newFactory);
|
||||
|
@ -375,6 +450,20 @@ bool GLScreenBuffer::Attach(SharedSurface* surf, const gfx::IntSize& size) {
|
|||
// Check that we're all set up.
|
||||
MOZ_ASSERT(SharedSurf() == surf);
|
||||
|
||||
// Update the ReadBuffer mode.
|
||||
if (mGL->IsSupported(gl::GLFeature::read_buffer)) {
|
||||
BindFB(0);
|
||||
mRead->SetReadBuffer(mUserReadBufferMode);
|
||||
}
|
||||
|
||||
// Update the DrawBuffer mode.
|
||||
if (mGL->IsSupported(gl::GLFeature::draw_buffers)) {
|
||||
BindFB(0);
|
||||
SetDrawBuffer(mUserDrawBufferMode);
|
||||
}
|
||||
|
||||
RequireBlit();
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -398,7 +487,7 @@ bool GLScreenBuffer::Swap(const gfx::IntSize& size) {
|
|||
mFront = mBack;
|
||||
mBack = newBack;
|
||||
|
||||
if (mCaps.preserve && mFront && mBack) {
|
||||
if (ShouldPreserveBuffer() && mFront && mBack) {
|
||||
auto src = mFront->Surf();
|
||||
auto dest = mBack->Surf();
|
||||
|
||||
|
@ -435,6 +524,13 @@ bool GLScreenBuffer::Swap(const gfx::IntSize& size) {
|
|||
return true;
|
||||
}
|
||||
|
||||
bool GLScreenBuffer::PublishFrame(const gfx::IntSize& size) {
|
||||
AssureBlitted();
|
||||
|
||||
bool good = Swap(size);
|
||||
return good;
|
||||
}
|
||||
|
||||
bool GLScreenBuffer::Resize(const gfx::IntSize& size) {
|
||||
RefPtr<layers::SharedSurfaceTextureClient> newBack =
|
||||
mFactory->NewTexClient(size);
|
||||
|
@ -459,6 +555,58 @@ UniquePtr<ReadBuffer> GLScreenBuffer::CreateRead(SharedSurface* surf) {
|
|||
return ReadBuffer::Create(gl, caps, formats, surf);
|
||||
}
|
||||
|
||||
void GLScreenBuffer::SetDrawBuffer(GLenum mode) {
|
||||
MOZ_ASSERT(mGL->IsSupported(gl::GLFeature::draw_buffers));
|
||||
MOZ_ASSERT(GetDrawFB() == 0);
|
||||
|
||||
if (!mGL->IsSupported(GLFeature::draw_buffers)) return;
|
||||
|
||||
mUserDrawBufferMode = mode;
|
||||
|
||||
GLuint fb = mRead->mFB;
|
||||
GLenum internalMode;
|
||||
|
||||
switch (mode) {
|
||||
case LOCAL_GL_BACK:
|
||||
internalMode = (fb == 0) ? LOCAL_GL_BACK : LOCAL_GL_COLOR_ATTACHMENT0;
|
||||
break;
|
||||
|
||||
case LOCAL_GL_NONE:
|
||||
internalMode = LOCAL_GL_NONE;
|
||||
break;
|
||||
|
||||
default:
|
||||
MOZ_CRASH("GFX: Bad value.");
|
||||
}
|
||||
|
||||
mGL->MakeCurrent();
|
||||
mGL->fDrawBuffers(1, &internalMode);
|
||||
}
|
||||
|
||||
void GLScreenBuffer::SetReadBuffer(GLenum mode) {
|
||||
MOZ_ASSERT(mGL->IsSupported(gl::GLFeature::read_buffer));
|
||||
MOZ_ASSERT(GetReadFB() == 0);
|
||||
|
||||
mUserReadBufferMode = mode;
|
||||
mRead->SetReadBuffer(mUserReadBufferMode);
|
||||
}
|
||||
|
||||
bool GLScreenBuffer::IsDrawFramebufferDefault() const {
|
||||
return IsReadFramebufferDefault();
|
||||
}
|
||||
|
||||
bool GLScreenBuffer::IsReadFramebufferDefault() const {
|
||||
return SharedSurf()->mAttachType == AttachmentType::Screen;
|
||||
}
|
||||
|
||||
uint32_t GLScreenBuffer::DepthBits() const {
|
||||
const GLFormats& formats = mFactory->mFormats;
|
||||
|
||||
if (formats.depth == LOCAL_GL_DEPTH_COMPONENT16) return 16;
|
||||
|
||||
return 24;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Utils
|
||||
|
||||
|
@ -610,4 +758,27 @@ void ReadBuffer::Attach(SharedSurface* surf) {
|
|||
|
||||
const gfx::IntSize& ReadBuffer::Size() const { return mSurf->mSize; }
|
||||
|
||||
void ReadBuffer::SetReadBuffer(GLenum userMode) const {
|
||||
if (!mGL->IsSupported(GLFeature::read_buffer)) return;
|
||||
|
||||
GLenum internalMode;
|
||||
|
||||
switch (userMode) {
|
||||
case LOCAL_GL_BACK:
|
||||
case LOCAL_GL_FRONT:
|
||||
internalMode = (mFB == 0) ? userMode : LOCAL_GL_COLOR_ATTACHMENT0;
|
||||
break;
|
||||
|
||||
case LOCAL_GL_NONE:
|
||||
internalMode = LOCAL_GL_NONE;
|
||||
break;
|
||||
|
||||
default:
|
||||
MOZ_CRASH("GFX: Bad value.");
|
||||
}
|
||||
|
||||
mGL->MakeCurrent();
|
||||
mGL->fReadBuffer(internalMode);
|
||||
}
|
||||
|
||||
} // namespace mozilla::gl
|
||||
|
|
|
@ -75,9 +75,11 @@ class ReadBuffer {
|
|||
const gfx::IntSize& Size() const;
|
||||
|
||||
SharedSurface* SharedSurf() const { return mSurf; }
|
||||
|
||||
void SetReadBuffer(GLenum mode) const;
|
||||
};
|
||||
|
||||
class GLScreenBuffer final {
|
||||
class GLScreenBuffer {
|
||||
public:
|
||||
// Infallible.
|
||||
static UniquePtr<GLScreenBuffer> Create(GLContext* gl,
|
||||
|
@ -94,12 +96,12 @@ class GLScreenBuffer final {
|
|||
layers::LayersIPCChannel* ipcChannel, layers::LayersBackend backend,
|
||||
bool useANGLE, const layers::TextureFlags& flags);
|
||||
|
||||
private:
|
||||
protected:
|
||||
GLContext* const mGL; // Owns us.
|
||||
public:
|
||||
const SurfaceCaps mCaps;
|
||||
|
||||
private:
|
||||
protected:
|
||||
UniquePtr<SurfaceFactory> mFactory;
|
||||
|
||||
RefPtr<layers::SharedSurfaceTextureClient> mBack;
|
||||
|
@ -107,6 +109,11 @@ class GLScreenBuffer final {
|
|||
|
||||
UniquePtr<ReadBuffer> mRead;
|
||||
|
||||
bool mNeedsBlit;
|
||||
|
||||
GLenum mUserReadBufferMode;
|
||||
GLenum mUserDrawBufferMode;
|
||||
|
||||
// Below are the parts that help us pretend to be framebuffer 0:
|
||||
GLuint mUserDrawFB;
|
||||
GLuint mUserReadFB;
|
||||
|
@ -124,19 +131,25 @@ class GLScreenBuffer final {
|
|||
public:
|
||||
virtual ~GLScreenBuffer();
|
||||
|
||||
const auto& Factory() const { return mFactory; }
|
||||
const auto& Front() const { return mFront; }
|
||||
SurfaceFactory* Factory() const { return mFactory.get(); }
|
||||
|
||||
const RefPtr<layers::SharedSurfaceTextureClient>& Front() const {
|
||||
return mFront;
|
||||
}
|
||||
|
||||
SharedSurface* SharedSurf() const {
|
||||
MOZ_ASSERT(mRead);
|
||||
return mRead->SharedSurf();
|
||||
}
|
||||
|
||||
private:
|
||||
bool ShouldPreserveBuffer() const { return mCaps.preserve; }
|
||||
|
||||
GLuint DrawFB() const { return ReadFB(); }
|
||||
|
||||
GLuint ReadFB() const { return mRead->mFB; }
|
||||
|
||||
public:
|
||||
uint32_t DepthBits() const;
|
||||
|
||||
void DeletingFB(GLuint fb);
|
||||
|
||||
const gfx::IntSize& Size() const {
|
||||
|
@ -146,10 +159,23 @@ class GLScreenBuffer final {
|
|||
|
||||
bool IsReadBufferReady() const { return mRead.get() != nullptr; }
|
||||
|
||||
void BindAsFramebuffer(GLContext* const gl, GLenum target) const;
|
||||
|
||||
void RequireBlit();
|
||||
void AssureBlitted();
|
||||
void AfterDrawCall();
|
||||
void BeforeReadCall();
|
||||
|
||||
bool CopyTexImage2D(GLenum target, GLint level, GLenum internalformat,
|
||||
GLint x, GLint y, GLsizei width, GLsizei height,
|
||||
GLint border);
|
||||
|
||||
void SetReadBuffer(GLenum userMode);
|
||||
void SetDrawBuffer(GLenum userMode);
|
||||
|
||||
GLenum GetReadBufferMode() const { return mUserReadBufferMode; }
|
||||
GLenum GetDrawBufferMode() const { return mUserDrawBufferMode; }
|
||||
|
||||
/**
|
||||
* Attempts to read pixels from the current bound framebuffer, if
|
||||
* it is backed by a SharedSurface.
|
||||
|
@ -163,16 +189,16 @@ class GLScreenBuffer final {
|
|||
// Morph changes the factory used to create surfaces.
|
||||
void Morph(UniquePtr<SurfaceFactory> newFactory);
|
||||
|
||||
private:
|
||||
protected:
|
||||
// Returns false on error or inability to resize.
|
||||
bool Swap(const gfx::IntSize& size);
|
||||
|
||||
public:
|
||||
bool PublishFrame(const gfx::IntSize& size) { return Swap(size); }
|
||||
bool PublishFrame(const gfx::IntSize& size);
|
||||
|
||||
bool Resize(const gfx::IntSize& size);
|
||||
|
||||
private:
|
||||
protected:
|
||||
bool Attach(SharedSurface* surf, const gfx::IntSize& size);
|
||||
|
||||
UniquePtr<ReadBuffer> CreateRead(SharedSurface* surf);
|
||||
|
@ -192,7 +218,12 @@ class GLScreenBuffer final {
|
|||
|
||||
// Here `fb` is the actual framebuffer you want bound. Binding 0 will
|
||||
// bind the (generally useless) default framebuffer.
|
||||
void BindFB_Internal(GLuint fb);
|
||||
void BindDrawFB_Internal(GLuint fb);
|
||||
void BindReadFB_Internal(GLuint fb);
|
||||
|
||||
bool IsDrawFramebufferDefault() const;
|
||||
bool IsReadFramebufferDefault() const;
|
||||
};
|
||||
|
||||
} // namespace gl
|
||||
|
|
|
@ -416,7 +416,7 @@ void CanvasClientSharedSurface::UpdateRenderer(gfx::IntSize aSize,
|
|||
mShSurfClient->GetAllocator() !=
|
||||
GetForwarder()->GetTextureForwarder()) {
|
||||
mShSurfClient =
|
||||
CloneSurface(mShSurfClient->Surf(), gl->Screen()->Factory().get());
|
||||
CloneSurface(mShSurfClient->Surf(), gl->Screen()->Factory());
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Загрузка…
Ссылка в новой задаче