From f5afb2dbbd123c135b1537a053852e590ecd6be8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Henrik=20Rydg=C3=A5rd?= Date: Sat, 27 Jun 2020 09:41:48 +0200 Subject: [PATCH 1/2] Improve some logging, and print the line number from PanicAlerts. --- Common/MsgHandler.cpp | 12 ++++++------ Common/MsgHandler.h | 8 ++++---- ext/native/thin3d/VulkanRenderManager.cpp | 14 +++----------- 3 files changed, 13 insertions(+), 21 deletions(-) diff --git a/Common/MsgHandler.cpp b/Common/MsgHandler.cpp index b53d79d41a27..f2ec4dcadd31 100644 --- a/Common/MsgHandler.cpp +++ b/Common/MsgHandler.cpp @@ -24,9 +24,9 @@ #include "base/logging.h" #include "util/text/utf8.h" -bool MsgHandler(const char *caption, const char *text, bool yes_no, int Style); +bool MsgHandler(const char *caption, const char *text, const char *file, int line, bool yes_no, int Style); -bool MsgAlert(bool yes_no, int Style, const char* format, ...) { +bool MsgAlert(bool yes_no, int Style, const char *file, int line, const char* format, ...) { // Read message and write it to the log char buffer[2048]; static const char *captions[] = { @@ -42,10 +42,10 @@ bool MsgAlert(bool yes_no, int Style, const char* format, ...) { CharArrayFromFormatV(buffer, sizeof(buffer)-1, format, args); va_end(args); // Normal logging (will also log to Android log) - ERROR_LOG(SYSTEM, "%s: %s", caption, buffer); + ERROR_LOG(SYSTEM, "(%s:%d) %s: %s", file, line, caption, buffer); // Don't ignore questions, especially AskYesNo, PanicYesNo could be ignored if (Style == QUESTION || Style == CRITICAL) - return MsgHandler(caption, buffer, yes_no, Style); + return MsgHandler(caption, buffer, file, line, yes_no, Style); return true; } @@ -54,7 +54,7 @@ bool MsgAlert(bool yes_no, int Style, const char* format, ...) { #endif // Default non library dependent panic alert -bool MsgHandler(const char* caption, const char* text, bool yes_no, int Style) { +bool MsgHandler(const char* caption, const char* text, const char *file, int line, bool yes_no, int Style) { #if defined(USING_WIN_UI) int msgBoxStyle = MB_ICONINFORMATION; if (Style == QUESTION) msgBoxStyle = MB_ICONQUESTION; @@ -69,7 +69,7 @@ bool MsgHandler(const char* caption, const char* text, bool yes_no, int Style) { return false; #else // Will use android-log if available, printf if not. - ELOG("%s", text); + ELOG("(%s:%d) %s", file, line, text); return false; #endif } diff --git a/Common/MsgHandler.h b/Common/MsgHandler.h index ee28d8ea334f..4f453172c931 100644 --- a/Common/MsgHandler.h +++ b/Common/MsgHandler.h @@ -25,13 +25,13 @@ enum MSG_TYPE { CRITICAL }; -bool MsgAlert(bool yes_no, int Style, const char* format, ...) +bool MsgAlert(bool yes_no, int Style, const char *file, int line, const char* format, ...) #ifdef __GNUC__ - __attribute__((format(printf, 3, 4))) + __attribute__((format(printf, 5, 6))) #endif ; -#define PanicAlert(...) MsgAlert(false, WARNING, __VA_ARGS__) +#define PanicAlert(...) MsgAlert(false, WARNING, __FILE__, __LINE__, __VA_ARGS__) // Used only for asserts. -#define PanicYesNo(...) MsgAlert(true, CRITICAL, __VA_ARGS__) +#define PanicYesNo(...) MsgAlert(true, CRITICAL, __FILE__, __LINE__, __VA_ARGS__) diff --git a/ext/native/thin3d/VulkanRenderManager.cpp b/ext/native/thin3d/VulkanRenderManager.cpp index 8d8659be3472..8278e1ca997c 100644 --- a/ext/native/thin3d/VulkanRenderManager.cpp +++ b/ext/native/thin3d/VulkanRenderManager.cpp @@ -1040,7 +1040,7 @@ void VulkanRenderManager::BeginSubmitFrame(int frame) { // Hopefully the resize will happen shortly. Ignore - one frame might look bad or something. WLOG("VK_SUBOPTIMAL_KHR returned - ignoring"); } else if (res == VK_ERROR_OUT_OF_DATE_KHR) { - WLOG("VK_ERROR_OUT_OF_DATE_KHR returned - not presenting"); + WLOG("VK_ERROR_OUT_OF_DATE_KHR returned - processing the frame, but not presenting"); frameData.skipSwap = true; } else { _assert_msg_(G3D, res == VK_SUCCESS, "vkAcquireNextImageKHR failed! result=%s", VulkanResultToString(res)); @@ -1084,11 +1084,7 @@ void VulkanRenderManager::Submit(int frame, bool triggerFrameFence) { submit_info.pCommandBuffers = cmdBufs; res = vkQueueSubmit(vulkan_->GetGraphicsQueue(), 1, &submit_info, VK_NULL_HANDLE); if (res == VK_ERROR_DEVICE_LOST) { -#ifdef _WIN32 - _assert_msg_(G3D, false, "Lost the Vulkan device! If this happens again, switch Graphics Backend from Vulkan to Direct3D11"); -#else - _assert_msg_(G3D, false, "Lost the Vulkan device! If this happens again, switch Graphics Backend from Vulkan to OpenGL"); -#endif + _assert_msg_(G3D, false, "Lost the Vulkan device in split submit! If this happens again, switch Graphics Backend away from Vulkan"); } else { _assert_msg_(G3D, res == VK_SUCCESS, "vkQueueSubmit failed (init)! result=%s", VulkanResultToString(res)); } @@ -1112,11 +1108,7 @@ void VulkanRenderManager::Submit(int frame, bool triggerFrameFence) { } res = vkQueueSubmit(vulkan_->GetGraphicsQueue(), 1, &submit_info, triggerFrameFence ? frameData.fence : frameData.readbackFence); if (res == VK_ERROR_DEVICE_LOST) { -#ifdef _WIN32 - _assert_msg_(G3D, false, "Lost the Vulkan device! If this happens again, switch Graphics Backend from Vulkan to Direct3D11"); -#else - _assert_msg_(G3D, false, "Lost the Vulkan device! If this happens again, switch Graphics Backend from Vulkan to OpenGL"); -#endif + _assert_msg_(G3D, false, "Lost the Vulkan device in vkQueueSubmit! If this happens again, switch Graphics Backend away from Vulkan"); } else { _assert_msg_(G3D, res == VK_SUCCESS, "vkQueueSubmit failed (main, split=%d)! result=%s", (int)splitSubmit_, VulkanResultToString(res)); } From 6560192d8ef1d89a7646a4cf8e13038ec179dd50 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Henrik=20Rydg=C3=A5rd?= Date: Sun, 19 Jul 2020 11:03:46 +0200 Subject: [PATCH 2/2] Support full VSync control in SDL OpenGL. (Not yet Qt). Forgot about iOS SDL headless buildfix Additional iOS buildfix --- Common/GraphicsContext.h | 10 ---------- Core/Config.cpp | 2 +- GPU/GPUCommon.cpp | 2 +- GPU/GPUCommon.h | 2 -- Qt/QtMain.h | 7 ++++++- SDL/SDLGLGraphicsContext.cpp | 9 +++++++++ SDL/SDLGLGraphicsContext.h | 7 ++++++- UI/GameSettingsScreen.cpp | 4 ++-- ext/native/thin3d/thin3d_gl.cpp | 2 -- headless/SDLHeadlessHost.cpp | 9 +++++++-- ios/ViewController.mm | 9 ++++++++- 11 files changed, 40 insertions(+), 23 deletions(-) diff --git a/Common/GraphicsContext.h b/Common/GraphicsContext.h index d17d77d7260e..bf4f4938718d 100644 --- a/Common/GraphicsContext.h +++ b/Common/GraphicsContext.h @@ -40,13 +40,3 @@ class GraphicsContext { virtual Draw::DrawContext *GetDrawContext() = 0; }; - -class DummyGraphicsContext : public GraphicsContext { -public: - void Shutdown() override {} - void SwapInterval(int interval) override {} - void SwapBuffers() override {} - void Resize() override {} - - Draw::DrawContext *GetDrawContext() override { return nullptr; } -}; diff --git a/Core/Config.cpp b/Core/Config.cpp index 1ef4dc5ba22a..84e8bcf01e0e 100644 --- a/Core/Config.cpp +++ b/Core/Config.cpp @@ -530,7 +530,7 @@ static int DefaultInternalResolution() { } static bool DefaultFrameskipUnthrottle() { -#if !PPSSPP_PLATFORM(WINDOWS) || PPSSPP_PLATFORM(UWP) +#if PPSSPP_PLATFORM(ANDROID) || defined(USING_QT_UI) || PPSSPP_PLATFORM(UWP) || PPSSPP_PLATFORM(IOS) return true; #else return false; diff --git a/GPU/GPUCommon.cpp b/GPU/GPUCommon.cpp index 0a09725677f7..9c7baedf546b 100644 --- a/GPU/GPUCommon.cpp +++ b/GPU/GPUCommon.cpp @@ -467,7 +467,7 @@ void GPUCommon::Reinitialize() { } void GPUCommon::UpdateVsyncInterval(bool force) { -#ifdef _WIN32 +#if !(PPSSPP_PLATFORM(ANDROID) || USING_QT_UI || PPSSPP_PLATFORM(UWP) || PPSSPP_PLATFORM(IOS)) int desiredVSyncInterval = g_Config.bVSync ? 1 : 0; if (PSP_CoreParameter().unthrottle) { desiredVSyncInterval = 0; diff --git a/GPU/GPUCommon.h b/GPU/GPUCommon.h index 27deb1b77bf7..2dd4d7da1bbe 100644 --- a/GPU/GPUCommon.h +++ b/GPU/GPUCommon.h @@ -364,9 +364,7 @@ class GPUCommon : public GPUInterface, public GPUDebugInterface { double timeSteppingStarted_; double timeSpentStepping_; -#ifdef _WIN32 int lastVsync_ = -1; -#endif }; struct CommonCommandTableEntry { diff --git a/Qt/QtMain.h b/Qt/QtMain.h index 93bf5ccb7594..ebb2c03cea84 100644 --- a/Qt/QtMain.h +++ b/Qt/QtMain.h @@ -56,6 +56,8 @@ class QtGLGraphicsContext : public GraphicsContext { renderManager_->SetInflightFrames(g_Config.iInflightFrames); bool success = draw_->CreatePresets(); _assert_msg_(G3D, success, "Failed to compile preset shaders"); + + // TODO: Need to figure out how to implement SetSwapInterval for Qt. } ~QtGLGraphicsContext() { @@ -65,7 +67,10 @@ class QtGLGraphicsContext : public GraphicsContext { } void Shutdown() override {} - void SwapInterval(int interval) override {} + void SwapInterval(int interval) override { + // See TODO in constructor. + // renderManager_->SwapInterval(interval); + } void SwapBuffers() override {} void Resize() override {} diff --git a/SDL/SDLGLGraphicsContext.cpp b/SDL/SDLGLGraphicsContext.cpp index 7f1a58c66abd..772f5c764f2c 100644 --- a/SDL/SDLGLGraphicsContext.cpp +++ b/SDL/SDLGLGraphicsContext.cpp @@ -423,10 +423,19 @@ int SDLGLGraphicsContext::Init(SDL_Window *&window, int x, int y, int mode, std: SDL_GL_SwapWindow(window_); #endif }); + + renderManager_->SetSwapIntervalFunction([&](int interval) { + ILOG("SDL SwapInterval: %d", interval); + SDL_GL_SetSwapInterval(interval); + }); window_ = window; return 0; } +void SDLGLGraphicsContext::SwapInterval(int interval) { + renderManager_->SwapInterval(interval); +} + void SDLGLGraphicsContext::Shutdown() { } diff --git a/SDL/SDLGLGraphicsContext.h b/SDL/SDLGLGraphicsContext.h index 666aa727745d..88c9d8202d01 100644 --- a/SDL/SDLGLGraphicsContext.h +++ b/SDL/SDLGLGraphicsContext.h @@ -5,7 +5,7 @@ #include "gfx/gl_common.h" #include "Common/GraphicsContext.h" -class SDLGLGraphicsContext : public DummyGraphicsContext { +class SDLGLGraphicsContext : public GraphicsContext { public: SDLGLGraphicsContext() { } @@ -20,6 +20,11 @@ class SDLGLGraphicsContext : public DummyGraphicsContext { // Do nothing, the render thread takes care of this. } + // Gets forwarded to the render thread. + void SwapInterval(int interval) override; + + void Resize() override {} + Draw::DrawContext *GetDrawContext() override { return draw_; } diff --git a/UI/GameSettingsScreen.cpp b/UI/GameSettingsScreen.cpp index 1b353d879769..44d6f5215187 100644 --- a/UI/GameSettingsScreen.cpp +++ b/UI/GameSettingsScreen.cpp @@ -338,7 +338,7 @@ void GameSettingsScreen::CreateViews() { return !g_Config.bSoftwareRendering && g_Config.iRenderingMode != FB_NON_BUFFERED_MODE; }); -#ifdef __ANDROID__ +#if PPSSPP_PLATFORM(ANDROID) if (System_GetPropertyInt(SYSPROP_DEVICE_TYPE) != DEVICE_TYPE_TV) { static const char *deviceResolutions[] = { "Native device resolution", "Auto (same as Rendering)", "1x PSP", "2x PSP", "3x PSP", "4x PSP", "5x PSP" }; int max_res_temp = std::max(System_GetPropertyInt(SYSPROP_DISPLAY_XRES), System_GetPropertyInt(SYSPROP_DISPLAY_YRES)) / 480 + 2; @@ -350,7 +350,7 @@ void GameSettingsScreen::CreateViews() { } #endif -#if !PPSSPP_PLATFORM(ANDROID) +#if !(PPSSPP_PLATFORM(ANDROID) || defined(USING_QT_UI) || PPSSPP_PLATFORM(UWP)) || PPSSPP_PLATFORM(IOS) CheckBox *vSync = graphicsSettings->Add(new CheckBox(&g_Config.bVSync, gr->T("VSync"))); vSync->OnClick.Add([=](EventParams &e) { NativeResized(); diff --git a/ext/native/thin3d/thin3d_gl.cpp b/ext/native/thin3d/thin3d_gl.cpp index bc2eece3797f..e25535816fcc 100644 --- a/ext/native/thin3d/thin3d_gl.cpp +++ b/ext/native/thin3d/thin3d_gl.cpp @@ -297,7 +297,6 @@ class OpenGLPipeline : public Pipeline { OpenGLPipeline(GLRenderManager *render) : render_(render) { } ~OpenGLPipeline() { - DLOG("OpenGLPipeline released"); for (auto &iter : shaders) { iter->Release(); } @@ -979,7 +978,6 @@ Pipeline *OpenGLContext::CreateGraphicsPipeline(const PipelineDesc &desc) { pipeline->dynamicUniforms = *desc.uniformDesc; pipeline->dynamicUniformLocs_.resize(desc.uniformDesc->uniforms.size()); } - ILOG("Linking shaders."); if (pipeline->LinkShaders()) { // Build the rest of the virtual pipeline object. pipeline->prim = primToGL[(int)desc.prim]; diff --git a/headless/SDLHeadlessHost.cpp b/headless/SDLHeadlessHost.cpp index d0e5757fff0d..b45b50724d69 100644 --- a/headless/SDLHeadlessHost.cpp +++ b/headless/SDLHeadlessHost.cpp @@ -53,7 +53,7 @@ SDL_Window *CreateHiddenWindow() { return SDL_CreateWindow("PPSSPPHeadless", 0, 0, WINDOW_WIDTH, WINDOW_HEIGHT, flags); } -class GLDummyGraphicsContext : public DummyGraphicsContext { +class GLDummyGraphicsContext : public GraphicsContext { public: GLDummyGraphicsContext() { } @@ -92,6 +92,11 @@ class GLDummyGraphicsContext : public DummyGraphicsContext { renderManager_->StopThread(); } + void Shutdown() override {} + void Resize() override {} + void SwapInterval(int interval) override {} + void SwapBuffers() override {} + private: Draw::DrawContext *draw_; GLRenderManager *renderManager_ = nullptr; @@ -124,7 +129,7 @@ bool GLDummyGraphicsContext::InitFromRenderThread(std::string *errorMessage) { glContext_ = SDL_GL_CreateContext(screen_); // Ensure that the swap interval is set after context creation (needed for kmsdrm) - SDL_GL_SetSwapInterval(1); + SDL_GL_SetSwapInterval(0); #ifndef USING_GLES2 // Some core profile drivers elide certain extensions from GL_EXTENSIONS/etc. diff --git a/ios/ViewController.mm b/ios/ViewController.mm index 73fd05c7fd9b..d36ae51b07b2 100644 --- a/ios/ViewController.mm +++ b/ios/ViewController.mm @@ -38,7 +38,7 @@ #define IS_IPAD() ([UIDevice currentDevice].userInterfaceIdiom == UIUserInterfaceIdiomPad) #define IS_IPHONE() ([UIDevice currentDevice].userInterfaceIdiom == UIUserInterfaceIdiomPhone) -class IOSGraphicsContext : public DummyGraphicsContext { +class IOSGraphicsContext : public GraphicsContext { public: IOSGraphicsContext() { CheckGLExtensions(); @@ -55,6 +55,12 @@ Draw::DrawContext *GetDrawContext() override { return draw_; } + + void SwapInterval(int interval) override {} + void SwapBuffers() override {} + void Resize() override {} + void Shutdown() override {} + void ThreadStart() override { renderManager_->ThreadStart(draw_); } @@ -71,6 +77,7 @@ void StopThread() override { renderManager_->WaitUntilQueueIdle(); renderManager_->StopThread(); } + private: Draw::DrawContext *draw_; GLRenderManager *renderManager_;