diff --git a/gfx/common/drm_common.c b/gfx/common/drm_common.c index 33052c83e1..577d2f09a5 100644 --- a/gfx/common/drm_common.c +++ b/gfx/common/drm_common.c @@ -168,6 +168,18 @@ void drm_setup(int fd) RARCH_WARN("[DRM]: Cannot find original CRTC.\n"); } +float drm_get_refresh_rate(void *data) +{ + float refresh_rate = 0.0f; + + if (g_drm_mode) + { + refresh_rate = g_drm_mode->clock * 1000.0f / g_drm_mode->htotal / g_drm_mode->vtotal; + } + + return refresh_rate; +} + void drm_free(void) { if (g_drm_encoder) diff --git a/gfx/common/drm_common.h b/gfx/common/drm_common.h index 87458dac9a..e8cb3ac411 100644 --- a/gfx/common/drm_common.h +++ b/gfx/common/drm_common.h @@ -55,6 +55,8 @@ void drm_free(void); bool drm_get_connector(int fd, video_frame_info_t *video_info); +float drm_get_refresh_rate(void *data); + static INLINE bool drm_wait_flip(int timeout) { g_drm_fds.revents = 0; diff --git a/gfx/common/win32_common.c b/gfx/common/win32_common.c index d9816ea3ac..b29359a8ce 100644 --- a/gfx/common/win32_common.c +++ b/gfx/common/win32_common.c @@ -13,6 +13,22 @@ * If not, see . */ +#if !defined(_XBOX) + +#ifndef _WIN32_WINNT +#define _WIN32_WINNT 0x0601 /* Windows 7 */ +#endif + +#if !defined(_MSC_VER) || _WIN32_WINNT >= 0x0601 +#undef WINVER +#define WINVER 0x0601 +#endif + +#define IDI_ICON 1 + +#include +#endif /* !defined(_XBOX) */ + #include #include @@ -33,13 +49,6 @@ #if !defined(_XBOX) -#define IDI_ICON 1 - -#ifndef _WIN32_WINNT -#define _WIN32_WINNT 0x0500 /* _WIN32_WINNT_WIN2K */ -#endif - -#include #include #include #include "../../retroarch.h" @@ -284,45 +293,6 @@ void win32_monitor_get_info(void) win32_change_display_settings(current_mon.szDevice, NULL, 0); } -float win32_get_refresh_rate(void *data) -{ - float refresh_rate = 0.0f; -#if _WIN32_WINNT >= 0x0601 || _WIN32_WINDOWS >= 0x0601 /* Win 7 */ - DISPLAYCONFIG_TOPOLOGY_ID TopologyID; - unsigned int NumPathArrayElements = 0; - unsigned int NumModeInfoArrayElements = 0; - DISPLAYCONFIG_PATH_INFO *PathInfoArray = NULL; - DISPLAYCONFIG_MODE_INFO *ModeInfoArray = NULL; - int result = 0; - - GetDisplayConfigBufferSizes(QDC_DATABASE_CURRENT, - &NumPathArrayElements, - &NumModeInfoArrayElements); - - PathInfoArray = (DISPLAYCONFIG_PATH_INFO *) - malloc(sizeof (DISPLAYCONFIG_PATH_INFO) * NumPathArrayElements); - ModeInfoArray = (DISPLAYCONFIG_MODE_INFO *) - malloc(sizeof (DISPLAYCONFIG_MODE_INFO) * NumModeInfoArrayElements); - - result = QueryDisplayConfig(QDC_DATABASE_CURRENT, - &NumPathArrayElements, - PathInfoArray, - &NumModeInfoArrayElements, - ModeInfoArray, - &TopologyID); - if (result == ERROR_SUCCESS && NumPathArrayElements >= 1) - { - refresh_rate = (float) PathInfoArray[0].targetInfo.refreshRate.Numerator / - PathInfoArray[0].targetInfo.refreshRate.Denominator; - } - - free(ModeInfoArray); - free(PathInfoArray); - -#endif - return refresh_rate; -} - void win32_monitor_info(void *data, void *hm_data, unsigned *mon_id) { unsigned i; @@ -1295,6 +1265,57 @@ void win32_get_video_output_prev( } } +float win32_get_refresh_rate(void *data) +{ + float refresh_rate = 0.0f; +#if _WIN32_WINNT >= 0x0601 || _WIN32_WINDOWS >= 0x0601 /* Win 7 */ + OSVERSIONINFO version_info; + DISPLAYCONFIG_TOPOLOGY_ID TopologyID; + unsigned int NumPathArrayElements = 0; + unsigned int NumModeInfoArrayElements = 0; + DISPLAYCONFIG_PATH_INFO *PathInfoArray = NULL; + DISPLAYCONFIG_MODE_INFO *ModeInfoArray = NULL; + int result = 0; + + version_info.dwOSVersionInfoSize = sizeof(OSVERSIONINFO); + if (!GetVersionEx(&version_info)) + return refresh_rate; + + if (version_info.dwMajorVersion < 6 || + (version_info.dwMajorVersion == 6 && version_info.dwMinorVersion < 1)) + return refresh_rate; + + result = GetDisplayConfigBufferSizes(QDC_DATABASE_CURRENT, + &NumPathArrayElements, + &NumModeInfoArrayElements); + + if (result != ERROR_SUCCESS) + return refresh_rate; + + PathInfoArray = (DISPLAYCONFIG_PATH_INFO *) + malloc(sizeof(DISPLAYCONFIG_PATH_INFO) * NumPathArrayElements); + ModeInfoArray = (DISPLAYCONFIG_MODE_INFO *) + malloc(sizeof(DISPLAYCONFIG_MODE_INFO) * NumModeInfoArrayElements); + + result = QueryDisplayConfig(QDC_DATABASE_CURRENT, + &NumPathArrayElements, + PathInfoArray, + &NumModeInfoArrayElements, + ModeInfoArray, + &TopologyID); + if (result == ERROR_SUCCESS && NumPathArrayElements >= 1) + { + refresh_rate = (float) PathInfoArray[0].targetInfo.refreshRate.Numerator / + PathInfoArray[0].targetInfo.refreshRate.Denominator; + } + + free(ModeInfoArray); + free(PathInfoArray); + +#endif + return refresh_rate; +} + void win32_get_video_output_next( unsigned *width, unsigned *height) { diff --git a/gfx/common/x11_common.c b/gfx/common/x11_common.c index 97ec6adb08..e7b5172d6a 100644 --- a/gfx/common/x11_common.c +++ b/gfx/common/x11_common.c @@ -66,7 +66,7 @@ Display *g_x11_dpy = NULL; unsigned g_x11_screen = 0; Colormap g_x11_cmap; -Window g_x11_win; +Window g_x11_win = None; static Atom XA_NET_WM_STATE; static Atom XA_NET_WM_STATE_FULLSCREEN; @@ -242,7 +242,12 @@ float x11_get_refresh_rate(void *data) int screenid; int dotclock; - XGetWindowAttributes(g_x11_dpy, g_x11_win, &attr); + if (!g_x11_dpy || g_x11_win == None) + return 0.0f; + + if (!XGetWindowAttributes(g_x11_dpy, g_x11_win, &attr)) + return 0.0f; + screen = attr.screen; screenid = XScreenNumberOfScreen(screen); diff --git a/gfx/drivers/drm_gfx.c b/gfx/drivers/drm_gfx.c index 41416b8b3a..ba069adcb5 100644 --- a/gfx/drivers/drm_gfx.c +++ b/gfx/drivers/drm_gfx.c @@ -39,6 +39,7 @@ #include "../font_driver.h" #include "../../retroarch.h" #include "../../verbosity.h" +#include "../common/drm_common.h" #include "drm_pixformats.h" @@ -683,6 +684,7 @@ static bool init_drm(void) * on exit in case we change it. */ drm.orig_crtc = drmModeGetCrtc(drm.fd, drm.encoder->crtc_id); drm.current_mode = &(drm.orig_crtc->mode); + g_drm_mode = drm.current_mode; /* Set mode physical video mode. Not really needed, but clears TTY console. */ struct modeset_buf buf; @@ -969,7 +971,7 @@ static const video_poke_interface_t drm_poke_interface = { NULL, NULL, NULL, /* set_video_mode */ - NULL, /* get_refresh_rate */ + drm_get_refresh_rate, NULL, /* set_filtering */ NULL, /* get_video_output_size */ NULL, /* get_video_output_prev */ @@ -1012,6 +1014,8 @@ static void drm_gfx_free(void *data) slock_free(_drmvars->vsync_cond_mutex); scond_free(_drmvars->vsync_condition); + g_drm_mode = NULL; + free(_drmvars); } diff --git a/gfx/drivers/exynos_gfx.c b/gfx/drivers/exynos_gfx.c index 78ed3502c7..659e87bba5 100644 --- a/gfx/drivers/exynos_gfx.c +++ b/gfx/drivers/exynos_gfx.c @@ -663,6 +663,7 @@ static void exynos_deinit(struct exynos_data *pdata) { drm_restore_crtc(); + g_drm_mode = NULL; pdata->width = 0; pdata->height = 0; pdata->num_pages = 0; @@ -1494,7 +1495,7 @@ static const video_poke_interface_t exynos_poke_interface = { NULL, NULL, NULL, /* set_video_mode */ - NULL, /* get_refresh_rate */ + drm_get_refresh_rate, NULL, /* set_filtering */ NULL, /* get_video_output_size */ NULL, /* get_video_output_prev */ diff --git a/gfx/drivers/omap_gfx.c b/gfx/drivers/omap_gfx.c index 9c650f27a0..fc7bc1fd21 100644 --- a/gfx/drivers/omap_gfx.c +++ b/gfx/drivers/omap_gfx.c @@ -1129,13 +1129,23 @@ static void omap_gfx_set_texture_enable(void *data, bool state, bool full_screen (void) full_screen; } +static float omap_get_refresh_rate(void *data) +{ + omap_video_t *vid = (omap_video_t*)data; + struct fb_var_screeninfo *s = &vid->omap->current_state->si; + + return 1000000.0f / s->pixclock / + (s->xres + s->left_margin + s->right_margin + s->hsync_len) * 1000000.0f / + (s->yres + s->upper_margin + s->lower_margin + s->vsync_len); +} + static const video_poke_interface_t omap_gfx_poke_interface = { NULL, /* set_coords */ NULL, /* set_mvp */ NULL, NULL, NULL, - NULL, /* get_refresh_rate */ + omap_get_refresh_rate, NULL, /* set_filtering */ NULL, /* get_video_output_size */ NULL, /* get_video_output_prev */ diff --git a/gfx/drivers/sunxi_gfx.c b/gfx/drivers/sunxi_gfx.c index 9d6e786deb..d2336eaaf8 100644 --- a/gfx/drivers/sunxi_gfx.c +++ b/gfx/drivers/sunxi_gfx.c @@ -109,6 +109,7 @@ typedef struct uint32_t framebuffer_size; /* total size of the framebuffer */ int framebuffer_height;/* virtual vertical resolution */ uint32_t gfx_layer_size; /* the size of the primary layer */ + float refresh_rate; /* Layers support */ int gfx_layer_id; @@ -416,6 +417,9 @@ static sunxi_disp_t *sunxi_disp_init(const char *device) ctx->framebuffer_height = ctx->framebuffer_size / (ctx->xres * ctx->bits_per_pixel / 8); ctx->gfx_layer_size = ctx->xres * ctx->yres * fb_var.bits_per_pixel / 8; + ctx->refresh_rate = 1000000.0f / fb_var.pixclock * 1000000.0f / + (fb_var.yres + fb_var.upper_margin + fb_var.lower_margin + fb_var.vsync_len) + (fb_var.xres + fb_var.left_margin + fb_var.right_margin + fb_var.hsync_len); if (ctx->framebuffer_size < ctx->gfx_layer_size) { @@ -931,6 +935,13 @@ static void sunxi_set_aspect_ratio (void *data, unsigned aspect_ratio_idx) } } +static float sunxi_get_refresh_rate (void *data) +{ + struct sunxi_video *_dispvars = (struct sunxi_video*)data; + + return _dispvars->sunxi_disp->refresh_rate; +} + static const video_poke_interface_t sunxi_poke_interface = { NULL, /* set_coords */ NULL, /* set_mvp */ diff --git a/gfx/drivers/xshm_gfx.c b/gfx/drivers/xshm_gfx.c index 6385f591ed..7f6ce812f8 100644 --- a/gfx/drivers/xshm_gfx.c +++ b/gfx/drivers/xshm_gfx.c @@ -203,18 +203,13 @@ static void xshm_grab_mouse_toggle(void *data) } -static float xshm_poke_get_refresh_rate(void *data) -{ - return x11_get_refresh_rate(data); -} - static video_poke_interface_t xshm_video_poke_interface = { NULL, /* set_coords */ NULL, /* set_mvp */ NULL, NULL, NULL, - xshm_poke_get_refresh_rate, + x11_get_refresh_rate, xshm_poke_set_filtering, NULL, /* get_video_output_size */ NULL, /* get_video_output_prev */ diff --git a/gfx/drivers/xvideo.c b/gfx/drivers/xvideo.c index 94e81e6f87..bb6f1dc6e9 100644 --- a/gfx/drivers/xvideo.c +++ b/gfx/drivers/xvideo.c @@ -933,11 +933,36 @@ static bool xv_read_viewport(void *data, uint8_t *buffer, bool is_idle) return true; } +static video_poke_interface_t xv_video_poke_interface = { + NULL, + NULL, + NULL, + NULL, + NULL, + x11_get_refresh_rate, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL +}; + static void xv_get_poke_interface(void *data, const video_poke_interface_t **iface) { (void)data; - (void)iface; + *iface = &xv_video_poke_interface; } static bool xv_set_shader(void *data, diff --git a/gfx/drivers_context/drm_ctx.c b/gfx/drivers_context/drm_ctx.c index a4937368f1..434c79502b 100644 --- a/gfx/drivers_context/drm_ctx.c +++ b/gfx/drivers_context/drm_ctx.c @@ -908,7 +908,7 @@ const gfx_ctx_driver_t gfx_ctx_drm = { gfx_ctx_drm_swap_interval, gfx_ctx_drm_set_video_mode, gfx_ctx_drm_get_video_size, - NULL, /* get_refresh_rate */ + drm_get_refresh_rate, NULL, /* get_video_output_size */ NULL, /* get_video_output_prev */ NULL, /* get_video_output_next */ diff --git a/gfx/drivers_context/mali_fbdev_ctx.c b/gfx/drivers_context/mali_fbdev_ctx.c index b30de94dcf..b2ef7917c8 100644 --- a/gfx/drivers_context/mali_fbdev_ctx.c +++ b/gfx/drivers_context/mali_fbdev_ctx.c @@ -50,6 +50,7 @@ typedef struct } native_window; bool resize; unsigned width, height; + float refresh_rate; } mali_ctx_data_t; static enum gfx_ctx_api mali_api = GFX_CTX_NONE; @@ -178,6 +179,11 @@ static bool gfx_ctx_mali_fbdev_set_video_mode(void *data, mali->native_window.width = vinfo.xres; mali->native_window.height = vinfo.yres; + mali->refresh_rate = + ctx->refresh_rate = 1000000.0f / vinfo.pixclock * 1000000.0f / + (vinfo.yres + vinfo.upper_margin + vinfo.lower_margin + vinfo.vsync_len) + (vinfo.xres + vinfo.left_margin + vinfo.right_margin + vinfo.hsync_len); + #ifdef HAVE_EGL if (!egl_create_context(&mali->egl, attribs)) { @@ -286,6 +292,13 @@ static void gfx_ctx_mali_fbdev_set_flags(void *data, uint32_t flags) (void)data; } +static float gfx_ctx_mali_fbdev_get_refresh_rate(void *data) +{ + mali_ctx_data_t *mali = (mali_ctx_data_t*)data; + + return mali->refresh_rate; +} + const gfx_ctx_driver_t gfx_ctx_mali_fbdev = { gfx_ctx_mali_fbdev_init, gfx_ctx_mali_fbdev_destroy, @@ -294,7 +307,7 @@ const gfx_ctx_driver_t gfx_ctx_mali_fbdev = { gfx_ctx_mali_fbdev_set_swap_interval, gfx_ctx_mali_fbdev_set_video_mode, gfx_ctx_mali_fbdev_get_video_size, - NULL, /* get_refresh_rate */ + gfx_ctx_mali_fbdev_get_refresh_rate, NULL, /* get_video_output_size */ NULL, /* get_video_output_prev */ NULL, /* get_video_output_next */