mirror of
https://github.com/libretro/RetroArch
synced 2025-03-22 07:21:15 +00:00
Adds video_hard_sync_frames.
Allows to control the maximum amount of frames that can be queued on GPU.
This commit is contained in:
parent
cb84451542
commit
43a6346d26
@ -225,6 +225,11 @@ static const bool vsync = true;
|
||||
|
||||
// Attempts to hard-synchronize CPU and GPU. Can reduce latency at cost of performance.
|
||||
static const bool hard_sync = false;
|
||||
// Configures how many frames the GPU can run ahead of CPU.
|
||||
// 0: Syncs to GPU immediately.
|
||||
// 1: Syncs to previous frame.
|
||||
// 2: Etc ...
|
||||
static const unsigned hard_sync_frames = 0;
|
||||
|
||||
// Threaded video. Will possibly increase performance significantly at cost of worse synchronization and latency.
|
||||
static const bool video_threaded = false;
|
||||
|
@ -117,6 +117,7 @@ typedef enum
|
||||
RGUI_SETTINGS_VIDEO_ROTATION,
|
||||
RGUI_SETTINGS_VIDEO_VSYNC,
|
||||
RGUI_SETTINGS_VIDEO_HARD_SYNC,
|
||||
RGUI_SETTINGS_VIDEO_HARD_SYNC_FRAMES,
|
||||
RGUI_SETTINGS_VIDEO_OPTIONS_LAST,
|
||||
#ifdef HAVE_SHADER_MANAGER
|
||||
RGUI_SETTINGS_SHADER_OPTIONS,
|
||||
|
@ -592,10 +592,13 @@ static void render_text(rgui_handle_t *rgui)
|
||||
snprintf(type_str, sizeof(type_str), "%d", g_extern.console.screen.gamma_correction);
|
||||
break;
|
||||
case RGUI_SETTINGS_VIDEO_VSYNC:
|
||||
snprintf(type_str, sizeof(type_str), g_settings.video.vsync ? "ON" : "OFF");
|
||||
strlcpy(type_str, g_settings.video.vsync ? "ON" : "OFF", sizeof(type_str));
|
||||
break;
|
||||
case RGUI_SETTINGS_VIDEO_HARD_SYNC:
|
||||
snprintf(type_str, sizeof(type_str), g_settings.video.hard_sync ? "ON" : "OFF");
|
||||
strlcpy(type_str, g_settings.video.hard_sync ? "ON" : "OFF", sizeof(type_str));
|
||||
break;
|
||||
case RGUI_SETTINGS_VIDEO_HARD_SYNC_FRAMES:
|
||||
snprintf(type_str, sizeof(type_str), "%u", g_settings.video.hard_sync_frames);
|
||||
break;
|
||||
case RGUI_SETTINGS_VIDEO_INTEGER_SCALE:
|
||||
strlcpy(type_str, g_settings.video.scale_integer ? "ON" : "OFF", sizeof(type_str));
|
||||
@ -1499,6 +1502,7 @@ static void rgui_settings_video_options_populate_entries(rgui_handle_t *rgui)
|
||||
rgui_list_push(rgui->selection_buf, "Rotation", RGUI_SETTINGS_VIDEO_ROTATION, 0);
|
||||
rgui_list_push(rgui->selection_buf, "VSync", RGUI_SETTINGS_VIDEO_VSYNC, 0);
|
||||
rgui_list_push(rgui->selection_buf, "Hard GPU Sync", RGUI_SETTINGS_VIDEO_HARD_SYNC, 0);
|
||||
rgui_list_push(rgui->selection_buf, "Hard GPU Sync Frames", RGUI_SETTINGS_VIDEO_HARD_SYNC_FRAMES, 0);
|
||||
}
|
||||
|
||||
#ifdef HAVE_SHADER_MANAGER
|
||||
@ -1927,6 +1931,29 @@ static int video_option_toggle_setting(rgui_handle_t *rgui, unsigned setting, rg
|
||||
}
|
||||
break;
|
||||
|
||||
case RGUI_SETTINGS_VIDEO_HARD_SYNC_FRAMES:
|
||||
switch (action)
|
||||
{
|
||||
case RGUI_ACTION_START:
|
||||
g_settings.video.hard_sync_frames = 0;
|
||||
break;
|
||||
|
||||
case RGUI_ACTION_LEFT:
|
||||
if (g_settings.video.hard_sync_frames > 0)
|
||||
g_settings.video.hard_sync_frames--;
|
||||
break;
|
||||
|
||||
case RGUI_ACTION_RIGHT:
|
||||
case RGUI_ACTION_OK:
|
||||
if (g_settings.video.hard_sync_frames < 3)
|
||||
g_settings.video.hard_sync_frames++;
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
@ -155,6 +155,7 @@ struct settings
|
||||
unsigned fullscreen_y;
|
||||
bool vsync;
|
||||
bool hard_sync;
|
||||
unsigned hard_sync_frames;
|
||||
bool smooth;
|
||||
bool force_aspect;
|
||||
bool crop_overscan;
|
||||
|
26
gfx/gl.c
26
gfx/gl.c
@ -1546,9 +1546,17 @@ static bool gl_frame(void *data, const void *frame, unsigned width, unsigned hei
|
||||
RARCH_PERFORMANCE_INIT(gl_fence);
|
||||
RARCH_PERFORMANCE_START(gl_fence);
|
||||
glClear(GL_COLOR_BUFFER_BIT);
|
||||
GLsync sync = pglFenceSync(GL_SYNC_GPU_COMMANDS_COMPLETE, 0);
|
||||
pglClientWaitSync(sync, GL_SYNC_FLUSH_COMMANDS_BIT, 1000000000);
|
||||
pglDeleteSync(sync);
|
||||
gl->fences[gl->fence_count++] = pglFenceSync(GL_SYNC_GPU_COMMANDS_COMPLETE, 0);
|
||||
|
||||
while (gl->fence_count > g_settings.video.hard_sync_frames)
|
||||
{
|
||||
pglClientWaitSync(gl->fences[0], GL_SYNC_FLUSH_COMMANDS_BIT, 1000000000);
|
||||
pglDeleteSync(gl->fences[0]);
|
||||
|
||||
gl->fence_count--;
|
||||
memmove(gl->fences, gl->fences + 1, gl->fence_count * sizeof(GLsync));
|
||||
}
|
||||
|
||||
RARCH_PERFORMANCE_STOP(gl_fence);
|
||||
}
|
||||
#endif
|
||||
@ -1565,6 +1573,18 @@ static void gl_free(void *data)
|
||||
|
||||
gl_t *gl = (gl_t*)data;
|
||||
|
||||
#ifdef HAVE_GL_SYNC
|
||||
if (gl->have_sync)
|
||||
{
|
||||
for (unsigned i = 0; i < gl->fence_count; i++)
|
||||
{
|
||||
pglClientWaitSync(gl->fences[i], GL_SYNC_FLUSH_COMMANDS_BIT, 1000000000);
|
||||
pglDeleteSync(gl->fences[i]);
|
||||
}
|
||||
gl->fence_count = 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
if (gl->font_ctx)
|
||||
gl->font_ctx->deinit(gl);
|
||||
gl_shader_deinit(gl);
|
||||
|
@ -284,7 +284,10 @@ typedef struct gl
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_GL_SYNC
|
||||
#define MAX_FENCES 4
|
||||
bool have_sync;
|
||||
GLsync fences[MAX_FENCES];
|
||||
unsigned fence_count;
|
||||
#endif
|
||||
} gl_t;
|
||||
|
||||
|
@ -76,6 +76,10 @@
|
||||
# Attempts to hard-synchronize CPU and GPU. Can reduce latency at cost of performance.
|
||||
# video_hard_sync = false
|
||||
|
||||
# Sets how many frames CPU can run ahead of GPU when using video_hard_sync.
|
||||
# Maximum is 3.
|
||||
# video_hard_sync_frames = 0
|
||||
|
||||
# Use threaded video driver. Using this might improve performance at possible cost of latency and more video stuttering.
|
||||
# video_threaded = false
|
||||
|
||||
|
@ -165,6 +165,7 @@ void config_set_defaults(void)
|
||||
g_settings.video.disable_composition = disable_composition;
|
||||
g_settings.video.vsync = vsync;
|
||||
g_settings.video.hard_sync = hard_sync;
|
||||
g_settings.video.hard_sync_frames = hard_sync_frames;
|
||||
g_settings.video.threaded = video_threaded;
|
||||
g_settings.video.smooth = video_smooth;
|
||||
g_settings.video.force_aspect = force_aspect;
|
||||
@ -469,6 +470,11 @@ bool config_load_file(const char *path)
|
||||
CONFIG_GET_BOOL(video.disable_composition, "video_disable_composition");
|
||||
CONFIG_GET_BOOL(video.vsync, "video_vsync");
|
||||
CONFIG_GET_BOOL(video.hard_sync, "video_hard_sync");
|
||||
|
||||
CONFIG_GET_INT(video.hard_sync_frames, "video_hard_sync_frames");
|
||||
if (g_settings.video.hard_sync_frames > 3)
|
||||
g_settings.video.hard_sync_frames = 3;
|
||||
|
||||
CONFIG_GET_BOOL(video.threaded, "video_threaded");
|
||||
CONFIG_GET_BOOL(video.smooth, "video_smooth");
|
||||
CONFIG_GET_BOOL(video.force_aspect, "video_force_aspect");
|
||||
@ -954,6 +960,7 @@ bool config_save_file(const char *path)
|
||||
config_set_bool(conf, "video_smooth", g_settings.video.smooth);
|
||||
config_set_bool(conf, "video_vsync", g_settings.video.vsync);
|
||||
config_set_bool(conf, "video_hard_sync", g_settings.video.hard_sync);
|
||||
config_set_int(conf, "video_hard_sync_frames", g_settings.video.hard_sync_frames);
|
||||
config_set_int(conf, "aspect_ratio_index", g_settings.video.aspect_ratio_idx);
|
||||
config_set_string(conf, "audio_device", g_settings.audio.device);
|
||||
config_set_bool(conf, "audio_rate_control", g_settings.audio.rate_control);
|
||||
|
Loading…
x
Reference in New Issue
Block a user