From 58b81e3b0c245c74e2897fc82bede0ff3328472b Mon Sep 17 00:00:00 2001 From: samcake Date: Mon, 24 Oct 2016 18:34:16 -0700 Subject: [PATCH 01/11] Adding counter for the amount of memory used in texture for Framebuffers --- interface/resources/qml/Stats.qml | 3 +++ interface/src/ui/Stats.cpp | 1 + interface/src/ui/Stats.h | 2 ++ libraries/gpu-gl/src/gpu/gl/GLFramebuffer.cpp | 2 +- libraries/gpu-gl/src/gpu/gl/GLTexture.cpp | 8 +++++++- libraries/gpu/src/gpu/Context.cpp | 19 ++++++++++++++++++- libraries/gpu/src/gpu/Context.h | 4 ++++ libraries/gpu/src/gpu/Texture.cpp | 5 +++++ libraries/gpu/src/gpu/Texture.h | 1 + 9 files changed, 42 insertions(+), 3 deletions(-) diff --git a/interface/resources/qml/Stats.qml b/interface/resources/qml/Stats.qml index 6ebe3f2278..7ca527ad3f 100644 --- a/interface/resources/qml/Stats.qml +++ b/interface/resources/qml/Stats.qml @@ -215,6 +215,9 @@ Item { StatText { text: " Commited Memory: " + root.gpuTextureMemory + " MB"; } + StatText { + text: " Framebuffer Memory: " + root.gpuTextureFramebufferMemory + " MB"; + } StatText { text: " Sparse Memory: " + root.gpuTextureSparseMemory + " MB"; visible: 0 != root.gpuSparseTextureEnabled; diff --git a/interface/src/ui/Stats.cpp b/interface/src/ui/Stats.cpp index 6c301f6f0a..9c7d66e0e2 100644 --- a/interface/src/ui/Stats.cpp +++ b/interface/src/ui/Stats.cpp @@ -290,6 +290,7 @@ void Stats::updateStats(bool force) { STAT_UPDATE(qmlTextureMemory, (int)BYTES_TO_MB(OffscreenQmlSurface::getUsedTextureMemory())); STAT_UPDATE(gpuTextureMemory, (int)BYTES_TO_MB(gpu::Texture::getTextureGPUMemoryUsage())); STAT_UPDATE(gpuTextureVirtualMemory, (int)BYTES_TO_MB(gpu::Texture::getTextureGPUVirtualMemoryUsage())); + STAT_UPDATE(gpuTextureFramebufferMemory, (int)BYTES_TO_MB(gpu::Texture::getTextureGPUFramebufferMemoryUsage())); STAT_UPDATE(gpuTextureSparseMemory, (int)BYTES_TO_MB(gpu::Texture::getTextureGPUSparseMemoryUsage())); STAT_UPDATE(gpuSparseTextureEnabled, gpu::Texture::getEnableSparseTextures() ? 1 : 0); STAT_UPDATE(gpuFreeMemory, (int)BYTES_TO_MB(gpu::Context::getFreeGPUMemory())); diff --git a/interface/src/ui/Stats.h b/interface/src/ui/Stats.h index c9fccf02d9..97f047c3d5 100644 --- a/interface/src/ui/Stats.h +++ b/interface/src/ui/Stats.h @@ -93,6 +93,7 @@ class Stats : public QQuickItem { STATS_PROPERTY(int, qmlTextureMemory, 0) STATS_PROPERTY(int, gpuTextureMemory, 0) STATS_PROPERTY(int, gpuTextureVirtualMemory, 0) + STATS_PROPERTY(int, gpuTextureFramebufferMemory, 0) STATS_PROPERTY(int, gpuTextureSparseMemory, 0) STATS_PROPERTY(int, gpuSparseTextureEnabled, 0) STATS_PROPERTY(int, gpuFreeMemory, 0) @@ -187,6 +188,7 @@ signals: void gpuTexturesSparseChanged(); void gpuTextureMemoryChanged(); void gpuTextureVirtualMemoryChanged(); + void gpuTextureFramebufferMemoryChanged(); void gpuTextureSparseMemoryChanged(); void gpuSparseTextureEnabledChanged(); void gpuFreeMemoryChanged(); diff --git a/libraries/gpu-gl/src/gpu/gl/GLFramebuffer.cpp b/libraries/gpu-gl/src/gpu/gl/GLFramebuffer.cpp index eaca31ebdc..0ff00697ca 100644 --- a/libraries/gpu-gl/src/gpu/gl/GLFramebuffer.cpp +++ b/libraries/gpu-gl/src/gpu/gl/GLFramebuffer.cpp @@ -13,7 +13,7 @@ using namespace gpu; using namespace gpu::gl; GLFramebuffer::~GLFramebuffer() { - if (_id) { + if (_id) { auto backend = _backend.lock(); if (backend) { backend->releaseFramebuffer(_id); diff --git a/libraries/gpu-gl/src/gpu/gl/GLTexture.cpp b/libraries/gpu-gl/src/gpu/gl/GLTexture.cpp index ef16e3b53f..cd9807fd46 100644 --- a/libraries/gpu-gl/src/gpu/gl/GLTexture.cpp +++ b/libraries/gpu-gl/src/gpu/gl/GLTexture.cpp @@ -181,8 +181,11 @@ GLTexture::~GLTexture() { // the GL45Texture destructor for doing any required work tracking GPU stats backend->releaseTexture(_id, _size); } + + if (!_external && !_transferrable) { + Backend::updateTextureGPUFramebufferMemoryUsage(_size, 0); + } } - Backend::updateTextureGPUVirtualMemoryUsage(_virtualSize, 0); } void GLTexture::createTexture() { @@ -217,6 +220,9 @@ void GLTexture::withPreservedTexture(std::function f) const { } void GLTexture::setSize(GLuint size) const { + if (!_external && !_transferrable) { + Backend::updateTextureGPUFramebufferMemoryUsage(_size, size); + } Backend::updateTextureGPUMemoryUsage(_size, size); const_cast(_size) = size; } diff --git a/libraries/gpu/src/gpu/Context.cpp b/libraries/gpu/src/gpu/Context.cpp index 6e8a5e312f..ab6bba178a 100644 --- a/libraries/gpu/src/gpu/Context.cpp +++ b/libraries/gpu/src/gpu/Context.cpp @@ -170,7 +170,8 @@ std::atomic Context::_bufferGPUMemoryUsage { 0 }; std::atomic Context::_textureGPUCount{ 0 }; std::atomic Context::_textureGPUSparseCount { 0 }; std::atomic Context::_textureGPUMemoryUsage { 0 }; -std::atomic Context::_textureGPUVirtualMemoryUsage{ 0 }; +std::atomic Context::_textureGPUVirtualMemoryUsage { 0 }; +std::atomic Context::_textureGPUFramebufferMemoryUsage { 0 }; std::atomic Context::_textureGPUSparseMemoryUsage { 0 }; std::atomic Context::_textureGPUTransferCount { 0 }; @@ -262,6 +263,17 @@ void Context::updateTextureGPUVirtualMemoryUsage(Size prevObjectSize, Size newOb } } +void Context::updateTextureGPUFramebufferMemoryUsage(Size prevObjectSize, Size newObjectSize) { + if (prevObjectSize == newObjectSize) { + return; + } + if (newObjectSize > prevObjectSize) { + _textureGPUFramebufferMemoryUsage.fetch_add(newObjectSize - prevObjectSize); + } else { + _textureGPUFramebufferMemoryUsage.fetch_sub(prevObjectSize - newObjectSize); + } +} + void Context::updateTextureGPUSparseMemoryUsage(Size prevObjectSize, Size newObjectSize) { if (prevObjectSize == newObjectSize) { return; @@ -310,6 +322,10 @@ Context::Size Context::getTextureGPUVirtualMemoryUsage() { return _textureGPUVirtualMemoryUsage.load(); } +Context::Size Context::getTextureGPUFramebufferMemoryUsage() { + return _textureGPUFramebufferMemoryUsage.load(); +} + Context::Size Context::getTextureGPUSparseMemoryUsage() { return _textureGPUSparseMemoryUsage.load(); } @@ -329,6 +345,7 @@ void Backend::incrementTextureGPUSparseCount() { Context::incrementTextureGPUSpa void Backend::decrementTextureGPUSparseCount() { Context::decrementTextureGPUSparseCount(); } void Backend::updateTextureGPUMemoryUsage(Resource::Size prevObjectSize, Resource::Size newObjectSize) { Context::updateTextureGPUMemoryUsage(prevObjectSize, newObjectSize); } void Backend::updateTextureGPUVirtualMemoryUsage(Resource::Size prevObjectSize, Resource::Size newObjectSize) { Context::updateTextureGPUVirtualMemoryUsage(prevObjectSize, newObjectSize); } +void Backend::updateTextureGPUFramebufferMemoryUsage(Resource::Size prevObjectSize, Resource::Size newObjectSize) { Context::updateTextureGPUFramebufferMemoryUsage(prevObjectSize, newObjectSize); } void Backend::updateTextureGPUSparseMemoryUsage(Resource::Size prevObjectSize, Resource::Size newObjectSize) { Context::updateTextureGPUSparseMemoryUsage(prevObjectSize, newObjectSize); } void Backend::incrementTextureGPUTransferCount() { Context::incrementTextureGPUTransferCount(); } void Backend::decrementTextureGPUTransferCount() { Context::decrementTextureGPUTransferCount(); } diff --git a/libraries/gpu/src/gpu/Context.h b/libraries/gpu/src/gpu/Context.h index ea199db3aa..763e91b3e4 100644 --- a/libraries/gpu/src/gpu/Context.h +++ b/libraries/gpu/src/gpu/Context.h @@ -101,6 +101,7 @@ public: static void updateTextureGPUMemoryUsage(Resource::Size prevObjectSize, Resource::Size newObjectSize); static void updateTextureGPUSparseMemoryUsage(Resource::Size prevObjectSize, Resource::Size newObjectSize); static void updateTextureGPUVirtualMemoryUsage(Resource::Size prevObjectSize, Resource::Size newObjectSize); + static void updateTextureGPUFramebufferMemoryUsage(Resource::Size prevObjectSize, Resource::Size newObjectSize); static void incrementTextureGPUTransferCount(); static void decrementTextureGPUTransferCount(); @@ -210,6 +211,7 @@ public: static Size getFreeGPUMemory(); static Size getTextureGPUMemoryUsage(); static Size getTextureGPUVirtualMemoryUsage(); + static Size getTextureGPUFramebufferMemoryUsage(); static Size getTextureGPUSparseMemoryUsage(); static uint32_t getTextureGPUTransferCount(); @@ -249,6 +251,7 @@ protected: static void updateTextureGPUMemoryUsage(Size prevObjectSize, Size newObjectSize); static void updateTextureGPUSparseMemoryUsage(Size prevObjectSize, Size newObjectSize); static void updateTextureGPUVirtualMemoryUsage(Size prevObjectSize, Size newObjectSize); + static void updateTextureGPUFramebufferMemoryUsage(Size prevObjectSize, Size newObjectSize); static void incrementTextureGPUTransferCount(); static void decrementTextureGPUTransferCount(); @@ -264,6 +267,7 @@ protected: static std::atomic _textureGPUMemoryUsage; static std::atomic _textureGPUSparseMemoryUsage; static std::atomic _textureGPUVirtualMemoryUsage; + static std::atomic _textureGPUFramebufferMemoryUsage; static std::atomic _textureGPUTransferCount; diff --git a/libraries/gpu/src/gpu/Texture.cpp b/libraries/gpu/src/gpu/Texture.cpp index 5c393d758e..3283f5a4d9 100755 --- a/libraries/gpu/src/gpu/Texture.cpp +++ b/libraries/gpu/src/gpu/Texture.cpp @@ -102,6 +102,11 @@ Texture::Size Texture::getTextureGPUVirtualMemoryUsage() { return Context::getTextureGPUVirtualMemoryUsage(); } + +Texture::Size Texture::getTextureGPUFramebufferMemoryUsage() { + return Context::getTextureGPUFramebufferMemoryUsage(); +} + Texture::Size Texture::getTextureGPUSparseMemoryUsage() { return Context::getTextureGPUSparseMemoryUsage(); } diff --git a/libraries/gpu/src/gpu/Texture.h b/libraries/gpu/src/gpu/Texture.h index 881f4439a1..0f1022a0c9 100755 --- a/libraries/gpu/src/gpu/Texture.h +++ b/libraries/gpu/src/gpu/Texture.h @@ -154,6 +154,7 @@ public: static uint32_t getTextureGPUSparseCount(); static Size getTextureGPUMemoryUsage(); static Size getTextureGPUVirtualMemoryUsage(); + static Size getTextureGPUFramebufferMemoryUsage(); static Size getTextureGPUSparseMemoryUsage(); static uint32_t getTextureGPUTransferCount(); static Size getAllowedGPUMemoryUsage(); From 6b2b68e69186129111b736b18751724dce906ef0 Mon Sep 17 00:00:00 2001 From: sam Date: Tue, 25 Oct 2016 03:36:23 -0700 Subject: [PATCH 02/11] trying to add counters for the default FBO --- interface/resources/qml/Stats.qml | 3 +++ interface/src/ui/Stats.cpp | 3 +++ interface/src/ui/Stats.h | 2 ++ libraries/gl/src/gl/Context.cpp | 23 +++++++++++++++++++++++ libraries/gl/src/gl/Context.h | 11 ++++++++++- libraries/gl/src/gl/OffscreenGLCanvas.cpp | 21 +++++++++++++++++++-- libraries/gl/src/gl/OffscreenGLCanvas.h | 2 ++ 7 files changed, 62 insertions(+), 3 deletions(-) diff --git a/interface/resources/qml/Stats.qml b/interface/resources/qml/Stats.qml index 7ca527ad3f..d8333112ce 100644 --- a/interface/resources/qml/Stats.qml +++ b/interface/resources/qml/Stats.qml @@ -228,6 +228,9 @@ Item { StatText { text: " Count: " + root.gpuTextures; } + StatText { + text: "GL Context FBO Memory: " + root.glContextFBOMemory + " MB"; + } StatText { text: "QML Texture Memory: " + root.qmlTextureMemory + " MB"; } diff --git a/interface/src/ui/Stats.cpp b/interface/src/ui/Stats.cpp index 9c7d66e0e2..b0c5113c84 100644 --- a/interface/src/ui/Stats.cpp +++ b/interface/src/ui/Stats.cpp @@ -25,6 +25,8 @@ #include #include +#include + #include "BandwidthRecorder.h" #include "Menu.h" #include "Util.h" @@ -287,6 +289,7 @@ void Stats::updateStats(bool force) { STAT_UPDATE(gpuBuffers, (int)gpu::Context::getBufferGPUCount()); STAT_UPDATE(gpuTextures, (int)gpu::Context::getTextureGPUCount()); STAT_UPDATE(gpuTexturesSparse, (int)gpu::Context::getTextureGPUSparseCount()); + STAT_UPDATE(glContextFBOMemory, (int)BYTES_TO_MB(gl::Context::getDefaultFBOMemoryUsage())); STAT_UPDATE(qmlTextureMemory, (int)BYTES_TO_MB(OffscreenQmlSurface::getUsedTextureMemory())); STAT_UPDATE(gpuTextureMemory, (int)BYTES_TO_MB(gpu::Texture::getTextureGPUMemoryUsage())); STAT_UPDATE(gpuTextureVirtualMemory, (int)BYTES_TO_MB(gpu::Texture::getTextureGPUVirtualMemoryUsage())); diff --git a/interface/src/ui/Stats.h b/interface/src/ui/Stats.h index 97f047c3d5..964920210c 100644 --- a/interface/src/ui/Stats.h +++ b/interface/src/ui/Stats.h @@ -90,6 +90,7 @@ class Stats : public QQuickItem { STATS_PROPERTY(int, gpuBuffers, 0) STATS_PROPERTY(int, gpuTextures, 0) STATS_PROPERTY(int, gpuTexturesSparse, 0) + STATS_PROPERTY(int, glContextFBOMemory, 0) STATS_PROPERTY(int, qmlTextureMemory, 0) STATS_PROPERTY(int, gpuTextureMemory, 0) STATS_PROPERTY(int, gpuTextureVirtualMemory, 0) @@ -182,6 +183,7 @@ signals: void localInternalChanged(); void localLeavesChanged(); void timingStatsChanged(); + void glContextFBOMemoryChanged(); void qmlTextureMemoryChanged(); void gpuBuffersChanged(); void gpuTexturesChanged(); diff --git a/libraries/gl/src/gl/Context.cpp b/libraries/gl/src/gl/Context.cpp index 5b8a1a2fa1..fda457f94a 100644 --- a/libraries/gl/src/gl/Context.cpp +++ b/libraries/gl/src/gl/Context.cpp @@ -40,6 +40,27 @@ static bool enableDebugLogger = QProcessEnvironment::systemEnvironment().contain using namespace gl; + +std::atomic Context::_defaultFBOMemoryUsage { 0 }; + +size_t Context::getDefaultFBOMemoryUsage() { return _defaultFBOMemoryUsage.load(); } + +size_t Context::evalMemoryUsage(uint32_t width, uint32_t height) { + return width * height * 4; +} + +void Context::updateDefaultFBOMemoryUsage(size_t prevFBOSize, size_t newFBOSize) { + if (prevFBOSize == newFBOSize) { + return; + } + if (newFBOSize > prevFBOSize) { + _defaultFBOMemoryUsage.fetch_add(newFBOSize - prevFBOSize); + } else { + _defaultFBOMemoryUsage.fetch_sub(prevFBOSize - newFBOSize); + } +} + + Context* Context::PRIMARY = nullptr; Context::Context() {} @@ -277,6 +298,8 @@ void OffscreenContext::create() { _window->setSurfaceType(QSurface::OpenGLSurface); _window->create(); setWindow(_window); + QSize windowSize = _window->size() * _window->devicePixelRatio(); + qCDebug(glLogging) << "New Offscreen GLContext, window size = " << windowSize.width() << " , " << windowSize.height(); QGuiApplication::processEvents(); } Parent::create(); diff --git a/libraries/gl/src/gl/Context.h b/libraries/gl/src/gl/Context.h index 6dc859f222..783b634f75 100644 --- a/libraries/gl/src/gl/Context.h +++ b/libraries/gl/src/gl/Context.h @@ -11,6 +11,7 @@ #include #include +#include #if defined(Q_OS_WIN) #include @@ -23,7 +24,7 @@ class QThread; namespace gl { -class Context { + class Context { protected: QWindow* _window { nullptr }; static Context* PRIMARY; @@ -57,6 +58,13 @@ class Context { virtual void create(); QOpenGLContext* qglContext(); void moveToThread(QThread* thread); + + static size_t getDefaultFBOMemoryUsage(); + static size_t evalMemoryUsage(uint32_t width, uint32_t height); + static void updateDefaultFBOMemoryUsage(size_t prevFBOSize, size_t newFBOSize); + + private: + static std::atomic _defaultFBOMemoryUsage; }; class OffscreenContext : public Context { @@ -67,6 +75,7 @@ class Context { virtual ~OffscreenContext(); void create() override; }; + } #endif // hifi_gpu_GPUConfig_h diff --git a/libraries/gl/src/gl/OffscreenGLCanvas.cpp b/libraries/gl/src/gl/OffscreenGLCanvas.cpp index dbd338bc34..ac12f95c25 100644 --- a/libraries/gl/src/gl/OffscreenGLCanvas.cpp +++ b/libraries/gl/src/gl/OffscreenGLCanvas.cpp @@ -17,11 +17,16 @@ #include #include +#include "Context.h" #include "GLHelpers.h" #include "GLLogging.h" -OffscreenGLCanvas::OffscreenGLCanvas() : _context(new QOpenGLContext), _offscreenSurface(new QOffscreenSurface){ +OffscreenGLCanvas::OffscreenGLCanvas() : + _context(new QOpenGLContext), + _offscreenSurface(new QOffscreenSurface), + _offscreenSurfaceCurrentMemoryUsage(0) +{ } OffscreenGLCanvas::~OffscreenGLCanvas() { @@ -30,6 +35,8 @@ OffscreenGLCanvas::~OffscreenGLCanvas() { delete _context; _context = nullptr; + gl::Context::updateDefaultFBOMemoryUsage(_offscreenSurfaceCurrentMemoryUsage, 0); + _offscreenSurface->destroy(); delete _offscreenSurface; _offscreenSurface = nullptr; @@ -53,10 +60,18 @@ bool OffscreenGLCanvas::create(QOpenGLContext* sharedContext) { return false; } +void OffscreenGLCanvas::updateMemoryCounter() { + if (_offscreenSurface) { + auto newSize =_offscreenSurface->size(); + auto newMemSize = gl::Context::evalMemoryUsage(newSize.width(), newSize.height()); + gl::Context::updateDefaultFBOMemoryUsage(_offscreenSurfaceCurrentMemoryUsage, newMemSize); + _offscreenSurfaceCurrentMemoryUsage = newMemSize; + } +} + bool OffscreenGLCanvas::makeCurrent() { bool result = _context->makeCurrent(_offscreenSurface); Q_ASSERT(result); - std::call_once(_reportOnce, [this]{ qCDebug(glLogging) << "GL Version: " << QString((const char*) glGetString(GL_VERSION)); qCDebug(glLogging) << "GL Shader Language Version: " << QString((const char*) glGetString(GL_SHADING_LANGUAGE_VERSION)); @@ -64,6 +79,8 @@ bool OffscreenGLCanvas::makeCurrent() { qCDebug(glLogging) << "GL Renderer: " << QString((const char*) glGetString(GL_RENDERER)); }); + updateMemoryCounter(); + return result; } diff --git a/libraries/gl/src/gl/OffscreenGLCanvas.h b/libraries/gl/src/gl/OffscreenGLCanvas.h index 583aa7c60f..be7d8986f6 100644 --- a/libraries/gl/src/gl/OffscreenGLCanvas.h +++ b/libraries/gl/src/gl/OffscreenGLCanvas.h @@ -36,6 +36,8 @@ protected: std::once_flag _reportOnce; QOpenGLContext* _context{ nullptr }; QOffscreenSurface* _offscreenSurface{ nullptr }; + size_t _offscreenSurfaceCurrentMemoryUsage { 0 }; + void updateMemoryCounter(); }; #endif // hifi_OffscreenGLCanvas_h From 507d3e5a39605c620d4b9d7aa2c1f5e9ed85c656 Mon Sep 17 00:00:00 2001 From: samcake Date: Tue, 25 Oct 2016 12:28:07 -0700 Subject: [PATCH 03/11] IMprove the counting and namoing of the new couters the gl swapchain --- interface/resources/qml/Stats.qml | 2 +- interface/src/ui/Stats.cpp | 4 ++- interface/src/ui/Stats.h | 4 +-- libraries/gl/src/gl/Context.cpp | 43 +++++++++++++++++------ libraries/gl/src/gl/Context.h | 12 ++++--- libraries/gl/src/gl/ContextQt.cpp | 4 +++ libraries/gl/src/gl/GLHelpers.cpp | 9 +++++ libraries/gl/src/gl/GLHelpers.h | 2 ++ libraries/gl/src/gl/OffscreenGLCanvas.cpp | 16 +-------- libraries/gl/src/gl/OffscreenGLCanvas.h | 2 -- libraries/gpu-gl/src/gpu/gl/GLTexture.cpp | 1 + 11 files changed, 64 insertions(+), 35 deletions(-) diff --git a/interface/resources/qml/Stats.qml b/interface/resources/qml/Stats.qml index d8333112ce..2439aaf5c0 100644 --- a/interface/resources/qml/Stats.qml +++ b/interface/resources/qml/Stats.qml @@ -229,7 +229,7 @@ Item { text: " Count: " + root.gpuTextures; } StatText { - text: "GL Context FBO Memory: " + root.glContextFBOMemory + " MB"; + text: "GL Swapchain Memory: " + root.glContextSwapchainMemory + " MB"; } StatText { text: "QML Texture Memory: " + root.qmlTextureMemory + " MB"; diff --git a/interface/src/ui/Stats.cpp b/interface/src/ui/Stats.cpp index b0c5113c84..b1fc0ce503 100644 --- a/interface/src/ui/Stats.cpp +++ b/interface/src/ui/Stats.cpp @@ -289,7 +289,9 @@ void Stats::updateStats(bool force) { STAT_UPDATE(gpuBuffers, (int)gpu::Context::getBufferGPUCount()); STAT_UPDATE(gpuTextures, (int)gpu::Context::getTextureGPUCount()); STAT_UPDATE(gpuTexturesSparse, (int)gpu::Context::getTextureGPUSparseCount()); - STAT_UPDATE(glContextFBOMemory, (int)BYTES_TO_MB(gl::Context::getDefaultFBOMemoryUsage())); + + STAT_UPDATE(glContextSwapchainMemory, (int)BYTES_TO_MB(gl::Context::getSwapchainMemoryUsage())); + STAT_UPDATE(qmlTextureMemory, (int)BYTES_TO_MB(OffscreenQmlSurface::getUsedTextureMemory())); STAT_UPDATE(gpuTextureMemory, (int)BYTES_TO_MB(gpu::Texture::getTextureGPUMemoryUsage())); STAT_UPDATE(gpuTextureVirtualMemory, (int)BYTES_TO_MB(gpu::Texture::getTextureGPUVirtualMemoryUsage())); diff --git a/interface/src/ui/Stats.h b/interface/src/ui/Stats.h index 964920210c..a98a99f093 100644 --- a/interface/src/ui/Stats.h +++ b/interface/src/ui/Stats.h @@ -90,7 +90,7 @@ class Stats : public QQuickItem { STATS_PROPERTY(int, gpuBuffers, 0) STATS_PROPERTY(int, gpuTextures, 0) STATS_PROPERTY(int, gpuTexturesSparse, 0) - STATS_PROPERTY(int, glContextFBOMemory, 0) + STATS_PROPERTY(int, glContextSwapchainMemory, 0) STATS_PROPERTY(int, qmlTextureMemory, 0) STATS_PROPERTY(int, gpuTextureMemory, 0) STATS_PROPERTY(int, gpuTextureVirtualMemory, 0) @@ -183,7 +183,7 @@ signals: void localInternalChanged(); void localLeavesChanged(); void timingStatsChanged(); - void glContextFBOMemoryChanged(); + void glContextSwapchainMemoryChanged(); void qmlTextureMemoryChanged(); void gpuBuffersChanged(); void gpuTexturesChanged(); diff --git a/libraries/gl/src/gl/Context.cpp b/libraries/gl/src/gl/Context.cpp index fda457f94a..f748703506 100644 --- a/libraries/gl/src/gl/Context.cpp +++ b/libraries/gl/src/gl/Context.cpp @@ -41,22 +41,22 @@ static bool enableDebugLogger = QProcessEnvironment::systemEnvironment().contain using namespace gl; -std::atomic Context::_defaultFBOMemoryUsage { 0 }; +std::atomic Context::_totalSwapchainMemoryUsage { 0 }; -size_t Context::getDefaultFBOMemoryUsage() { return _defaultFBOMemoryUsage.load(); } +size_t Context::getSwapchainMemoryUsage() { return _totalSwapchainMemoryUsage.load(); } -size_t Context::evalMemoryUsage(uint32_t width, uint32_t height) { - return width * height * 4; +size_t Context::evalSurfaceMemoryUsage(uint32_t width, uint32_t height, uint32_t pixelSize) { + return width * height * pixelSize; } -void Context::updateDefaultFBOMemoryUsage(size_t prevFBOSize, size_t newFBOSize) { - if (prevFBOSize == newFBOSize) { +void Context::updateSwapchainMemoryUsage(size_t prevSize, size_t newSize) { + if (prevSize == newSize) { return; } - if (newFBOSize > prevFBOSize) { - _defaultFBOMemoryUsage.fetch_add(newFBOSize - prevFBOSize); + if (newSize > prevSize) { + _totalSwapchainMemoryUsage.fetch_add(newSize - prevSize); } else { - _defaultFBOMemoryUsage.fetch_sub(prevFBOSize - newFBOSize); + _totalSwapchainMemoryUsage.fetch_sub(prevSize - newSize); } } @@ -99,18 +99,35 @@ void Context::release() { if (PRIMARY == this) { PRIMARY = nullptr; } - } + updateSwapchainMemoryCounter(); +} Context::~Context() { release(); } +void Context::updateSwapchainMemoryCounter() { + if (_window) { + auto newSize = _window->size(); + auto newMemSize = gl::Context::evalSurfaceMemoryUsage(newSize.width(), newSize.height(), _swapchainPixelSize); + gl::Context::updateSwapchainMemoryUsage(_swapchainMemoryUsage, newMemSize); + _swapchainMemoryUsage = newMemSize; + } else { + // No window ? no more swapchain + gl::Context::updateSwapchainMemoryUsage(_swapchainMemoryUsage, 0); + _swapchainMemoryUsage = 0; + } +} + void Context::setWindow(QWindow* window) { release(); _window = window; + #ifdef Q_OS_WIN _hwnd = (HWND)window->winId(); #endif + + updateSwapchainMemoryCounter(); } #ifdef Q_OS_WIN @@ -119,6 +136,8 @@ static const char* PRIMARY_CONTEXT_PROPERTY_NAME = "com.highfidelity.gl.primaryC bool Context::makeCurrent() { BOOL result = wglMakeCurrent(_hdc, _hglrc); assert(result); + updateSwapchainMemoryCounter(); + return result; } @@ -238,6 +257,10 @@ void Context::create() { wglChoosePixelFormatARB(_hdc, &formatAttribs[0], NULL, 1, &pixelFormat, &numFormats); DescribePixelFormat(_hdc, pixelFormat, sizeof(pfd), &pfd); } + // The swap chain pixel size for swap chains is : rgba32 * double buffer + depth24stencil8 + _swapchainPixelSize = 32 * 2 + 32; + updateSwapchainMemoryCounter(); + SetPixelFormat(_hdc, pixelFormat, &pfd); { std::vector contextAttribs; diff --git a/libraries/gl/src/gl/Context.h b/libraries/gl/src/gl/Context.h index 783b634f75..d1b0d53631 100644 --- a/libraries/gl/src/gl/Context.h +++ b/libraries/gl/src/gl/Context.h @@ -59,12 +59,16 @@ namespace gl { QOpenGLContext* qglContext(); void moveToThread(QThread* thread); - static size_t getDefaultFBOMemoryUsage(); - static size_t evalMemoryUsage(uint32_t width, uint32_t height); - static void updateDefaultFBOMemoryUsage(size_t prevFBOSize, size_t newFBOSize); + static size_t evalSurfaceMemoryUsage(uint32_t width, uint32_t height, uint32_t pixelSize); + static size_t getSwapchainMemoryUsage(); + static void updateSwapchainMemoryUsage(size_t prevSize, size_t newSize); private: - static std::atomic _defaultFBOMemoryUsage; + static std::atomic _totalSwapchainMemoryUsage; + + size_t _swapchainMemoryUsage { 0 }; + size_t _swapchainPixelSize { 0 }; + void updateSwapchainMemoryCounter(); }; class OffscreenContext : public Context { diff --git a/libraries/gl/src/gl/ContextQt.cpp b/libraries/gl/src/gl/ContextQt.cpp index ff59b8f1e1..5021bddc7f 100644 --- a/libraries/gl/src/gl/ContextQt.cpp +++ b/libraries/gl/src/gl/ContextQt.cpp @@ -45,6 +45,7 @@ void Context::moveToThread(QThread* thread) { #ifndef Q_OS_WIN bool Context::makeCurrent() { + updateSwapchainMemoryCounter(); return _context->makeCurrent(_window); } @@ -70,6 +71,9 @@ void Context::create() { } _context->setFormat(getDefaultOpenGLSurfaceFormat()); _context->create(); + + _swapchainPixelSize = evalGLFormatSwapchainPixelSize(_context->format()); + updateSwapchainMemoryCounter(); } #endif diff --git a/libraries/gl/src/gl/GLHelpers.cpp b/libraries/gl/src/gl/GLHelpers.cpp index dde1e0ec97..e845c402be 100644 --- a/libraries/gl/src/gl/GLHelpers.cpp +++ b/libraries/gl/src/gl/GLHelpers.cpp @@ -13,6 +13,15 @@ #include +size_t evalGLFormatSwapchainPixelSize(const QSurfaceFormat& format) { + size_t pixelSize = format.redBufferSize() + format.greenBufferSize() + format.blueBufferSize() + format.alphaBufferSize(); + if (format.swapBehavior() > 0) { + pixelSize *= format.swapBehavior(); // multiply the color buffer pixel size by the actual swapchain depth + } + pixelSize += format.stencilBufferSize() + format.depthBufferSize(); + return pixelSize; +} + const QSurfaceFormat& getDefaultOpenGLSurfaceFormat() { static QSurfaceFormat format; static std::once_flag once; diff --git a/libraries/gl/src/gl/GLHelpers.h b/libraries/gl/src/gl/GLHelpers.h index 8834a718fd..daa181467d 100644 --- a/libraries/gl/src/gl/GLHelpers.h +++ b/libraries/gl/src/gl/GLHelpers.h @@ -26,6 +26,8 @@ class QGLFormat; template void setGLFormatVersion(F& format, int major = 4, int minor = 5) { format.setVersion(major, minor); } +size_t evalGLFormatSwapchainPixelSize(const QSurfaceFormat& format); + const QSurfaceFormat& getDefaultOpenGLSurfaceFormat(); QJsonObject getGLContextData(); int glVersionToInteger(QString glVersion); diff --git a/libraries/gl/src/gl/OffscreenGLCanvas.cpp b/libraries/gl/src/gl/OffscreenGLCanvas.cpp index ac12f95c25..e54846196b 100644 --- a/libraries/gl/src/gl/OffscreenGLCanvas.cpp +++ b/libraries/gl/src/gl/OffscreenGLCanvas.cpp @@ -24,8 +24,7 @@ OffscreenGLCanvas::OffscreenGLCanvas() : _context(new QOpenGLContext), - _offscreenSurface(new QOffscreenSurface), - _offscreenSurfaceCurrentMemoryUsage(0) + _offscreenSurface(new QOffscreenSurface) { } @@ -35,8 +34,6 @@ OffscreenGLCanvas::~OffscreenGLCanvas() { delete _context; _context = nullptr; - gl::Context::updateDefaultFBOMemoryUsage(_offscreenSurfaceCurrentMemoryUsage, 0); - _offscreenSurface->destroy(); delete _offscreenSurface; _offscreenSurface = nullptr; @@ -60,15 +57,6 @@ bool OffscreenGLCanvas::create(QOpenGLContext* sharedContext) { return false; } -void OffscreenGLCanvas::updateMemoryCounter() { - if (_offscreenSurface) { - auto newSize =_offscreenSurface->size(); - auto newMemSize = gl::Context::evalMemoryUsage(newSize.width(), newSize.height()); - gl::Context::updateDefaultFBOMemoryUsage(_offscreenSurfaceCurrentMemoryUsage, newMemSize); - _offscreenSurfaceCurrentMemoryUsage = newMemSize; - } -} - bool OffscreenGLCanvas::makeCurrent() { bool result = _context->makeCurrent(_offscreenSurface); Q_ASSERT(result); @@ -79,8 +67,6 @@ bool OffscreenGLCanvas::makeCurrent() { qCDebug(glLogging) << "GL Renderer: " << QString((const char*) glGetString(GL_RENDERER)); }); - updateMemoryCounter(); - return result; } diff --git a/libraries/gl/src/gl/OffscreenGLCanvas.h b/libraries/gl/src/gl/OffscreenGLCanvas.h index be7d8986f6..583aa7c60f 100644 --- a/libraries/gl/src/gl/OffscreenGLCanvas.h +++ b/libraries/gl/src/gl/OffscreenGLCanvas.h @@ -36,8 +36,6 @@ protected: std::once_flag _reportOnce; QOpenGLContext* _context{ nullptr }; QOffscreenSurface* _offscreenSurface{ nullptr }; - size_t _offscreenSurfaceCurrentMemoryUsage { 0 }; - void updateMemoryCounter(); }; #endif // hifi_OffscreenGLCanvas_h diff --git a/libraries/gpu-gl/src/gpu/gl/GLTexture.cpp b/libraries/gpu-gl/src/gpu/gl/GLTexture.cpp index cd9807fd46..9a19d6f309 100644 --- a/libraries/gpu-gl/src/gpu/gl/GLTexture.cpp +++ b/libraries/gpu-gl/src/gpu/gl/GLTexture.cpp @@ -186,6 +186,7 @@ GLTexture::~GLTexture() { Backend::updateTextureGPUFramebufferMemoryUsage(_size, 0); } } + Backend::updateTextureGPUVirtualMemoryUsage(_virtualSize, 0); } void GLTexture::createTexture() { From c586bef45216c0379929b7dedab531e57e1ed5a9 Mon Sep 17 00:00:00 2001 From: samcake Date: Tue, 25 Oct 2016 12:56:26 -0700 Subject: [PATCH 04/11] Actually remove the multiplication of the color buffer cost by the swapchain length in the pixel SIze estimation since it doesn;t look true --- libraries/gl/src/gl/Context.cpp | 7 ++++--- libraries/gl/src/gl/GLHelpers.cpp | 8 +++++--- 2 files changed, 9 insertions(+), 6 deletions(-) diff --git a/libraries/gl/src/gl/Context.cpp b/libraries/gl/src/gl/Context.cpp index f748703506..ec1c284e99 100644 --- a/libraries/gl/src/gl/Context.cpp +++ b/libraries/gl/src/gl/Context.cpp @@ -109,7 +109,7 @@ Context::~Context() { void Context::updateSwapchainMemoryCounter() { if (_window) { auto newSize = _window->size(); - auto newMemSize = gl::Context::evalSurfaceMemoryUsage(newSize.width(), newSize.height(), _swapchainPixelSize); + auto newMemSize = gl::Context::evalSurfaceMemoryUsage(newSize.width(), newSize.height(), (uint32_t) _swapchainPixelSize); gl::Context::updateSwapchainMemoryUsage(_swapchainMemoryUsage, newMemSize); _swapchainMemoryUsage = newMemSize; } else { @@ -257,8 +257,9 @@ void Context::create() { wglChoosePixelFormatARB(_hdc, &formatAttribs[0], NULL, 1, &pixelFormat, &numFormats); DescribePixelFormat(_hdc, pixelFormat, sizeof(pfd), &pfd); } - // The swap chain pixel size for swap chains is : rgba32 * double buffer + depth24stencil8 - _swapchainPixelSize = 32 * 2 + 32; + // The swap chain pixel size for swap chains is : rgba32 + depth24stencil8 + // We don't apply the length of the swap chain into this pixelSize since it is not vsible for the Process (on windows). + _swapchainPixelSize = 32 + 32; updateSwapchainMemoryCounter(); SetPixelFormat(_hdc, pixelFormat, &pfd); diff --git a/libraries/gl/src/gl/GLHelpers.cpp b/libraries/gl/src/gl/GLHelpers.cpp index e845c402be..02c1f308de 100644 --- a/libraries/gl/src/gl/GLHelpers.cpp +++ b/libraries/gl/src/gl/GLHelpers.cpp @@ -15,9 +15,11 @@ size_t evalGLFormatSwapchainPixelSize(const QSurfaceFormat& format) { size_t pixelSize = format.redBufferSize() + format.greenBufferSize() + format.blueBufferSize() + format.alphaBufferSize(); - if (format.swapBehavior() > 0) { - pixelSize *= format.swapBehavior(); // multiply the color buffer pixel size by the actual swapchain depth - } + // We don't apply the length of the swap chain into this pixelSize since it is not vsible for the Process (on windows). + // Let s keep this here remember that: + // if (format.swapBehavior() > 0) { + // pixelSize *= format.swapBehavior(); // multiply the color buffer pixel size by the actual swapchain depth + // } pixelSize += format.stencilBufferSize() + format.depthBufferSize(); return pixelSize; } From 133b0b38fdd20d140eab6e10eb2024649dbd679b Mon Sep 17 00:00:00 2001 From: samcake Date: Tue, 25 Oct 2016 13:24:39 -0700 Subject: [PATCH 05/11] Fixing build issue on non win --- libraries/gl/src/gl/ContextQt.cpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/libraries/gl/src/gl/ContextQt.cpp b/libraries/gl/src/gl/ContextQt.cpp index 5021bddc7f..4d5d2c4e9f 100644 --- a/libraries/gl/src/gl/ContextQt.cpp +++ b/libraries/gl/src/gl/ContextQt.cpp @@ -15,6 +15,8 @@ #include #endif +#include "GLHelpers.h" + using namespace gl; void Context::destroyContext(QOpenGLContext* context) { From 3903a5106250ae2ba606155514f9f138153ae2a9 Mon Sep 17 00:00:00 2001 From: Seth Alves Date: Tue, 25 Oct 2016 13:58:48 -0700 Subject: [PATCH 06/11] fix a couple of crash-on-exits --- interface/src/Application.cpp | 3 +++ libraries/audio-client/src/AudioClient.cpp | 20 +++++++++++++------- libraries/audio-client/src/AudioClient.h | 4 ++++ libraries/shared/src/RunningMarker.cpp | 2 +- 4 files changed, 21 insertions(+), 8 deletions(-) diff --git a/interface/src/Application.cpp b/interface/src/Application.cpp index 861e3a2246..376af97b66 100644 --- a/interface/src/Application.cpp +++ b/interface/src/Application.cpp @@ -1478,6 +1478,7 @@ void Application::updateHeartbeat() const { void Application::aboutToQuit() { emit beforeAboutToQuit(); + DependencyManager::get()->beforeAboutToQuit(); foreach(auto inputPlugin, PluginManager::getInstance()->getInputPlugins()) { if (inputPlugin->isActive()) { @@ -1579,6 +1580,8 @@ void Application::cleanupBeforeQuit() { } Application::~Application() { + DependencyManager::destroy(); + _entityClipboard->eraseAllOctreeElements(); _entityClipboard.reset(); diff --git a/libraries/audio-client/src/AudioClient.cpp b/libraries/audio-client/src/AudioClient.cpp index 5fced85d2d..5208b893ac 100644 --- a/libraries/audio-client/src/AudioClient.cpp +++ b/libraries/audio-client/src/AudioClient.cpp @@ -82,10 +82,10 @@ public: CheckDevicesThread(AudioClient* audioClient) : _audioClient(audioClient) { + } - connect(qApp, &QCoreApplication::aboutToQuit, [this] { - _quit = true; - }); + void beforeAboutToQuit() { + _quit = true; } void run() override { @@ -159,10 +159,10 @@ AudioClient::AudioClient() : _outputDevices = getDeviceNames(QAudio::AudioOutput); // start a thread to detect any device changes - QThread* checkDevicesThread = new CheckDevicesThread(this); - checkDevicesThread->setObjectName("CheckDevices Thread"); - checkDevicesThread->setPriority(QThread::LowPriority); - checkDevicesThread->start(); + _checkDevicesThread = new CheckDevicesThread(this); + _checkDevicesThread->setObjectName("CheckDevices Thread"); + _checkDevicesThread->setPriority(QThread::LowPriority); + _checkDevicesThread->start(); configureReverb(); @@ -177,6 +177,7 @@ AudioClient::AudioClient() : } AudioClient::~AudioClient() { + delete _checkDevicesThread; stop(); if (_codec && _encoder) { _codec->releaseEncoder(_encoder); @@ -184,6 +185,11 @@ AudioClient::~AudioClient() { } } +void AudioClient::beforeAboutToQuit() { + static_cast(_checkDevicesThread)->beforeAboutToQuit(); +} + + void AudioClient::handleMismatchAudioFormat(SharedNodePointer node, const QString& currentCodec, const QString& recievedCodec) { qCDebug(audioclient) << __FUNCTION__ << "sendingNode:" << *node << "currentCodec:" << currentCodec << "recievedCodec:" << recievedCodec; selectAudioFormat(recievedCodec); diff --git a/libraries/audio-client/src/AudioClient.h b/libraries/audio-client/src/AudioClient.h index 72f5cf5fdc..d6f111cafc 100644 --- a/libraries/audio-client/src/AudioClient.h +++ b/libraries/audio-client/src/AudioClient.h @@ -155,6 +155,8 @@ public slots: void audioMixerKilled(); void toggleMute(); + void beforeAboutToQuit(); + virtual void setIsStereoInput(bool stereo) override; void toggleAudioNoiseReduction() { _isNoiseGateEnabled = !_isNoiseGateEnabled; } @@ -332,6 +334,8 @@ private: CodecPluginPointer _codec; QString _selectedCodecName; Encoder* _encoder { nullptr }; // for outbound mic stream + + QThread* _checkDevicesThread { nullptr }; }; diff --git a/libraries/shared/src/RunningMarker.cpp b/libraries/shared/src/RunningMarker.cpp index 80247150fd..89fb3ada23 100644 --- a/libraries/shared/src/RunningMarker.cpp +++ b/libraries/shared/src/RunningMarker.cpp @@ -47,7 +47,7 @@ void RunningMarker::startRunningMarker() { RunningMarker::~RunningMarker() { deleteRunningMarkerFile(); - _runningMarkerTimer->stop(); + QMetaObject::invokeMethod(_runningMarkerTimer, "stop", Qt::BlockingQueuedConnection); _runningMarkerThread->quit(); _runningMarkerTimer->deleteLater(); _runningMarkerThread->deleteLater(); From 272055b6ee6f66b1153f2047a9b4262f868225e0 Mon Sep 17 00:00:00 2001 From: Brad Hefta-Gaub Date: Tue, 25 Oct 2016 14:19:44 -0700 Subject: [PATCH 07/11] add location and build info to user activity stats --- interface/src/Application.cpp | 11 +++++++++++ libraries/networking/src/AddressManager.cpp | 15 +++++++++------ libraries/networking/src/AddressManager.h | 4 ++-- 3 files changed, 22 insertions(+), 8 deletions(-) diff --git a/interface/src/Application.cpp b/interface/src/Application.cpp index 861e3a2246..e6fc4398c4 100644 --- a/interface/src/Application.cpp +++ b/interface/src/Application.cpp @@ -1173,10 +1173,21 @@ Application::Application(int& argc, char** argv, QElapsedTimer& startupTimer, bo properties["process_memory_used"] = static_cast(memInfo.processUsedMemoryBytes); } + // content location and build info - useful for filtering stats + auto addressManager = DependencyManager::get(); + auto currentDomain = addressManager->currentShareableAddress(true).toString(); // domain only + auto currentPath = addressManager->currentPath(true); // with orientation + properties["current_domain"] = currentDomain; + properties["current_path"] = currentPath; + properties["build_version"] = BuildInfo::VERSION; + + qDebug() << "just sent stats with:" << currentDomain << currentPath << "build:" << BuildInfo::VERSION; + auto displayPlugin = qApp->getActiveDisplayPlugin(); properties["fps"] = _frameCounter.rate(); properties["target_frame_rate"] = getTargetFrameRate(); + properties["render_rate"] = displayPlugin->renderRate(); properties["present_rate"] = displayPlugin->presentRate(); properties["new_frame_present_rate"] = displayPlugin->newFramePresentRate(); properties["dropped_frame_rate"] = displayPlugin->droppedFrameRate(); diff --git a/libraries/networking/src/AddressManager.cpp b/libraries/networking/src/AddressManager.cpp index c40fe29642..90250f839e 100644 --- a/libraries/networking/src/AddressManager.cpp +++ b/libraries/networking/src/AddressManager.cpp @@ -47,7 +47,7 @@ bool AddressManager::isConnected() { return DependencyManager::get()->getDomainHandler().isConnected(); } -QUrl AddressManager::currentAddress() const { +QUrl AddressManager::currentAddress(bool domainOnly) const { QUrl hifiURL; hifiURL.setScheme(HIFI_URL_SCHEME); @@ -57,7 +57,9 @@ QUrl AddressManager::currentAddress() const { hifiURL.setPort(_port); } - hifiURL.setPath(currentPath()); + if (!domainOnly) { + hifiURL.setPath(currentPath()); + } return hifiURL; } @@ -69,8 +71,7 @@ QUrl AddressManager::currentFacingAddress() const { return hifiURL; } - -QUrl AddressManager::currentShareableAddress() const { +QUrl AddressManager::currentShareableAddress(bool domainOnly) const { if (!_shareablePlaceName.isEmpty()) { // if we have a shareable place name use that instead of whatever the current host is QUrl hifiURL; @@ -78,11 +79,13 @@ QUrl AddressManager::currentShareableAddress() const { hifiURL.setScheme(HIFI_URL_SCHEME); hifiURL.setHost(_shareablePlaceName); - hifiURL.setPath(currentPath()); + if (!domainOnly) { + hifiURL.setPath(currentPath()); + } return hifiURL; } else { - return currentAddress(); + return currentAddress(domainOnly); } } diff --git a/libraries/networking/src/AddressManager.h b/libraries/networking/src/AddressManager.h index 06c5a8c554..ca0585583d 100644 --- a/libraries/networking/src/AddressManager.h +++ b/libraries/networking/src/AddressManager.h @@ -63,9 +63,9 @@ public: bool isConnected(); const QString& getProtocol() { return HIFI_URL_SCHEME; }; - QUrl currentAddress() const; + QUrl currentAddress(bool domainOnly = false) const; QUrl currentFacingAddress() const; - QUrl currentShareableAddress() const; + QUrl currentShareableAddress(bool domainOnly = false) const; QUrl currentFacingShareableAddress() const; QString currentPath(bool withOrientation = true) const; QString currentFacingPath() const; From e22a2e9e2fc424cb5584774d8f087b7c7c79e3ef Mon Sep 17 00:00:00 2001 From: Brad Hefta-Gaub Date: Tue, 25 Oct 2016 14:56:54 -0700 Subject: [PATCH 08/11] add gl info and gpu free memory to user stats --- interface/src/Application.cpp | 6 ++++-- libraries/gl/src/gl/GLHelpers.cpp | 25 +++++++++++++++---------- 2 files changed, 19 insertions(+), 12 deletions(-) diff --git a/interface/src/Application.cpp b/interface/src/Application.cpp index e6fc4398c4..f70685a8b2 100644 --- a/interface/src/Application.cpp +++ b/interface/src/Application.cpp @@ -1181,8 +1181,6 @@ Application::Application(int& argc, char** argv, QElapsedTimer& startupTimer, bo properties["current_path"] = currentPath; properties["build_version"] = BuildInfo::VERSION; - qDebug() << "just sent stats with:" << currentDomain << currentPath << "build:" << BuildInfo::VERSION; - auto displayPlugin = qApp->getActiveDisplayPlugin(); properties["fps"] = _frameCounter.rate(); @@ -1233,6 +1231,10 @@ Application::Application(int& argc, char** argv, QElapsedTimer& startupTimer, bo properties["active_display_plugin"] = getActiveDisplayPlugin()->getName(); properties["using_hmd"] = isHMDMode(); + auto glInfo = getGLContextData(); + properties["gl_info"] = glInfo; + properties["gpu_free_memory"] = (int)BYTES_TO_MB(gpu::Context::getFreeGPUMemory()); + auto hmdHeadPose = getHMDSensorPose(); properties["hmd_head_pose_changed"] = isHMDMode() && (hmdHeadPose != lastHMDHeadPose); lastHMDHeadPose = hmdHeadPose; diff --git a/libraries/gl/src/gl/GLHelpers.cpp b/libraries/gl/src/gl/GLHelpers.cpp index dde1e0ec97..1604edccac 100644 --- a/libraries/gl/src/gl/GLHelpers.cpp +++ b/libraries/gl/src/gl/GLHelpers.cpp @@ -35,17 +35,22 @@ int glVersionToInteger(QString glVersion) { } QJsonObject getGLContextData() { - QString glVersion = QString((const char*)glGetString(GL_VERSION)); - QString glslVersion = QString((const char*) glGetString(GL_SHADING_LANGUAGE_VERSION)); - QString glVendor = QString((const char*) glGetString(GL_VENDOR)); - QString glRenderer = QString((const char*)glGetString(GL_RENDERER)); + static QJsonObject result; + static std::once_flag once; + std::call_once(once, [] { + QString glVersion = QString((const char*)glGetString(GL_VERSION)); + QString glslVersion = QString((const char*) glGetString(GL_SHADING_LANGUAGE_VERSION)); + QString glVendor = QString((const char*) glGetString(GL_VENDOR)); + QString glRenderer = QString((const char*)glGetString(GL_RENDERER)); - return QJsonObject { - { "version", glVersion }, - { "slVersion", glslVersion }, - { "vendor", glVendor }, - { "renderer", glRenderer }, - }; + result = QJsonObject { + { "version", glVersion }, + { "slVersion", glslVersion }, + { "vendor", glVendor }, + { "renderer", glRenderer }, + }; + }); + return result; } QThread* RENDER_THREAD = nullptr; From 822e088240d4f3353180785d813690f08a0bdea2 Mon Sep 17 00:00:00 2001 From: Brad Hefta-Gaub Date: Tue, 25 Oct 2016 15:20:10 -0700 Subject: [PATCH 09/11] tweak format of gl_info --- interface/src/Application.cpp | 2 +- libraries/gl/src/gl/GLHelpers.cpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/interface/src/Application.cpp b/interface/src/Application.cpp index f70685a8b2..6ebe997057 100644 --- a/interface/src/Application.cpp +++ b/interface/src/Application.cpp @@ -858,7 +858,7 @@ Application::Application(int& argc, char** argv, QElapsedTimer& startupTimer, bo { "gl_version_int", glVersionToInteger(glContextData.value("version").toString()) }, { "gl_version", glContextData["version"] }, { "gl_vender", glContextData["vendor"] }, - { "gl_sl_version", glContextData["slVersion"] }, + { "gl_sl_version", glContextData["sl_version"] }, { "gl_renderer", glContextData["renderer"] }, { "ideal_thread_count", QThread::idealThreadCount() } }; diff --git a/libraries/gl/src/gl/GLHelpers.cpp b/libraries/gl/src/gl/GLHelpers.cpp index 1604edccac..4091a0d0b6 100644 --- a/libraries/gl/src/gl/GLHelpers.cpp +++ b/libraries/gl/src/gl/GLHelpers.cpp @@ -45,7 +45,7 @@ QJsonObject getGLContextData() { result = QJsonObject { { "version", glVersion }, - { "slVersion", glslVersion }, + { "sl_version", glslVersion }, { "vendor", glVendor }, { "renderer", glRenderer }, }; From 727fabeab2a48666f07096c038a4b334262fb9ab Mon Sep 17 00:00:00 2001 From: Ryan Huffman Date: Tue, 25 Oct 2016 15:28:11 -0700 Subject: [PATCH 10/11] Fix away.js logging all Messages --- scripts/system/away.js | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/scripts/system/away.js b/scripts/system/away.js index 29bbd65d11..79ec22967d 100644 --- a/scripts/system/away.js +++ b/scripts/system/away.js @@ -304,9 +304,9 @@ function setEnabled(value) { var CHANNEL_AWAY_ENABLE = "Hifi-Away-Enable"; var handleMessage = function(channel, message, sender) { - print("Got away message"); - if (channel == CHANNEL_AWAY_ENABLE) { - setEnabled(message == 'enable'); + if (channel === CHANNEL_AWAY_ENABLE) { + print("away.js | Got message on Hifi-Away-Enable: ", message); + setEnabled(message === 'enable'); } } Messages.subscribe(CHANNEL_AWAY_ENABLE); @@ -343,6 +343,7 @@ Script.scriptEnding.connect(function () { Controller.disableMapping(eventMappingName); Controller.mousePressEvent.disconnect(goActive); Controller.keyPressEvent.disconnect(maybeGoActive); + Messages.messageReceived.disconnect(handleMessage); }); if (HMD.active && !HMD.mounted) { From 23aa6267551c7db26b1c18f2bacfcf1be9e36e41 Mon Sep 17 00:00:00 2001 From: Anthony Thibault Date: Tue, 25 Oct 2016 15:28:37 -0700 Subject: [PATCH 11/11] Destroy render scene & engine before Application is destroyed Many render items/payloads contain smart pointers back to the objects that added them to the scene, including entity and avatar objects. Currently, those render items are destroyed when the scene is destroyed very late in the application life-cycle. There are rare crashes that can occur when these render items are destroyed. Possibly, due to them referencing objects that have already been destroyed via raw pointers. In an effort to eliminate these crashes, we now destroy the scene earlier, within Application::aboutToQuit() which is connected to the QCoreApplication::aboutToQuit signal. Also, we guard against null scene pointer dereferences. Any location that accesses the scene off the main thread, now checks the validity of the scene pointer. --- interface/src/Application.cpp | 6 ++++ interface/src/avatar/AvatarManager.cpp | 13 +++++--- .../src/EntityTreeRenderer.cpp | 30 +++++++++++++------ .../src/RenderableEntityItem.h | 11 +++++-- .../src/RenderableZoneEntityItem.cpp | 11 ++++--- libraries/render-utils/src/Model.cpp | 8 +++-- libraries/render/src/render/Scene.cpp | 4 +++ libraries/render/src/render/Scene.h | 2 +- 8 files changed, 62 insertions(+), 23 deletions(-) diff --git a/interface/src/Application.cpp b/interface/src/Application.cpp index 861e3a2246..7e37dd7455 100644 --- a/interface/src/Application.cpp +++ b/interface/src/Application.cpp @@ -1576,6 +1576,12 @@ void Application::cleanupBeforeQuit() { #endif DependencyManager::destroy(); + + // shutdown render engine + _main3DScene = nullptr; + _renderEngine = nullptr; + + qCDebug(interfaceapp) << "Application::cleanupBeforeQuit() complete"; } Application::~Application() { diff --git a/interface/src/avatar/AvatarManager.cpp b/interface/src/avatar/AvatarManager.cpp index 18856ff914..e7f3deeaea 100644 --- a/interface/src/avatar/AvatarManager.cpp +++ b/interface/src/avatar/AvatarManager.cpp @@ -36,6 +36,7 @@ #include "Application.h" #include "Avatar.h" #include "AvatarManager.h" +#include "InterfaceLogging.h" #include "Menu.h" #include "MyAvatar.h" #include "SceneScriptingInterface.h" @@ -208,11 +209,15 @@ AvatarSharedPointer AvatarManager::addAvatar(const QUuid& sessionUUID, const QWe auto rawRenderableAvatar = std::static_pointer_cast(newAvatar); render::ScenePointer scene = qApp->getMain3DScene(); - render::PendingChanges pendingChanges; - if (DependencyManager::get()->shouldRenderAvatars()) { - rawRenderableAvatar->addToScene(rawRenderableAvatar, scene, pendingChanges); + if (scene) { + render::PendingChanges pendingChanges; + if (DependencyManager::get()->shouldRenderAvatars()) { + rawRenderableAvatar->addToScene(rawRenderableAvatar, scene, pendingChanges); + } + scene->enqueuePendingChanges(pendingChanges); + } else { + qCWarning(interfaceapp) << "AvatarManager::addAvatar() : Unexpected null scene, possibly during application shutdown"; } - scene->enqueuePendingChanges(pendingChanges); return newAvatar; } diff --git a/libraries/entities-renderer/src/EntityTreeRenderer.cpp b/libraries/entities-renderer/src/EntityTreeRenderer.cpp index e0fc03897a..c842a78dc5 100644 --- a/libraries/entities-renderer/src/EntityTreeRenderer.cpp +++ b/libraries/entities-renderer/src/EntityTreeRenderer.cpp @@ -128,11 +128,15 @@ void EntityTreeRenderer::clear() { // remove all entities from the scene auto scene = _viewState->getMain3DScene(); - render::PendingChanges pendingChanges; - foreach(auto entity, _entitiesInScene) { - entity->removeFromScene(entity, scene, pendingChanges); + if (scene) { + render::PendingChanges pendingChanges; + foreach(auto entity, _entitiesInScene) { + entity->removeFromScene(entity, scene, pendingChanges); + } + scene->enqueuePendingChanges(pendingChanges); + } else { + qCWarning(entitiesrenderer) << "EntitityTreeRenderer::clear(), Unexpected null scene, possibly during application shutdown"; } - scene->enqueuePendingChanges(pendingChanges); _entitiesInScene.clear(); // reset the zone to the default (while we load the next scene) @@ -901,8 +905,12 @@ void EntityTreeRenderer::deletingEntity(const EntityItemID& entityID) { auto entity = _entitiesInScene.take(entityID); render::PendingChanges pendingChanges; auto scene = _viewState->getMain3DScene(); - entity->removeFromScene(entity, scene, pendingChanges); - scene->enqueuePendingChanges(pendingChanges); + if (scene) { + entity->removeFromScene(entity, scene, pendingChanges); + scene->enqueuePendingChanges(pendingChanges); + } else { + qCWarning(entitiesrenderer) << "EntityTreeRenderer::deletingEntity(), Unexpected null scene, possibly during application shutdown"; + } } } @@ -919,10 +927,14 @@ void EntityTreeRenderer::addEntityToScene(EntityItemPointer entity) { // here's where we add the entity payload to the scene render::PendingChanges pendingChanges; auto scene = _viewState->getMain3DScene(); - if (entity->addToScene(entity, scene, pendingChanges)) { - _entitiesInScene.insert(entity->getEntityItemID(), entity); + if (scene) { + if (entity->addToScene(entity, scene, pendingChanges)) { + _entitiesInScene.insert(entity->getEntityItemID(), entity); + } + scene->enqueuePendingChanges(pendingChanges); + } else { + qCWarning(entitiesrenderer) << "EntityTreeRenderer::addEntityToScene(), Unexpected null scene, possibly during application shutdown"; } - scene->enqueuePendingChanges(pendingChanges); } diff --git a/libraries/entities-renderer/src/RenderableEntityItem.h b/libraries/entities-renderer/src/RenderableEntityItem.h index 22b6264520..ec65bab1c8 100644 --- a/libraries/entities-renderer/src/RenderableEntityItem.h +++ b/libraries/entities-renderer/src/RenderableEntityItem.h @@ -15,6 +15,7 @@ #include #include #include "AbstractViewStateInterface.h" +#include "EntitiesRendererLogging.h" // These or the icon "name" used by the render item status value, they correspond to the atlas texture used by the DrawItemStatus @@ -79,10 +80,14 @@ public: render::PendingChanges pendingChanges; render::ScenePointer scene = AbstractViewStateInterface::instance()->getMain3DScene(); - pendingChanges.updateItem(_myItem, [](RenderableEntityItemProxy& data) { - }); + if (scene) { + pendingChanges.updateItem(_myItem, [](RenderableEntityItemProxy& data) { + }); - scene->enqueuePendingChanges(pendingChanges); + scene->enqueuePendingChanges(pendingChanges); + } else { + qCWarning(entitiesrenderer) << "SimpleRenderableEntityItem::notifyChanged(), Unexpected null scene, possibly during application shutdown"; + } } private: diff --git a/libraries/entities-renderer/src/RenderableZoneEntityItem.cpp b/libraries/entities-renderer/src/RenderableZoneEntityItem.cpp index 9aa52f5ad3..0215ce4d07 100644 --- a/libraries/entities-renderer/src/RenderableZoneEntityItem.cpp +++ b/libraries/entities-renderer/src/RenderableZoneEntityItem.cpp @@ -248,9 +248,12 @@ void RenderableZoneEntityItem::notifyBoundChanged() { } render::PendingChanges pendingChanges; render::ScenePointer scene = AbstractViewStateInterface::instance()->getMain3DScene(); + if (scene) { + pendingChanges.updateItem(_myMetaItem, [](RenderableZoneEntityItemMeta& data) { + }); - pendingChanges.updateItem(_myMetaItem, [](RenderableZoneEntityItemMeta& data) { - }); - - scene->enqueuePendingChanges(pendingChanges); + scene->enqueuePendingChanges(pendingChanges); + } else { + qCWarning(entitiesrenderer) << "RenderableZoneEntityItem::notifyBoundChanged(), Unexpected null scene, possibly during application shutdown"; + } } diff --git a/libraries/render-utils/src/Model.cpp b/libraries/render-utils/src/Model.cpp index 28a1c3d579..6e1f57778b 100644 --- a/libraries/render-utils/src/Model.cpp +++ b/libraries/render-utils/src/Model.cpp @@ -862,8 +862,12 @@ void Model::setURL(const QUrl& url) { { render::PendingChanges pendingChanges; render::ScenePointer scene = AbstractViewStateInterface::instance()->getMain3DScene(); - removeFromScene(scene, pendingChanges); - scene->enqueuePendingChanges(pendingChanges); + if (scene) { + removeFromScene(scene, pendingChanges); + scene->enqueuePendingChanges(pendingChanges); + } else { + qCWarning(renderutils) << "Model::setURL(), Unexpected null scene, possibly during application shutdown"; + } } _needsReload = true; diff --git a/libraries/render/src/render/Scene.cpp b/libraries/render/src/render/Scene.cpp index 0b1d8fb55f..6bc42ac656 100644 --- a/libraries/render/src/render/Scene.cpp +++ b/libraries/render/src/render/Scene.cpp @@ -48,6 +48,10 @@ Scene::Scene(glm::vec3 origin, float size) : _items.push_back(Item()); // add the itemID #0 to nothing } +Scene::~Scene() { + qDebug() << "Scene::~Scene()"; +} + ItemID Scene::allocateID() { // Just increment and return the proevious value initialized at 0 return _IDAllocator.fetch_add(1); diff --git a/libraries/render/src/render/Scene.h b/libraries/render/src/render/Scene.h index b7cfc367b8..6b57a22a36 100644 --- a/libraries/render/src/render/Scene.h +++ b/libraries/render/src/render/Scene.h @@ -55,7 +55,7 @@ typedef std::queue PendingChangesQueue; class Scene { public: Scene(glm::vec3 origin, float size); - ~Scene() {} + ~Scene(); // This call is thread safe, can be called from anywhere to allocate a new ID ItemID allocateID();