diff options
author | kkinnunen <kkinnunen@nvidia.com> | 2014-12-22 06:06:41 -0800 |
---|---|---|
committer | Commit bot <commit-bot@chromium.org> | 2014-12-22 06:06:41 -0800 |
commit | 4be0238b116cb271122f26d0114540d15dce5bf1 (patch) | |
tree | 97df967a0300befb8f761a92e9ab7c8068f5be76 /debugger | |
parent | ac6692b606322eac034fda9b7dceb50689b3f178 (diff) |
Avoid leaking render targets in debugger
Render targets were not unreffed when QGLWidget::resizeGL was called.
Review URL: https://codereview.chromium.org/817243002
Diffstat (limited to 'debugger')
-rw-r--r-- | debugger/QT/SkGLWidget.cpp | 70 | ||||
-rw-r--r-- | debugger/QT/SkGLWidget.h | 9 |
2 files changed, 41 insertions, 38 deletions
diff --git a/debugger/QT/SkGLWidget.cpp b/debugger/QT/SkGLWidget.cpp index bd24d4e3cb..7b2a9186a9 100644 --- a/debugger/QT/SkGLWidget.cpp +++ b/debugger/QT/SkGLWidget.cpp @@ -13,21 +13,12 @@ SkGLWidget::SkGLWidget(SkDebugger* debugger) : QGLWidget() { fDebugger = debugger; - fCurIntf = NULL; - fCurContext = NULL; - fGpuDevice = NULL; - fCanvas = NULL; } SkGLWidget::~SkGLWidget() { - SkSafeUnref(fCurIntf); - SkSafeUnref(fCurContext); - SkSafeUnref(fGpuDevice); - SkSafeUnref(fCanvas); } -void SkGLWidget::setSampleCount(int sampleCount) -{ +void SkGLWidget::setSampleCount(int sampleCount) { QGLFormat currentFormat = format(); currentFormat.setSampleBuffers(sampleCount > 0); currentFormat.setSamples(sampleCount); @@ -35,48 +26,59 @@ void SkGLWidget::setSampleCount(int sampleCount) } void SkGLWidget::initializeGL() { - fCurIntf = GrGLCreateNativeInterface(); + if (!fCurIntf) { + fCurIntf.reset(GrGLCreateNativeInterface()); + } if (!fCurIntf) { return; } + if (!fCurContext) { + fCurContext.reset(GrContext::Create(kOpenGL_GrBackend, (GrBackendContext) fCurIntf.get())); + } + if (!fCurContext) { + return; + } + + // The call may come multiple times, for example after setSampleCount(). The QGLContext will be + // different, but we do not have a mechanism to catch the destroying of QGLContext, so that + // proper resource cleanup could be made. Instead, we assume that the underlying GL context + // never actually changes. If it would, we could not destroy the resources. + fGpuDevice.reset(NULL); + fCanvas.reset(NULL); +} + +void SkGLWidget::createRenderTarget() { + if (!fCurContext) { + return; + } + + glDisable(GL_SCISSOR_TEST); glStencilMask(0xffffffff); glClearStencil(0); glClear(GL_STENCIL_BUFFER_BIT); + fCurContext->resetContext(); + + fGpuDevice.reset(NULL); + fCanvas.reset(NULL); - fCurContext = GrContext::Create(kOpenGL_GrBackend, (GrBackendContext) fCurIntf); GrBackendRenderTargetDesc desc = this->getDesc(this->width(), this->height()); desc.fOrigin = kBottomLeft_GrSurfaceOrigin; - GrRenderTarget* curRenderTarget = fCurContext->wrapBackendRenderTarget(desc); - fGpuDevice = SkGpuDevice::Create(curRenderTarget, - SkSurfaceProps(SkSurfaceProps::kLegacyFontHost_InitType)); - fCanvas = new SkCanvas(fGpuDevice); - curRenderTarget->unref(); + SkAutoTUnref<GrRenderTarget> curRenderTarget(fCurContext->wrapBackendRenderTarget(desc)); + fGpuDevice.reset(SkGpuDevice::Create(curRenderTarget.get(), + SkSurfaceProps(SkSurfaceProps::kLegacyFontHost_InitType))); + fCanvas.reset(new SkCanvas(fGpuDevice)); } void SkGLWidget::resizeGL(int w, int h) { - if (fCurContext) { - glDisable(GL_SCISSOR_TEST); - glStencilMask(0xffffffff); - glClearStencil(0); - glClear(GL_STENCIL_BUFFER_BIT); - fCurContext->resetContext(); - - GrBackendRenderTargetDesc desc = this->getDesc(w, h); - desc.fOrigin = kBottomLeft_GrSurfaceOrigin; - GrRenderTarget* curRenderTarget = fCurContext->wrapBackendRenderTarget(desc); - SkSafeUnref(fGpuDevice); - SkSafeUnref(fCanvas); - fGpuDevice = SkGpuDevice::Create(curRenderTarget, - SkSurfaceProps(SkSurfaceProps::kLegacyFontHost_InitType)); - fCanvas = new SkCanvas(fGpuDevice); - } + SkASSERT(w == this->width() && h == this->height()); + this->createRenderTarget(); fDebugger->setWindowSize(w, h); draw(); } void SkGLWidget::paintGL() { if (!this->isHidden() && fCanvas) { - fDebugger->draw(fCanvas); + fDebugger->draw(fCanvas.get()); // TODO(chudy): Implement an optional flush button in Gui. fCanvas->flush(); emit drawComplete(); diff --git a/debugger/QT/SkGLWidget.h b/debugger/QT/SkGLWidget.h index a8e4604fca..d78ff979fa 100644 --- a/debugger/QT/SkGLWidget.h +++ b/debugger/QT/SkGLWidget.h @@ -45,10 +45,11 @@ protected: private: - const GrGLInterface* fCurIntf; - GrContext* fCurContext; - SkGpuDevice* fGpuDevice; - SkCanvas* fCanvas; + void createRenderTarget(); + SkAutoTUnref<const GrGLInterface> fCurIntf; + SkAutoTUnref<GrContext> fCurContext; + SkAutoTUnref<SkGpuDevice> fGpuDevice; + SkAutoTUnref<SkCanvas> fCanvas; SkDebugger* fDebugger; GrBackendRenderTargetDesc getDesc(int w, int h); }; |