Skip to content

Commit fa8968f

Browse files
authored
Merge pull request #12660 from unknownbrackets/frame-latency
GPU: Add setting to control inflight frame usage
2 parents c363c16 + 98df4bb commit fa8968f

File tree

12 files changed

+56
-4
lines changed

12 files changed

+56
-4
lines changed

Common/Vulkan/VulkanContext.cpp

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -285,6 +285,14 @@ void VulkanContext::EndFrame() {
285285
}
286286
}
287287

288+
void VulkanContext::UpdateInflightFrames(int n) {
289+
assert(n >= 1 && n <= MAX_INFLIGHT_FRAMES);
290+
inflightFrames_ = n;
291+
if (curFrame_ >= inflightFrames_) {
292+
curFrame_ = 0;
293+
}
294+
}
295+
288296
void VulkanContext::WaitUntilQueueIdle() {
289297
// Should almost never be used
290298
vkQueueWaitIdle(gfx_queue_);

Common/Vulkan/VulkanContext.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -254,6 +254,8 @@ class VulkanContext {
254254
int GetInflightFrames() const {
255255
return inflightFrames_;
256256
}
257+
// Don't call while a frame is in progress.
258+
void UpdateInflightFrames(int n);
257259

258260
int GetCurFrame() const {
259261
return curFrame_;

Core/Config.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -774,6 +774,8 @@ static ConfigSetting graphicsSettings[] = {
774774
ConfigSetting("GfxDebugSplitSubmit", &g_Config.bGfxDebugSplitSubmit, false, false, false),
775775
ConfigSetting("LogFrameDrops", &g_Config.bLogFrameDrops, false, true, false),
776776

777+
ConfigSetting("InflightFrames", &g_Config.iInflightFrames, 3, true, true),
778+
777779
ConfigSetting(false),
778780
};
779781

Core/Config.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -195,6 +195,7 @@ struct Config {
195195
std::string sPostShaderName; // Off for off.
196196
bool bGfxDebugOutput;
197197
bool bGfxDebugSplitSubmit;
198+
int iInflightFrames;
198199

199200
// Sound
200201
bool bEnableSound;

Core/FileLoaders/RamCachingFileLoader.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -78,7 +78,7 @@ size_t RamCachingFileLoader::ReadAt(s64 absolutePos, size_t bytes, void *data, F
7878
size_t bytesFromCache = ReadFromCache(absolutePos + readSize, bytes - readSize, (u8 *)data + readSize);
7979
readSize += bytesFromCache;
8080
if (bytesFromCache == 0) {
81-
// We can't read any more.
81+
// We can't read any more.
8282
break;
8383
}
8484
}

GPU/GLES/GPU_GLES.cpp

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -97,6 +97,9 @@ GPU_GLES::GPU_GLES(GraphicsContext *gfxCtx, Draw::DrawContext *draw)
9797

9898
textureCacheGL_->NotifyConfigChanged();
9999

100+
GLRenderManager *rm = (GLRenderManager *)draw_->GetNativeObject(Draw::NativeObject::RENDER_MANAGER);
101+
rm->SetInflightFrames(g_Config.iInflightFrames);
102+
100103
// Load shader cache.
101104
std::string discID = g_paramSFO.GetDiscID();
102105
if (discID.size()) {
@@ -355,6 +358,9 @@ void GPU_GLES::BeginHostFrame() {
355358
GPUCommon::BeginHostFrame();
356359
UpdateCmdInfo();
357360
if (resized_) {
361+
GLRenderManager *rm = (GLRenderManager *)draw_->GetNativeObject(Draw::NativeObject::RENDER_MANAGER);
362+
rm->SetInflightFrames(g_Config.iInflightFrames);
363+
358364
CheckGPUFeatures();
359365
framebufferManager_->Resized();
360366
drawEngine_.Resized();

GPU/Vulkan/GPU_Vulkan.cpp

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,6 @@
2828
#include "Core/Config.h"
2929
#include "Core/Debugger/Breakpoints.h"
3030
#include "Core/MemMapHelpers.h"
31-
#include "Core/Config.h"
3231
#include "Core/Reporting.h"
3332
#include "Core/System.h"
3433
#include "Core/ELF/ParamSFO.h"
@@ -98,6 +97,8 @@ GPU_Vulkan::GPU_Vulkan(GraphicsContext *gfxCtx, Draw::DrawContext *draw)
9897
if (vulkan_->GetDeviceFeatures().enabled.wideLines) {
9998
drawEngine_.SetLineWidth(PSP_CoreParameter().renderWidth / 480.0f);
10099
}
100+
VulkanRenderManager *rm = (VulkanRenderManager *)draw_->GetNativeObject(Draw::NativeObject::RENDER_MANAGER);
101+
rm->SetInflightFrames(g_Config.iInflightFrames);
101102

102103
// Load shader cache.
103104
std::string discID = g_paramSFO.GetDiscID();
@@ -283,6 +284,9 @@ void GPU_Vulkan::BeginHostFrame() {
283284
UpdateCmdInfo();
284285

285286
if (resized_) {
287+
VulkanRenderManager *rm = (VulkanRenderManager *)draw_->GetNativeObject(Draw::NativeObject::RENDER_MANAGER);
288+
rm->SetInflightFrames(g_Config.iInflightFrames);
289+
286290
CheckGPUFeatures();
287291
// In case the GPU changed.
288292
BuildReportingInfo();

UI/GameSettingsScreen.cpp

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -349,6 +349,15 @@ void GameSettingsScreen::CreateViews() {
349349
});
350350
#endif
351351

352+
if (GetGPUBackend() == GPUBackend::VULKAN || GetGPUBackend() == GPUBackend::OPENGL) {
353+
static const char *bufferOptions[] = { "No buffer", "Up to 1", "Up to 2" };
354+
PopupMultiChoice *inflightChoice = graphicsSettings->Add(new PopupMultiChoice(&g_Config.iInflightFrames, gr->T("Buffer graphics commands (faster, input lag)"), bufferOptions, 0, ARRAY_SIZE(bufferOptions), gr->GetName(), screenManager()));
355+
inflightChoice->OnChoice.Add([=](EventParams &e) {
356+
NativeMessageReceived("gpu_resized", "");
357+
return UI::EVENT_CONTINUE;
358+
});
359+
}
360+
352361
CheckBox *hwTransform = graphicsSettings->Add(new CheckBox(&g_Config.bHardwareTransform, gr->T("Hardware Transform")));
353362
hwTransform->OnClick.Handle(this, &GameSettingsScreen::OnHardwareTransform);
354363
hwTransform->SetDisabledPtr(&g_Config.bSoftwareRendering);

ext/native/thin3d/GLRenderManager.cpp

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -166,7 +166,7 @@ bool GLRenderManager::ThreadFrame() {
166166
do {
167167
if (nextFrame) {
168168
threadFrame_++;
169-
if (threadFrame_ >= MAX_INFLIGHT_FRAMES)
169+
if (threadFrame_ >= inflightFrames_)
170170
threadFrame_ = 0;
171171
}
172172
FrameData &frameData = frameData_[threadFrame_];
@@ -449,7 +449,11 @@ void GLRenderManager::Finish() {
449449
frameData.pull_condVar.notify_all();
450450

451451
curFrame_++;
452-
if (curFrame_ >= MAX_INFLIGHT_FRAMES)
452+
if (newInflightFrames_ != -1) {
453+
inflightFrames_ = newInflightFrames_;
454+
newInflightFrames_ = -1;
455+
}
456+
if (curFrame_ >= inflightFrames_)
453457
curFrame_ = 0;
454458

455459
insideFrame_ = false;

ext/native/thin3d/GLRenderManager.h

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -862,6 +862,10 @@ class GLRenderManager {
862862

863863
enum { MAX_INFLIGHT_FRAMES = 3 };
864864

865+
void SetInflightFrames(int f) {
866+
newInflightFrames_ = f < 1 || f > MAX_INFLIGHT_FRAMES ? MAX_INFLIGHT_FRAMES : f;
867+
}
868+
865869
int GetCurFrame() const {
866870
return curFrame_;
867871
}
@@ -988,6 +992,9 @@ class GLRenderManager {
988992
std::function<void(int)> swapIntervalFunction_;
989993
GLBufferStrategy bufferStrategy_ = GLBufferStrategy::SUBDATA;
990994

995+
int inflightFrames_ = MAX_INFLIGHT_FRAMES;
996+
int newInflightFrames_ = -1;
997+
991998
int swapInterval_ = 0;
992999
bool swapIntervalChanged_ = true;
9931000

0 commit comments

Comments
 (0)