Merge branch 'master' of https://github.com/libretro/RetroArch into staging

This commit is contained in:
twinaphex 2016-05-15 04:22:01 +02:00
commit 00d0cdd04e
304 changed files with 18187 additions and 11411 deletions

6
.gitmodules vendored
View File

@ -1,6 +1,6 @@
[submodule "deps/glslang/glslang"]
path = deps/glslang/glslang
url = git://github.com/KhronosGroup/glslang.git
[submodule "deps/spir2cross"]
path = deps/spir2cross
url = git://github.com/ARM-software/spir2cross
[submodule "deps/SPIRV-Cross"]
path = deps/SPIRV-Cross
url = git://github.com/KhronosGroup/SPIRV-Cross

View File

@ -108,10 +108,10 @@ OBJ += frontend/frontend.o \
frontend/drivers/platform_null.o \
ui/ui_companion_driver.o \
ui/drivers/ui_null.o \
libretro_version_1.o \
core_impl.o \
retroarch.o \
input/input_keyboard.o \
command_event.o \
command.o \
msg_hash.o \
intl/msg_hash_de.o \
intl/msg_hash_eo.o \
@ -127,6 +127,7 @@ OBJ += frontend/frontend.o \
tasks/tasks_internal.o \
tasks/task_content.o \
tasks/task_file_transfer.o \
tasks/task_image.o \
content.o \
libretro-common/encodings/encoding_utf.o \
libretro-common/lists/file_list.o \
@ -157,7 +158,7 @@ OBJ += frontend/frontend.o \
dynamic.o \
cores/dynamic_dummy.o \
libretro-common/queues/message_queue.o \
rewind.o \
managers/state_manager.o \
gfx/drivers_font_renderer/bitmapfont.o \
input/input_autodetect.o \
input/input_joypad_driver.o \
@ -168,10 +169,10 @@ OBJ += frontend/frontend.o \
input/input_overlay.o \
patch.o \
libretro-common/queues/fifo_queue.o \
core_options.o \
managers/core_option_manager.o \
libretro-common/compat/compat_fnmatch.o \
libretro-common/compat/compat_posix_string.o \
cheats.o \
managers/cheat_manager.o \
core_info.o \
libretro-common/file/config_file.o \
config_file_userdata.o \
@ -203,7 +204,8 @@ OBJ += frontend/frontend.o \
movie.o \
record/record_driver.o \
record/drivers/record_null.o \
performance.o \
libretro-common/features/features_cpu.o \
performance_counters.o \
verbosity.o
ifneq ($(HAVE_GETOPT_LONG), 1)
@ -289,8 +291,11 @@ ifeq ($(HAVE_OSS_BSD), 1)
endif
ifeq ($(HAVE_ALSA), 1)
OBJ += audio/drivers/alsa.o \
audio/drivers/alsathread.o
OBJ += audio/drivers/alsa.o
ifeq ($(HAVE_THREADS), 1)
OBJ += audio/drivers/alsathread.o
endif
LIBS += $(ALSA_LIBS)
DEFINES += $(ALSA_CFLAGS)
endif
@ -509,10 +514,6 @@ ifeq ($(HAVE_THREADS), 1)
endif
endif
ifeq ($(HAVE_COMMAND), 1)
OBJ += command.o
endif
ifeq ($(HAVE_WAYLAND), 1)
OBJ += gfx/drivers_context/wayland_ctx.o
DEFINES += $(WAYLAND_CFLAGS)
@ -577,11 +578,13 @@ ifeq ($(HAVE_UDEV), 1)
endif
ifeq ($(HAVE_LIBUSB), 1)
ifeq ($(HAVE_THREADS), 1)
DEFINES += -DHAVE_LIBUSB
OBJ += input/drivers_hid/libusb_hid.o
LIBS += -lusb-1.0
HAVE_HID = 1
endif
endif
ifeq ($(HAVE_IOHIDMANAGER), 1)
DEFINES += -DHAVE_IOHIDMANAGER
@ -752,7 +755,7 @@ ifeq ($(HAVE_VULKAN), 1)
$(wildcard deps/glslang/glslang/glslang/MachineIndependent/preprocessor/*.cpp) \
$(wildcard deps/glslang/glslang/glslang/OSDependent/$(GLSLANG_PLATFORM)/*.cpp)
SPIR2CROSS_SOURCES := deps/spir2cross/spir2cross.cpp
SPIRV_CROSS_SOURCES := deps/SPIRV-Cross/spirv_cross.cpp
DEFINES += \
-Ideps/glslang/glslang/glslang/OSDependent/$(GLSLANG_PLATFORM) \
@ -761,13 +764,13 @@ ifeq ($(HAVE_VULKAN), 1)
-Ideps/glslang/glslang/glslang/Public \
-Ideps/glslang/glslang/SPIRV \
-Ideps/glslang \
-Ideps/spir2cross
-Ideps/SPIRV-Cross
CXXFLAGS += -Wno-switch -Wno-sign-compare -fno-strict-aliasing -Wno-maybe-uninitialized -Wno-reorder -I./gfx/include/vulkan
CFLAGS += -I./gfx/include/vulkan
GLSLANG_OBJ := $(GLSLANG_SOURCES:.cpp=.o)
SPIR2CROSS_OBJ := $(SPIR2CROSS_SOURCES:.cpp=.o)
SPIRV_CROSS_OBJ := $(SPIRV_CROSS_SOURCES:.cpp=.o)
OBJ += gfx/drivers/vulkan.o \
gfx/common/vulkan_common.o \
@ -776,7 +779,7 @@ ifeq ($(HAVE_VULKAN), 1)
gfx/drivers_shader/glslang_util.o \
gfx/drivers_shader/slang_reflection.o \
$(GLSLANG_OBJ) \
$(SPIR2CROSS_OBJ)
$(SPIRV_CROSS_OBJ)
ifeq ($(HAVE_MENU_COMMON), 1)
OBJ += menu/drivers_display/menu_display_vulkan.o
endif
@ -887,7 +890,6 @@ ifeq ($(HAVE_ZLIB), 1)
tasks/task_decompress.o
OBJ += $(ZLIB_OBJS)
DEFINES += -DHAVE_ZLIB
HAVE_RPNG = 1
HAVE_COMPRESSION = 1
ifeq ($(WANT_ZLIB), 1)
DEFINES += -DWANT_ZLIB
@ -897,17 +899,24 @@ ifeq ($(HAVE_ZLIB), 1)
endif
endif
ifdef HAVE_RPNG
DEFINES += -DHAVE_RPNG
endif
ifeq ($(HAVE_RPNG), 1)
DEFINES += -DHAVE_RPNG
OBJ += libretro-common/formats/png/rpng.o \
libretro-common/formats/png/rpng_encode.o
endif
ifeq ($(HAVE_RJPEG), 1)
DEFINES += -DHAVE_RJPEG
OBJ += libretro-common/formats/jpeg/rjpeg.o
endif
OBJ += libretro-common/formats/bmp/rbmp_encode.o \
libretro-common/formats/tga/rtga.o \
libretro-common/formats/json/jsonsax.o
libretro-common/formats/json/jsonsax.o \
libretro-common/formats/image_transfer.o
ifeq ($(HAVE_RTGA), 1)
OBJ += libretro-common/formats/tga/rtga.o
endif
ifdef HAVE_COMPRESSION
DEFINES += -DHAVE_COMPRESSION
@ -952,7 +961,8 @@ ifeq ($(HAVE_NETWORKING), 1)
DEFINES += -DHAVE_NETWORKING
OBJ += libretro-common/net/net_compat.o \
libretro-common/net/net_http.o \
net_http_special.o \
libretro-common/net/net_socket.o \
network/net_http_special.o \
tasks/task_http.o
ifneq ($(HAVE_SOCKET_LEGACY),1)
@ -972,7 +982,7 @@ ifeq ($(HAVE_NETWORKING), 1)
ifeq ($(HAVE_NETPLAY), 1)
DEFINES += -DHAVE_NETPLAY -DHAVE_NETWORK_CMD -DHAVE_NETWORK_GAMEPAD
OBJ += netplay/netplay_net.o netplay/netplay_spectate.o netplay/netplay_common.o netplay/netplay.o
OBJ += network/netplay_net.o network/netplay_spectate.o network/netplay_common.o network/netplay.o
endif
# Retro Achievements (also depends on threads)
@ -985,7 +995,7 @@ ifeq ($(HAVE_NETWORKING), 1)
endif
ifeq ($(HAVE_NETWORK_GAMEPAD), 1)
OBJ += remote.o
OBJ += input/input_remote.o
endif
endif
@ -1012,7 +1022,7 @@ ifeq ($(HAVE_FFMPEG), 1)
cores/libretro-ffmpeg/ffmpeg_core.o
LIBS += $(AVCODEC_LIBS) $(AVFORMAT_LIBS) $(AVUTIL_LIBS) $(SWSCALE_LIBS) $(SWRESAMPLE_LIBS) $(FFMPEG_LIBS)
DEFINES += $(AVCODEC_CFLAGS) $(AVFORMAT_CFLAGS) $(AVUTIL_CFLAGS) $(SWSCALE_CFLAGS) $(SWRESAMPLE_CFLAGS)
DEFINES += -DHAVE_FFMPEG -Iffmpeg
DEFINES += -Wno-deprecated-declarations -DHAVE_FFMPEG -Iffmpeg
endif
ifeq ($(HAVE_COMPRESSION), 1)

View File

@ -37,7 +37,9 @@ PPU_SRCS = frontend/frontend_salamander.c \
ifeq ($(HAVE_LOGGER), 1)
PPU_CFLAGS += -DHAVE_LOGGER
PPU_SRCS += netlogger.c
PPU_SRCS += network/netlogger.c \
libretro-common/net/net_compat.c \
libretro-common/net/net_socket.c
endif
PPU_TARGET = retroarch-salamander_ps3.elf

View File

@ -83,7 +83,6 @@ OBJ = griffin/griffin.o
ifeq ($(HAVE_LOGGER), 1)
CFLAGS += -DHAVE_LOGGER
CFLAGS += -Ilogger/netlogger
endif
ifeq ($(HAVE_FILE_LOGGER), 1)

View File

@ -60,7 +60,9 @@ OBJ = frontend/frontend_salamander.o \
ifeq ($(HAVE_LOGGER), 1)
CFLAGS += -DHAVE_LOGGER
CFLAGS += -DPC_DEVELOPMENT_IP_ADDRESS=\"$(PC_DEVELOPMENT_IP_ADDRESS)\" -DPC_DEVELOPMENT_UDP_PORT=$(PC_DEVELOPMENT_UDP_PORT)
OBJ += logger/netlogger.o
OBJ += network/netlogger.o \
libretro-common/net/net_compat.o \
libretro-common/net/net_socket.o
endif
ifeq ($(HAVE_FILE_LOGGER), 1)

View File

@ -120,7 +120,6 @@ ifeq ($(DEBUG), 1)
else
CFLAGS += -O3 -ffast-math
CXXFLAGS += -O3 -ffast-math
LDCXXFLAGS += -s
endif
CFLAGS += -Wall -Wno-unused-result -Wno-unused-variable -I.

View File

@ -26,11 +26,11 @@
#include "audio_utils.h"
#include "audio_thread_wrapper.h"
#include "../command_event.h"
#include "../command.h"
#include "../configuration.h"
#include "../retroarch.h"
#include "../runloop.h"
#include "../performance.h"
#include "../performance_counters.h"
#include "../verbosity.h"
#include "../list_special.h"
@ -93,7 +93,7 @@ typedef struct audio_driver_input_data
static const audio_driver_t *audio_drivers[] = {
#ifdef HAVE_ALSA
&audio_alsa,
#ifndef __QNX__
#if !defined(__QNX__) && defined(HAVE_THREADS)
&audio_alsathread,
#endif
#endif
@ -154,6 +154,13 @@ static const audio_driver_t *audio_drivers[] = {
};
static audio_driver_input_data_t audio_driver_data;
static struct retro_audio_callback audio_callback;
static struct string_list *audio_driver_devices_list = NULL;
static struct retro_perf_counter resampler_proc = {0};
static const rarch_resampler_t *audio_driver_resampler = NULL;
static void *audio_driver_resampler_data = NULL;
static bool audio_driver_active = false;
static bool audio_driver_data_own = false;
static const audio_driver_t *current_audio = NULL;
static void *audio_driver_context_audio_data = NULL;
@ -253,7 +260,6 @@ const char *config_get_audio_driver_options(void)
return char_list_new_special(STRING_LIST_AUDIO_DRIVERS, NULL);
}
static bool uninit_audio(void)
{
settings_t *settings = config_get_ptr();
@ -277,11 +283,11 @@ static bool uninit_audio(void)
if (!settings->audio.enable)
{
audio_driver_ctl(RARCH_AUDIO_CTL_UNSET_ACTIVE, NULL);
audio_driver_unset_active();
return false;
}
audio_driver_ctl(RARCH_AUDIO_CTL_RESAMPLER_DEINIT, NULL);
audio_driver_deinit_resampler();
if (audio_driver_data.data)
free(audio_driver_data.data);
@ -291,14 +297,14 @@ static bool uninit_audio(void)
free(audio_driver_data.output_samples.buf);
audio_driver_data.output_samples.buf = NULL;
event_cmd_ctl(EVENT_CMD_DSP_FILTER_DEINIT, NULL);
command_event(CMD_EVENT_DSP_FILTER_DEINIT, NULL);
compute_audio_buffer_statistics();
return true;
}
static bool init_audio(bool audio_cb_inited)
static bool audio_driver_init_internal(bool audio_cb_inited)
{
size_t outsamples_max, max_bufsamples = AUDIO_CHUNK_SIZE_NONBLOCKING * 2;
settings_t *settings = config_get_ptr();
@ -332,16 +338,16 @@ static bool init_audio(bool audio_cb_inited)
if (!settings->audio.enable)
{
audio_driver_ctl(RARCH_AUDIO_CTL_UNSET_ACTIVE, NULL);
audio_driver_unset_active();
return false;
}
audio_driver_ctl(RARCH_AUDIO_CTL_FIND_DRIVER, NULL);
audio_driver_find_driver();
#ifdef HAVE_THREADS
if (audio_cb_inited)
{
RARCH_LOG("Starting threaded audio driver ...\n");
if (!rarch_threaded_audio_init(
if (!audio_init_thread(
&current_audio,
&audio_driver_context_audio_data,
*settings->audio.device ? settings->audio.device : NULL,
@ -349,7 +355,7 @@ static bool init_audio(bool audio_cb_inited)
current_audio))
{
RARCH_ERR("Cannot open threaded audio driver ... Exiting ...\n");
retro_fail(1, "init_audio()");
retroarch_fail(1, "audio_driver_init_internal()");
}
}
else
@ -364,17 +370,17 @@ static bool init_audio(bool audio_cb_inited)
if (!audio_driver_context_audio_data)
{
RARCH_ERR("Failed to initialize audio driver. Will continue without audio.\n");
audio_driver_ctl(RARCH_AUDIO_CTL_UNSET_ACTIVE, NULL);
audio_driver_unset_active();
}
audio_driver_data.use_float = false;
if ( audio_driver_ctl(RARCH_AUDIO_CTL_IS_ACTIVE, NULL)
if ( audio_driver_is_active()
&& current_audio->use_float(audio_driver_context_audio_data))
audio_driver_data.use_float = true;
if (!settings->audio.sync && audio_driver_ctl(RARCH_AUDIO_CTL_IS_ACTIVE, NULL))
if (!settings->audio.sync && audio_driver_is_active())
{
event_cmd_ctl(EVENT_CMD_AUDIO_SET_NONBLOCKING_STATE, NULL);
command_event(CMD_EVENT_AUDIO_SET_NONBLOCKING_STATE, NULL);
audio_driver_data.chunk.size = audio_driver_data.chunk.nonblock_size;
}
@ -390,11 +396,11 @@ static bool init_audio(bool audio_cb_inited)
audio_driver_data.audio_rate.source_ratio.current =
(double)settings->audio.out_rate / audio_driver_data.audio_rate.input;
if (!audio_driver_ctl(RARCH_AUDIO_CTL_RESAMPLER_INIT, NULL))
if (!audio_driver_init_resampler())
{
RARCH_ERR("Failed to initialize resampler \"%s\".\n",
settings->audio.resampler);
audio_driver_ctl(RARCH_AUDIO_CTL_UNSET_ACTIVE, NULL);
audio_driver_unset_active();
}
retro_assert(audio_driver_data.data = (float*)
@ -416,7 +422,7 @@ static bool init_audio(bool audio_cb_inited)
audio_driver_data.audio_rate.control = false;
if (
!audio_cb_inited
&& audio_driver_ctl(RARCH_AUDIO_CTL_IS_ACTIVE, NULL)
&& audio_driver_is_active()
&& settings->audio.rate_control
)
{
@ -432,22 +438,22 @@ static bool init_audio(bool audio_cb_inited)
RARCH_WARN("Audio rate control was desired, but driver does not support needed features.\n");
}
event_cmd_ctl(EVENT_CMD_DSP_FILTER_INIT, NULL);
command_event(CMD_EVENT_DSP_FILTER_INIT, NULL);
audio_driver_data.free_samples.count = 0;
/* Threaded driver is initially stopped. */
if (
audio_driver_ctl(RARCH_AUDIO_CTL_IS_ACTIVE, NULL)
audio_driver_is_active()
&& !settings->audio.mute_enable
&& audio_cb_inited
)
audio_driver_ctl(RARCH_AUDIO_CTL_START, NULL);
audio_driver_start();
return true;
error:
return audio_driver_ctl(RARCH_AUDIO_CTL_DEINIT, NULL);
return audio_driver_deinit();
}
/*
@ -487,7 +493,7 @@ void audio_driver_set_nonblocking_state(bool enable)
{
settings_t *settings = config_get_ptr();
if (
audio_driver_ctl(RARCH_AUDIO_CTL_IS_ACTIVE, NULL)
audio_driver_is_active()
&& audio_driver_context_audio_data
)
current_audio->set_nonblock_state(audio_driver_context_audio_data,
@ -525,7 +531,7 @@ static bool audio_driver_flush(const int16_t *data, size_t samples)
if (runloop_ctl(RUNLOOP_CTL_IS_PAUSED, NULL) || settings->audio.mute_enable)
return true;
if (!audio_driver_ctl(RARCH_AUDIO_CTL_IS_ACTIVE, NULL))
if (!audio_driver_is_active())
return false;
if (!audio_driver_data.data)
return false;
@ -566,7 +572,7 @@ static bool audio_driver_flush(const int16_t *data, size_t samples)
if (runloop_ctl(RUNLOOP_CTL_IS_SLOWMOTION, NULL))
src_data.ratio *= settings->slowmotion_ratio;
audio_driver_ctl(RARCH_AUDIO_CTL_RESAMPLER_PROCESS, &src_data);
audio_driver_process_resampler(&src_data);
output_data = audio_driver_data.output_samples.buf;
output_frames = src_data.output_frames;
@ -586,7 +592,7 @@ static bool audio_driver_flush(const int16_t *data, size_t samples)
if (current_audio->write(audio_driver_context_audio_data,
output_data, output_frames * output_size * 2) < 0)
{
audio_driver_ctl(RARCH_AUDIO_CTL_UNSET_ACTIVE, NULL);
audio_driver_unset_active();
return false;
}
@ -699,8 +705,7 @@ void audio_driver_set_buffer_size(size_t bufsize)
audio_driver_data.driver_buffer_size = bufsize;
}
static void audio_monitor_adjust_system_rates(void)
void audio_driver_monitor_adjust_system_rates(void)
{
float timing_skew;
settings_t *settings = config_get_ptr();
@ -723,7 +728,7 @@ static void audio_monitor_adjust_system_rates(void)
audio_driver_data.audio_rate.input);
}
static void audio_driver_setup_rewind(void)
void audio_driver_setup_rewind(void)
{
unsigned i;
@ -742,7 +747,7 @@ static void audio_driver_setup_rewind(void)
audio_driver_data.data_ptr = 0;
}
static bool find_audio_driver(void)
bool audio_driver_find_driver(void)
{
int i;
driver_ctx_info_t drv;
@ -770,38 +775,31 @@ static bool find_audio_driver(void)
current_audio = (const audio_driver_t*)audio_driver_find_handle(0);
if (!current_audio)
retro_fail(1, "find_audio_driver()");
retroarch_fail(1, "audio_driver_find()");
}
return true;
}
bool audio_driver_ctl(enum rarch_audio_ctl_state state, void *data)
void audio_driver_deinit_resampler(void)
{
static struct retro_audio_callback audio_callback;
static struct string_list *audio_driver_devices_list = NULL;
static struct retro_perf_counter resampler_proc = {0};
static const rarch_resampler_t *audio_driver_resampler = NULL;
static void *audio_driver_resampler_data = NULL;
static bool audio_driver_active = false;
static bool audio_driver_data_own = false;
settings_t *settings = config_get_ptr();
switch (state)
{
case RARCH_AUDIO_CTL_RESAMPLER_DEINIT:
rarch_resampler_freep(&audio_driver_resampler,
&audio_driver_resampler_data);
break;
case RARCH_AUDIO_CTL_DEVICES_LIST_FREE:
}
bool audio_driver_free_devices_list(void)
{
if (!current_audio || !current_audio->device_list_free
|| !audio_driver_context_audio_data)
return false;
current_audio->device_list_free(audio_driver_context_audio_data,
audio_driver_devices_list);
audio_driver_devices_list = NULL;
break;
case RARCH_AUDIO_CTL_DEVICES_LIST_NEW:
return true;
}
bool audio_driver_new_devices_list(void)
{
if (!current_audio || !current_audio->device_list_new
|| !audio_driver_context_audio_data)
return false;
@ -809,77 +807,53 @@ bool audio_driver_ctl(enum rarch_audio_ctl_state state, void *data)
current_audio->device_list_new(audio_driver_context_audio_data);
if (!audio_driver_devices_list)
return false;
break;
case RARCH_AUDIO_CTL_DEVICES_LIST_GET:
return true;
}
bool audio_driver_init(void)
{
return audio_driver_init_internal(audio_callback.callback != NULL);
}
bool audio_driver_get_devices_list(void **data)
{
struct string_list**ptr = (struct string_list**)data;
if (!ptr)
return false;
*ptr = audio_driver_devices_list;
return true;
}
break;
case RARCH_AUDIO_CTL_RESAMPLER_INIT:
bool audio_driver_init_resampler(void)
{
settings_t *settings = config_get_ptr();
return rarch_resampler_realloc(
&audio_driver_resampler_data,
&audio_driver_resampler,
settings->audio.resampler,
audio_driver_data.audio_rate.source_ratio.original);
case RARCH_AUDIO_CTL_RESAMPLER_PROCESS:
}
void audio_driver_process_resampler(struct resampler_data *data)
{
rarch_perf_init(&resampler_proc, "resampler_proc");
retro_perf_start(&resampler_proc);
rarch_resampler_process(audio_driver_resampler,
audio_driver_resampler_data,
(struct resampler_data*)data);
audio_driver_resampler_data, data);
retro_perf_stop(&resampler_proc);
break;
case RARCH_AUDIO_CTL_INIT:
return init_audio(audio_callback.callback != NULL);
case RARCH_AUDIO_CTL_DESTROY:
audio_driver_active = false;
audio_driver_data_own = false;
current_audio = NULL;
break;
case RARCH_AUDIO_CTL_DESTROY_DATA:
audio_driver_context_audio_data = NULL;
break;
case RARCH_AUDIO_CTL_DEINIT:
audio_driver_ctl(RARCH_AUDIO_CTL_DEVICES_LIST_FREE, NULL);
}
bool audio_driver_deinit(void)
{
audio_driver_free_devices_list();
if (!uninit_audio())
return false;
break;
case RARCH_AUDIO_CTL_SETUP_REWIND:
audio_driver_setup_rewind();
break;
case RARCH_AUDIO_CTL_SET_CALLBACK_ENABLE:
if (!audio_driver_ctl(RARCH_AUDIO_CTL_HAS_CALLBACK, NULL))
return false;
if (audio_callback.set_state)
audio_callback.set_state(true);
break;
case RARCH_AUDIO_CTL_SET_CALLBACK_DISABLE:
if (!audio_driver_ctl(RARCH_AUDIO_CTL_HAS_CALLBACK, NULL))
return false;
return true;
}
if (audio_callback.set_state)
audio_callback.set_state(false);
break;
case RARCH_AUDIO_CTL_HAS_CALLBACK:
return audio_callback.callback;
case RARCH_AUDIO_CTL_CALLBACK:
if (!audio_driver_ctl(RARCH_AUDIO_CTL_HAS_CALLBACK, NULL))
return false;
if (audio_callback.callback)
audio_callback.callback();
break;
case RARCH_AUDIO_CTL_UNSET_CALLBACK:
audio_callback.callback = NULL;
audio_callback.set_state = NULL;
break;
case RARCH_AUDIO_CTL_SET_CALLBACK:
bool audio_driver_set_callback(const void *data)
{
const struct retro_audio_callback *cb =
(const struct retro_audio_callback*)data;
const struct retro_audio_callback *cb = (const struct retro_audio_callback*)data;
#ifdef HAVE_NETPLAY
global_t *global = global_get_ptr();
#endif
@ -893,79 +867,152 @@ bool audio_driver_ctl(enum rarch_audio_ctl_state state, void *data)
#endif
if (cb)
audio_callback = *cb;
return true;
}
break;
case RARCH_AUDIO_CTL_MONITOR_ADJUST_SYSTEM_RATES:
audio_monitor_adjust_system_rates();
break;
case RARCH_AUDIO_CTL_MONITOR_SET_REFRESH_RATE:
bool audio_driver_enable_callback(void)
{
if (!audio_driver_has_callback())
return false;
if (audio_callback.set_state)
audio_callback.set_state(true);
return true;
}
bool audio_driver_disable_callback(void)
{
if (!audio_driver_has_callback())
return false;
if (audio_callback.set_state)
audio_callback.set_state(false);
return true;
}
/* Sets audio monitor rate to new value. */
void audio_driver_monitor_set_rate(void)
{
settings_t *settings = config_get_ptr();
double new_src_ratio = (double)settings->audio.out_rate /
audio_driver_data.audio_rate.input;
audio_driver_data.audio_rate.source_ratio.original = new_src_ratio;
audio_driver_data.audio_rate.source_ratio.current = new_src_ratio;
}
break;
case RARCH_AUDIO_CTL_MUTE_TOGGLE:
bool audio_driver_callback(void)
{
if (!audio_driver_has_callback())
return false;
if (audio_callback.callback)
audio_callback.callback();
return true;
}
bool audio_driver_has_callback(void)
{
return audio_callback.callback;
}
bool audio_driver_toggle_mute(void)
{
settings_t *settings = config_get_ptr();
if (!audio_driver_context_audio_data)
return false;
if (!audio_driver_ctl(RARCH_AUDIO_CTL_IS_ACTIVE, NULL))
if (!audio_driver_is_active())
return false;
settings->audio.mute_enable = !settings->audio.mute_enable;
if (settings->audio.mute_enable)
event_cmd_ctl(EVENT_CMD_AUDIO_STOP, NULL);
else if (!event_cmd_ctl(EVENT_CMD_AUDIO_START, NULL))
command_event(CMD_EVENT_AUDIO_STOP, NULL);
else if (!command_event(CMD_EVENT_AUDIO_START, NULL))
{
audio_driver_ctl(RARCH_AUDIO_CTL_UNSET_ACTIVE, NULL);
audio_driver_unset_active();
return false;
}
break;
case RARCH_AUDIO_CTL_ALIVE:
if (!current_audio || !current_audio->alive
|| !audio_driver_context_audio_data)
return false;
return current_audio->alive(audio_driver_context_audio_data);
case RARCH_AUDIO_CTL_START:
return true;
}
bool audio_driver_start(void)
{
if (!current_audio || !current_audio->start
|| !audio_driver_context_audio_data)
return false;
return current_audio->start(audio_driver_context_audio_data);
case RARCH_AUDIO_CTL_STOP:
}
bool audio_driver_stop(void)
{
if (!current_audio || !current_audio->stop
|| !audio_driver_context_audio_data)
return false;
return current_audio->stop(audio_driver_context_audio_data);
case RARCH_AUDIO_CTL_FIND_DRIVER:
return find_audio_driver();
case RARCH_AUDIO_CTL_SET_OWN_DRIVER:
audio_driver_data_own = true;
break;
case RARCH_AUDIO_CTL_UNSET_OWN_DRIVER:
audio_driver_data_own = false;
break;
case RARCH_AUDIO_CTL_OWNS_DRIVER:
return audio_driver_data_own;
case RARCH_AUDIO_CTL_SET_ACTIVE:
audio_driver_active = true;
break;
case RARCH_AUDIO_CTL_UNSET_ACTIVE:
audio_driver_active = false;
break;
case RARCH_AUDIO_CTL_IS_ACTIVE:
return audio_driver_active;
case RARCH_AUDIO_CTL_FRAME_IS_REVERSE:
}
void audio_driver_unset_callback(void)
{
audio_callback.callback = NULL;
audio_callback.set_state = NULL;
}
bool audio_driver_alive(void)
{
if (!current_audio || !current_audio->alive
|| !audio_driver_context_audio_data)
return false;
return current_audio->alive(audio_driver_context_audio_data);
}
void audio_driver_frame_is_reverse(void)
{
/* We just rewound. Flush rewind audio buffer. */
audio_driver_flush(
audio_driver_data.rewind.buf + audio_driver_data.rewind.ptr,
audio_driver_data.rewind.size - audio_driver_data.rewind.ptr);
break;
case RARCH_AUDIO_CTL_NONE:
default:
break;
}
return true;
void audio_driver_destroy_data(void)
{
audio_driver_context_audio_data = NULL;
}
void audio_driver_set_own_driver(void)
{
audio_driver_data_own = true;
}
void audio_driver_unset_own_driver(void)
{
audio_driver_data_own = false;
}
bool audio_driver_owns_driver(void)
{
return audio_driver_data_own;
}
void audio_driver_set_active(void)
{
audio_driver_active = true;
}
void audio_driver_unset_active(void)
{
audio_driver_active = false;
}
bool audio_driver_is_active(void)
{
return audio_driver_active;
}
void audio_driver_destroy(void)
{
audio_driver_active = false;
audio_driver_data_own = false;
current_audio = NULL;
}

View File

@ -20,8 +20,11 @@
#include <stdint.h>
#include <stddef.h>
#include <sys/types.h>
#include <boolean.h>
#include "audio_dsp_filter.h"
#include "audio_resampler_driver.h"
#ifdef __cplusplus
extern "C" {
@ -34,43 +37,6 @@ extern "C" {
#define AUDIO_MAX_RATIO 16
enum rarch_audio_ctl_state
{
RARCH_AUDIO_CTL_NONE = 0,
RARCH_AUDIO_CTL_INIT,
RARCH_AUDIO_CTL_DEINIT,
RARCH_AUDIO_CTL_DESTROY,
RARCH_AUDIO_CTL_DESTROY_DATA,
RARCH_AUDIO_CTL_START,
RARCH_AUDIO_CTL_STOP,
RARCH_AUDIO_CTL_FIND_DRIVER,
RARCH_AUDIO_CTL_SETUP_REWIND,
/* Sets audio monitor refresh rate to new value. */
RARCH_AUDIO_CTL_MONITOR_SET_REFRESH_RATE,
RARCH_AUDIO_CTL_MONITOR_ADJUST_SYSTEM_RATES,
RARCH_AUDIO_CTL_MUTE_TOGGLE,
RARCH_AUDIO_CTL_SET_CALLBACK_ENABLE,
RARCH_AUDIO_CTL_SET_CALLBACK_DISABLE,
RARCH_AUDIO_CTL_SET_CALLBACK,
RARCH_AUDIO_CTL_UNSET_CALLBACK,
RARCH_AUDIO_CTL_CALLBACK,
RARCH_AUDIO_CTL_HAS_CALLBACK,
RARCH_AUDIO_CTL_ALIVE,
RARCH_AUDIO_CTL_FRAME_IS_REVERSE,
RARCH_AUDIO_CTL_SET_OWN_DRIVER,
RARCH_AUDIO_CTL_UNSET_OWN_DRIVER,
RARCH_AUDIO_CTL_OWNS_DRIVER,
RARCH_AUDIO_CTL_SET_ACTIVE,
RARCH_AUDIO_CTL_UNSET_ACTIVE,
RARCH_AUDIO_CTL_IS_ACTIVE,
RARCH_AUDIO_CTL_RESAMPLER_DEINIT,
RARCH_AUDIO_CTL_RESAMPLER_INIT,
RARCH_AUDIO_CTL_RESAMPLER_PROCESS,
RARCH_AUDIO_CTL_DEVICES_LIST_NEW,
RARCH_AUDIO_CTL_DEVICES_LIST_FREE,
RARCH_AUDIO_CTL_DEVICES_LIST_GET
};
typedef struct audio_driver
{
/* Creates and initializes handle to audio driver.
@ -122,8 +88,33 @@ typedef struct audio_driver
size_t (*buffer_size)(void *data);
} audio_driver_t;
void audio_driver_destroy_data(void);
bool audio_driver_ctl(enum rarch_audio_ctl_state state, void *data);
void audio_driver_set_own_driver(void);
void audio_driver_unset_own_driver(void);
void audio_driver_set_active(void);
void audio_driver_unset_active(void);
bool audio_driver_is_active(void);
void audio_driver_destroy(void);
void audio_driver_deinit_resampler(void);
bool audio_driver_init_resampler(void);
void audio_driver_process_resampler(struct resampler_data *data);
bool audio_driver_free_devices_list(void);
bool audio_driver_new_devices_list(void);
bool audio_driver_enable_callback(void);
bool audio_driver_disable_callback(void);
/**
* audio_driver_find_handle:
@ -170,6 +161,41 @@ void audio_driver_dsp_filter_init(const char *device);
void audio_driver_set_buffer_size(size_t bufsize);
bool audio_driver_get_devices_list(void **ptr);
void audio_driver_setup_rewind(void);
void audio_driver_monitor_adjust_system_rates(void);
bool audio_driver_set_callback(const void *data);
bool audio_driver_callback(void);
bool audio_driver_has_callback(void);
/* Sets audio monitor rate to new value. */
void audio_driver_monitor_set_rate(void);
bool audio_driver_find_driver(void);
bool audio_driver_toggle_mute(void);
bool audio_driver_start(void);
bool audio_driver_stop(void);
bool audio_driver_owns_driver(void);
void audio_driver_unset_callback(void);
void audio_driver_frame_is_reverse(void);
bool audio_driver_alive(void);
bool audio_driver_deinit(void);
bool audio_driver_init(void);
extern audio_driver_t audio_rsound;
extern audio_driver_t audio_oss;
extern audio_driver_t audio_alsa;

View File

@ -23,13 +23,14 @@
#include <file/file_path.h>
#include <lists/dir_list.h>
#include <features/features_cpu.h>
#include "audio_dsp_filter.h"
#include "audio_filters/dspfilter.h"
#include "../config_file_userdata.h"
#include "../frontend/frontend_driver.h"
#include "../performance.h"
#include "../performance_counters.h"
#include "../dynamic.h"
struct rarch_dsp_plug
@ -146,7 +147,7 @@ static const dspfilter_get_implementation_t dsp_plugs_builtin[] = {
static bool append_plugs(rarch_dsp_filter_t *dsp, struct string_list *list)
{
unsigned i;
dspfilter_simd_mask_t mask = retro_get_cpu_features();
dspfilter_simd_mask_t mask = cpu_features_get();
(void)list;
@ -170,7 +171,7 @@ static bool append_plugs(rarch_dsp_filter_t *dsp, struct string_list *list)
static bool append_plugs(rarch_dsp_filter_t *dsp, struct string_list *list)
{
unsigned i;
dspfilter_simd_mask_t mask = retro_get_cpu_features();
dspfilter_simd_mask_t mask = cpu_features_get();
for (i = 0; i < list->size; i++)
{

View File

@ -17,11 +17,12 @@
#include <string.h>
#include <string/stdstring.h>
#include <features/features_cpu.h>
#include "audio_resampler_driver.h"
#include "../config_file_userdata.h"
#ifdef RARCH_INTERNAL
#include "../performance.h"
#include "../performance_counters.h"
#endif
#ifndef DONT_HAVE_STRING_LIST
#include "../list_special.h"
@ -141,11 +142,7 @@ retro_get_cpu_features_t perf_get_cpu_features_cb;
static resampler_simd_mask_t resampler_get_cpu_features(void)
{
#ifdef RARCH_INTERNAL
return retro_get_cpu_features();
#else
return perf_get_cpu_features_cb();
#endif
return cpu_features_get();
}
/**

View File

@ -22,12 +22,13 @@
extern "C" {
#endif
#include <stddef.h>
#include <stdint.h>
#include <stddef.h>
#include <math.h>
#include <boolean.h>
#include <retro_miscellaneous.h>
#include <boolean.h>
#include <libretro.h>
#define RESAMPLER_SIMD_SSE (1 << 0)
#define RESAMPLER_SIMD_SSE2 (1 << 1)
@ -200,10 +201,6 @@ bool rarch_resampler_realloc(void **re, const rarch_resampler_t **backend,
(backend)->process(handle, data); \
} while(0)
#ifndef RARCH_INTERNAL
#include "libretro.h"
extern retro_get_cpu_features_t perf_get_cpu_features_cb;
#endif
#ifdef __cplusplus
}

View File

@ -21,7 +21,7 @@
#include <rthreads/rthreads.h>
#include "audio_thread_wrapper.h"
#include "../performance.h"
#include "../performance_counters.h"
#include "../verbosity.h"
typedef struct audio_thread
@ -102,7 +102,7 @@ static void audio_thread_loop(void *data)
}
slock_unlock(thr->lock);
audio_driver_ctl(RARCH_AUDIO_CTL_CALLBACK, NULL);
audio_driver_callback();
}
RARCH_LOG("[Audio Thread]: Tearing down driver.\n");
@ -190,7 +190,7 @@ static bool audio_thread_stop(void *data)
audio_thread_block(thr);
thr->is_paused = true;
audio_driver_ctl(RARCH_AUDIO_CTL_SET_CALLBACK_DISABLE, NULL);
audio_driver_disable_callback();
return true;
}
@ -202,7 +202,7 @@ static bool audio_thread_start(void *data)
if (!thr)
return false;
audio_driver_ctl(RARCH_AUDIO_CTL_SET_CALLBACK_ENABLE, NULL);
audio_driver_enable_callback();
thr->is_paused = false;
audio_thread_unblock(thr);
@ -260,7 +260,7 @@ static const audio_driver_t audio_thread = {
};
/**
* rarch_threaded_audio_init:
* audio_init_thread:
* @out_driver : output driver
* @out_data : output audio data
* @device : audio device (optional)
@ -275,7 +275,7 @@ static const audio_driver_t audio_thread = {
*
* Returns: true (1) if successful, otherwise false (0).
**/
bool rarch_threaded_audio_init(const audio_driver_t **out_driver,
bool audio_init_thread(const audio_driver_t **out_driver,
void **out_data, const char *device, unsigned audio_out_rate,
unsigned latency, const audio_driver_t *drv)
{

View File

@ -22,7 +22,7 @@
#include "audio_driver.h"
/**
* rarch_threaded_audio_init:
* audio_init_thread:
* @out_driver : output driver
* @out_data : output audio data
* @device : audio device (optional)
@ -36,7 +36,7 @@
*
* Returns: true (1) if successful, otherwise false (0).
**/
bool rarch_threaded_audio_init(const audio_driver_t **out_driver, void **out_data,
bool audio_init_thread(const audio_driver_t **out_driver, void **out_data,
const char *device, unsigned out_rate, unsigned latency,
const audio_driver_t *driver);

View File

@ -13,18 +13,19 @@
* You should have received a copy of the GNU General Public License along with RetroArch.
* If not, see <http://www.gnu.org/licenses/>.
*/
#include <boolean.h>
#include "audio_utils.h"
#if defined(__SSE2__)
#include <emmintrin.h>
#elif defined(__ALTIVEC__)
#include <altivec.h>
#endif
#include <boolean.h>
#include <features/features_cpu.h>
#include "audio_utils.h"
#ifdef RARCH_INTERNAL
#include "../performance.h"
#include "../performance_counters.h"
#endif
/**
@ -409,7 +410,7 @@ retro_get_cpu_features_t perf_get_cpu_features_cb;
static unsigned audio_convert_get_cpu_features(void)
{
#ifdef RARCH_INTERNAL
return retro_get_cpu_features();
return cpu_features_get();
#else
return perf_get_cpu_features_cb();
#endif

View File

@ -351,7 +351,7 @@ static void *alsa_device_list_new(void *data)
/* description of device IOID - input / output identifcation
* ("Input" or "Output"), NULL means both) */
if (io == NULL)
if (!io || !strcmp(io,"Output"))
string_list_append(s, name, attr);
if (name)

View File

@ -369,7 +369,7 @@ static void *alsa_device_list_new(void *data)
/* description of device IOID - input / output identifcation
* ("Input" or "Output"), NULL means both) */
if (io == NULL)
if (!io || !strcmp(io,"Output"))
string_list_append(s, name, attr);
if (name)

View File

@ -18,7 +18,7 @@
#include "../audio_driver.h"
#include "../../configuration.h"
#include "../../performance.h"
#include "../../performance_counters.h"
#include "../../runloop.h"
typedef struct

View File

@ -18,7 +18,7 @@
#include "../audio_driver.h"
#include "../../configuration.h"
#include "../../performance.h"
#include "../../performance_counters.h"
#include "../../runloop.h"
#include "../../ctr/ctr_debug.h"

View File

@ -41,8 +41,10 @@ typedef struct jack
bool nonblock;
bool is_paused;
#ifdef HAVE_THREADS
scond_t *cond;
slock_t *cond_lock;
#endif
size_t buffer_size;
} jack_t;
@ -54,7 +56,9 @@ static int process_cb(jack_nframes_t nframes, void *data)
if (nframes <= 0)
{
#ifdef HAVE_THREADS
scond_signal(jd->cond);
#endif
return 0;
}
@ -74,7 +78,9 @@ static int process_cb(jack_nframes_t nframes, void *data)
for (f = min_avail; f < nframes; f++)
out[f] = 0.0f;
}
#ifdef HAVE_THREADS
scond_signal(jd->cond);
#endif
return 0;
}
@ -86,7 +92,9 @@ static void shutdown_cb(void *data)
return;
jd->shutdown = true;
#ifdef HAVE_THREADS
scond_signal(jd->cond);
#endif
}
static int parse_ports(char **dest_ports, const char **jports)
@ -149,8 +157,10 @@ static void *ja_init(const char *device, unsigned rate, unsigned latency)
if (!jd)
return NULL;
#ifdef HAVE_THREADS
jd->cond = scond_new();
jd->cond_lock = slock_new();
#endif
jd->client = jack_client_open("RetroArch", JackNullOption, NULL);
if (jd->client == NULL)
@ -258,12 +268,14 @@ static size_t write_buffer(jack_t *jd, const float *buf, size_t size)
}
written += write_frames;
}
#ifdef HAVE_THREADS
else
{
slock_lock(jd->cond_lock);
scond_wait(jd->cond, jd->cond_lock);
slock_unlock(jd->cond_lock);
}
#endif
if (jd->nonblock)
break;
@ -327,10 +339,12 @@ static void ja_free(void *data)
if (jd->buffer[i] != NULL)
jack_ringbuffer_free(jd->buffer[i]);
#ifdef HAVE_THREADS
if (jd->cond_lock)
slock_free(jd->cond_lock);
if (jd->cond)
scond_free(jd->cond);
#endif
free(jd);
}

View File

@ -35,8 +35,10 @@ typedef struct sdl_audio
bool nonblock;
bool is_paused;
#ifdef HAVE_THREADS
slock_t *lock;
scond_t *cond;
#endif
fifo_buffer_t *buffer;
} sdl_audio_t;
@ -47,7 +49,9 @@ static void sdl_audio_cb(void *data, Uint8 *stream, int len)
size_t write_size = len > (int)avail ? avail : len;
fifo_read(sdl->buffer, stream, write_size);
#ifdef HAVE_THREADS
scond_signal(sdl->cond);
#endif
/* If underrun, fill rest with silence. */
memset(stream + write_size, 0, len - write_size);
@ -109,8 +113,10 @@ static void *sdl_audio_init(const char *device,
settings->audio.out_rate = out.freq;
#ifdef HAVE_THREADS
sdl->lock = slock_new();
sdl->cond = scond_new();
#endif
RARCH_LOG("SDL audio: Requested %u ms latency, got %d ms\n",
latency, (int)(out.samples * 4 * 1000 / settings->audio.out_rate));
@ -160,9 +166,11 @@ static ssize_t sdl_audio_write(void *data, const void *buf, size_t size)
if (avail == 0)
{
SDL_UnlockAudio();
#ifdef HAVE_THREADS
slock_lock(sdl->lock);
scond_wait(sdl->cond, sdl->lock);
slock_unlock(sdl->lock);
#endif
}
else
{
@ -220,8 +228,10 @@ static void sdl_audio_free(void *data)
if (sdl)
{
fifo_free(sdl->buffer);
#ifdef HAVE_THREADS
slock_free(sdl->lock);
scond_free(sdl->cond);
#endif
}
free(sdl);
}

View File

@ -27,7 +27,7 @@
#include "configuration.h"
#include "msg_hash.h"
#include "runloop.h"
#include "libretro_version_1.h"
#include "core.h"
#include "verbosity.h"
/* Autosave support. */
@ -55,28 +55,6 @@ struct autosave
static struct autosave_st autosave_state;
/**
* autosave_lock:
* @handle : pointer to autosave object
*
* Locks autosave.
**/
static void autosave_lock(autosave_t *handle)
{
slock_lock(handle->lock);
}
/**
* autosave_unlock:
* @handle : pointer to autosave object
*
* Unlocks autosave.
**/
static void autosave_unlock(autosave_t *handle)
{
slock_unlock(handle->lock);
}
/**
* autosave_thread:
* @data : pointer to autosave object
@ -92,12 +70,12 @@ static void autosave_thread(void *data)
{
bool differ;
autosave_lock(save);
slock_lock(save->lock);
differ = memcmp(save->buffer, save->retro_buffer,
save->bufsize) != 0;
if (differ)
memcpy(save->buffer, save->retro_buffer, save->bufsize);
autosave_unlock(save);
slock_unlock(save->lock);
if (differ)
{
@ -208,38 +186,38 @@ static void autosave_free(autosave_t *handle)
}
/**
* lock_autosave:
* autosave_lock:
*
* Lock autosave.
**/
void lock_autosave(void)
void autosave_lock(void)
{
unsigned i;
for (i = 0; i < autosave_state.num; i++)
{
if (autosave_state.list[i])
autosave_lock(autosave_state.list[i]);
slock_lock(autosave_state.list[i]->lock);
}
}
/**
* unlock_autosave:
* autosave_unlock:
*
* Unlocks autosave.
**/
void unlock_autosave(void)
void autosave_unlock(void)
{
unsigned i;
for (i = 0; i < autosave_state.num; i++)
{
if (autosave_state.list[i])
autosave_unlock(autosave_state.list[i]);
slock_unlock(autosave_state.list[i]->lock);
}
}
void autosave_event_init(void)
void autosave_init(void)
{
unsigned i;
autosave_t **list = NULL;
@ -265,7 +243,7 @@ void autosave_event_init(void)
mem_info.id = type;
core_ctl(CORE_CTL_RETRO_GET_MEMORY, &mem_info);
core_get_memory(&mem_info);
if (mem_info.size <= 0)
continue;
@ -280,7 +258,7 @@ void autosave_event_init(void)
}
}
void autosave_event_deinit(void)
void autosave_deinit(void)
{
unsigned i;

View File

@ -26,22 +26,22 @@ extern "C" {
typedef struct autosave autosave_t;
/**
* lock_autosave:
* autosave_lock:
*
* Lock autosave.
**/
void lock_autosave(void);
void autosave_lock(void);
/**
* unlock_autosave:
* autosave_unlock:
*
* Unlocks autosave.
**/
void unlock_autosave(void);
void autosave_unlock(void);
void autosave_event_init(void);
void autosave_init(void);
void autosave_event_deinit(void);
void autosave_deinit(void);
#ifdef __cplusplus
}

View File

@ -153,7 +153,7 @@ bool camera_driver_ctl(enum rarch_camera_ctl_state state, void *data)
camera_driver = (const camera_driver_t*)camera_driver_find_handle(0);
if (!camera_driver)
retro_fail(1, "find_camera_driver()");
retroarch_fail(1, "find_camera_driver()");
}
}
break;

View File

@ -18,8 +18,9 @@
#define __CAMERA_DRIVER__H
#include <stdint.h>
#include <boolean.h>
#include "../libretro.h"
#include <libretro.h>
#ifdef __cplusplus
extern "C" {

View File

@ -41,7 +41,7 @@
#include <compat/strl.h>
#include "../camera_driver.h"
#include "../../performance.h"
#include "../../performance_counters.h"
#include "../../verbosity.h"
struct buffer
@ -249,9 +249,9 @@ static void v4l_stop(void *data)
static bool v4l_start(void *data)
{
video4linux_t *v4l = (video4linux_t*)data;
unsigned i;
enum v4l2_buf_type type;
video4linux_t *v4l = (video4linux_t*)data;
for (i = 0; i < v4l->n_buffers; i++)
{

414
cheevos.c
View File

@ -20,16 +20,19 @@
#include <streams/file_stream.h>
#include <rhash.h>
#include <rthreads/async_job.h>
#include <libretro.h>
#include "cheevos.h"
#include "command.h"
#include "dynamic.h"
#include "libretro.h"
#include "net_http_special.h"
#include "system.h"
#include "network/net_http_special.h"
#include "configuration.h"
#include "performance.h"
#include "performance_counters.h"
#include "msg_hash.h"
#include "runloop.h"
#include "libretro_version_1.h"
#include "core.h"
#ifdef HAVE_MENU
#include "menu/menu_driver.h"
@ -38,6 +41,15 @@
#include "verbosity.h"
/* Define this macro to deactivate awarded cheevos. */
#define CHEEVOS_DEACTIVATE
/* Define this macro to log URLs (will log the user token). */
#undef CHEEVOS_LOG_URLS
/* Define this macro to dump all cheevos' addresses. */
#undef CHEEVOS_DUMP_ADDRS
#define JSON_KEY_GAMEID 0xb4960eecU
#define JSON_KEY_ACHIEVEMENTS 0x69749ae1U
#define JSON_KEY_ID 0x005973f2U
@ -49,10 +61,17 @@
#define JSON_KEY_MODIFIED 0xdcea4fe6U
#define JSON_KEY_CREATED 0x3a84721dU
#define JSON_KEY_BADGENAME 0x887685d9U
#define JSON_KEY_CONSOLE_ID 0x071656e5U
#define JSON_KEY_TOKEN 0x0e2dbd26U
#define JSON_KEY_FLAGS 0x0d2e96b2U
enum
{
CHEEVOS_CONSOLE_GAMEBOY = 4,
CHEEVOS_CONSOLE_GAMEBOY_ADVANCED = 5,
CHEEVOS_CONSOLE_GAMEBOY_COLOR = 6,
};
enum
{
CHEEVOS_VAR_SIZE_BIT_0,
@ -130,7 +149,7 @@ typedef struct
{
unsigned size;
unsigned type;
unsigned bank_id;
int bank_id;
unsigned value;
unsigned previous;
} cheevos_var_t;
@ -176,16 +195,6 @@ typedef struct
unsigned count;
} cheevoset_t;
typedef struct
{
int loaded;
cheevoset_t core;
cheevoset_t unofficial;
char token[32];
} cheevos_locals_t;
typedef struct
{
int is_element;
@ -216,6 +225,7 @@ typedef struct
typedef struct
{
int in_cheevos;
int is_console_id;
unsigned core_count;
unsigned unofficial_count;
@ -231,15 +241,33 @@ typedef struct
const uint32_t *ext_hashes;
} cheevos_finder_t;
typedef struct
{
int loaded;
int console_id;
bool core_supports;
cheevoset_t core;
cheevoset_t unofficial;
char token[32];
retro_ctx_memory_info_t meminfo[4];
} cheevos_locals_t;
static cheevos_locals_t cheevos_locals =
{
0,
0,
true,
{NULL, 0},
{NULL, 0},
{0},
};
static int cheats_are_enabled = 0;
static int cheats_were_enabled = 0;
/* forward declaration */
int rarch_main_async_job_add(async_task_t task, void *payload);
@ -288,12 +316,10 @@ static int cheevos_http_get(const char **result, size_t *size,
break;
}
RARCH_LOG("CHEEVOS error getting %s: %s\n", url, msg);
RARCH_LOG("CHEEVOS http result was %s\n", *result ? *result : "(null)");
RARCH_ERR("CHEEVOS error getting %s: %s\n", url, msg);
return ret;
}
static int cheevos_getvalue__json_key(void *userdata,
const char *name, size_t length)
{
@ -388,7 +414,6 @@ static int cheevos_get_value(const char *json, unsigned key_hash,
Count number of achievements in a JSON file.
*****************************************************************************/
static int cheevos_count__json_end_array(void *userdata)
{
cheevos_countud_t* ud = (cheevos_countud_t*)userdata;
@ -560,7 +585,7 @@ static unsigned cheevos_parse_operator(const char **memaddr)
}
else
{
/* TODO log the exception */
RARCH_ERR("CHEEVOS Unknown operator %c\n", *str);
op = CHEEVOS_COND_OP_EQUALS;
}
@ -606,6 +631,69 @@ static void cheevos_parse_var(cheevos_var_t *var, const char **memaddr)
var->value = strtol(str, &end, base);
*memaddr = end;
if ( var->type == CHEEVOS_VAR_TYPE_ADDRESS
|| var->type == CHEEVOS_VAR_TYPE_DELTA_MEM)
{
rarch_system_info_t *system;
runloop_ctl(RUNLOOP_CTL_SYSTEM_INFO_GET, &system);
var->bank_id = -1;
if (system->mmaps.num_descriptors != 0)
{
const struct retro_memory_descriptor *desc;
const struct retro_memory_descriptor *end;
#if 0
if (cheevos_locals.console_id == CHEEVOS_CONSOLE_GAMEBOY_ADVANCED)
{
/* Patch the address to correctly map it to the mmaps */
if (var->value < 0x8000)
{
/* Internal RAM */
var->value += 0x3000000;
}
else
{
/* Work RAM */
var->value += 0x2000000 - 0x8000;
}
}
#endif
desc = system->mmaps.descriptors;
end = desc + system->mmaps.num_descriptors;
for (; desc < end; desc++)
{
if (var->value >= desc->start && var->value < (desc->start + desc->len))
{
var->bank_id = desc - system->mmaps.descriptors;
var->value = var->value - desc->start + desc->offset;
break;
}
}
}
else
{
unsigned i;
for (i = 0; i < sizeof(cheevos_locals.meminfo) / sizeof(cheevos_locals.meminfo[0]); i++)
{
if (var->value < cheevos_locals.meminfo[i].size)
{
var->bank_id = i;
break;
}
var->value -= cheevos_locals.meminfo[i].size;
}
}
#ifdef CHEEVOS_DUMP_ADDRS
RARCH_LOG("CHEEVOS var %03d:%08X\n", var->bank_id + 1, var->value);
#endif
}
}
static void cheevos_parse_cond(cheevos_cond_t *cond, const char **memaddr)
@ -707,7 +795,6 @@ static void cheevos_parse_memaddr(cheevos_cond_t *cond, const char *memaddr)
Load achievements from a JSON string.
*****************************************************************************/
static INLINE const char *cheevos_dupstr(const cheevos_field_t *field)
{
char *string = (char*)malloc(field->length + 1);
@ -794,7 +881,6 @@ static int cheevos_new_cheevo(cheevos_readud_t *ud)
return 0;
}
static int cheevos_read__json_key( void *userdata,
const char *name, size_t length)
{
@ -805,6 +891,8 @@ static int cheevos_read__json_key( void *userdata,
if (hash == JSON_KEY_ACHIEVEMENTS)
ud->in_cheevos = 1;
else if (hash == JSON_KEY_CONSOLE_ID)
ud->is_console_id = 1;
else if (ud->in_cheevos)
{
switch ( hash )
@ -869,6 +957,11 @@ static int cheevos_read__json_number(void *userdata,
ud->field->string = number;
ud->field->length = length;
}
else if (ud->is_console_id)
{
cheevos_locals.console_id = strtol(number, NULL, 10);
ud->is_console_id = 0;
}
return 0;
}
@ -947,13 +1040,14 @@ static int cheevos_parse(const char *json)
/* Load the achievements. */
ud.in_cheevos = 0;
ud.is_console_id = 0;
ud.field = NULL;
ud.core_count = 0;
ud.unofficial_count = 0;
if (jsonsax_parse(json, &handlers, (void*)&ud) != JSONSAX_OK)
{
cheevos_ctl(CHEEVOS_CTL_UNLOAD, NULL);
cheevos_unload();
return -1;
}
@ -964,61 +1058,21 @@ static int cheevos_parse(const char *json)
Test all the achievements (call once per frame).
*****************************************************************************/
static const uint8_t *cheevos_get_memory(unsigned offset)
static const uint8_t *cheevos_get_memory(const cheevos_var_t *var)
{
retro_ctx_memory_info_t mem_info;
uint8_t *memory = NULL;
mem_info.id = RETRO_MEMORY_SYSTEM_RAM;
core_ctl(CORE_CTL_RETRO_GET_MEMORY, &mem_info);
if (offset < mem_info.size)
if (var->bank_id >= 0)
{
memory = (uint8_t*)mem_info.data;
return memory + offset;
rarch_system_info_t *system;
runloop_ctl(RUNLOOP_CTL_SYSTEM_INFO_GET, &system);
if (system->mmaps.num_descriptors != 0)
{
return (uint8_t *)system->mmaps.descriptors[var->bank_id].ptr + var->value;
}
offset -= mem_info.size;
mem_info.data = NULL;
mem_info.size = 0;
mem_info.id = RETRO_MEMORY_SAVE_RAM;
core_ctl(CORE_CTL_RETRO_GET_MEMORY, &mem_info);
if (offset < mem_info.size)
else
{
memory = (uint8_t*)mem_info.data;
return memory + offset;
return (uint8_t *)cheevos_locals.meminfo[var->bank_id].data + var->value;
}
offset -= mem_info.size;
mem_info.data = NULL;
mem_info.size = 0;
mem_info.id = RETRO_MEMORY_VIDEO_RAM;
core_ctl(CORE_CTL_RETRO_GET_MEMORY, &mem_info);
if (offset < mem_info.size)
{
memory = (uint8_t*)mem_info.data;
return memory + offset;
}
offset -= mem_info.size;
mem_info.data = NULL;
mem_info.size = 0;
mem_info.id = RETRO_MEMORY_RTC;
core_ctl(CORE_CTL_RETRO_GET_MEMORY, &mem_info);
if (offset < mem_info.size)
{
memory = (uint8_t*)mem_info.data;
return memory + offset;
}
return NULL;
@ -1037,7 +1091,7 @@ static unsigned cheevos_get_var_value(cheevos_var_t *var)
|| var->type == CHEEVOS_VAR_TYPE_DELTA_MEM)
{
/* TODO Check with Scott if the bank id is needed */
memory = cheevos_get_memory(var->value);
memory = cheevos_get_memory(var);
if (memory)
{
@ -1319,7 +1373,7 @@ static int cheevos_login(retro_time_t *timeout)
{
runloop_msg_queue_push("Missing Retro Achievements account information", 0, 5 * 60, false);
runloop_msg_queue_push("Please fill in your account information in Settings", 0, 5 * 60, false);
RARCH_LOG("CHEEVOS username and/or password not informed\n");
RARCH_ERR("CHEEVOS username and/or password not informed\n");
return -1;
}
@ -1334,6 +1388,10 @@ static int cheevos_login(retro_time_t *timeout)
request[sizeof(request) - 1] = 0;
#ifdef CHEEVOS_LOG_URLS
RARCH_LOG("CHEEVOS url to login: %s\n", request);
#endif
if (!cheevos_http_get(&json, NULL, request, timeout))
{
res = cheevos_get_value(json, JSON_KEY_TOKEN,
@ -1343,7 +1401,6 @@ static int cheevos_login(retro_time_t *timeout)
if (!res)
{
RARCH_LOG("CHEEVOS user token is '%s'\n", cheevos_locals.token);
return 0;
}
}
@ -1353,7 +1410,7 @@ static int cheevos_login(retro_time_t *timeout)
runloop_msg_queue_push(
"Please make sure your account information is correct",
0, 5 * 60, false);
RARCH_LOG("CHEEVOS error getting user token.\n");
RARCH_ERR("CHEEVOS error getting user token.\n");
return -1;
}
@ -1373,7 +1430,10 @@ static void cheevos_unlocker(void *payload)
);
request[sizeof(request) - 1] = 0;
RARCH_LOG("CHEEVOS awarding achievement %u: %s\n", cheevo_id, request);
#ifdef CHEEVOS_LOG_URLS
RARCH_LOG("CHEEVOS url to award the cheevo: %s\n", request);
#endif
if (!cheevos_http_get(&result, NULL, request, NULL))
{
@ -1382,7 +1442,8 @@ static void cheevos_unlocker(void *payload)
}
else
{
RARCH_LOG("CHEEVOS error awarding achievement %u, will retry...\n", cheevo_id);
RARCH_ERR("CHEEVOS error awarding achievement %u, will retry...\n", cheevo_id);
/* re-schedule */
rarch_main_async_job_add(cheevos_unlocker, (void*)(uintptr_t)cheevo_id);
}
}
@ -1397,8 +1458,7 @@ static void cheevos_test_cheevo_set(const cheevoset_t *set)
{
if (cheevo->active && cheevos_test_cheevo(cheevo))
{
RARCH_LOG("CHEEVOS %s\n", cheevo->title);
RARCH_LOG("CHEEVOS %s\n", cheevo->description);
RARCH_LOG("CHEEVOS awarding cheevo %s (%s)\n", cheevo->title, cheevo->description);
runloop_msg_queue_push(cheevo->title, 0, 3 * 60, false);
runloop_msg_queue_push(cheevo->description, 0, 5 * 60, false);
@ -1464,13 +1524,17 @@ static int cheevos_get_by_game_id(const char **json,
request[sizeof(request) - 1] = 0;
#ifdef CHEEVOS_LOG_URLS
RARCH_LOG("CHEEVOS url to get the list of cheevos: %s\n", request);
#endif
if (!cheevos_http_get(json, NULL, request, timeout))
{
RARCH_LOG("CHEEVOS got achievements for game id %u\n", game_id);
return 0;
}
RARCH_LOG("CHEEVOS error getting achievements for game id %u\n", game_id);
RARCH_ERR("CHEEVOS error getting achievements for game id %u\n", game_id);
}
return -1;
@ -1502,6 +1566,10 @@ static unsigned cheevos_get_game_id(unsigned char *hash, retro_time_t *timeout)
request[sizeof(request) - 1] = 0;
#ifdef CHEEVOS_LOG_URLS
RARCH_LOG("CHEEVOS url to get the game's id: %s\n", request);
#endif
if (!cheevos_http_get(&json, NULL, request, timeout))
{
res = cheevos_get_value(json, JSON_KEY_GAMEID,
@ -1516,7 +1584,7 @@ static unsigned cheevos_get_game_id(unsigned char *hash, retro_time_t *timeout)
}
}
RARCH_LOG("CHEEVOS error getting game_id\n");
RARCH_ERR("CHEEVOS error getting game_id\n");
return 0;
}
@ -1537,6 +1605,10 @@ static void cheevos_playing(void *payload)
request[sizeof(request) - 1] = 0;
#ifdef CHEEVOS_LOG_URLS
RARCH_LOG("CHEEVOS url to post the 'playing' activity: %s\n", request);
#endif
if (!cheevos_http_get(&json, NULL, request, NULL))
{
free((void*)json);
@ -1545,13 +1617,14 @@ static void cheevos_playing(void *payload)
}
else
{
RARCH_LOG("CHEEVOS error posting playing game %u activity, will retry\n", game_id);
RARCH_ERR("CHEEVOS error posting playing game %u activity, will retry\n", game_id);
/* re-schedule */
rarch_main_async_job_add(cheevos_playing, (void*)(uintptr_t)game_id);
}
}
}
#ifdef CHEEVOS_DEACTIVATE
static int cheevos_deactivate__json_index(void *userdata, unsigned int index)
{
cheevos_deactivate_t *ud = (cheevos_deactivate_t*)userdata;
@ -1578,7 +1651,7 @@ static int cheevos_deactivate__json_number(void *userdata,
for (; cheevo < end; cheevo++)
{
if (cheevo->id == id)
if (cheevo->id == (unsigned)id)
{
cheevo->active = 0;
found = 1;
@ -1593,22 +1666,28 @@ static int cheevos_deactivate__json_number(void *userdata,
for (; cheevo < end; cheevo++)
{
if (cheevo->id != id)
continue;
if (cheevo->id == (unsigned)id)
{
cheevo->active = 0;
break;
}
}
}
if (found)
RARCH_LOG("CHEEVOS deactivated unlocked cheevo %s\n", cheevo->title);
else
RARCH_ERR("CHEEVOS unknown cheevo to deactivate: %u\n", id);
}
return 0;
}
#endif
static int cheevos_deactivate_unlocks(unsigned game_id, retro_time_t *timeout)
{
/* Only call this function after the cheevos have been loaded. */
#ifdef CHEEVOS_DEACTIVATE
static const jsonsax_handlers_t handlers =
{
NULL,
@ -1641,6 +1720,10 @@ static int cheevos_deactivate_unlocks(unsigned game_id, retro_time_t *timeout)
request[sizeof(request) - 1] = 0;
#ifdef CHEEVOS_LOG_URLS
RARCH_LOG("CHEEVOS url to get the list of unlocked cheevos: %s\n", request);
#endif
if (!cheevos_http_get(&json, NULL, request, timeout))
{
ud.is_element = 0;
@ -1655,8 +1738,12 @@ static int cheevos_deactivate_unlocks(unsigned game_id, retro_time_t *timeout)
}
}
RARCH_LOG("CHEEVOS error deactivating unlocked achievements\n");
RARCH_ERR("CHEEVOS error deactivating unlocked achievements\n");
return -1;
#else
RARCH_LOG("CHEEVOS cheevo deactivation is disabled\n");
return 0;
#endif
}
#define CHEEVOS_SIX_MB (6 * 1024 * 1024)
@ -1917,11 +2004,8 @@ static unsigned cheevos_find_game_id_nes(
return cheevos_get_game_id(hash, &to);
}
static bool cheevos_load(const void *data)
bool cheevos_load(const void *data)
{
retro_ctx_memory_info_t mem_info;
static const uint32_t genesis_exts[] =
{
0x0b888feeU, /* mdx */
@ -1958,7 +2042,6 @@ static bool cheevos_load(const void *data)
{cheevos_find_game_id_generic, "Generic (plain content)", NULL},
};
size_t memory;
struct retro_system_info sysinfo;
unsigned i;
const char *json = NULL;
@ -1969,56 +2052,25 @@ static bool cheevos_load(const void *data)
cheevos_locals.loaded = 0;
/* Just return OK if cheevos are disabled. */
if (!settings->cheevos.enable)
/* Just return OK if cheevos are disabled, the core doesn't support cheevos, or info is NULL. */
if (!settings->cheevos.enable || !cheevos_locals.core_supports || !info)
return true;
/* Also return OK if there's no content. */
if (!info)
return true;
cheevos_locals.meminfo[0].id = RETRO_MEMORY_SYSTEM_RAM;
core_get_memory(&cheevos_locals.meminfo[0]);
mem_info.data = NULL;
mem_info.size = 0;
mem_info.id = RETRO_MEMORY_SYSTEM_RAM;
cheevos_locals.meminfo[1].id = RETRO_MEMORY_SAVE_RAM;
core_get_memory(&cheevos_locals.meminfo[1]);
core_ctl(CORE_CTL_RETRO_GET_MEMORY, &mem_info);
cheevos_locals.meminfo[2].id = RETRO_MEMORY_VIDEO_RAM;
core_get_memory(&cheevos_locals.meminfo[2]);
memory = mem_info.size;
mem_info.data = NULL;
mem_info.size = 0;
mem_info.id = RETRO_MEMORY_VIDEO_RAM;
core_ctl(CORE_CTL_RETRO_GET_MEMORY, &mem_info);
memory += mem_info.size;
mem_info.data = NULL;
mem_info.size = 0;
mem_info.id = RETRO_MEMORY_RTC;
core_ctl(CORE_CTL_RETRO_GET_MEMORY, &mem_info);
memory += mem_info.size;
mem_info.data = NULL;
mem_info.size = 0;
mem_info.id = RETRO_MEMORY_SAVE_RAM;
core_ctl(CORE_CTL_RETRO_GET_MEMORY, &mem_info);
memory += mem_info.size;
if (!memory)
{
runloop_msg_queue_push("This core doesn't support achievements", 0, 5 * 60, false);
RARCH_LOG("This core doesn't support achievements\n");
return false;
}
cheevos_locals.meminfo[3].id = RETRO_MEMORY_RTC;
core_get_memory(&cheevos_locals.meminfo[3]);
/* The the supported extensions as a hint to what method we should use. */
core_ctl(CORE_CTL_RETRO_GET_SYSTEM_INFO, &sysinfo);
core_get_system_info(&sysinfo);
for (i = 0; i < sizeof(finders) / sizeof(finders[0]); i++)
{
@ -2077,6 +2129,7 @@ static bool cheevos_load(const void *data)
runloop_msg_queue_push("This game doesn't feature achievements",
0, 5 * 60, false);
RARCH_LOG("CHEEVOS this game doesn't feature achievements\n");
return false;
found:
@ -2097,12 +2150,13 @@ static bool cheevos_load(const void *data)
}
runloop_msg_queue_push("Error loading achievements", 0, 5 * 60, false);
RARCH_ERR("CHEEVOS error loading achievements\n", 0, 5 * 60, false);
return false;
}
#ifdef HAVE_MENU
static void cheevos_populate_menu(void *data)
void cheevos_populate_menu(void *data)
{
#ifdef HAVE_MENU
unsigned i;
const cheevo_t *end = NULL;
cheevo_t *cheevo = NULL;
@ -2165,20 +2219,11 @@ static void cheevos_populate_menu(void *data)
cheevo->description, MENU_SETTINGS_CHEEVOS_START + i, 0, 0);
}
}
}
#endif
}
bool cheevos_ctl(enum cheevos_ctl_state state, void *data)
bool cheevos_get_description(cheevos_ctx_desc_t *desc)
{
static int cheats_are_enabled = 0;
static int cheats_were_enabled = 0;
settings_t *settings = config_get_ptr();
switch (state)
{
case CHEEVOS_CTL_GET_DESCRIPTION:
{
cheevos_ctx_desc_t *desc = (cheevos_ctx_desc_t*)data;
cheevo_t *cheevos = cheevos_locals.core.cheevos;
if (desc->idx >= cheevos_locals.core.count)
@ -2189,21 +2234,20 @@ bool cheevos_ctl(enum cheevos_ctl_state state, void *data)
strncpy(desc->s, cheevos[desc->idx].description, desc->len);
desc->s[desc->len - 1] = 0;
return true;
}
break;
case CHEEVOS_CTL_APPLY_CHEATS:
bool cheevos_apply_cheats(bool *data_bool)
{
bool *data_bool = (bool*)data;
cheats_are_enabled = *data_bool;
cheats_were_enabled |= cheats_are_enabled;
}
break;
case CHEEVOS_CTL_LOAD:
if (!cheevos_load((const void*)data))
return false;
break;
case CHEEVOS_CTL_UNLOAD:
return true;
}
bool cheevos_unload(void)
{
if (!cheevos_locals.loaded)
return false;
@ -2211,15 +2255,20 @@ bool cheevos_ctl(enum cheevos_ctl_state state, void *data)
cheevos_free_cheevo_set(&cheevos_locals.unofficial);
cheevos_locals.loaded = 0;
break;
case CHEEVOS_CTL_TOGGLE_HARDCORE_MODE:
return true;
}
bool cheevos_toggle_hardcore_mode(void)
{
settings_t *settings = config_get_ptr();
/* reset and deinit rewind to avoid cheat the score */
if (settings->cheevos.hardcore_mode_enable)
{
/* send reset core cmd to avoid any user savestate previusly loaded */
event_cmd_ctl(EVENT_CMD_RESET, NULL);
command_event(CMD_EVENT_RESET, NULL);
if (settings->rewind_enable)
event_cmd_ctl(EVENT_CMD_REWIND_DEINIT, NULL);
command_event(CMD_EVENT_REWIND_DEINIT, NULL);
RARCH_LOG("%s\n", msg_hash_to_str(MSG_CHEEVOS_HARDCORE_MODE_ENABLE));
runloop_msg_queue_push(msg_hash_to_str(MSG_CHEEVOS_HARDCORE_MODE_ENABLE), 0, 3 * 60, true);
@ -2227,10 +2276,15 @@ bool cheevos_ctl(enum cheevos_ctl_state state, void *data)
else
{
if (settings->rewind_enable)
event_cmd_ctl(EVENT_CMD_REWIND_INIT, NULL);
command_event(CMD_EVENT_REWIND_INIT, NULL);
}
break;
case CHEEVOS_CTL_TEST:
return true;
}
bool cheevos_test(void)
{
settings_t *settings = config_get_ptr();
if (!cheevos_locals.loaded)
return false;
@ -2244,18 +2298,18 @@ bool cheevos_ctl(enum cheevos_ctl_state state, void *data)
if (settings->cheevos.test_unofficial)
cheevos_test_cheevo_set(&cheevos_locals.unofficial);
}
break;
case CHEEVOS_CTL_POPULATE_MENU:
#ifdef HAVE_MENU
cheevos_populate_menu(data);
#endif
break;
case CHEEVOS_CTL_SET_CHEATS:
cheats_were_enabled = cheats_are_enabled;
break;
case CHEEVOS_CTL_NONE:
default:
break;
}
return true;
}
bool cheevos_set_cheats(void)
{
cheats_were_enabled = cheats_are_enabled;
return true;
}
void cheevos_set_support_cheevos(bool state)
{
cheevos_locals.core_supports = state;
}

View File

@ -19,29 +19,6 @@
#include <stdint.h>
#include <stdlib.h>
enum cheevos_ctl_state
{
CHEEVOS_CTL_NONE = 0,
CHEEVOS_CTL_TEST,
CHEEVOS_CTL_LOAD,
CHEEVOS_CTL_APPLY_CHEATS,
/* Unload the achievements from memory. */
CHEEVOS_CTL_UNLOAD,
/* Toggle Hardcore Mode */
CHEEVOS_CTL_TOGGLE_HARDCORE_MODE,
/* Load the achievements into memory if
* the game has content. */
CHEEVOS_CTL_SET_CHEATS,
CHEEVOS_CTL_GET_DESCRIPTION,
CHEEVOS_CTL_POPULATE_MENU
};
typedef struct cheevos_ctx_desc
{
unsigned idx;
@ -49,6 +26,22 @@ typedef struct cheevos_ctx_desc
size_t len;
} cheevos_ctx_desc_t;
bool cheevos_ctl(enum cheevos_ctl_state state, void *data);
bool cheevos_load(const void *data);
void cheevos_populate_menu(void *data);
bool cheevos_get_description(cheevos_ctx_desc_t *desc);
bool cheevos_apply_cheats(bool *data_bool);
bool cheevos_unload(void);
bool cheevos_toggle_hardcore_mode(void);
bool cheevos_test(void);
bool cheevos_set_cheats(void);
void cheevos_set_support_cheevos(bool state);
#endif /* __RARCH_CHEEVOS_H */

2283
command.c

File diff suppressed because it is too large Load Diff

230
command.h
View File

@ -28,28 +28,226 @@
extern "C" {
#endif
enum rarch_cmd_ctl_state
typedef struct command command_t;
typedef struct command_handle
{
RARCH_CMD_CTL_NONE = 0,
RARCH_CMD_CTL_GET,
RARCH_CMD_CTL_SET,
RARCH_CMD_CTL_POLL,
RARCH_CMD_CTL_NETWORK_SEND,
RARCH_CMD_CTL_FREE
command_t *handle;
unsigned id;
} command_handle_t;
enum event_command
{
CMD_EVENT_NONE = 0,
/* Resets RetroArch. */
CMD_EVENT_RESET,
/* Loads content file. */
CMD_EVENT_LOAD_CONTENT,
CMD_EVENT_LOAD_CONTENT_PERSIST,
CMD_EVENT_LOAD_CONTENT_FFMPEG,
CMD_EVENT_LOAD_CONTENT_IMAGEVIEWER,
CMD_EVENT_SET_PER_GAME_RESOLUTION,
CMD_EVENT_SET_FRAME_LIMIT,
/* Loads core. */
CMD_EVENT_LOAD_CORE_DEINIT,
CMD_EVENT_LOAD_CORE,
CMD_EVENT_LOAD_CORE_PERSIST,
CMD_EVENT_UNLOAD_CORE,
CMD_EVENT_LOAD_STATE,
CMD_EVENT_SAVE_STATE,
CMD_EVENT_SAVE_STATE_DECREMENT,
CMD_EVENT_SAVE_STATE_INCREMENT,
/* Takes screenshot. */
CMD_EVENT_TAKE_SCREENSHOT,
/* Quits RetroArch. */
CMD_EVENT_QUIT,
/* Reinitialize all drivers. */
CMD_EVENT_REINIT,
/* Toggles cheevos hardcore mode. */
CMD_EVENT_CHEEVOS_HARDCORE_MODE_TOGGLE,
/* Deinitialize rewind. */
CMD_EVENT_REWIND_DEINIT,
/* Initializes rewind. */
CMD_EVENT_REWIND_INIT,
/* Toggles rewind. */
CMD_EVENT_REWIND_TOGGLE,
/* Deinitializes autosave. */
CMD_EVENT_AUTOSAVE_DEINIT,
/* Initializes autosave. */
CMD_EVENT_AUTOSAVE_INIT,
CMD_EVENT_AUTOSAVE_STATE,
/* Stops audio. */
CMD_EVENT_AUDIO_STOP,
/* Starts audio. */
CMD_EVENT_AUDIO_START,
/* Mutes audio. */
CMD_EVENT_AUDIO_MUTE_TOGGLE,
/* Initializes overlay. */
CMD_EVENT_OVERLAY_INIT,
/* Deinitializes overlay. */
CMD_EVENT_OVERLAY_DEINIT,
/* Sets current scale factor for overlay. */
CMD_EVENT_OVERLAY_SET_SCALE_FACTOR,
/* Sets current alpha modulation for overlay. */
CMD_EVENT_OVERLAY_SET_ALPHA_MOD,
/* Cycle to next overlay. */
CMD_EVENT_OVERLAY_NEXT,
/* Deinitializes overlay. */
CMD_EVENT_DSP_FILTER_INIT,
/* Deinitializes graphics filter. */
CMD_EVENT_DSP_FILTER_DEINIT,
/* Deinitializes GPU recoring. */
CMD_EVENT_GPU_RECORD_DEINIT,
/* Initializes recording system. */
CMD_EVENT_RECORD_INIT,
/* Deinitializes recording system. */
CMD_EVENT_RECORD_DEINIT,
/* Deinitializes history playlist. */
CMD_EVENT_HISTORY_DEINIT,
/* Initializes history playlist. */
CMD_EVENT_HISTORY_INIT,
/* Deinitializes core information. */
CMD_EVENT_CORE_INFO_DEINIT,
/* Initializes core information. */
CMD_EVENT_CORE_INFO_INIT,
/* Deinitializes core. */
CMD_EVENT_CORE_DEINIT,
/* Initializes core. */
CMD_EVENT_CORE_INIT,
/* Set audio blocking state. */
CMD_EVENT_AUDIO_SET_BLOCKING_STATE,
/* Set audio nonblocking state. */
CMD_EVENT_AUDIO_SET_NONBLOCKING_STATE,
/* Apply video state changes. */
CMD_EVENT_VIDEO_APPLY_STATE_CHANGES,
/* Set video blocking state. */
CMD_EVENT_VIDEO_SET_BLOCKING_STATE,
/* Set video nonblocking state. */
CMD_EVENT_VIDEO_SET_NONBLOCKING_STATE,
/* Sets current aspect ratio index. */
CMD_EVENT_VIDEO_SET_ASPECT_RATIO,
CMD_EVENT_RESET_CONTEXT,
/* Restarts RetroArch. */
CMD_EVENT_RESTART_RETROARCH,
/* Shutdown the OS */
CMD_EVENT_SHUTDOWN,
/* Reboot the OS */
CMD_EVENT_REBOOT,
/* Resume RetroArch when in menu. */
CMD_EVENT_RESUME,
/* Toggles pause. */
CMD_EVENT_PAUSE_TOGGLE,
/* Pauses RetroArch. */
CMD_EVENT_UNPAUSE,
/* Unpauses retroArch. */
CMD_EVENT_PAUSE,
CMD_EVENT_PAUSE_CHECKS,
CMD_EVENT_MENU_SAVE_CURRENT_CONFIG,
CMD_EVENT_MENU_SAVE_CONFIG,
CMD_EVENT_MENU_PAUSE_LIBRETRO,
/* Toggles menu on/off. */
CMD_EVENT_MENU_TOGGLE,
CMD_EVENT_MENU_REFRESH,
/* Applies shader changes. */
CMD_EVENT_SHADERS_APPLY_CHANGES,
/* Initializes shader directory. */
CMD_EVENT_SHADER_DIR_INIT,
/* Deinitializes shader directory. */
CMD_EVENT_SHADER_DIR_DEINIT,
/* Initializes controllers. */
CMD_EVENT_CONTROLLERS_INIT,
CMD_EVENT_SAVEFILES,
/* Initializes savefiles. */
CMD_EVENT_SAVEFILES_INIT,
/* Deinitializes savefiles. */
CMD_EVENT_SAVEFILES_DEINIT,
/* Initializes cheats. */
CMD_EVENT_CHEATS_INIT,
/* Deinitializes cheats. */
CMD_EVENT_CHEATS_DEINIT,
/* Apply cheats. */
CMD_EVENT_CHEATS_APPLY,
/* Deinitializes network system. */
CMD_EVENT_NETWORK_DEINIT,
/* Initializes network system. */
CMD_EVENT_NETWORK_INIT,
/* Initializes netplay system. */
CMD_EVENT_NETPLAY_INIT,
/* Deinitializes netplay system. */
CMD_EVENT_NETPLAY_DEINIT,
/* Flip netplay players. */
CMD_EVENT_NETPLAY_FLIP_PLAYERS,
/* Initializes BSV movie. */
CMD_EVENT_BSV_MOVIE_INIT,
/* Deinitializes BSV movie. */
CMD_EVENT_BSV_MOVIE_DEINIT,
/* Initializes command interface. */
CMD_EVENT_COMMAND_INIT,
/* Deinitialize command interface. */
CMD_EVENT_COMMAND_DEINIT,
/* Initializes remote gamepad interface. */
CMD_EVENT_REMOTE_INIT,
/* Deinitializes remote gamepad interface. */
CMD_EVENT_REMOTE_DEINIT,
/* Reinitializes audio driver. */
CMD_EVENT_AUDIO_REINIT,
/* Resizes windowed scale. Will reinitialize video driver. */
CMD_EVENT_RESIZE_WINDOWED_SCALE,
/* Deinitializes temporary content. */
CMD_EVENT_TEMPORARY_CONTENT_DEINIT,
CMD_EVENT_SUBSYSTEM_FULLPATHS_DEINIT,
CMD_EVENT_LOG_FILE_DEINIT,
/* Toggles disk eject. */
CMD_EVENT_DISK_EJECT_TOGGLE,
/* Cycle to next disk. */
CMD_EVENT_DISK_NEXT,
/* Cycle to previous disk. */
CMD_EVENT_DISK_PREV,
/* Appends disk image to disk image list. */
CMD_EVENT_DISK_APPEND_IMAGE,
/* Stops rumbling. */
CMD_EVENT_RUMBLE_STOP,
/* Toggles mouse grab. */
CMD_EVENT_GRAB_MOUSE_TOGGLE,
/* Toggles fullscreen mode. */
CMD_EVENT_FULLSCREEN_TOGGLE,
CMD_EVENT_PERFCNT_REPORT_FRONTEND_LOG,
CMD_EVENT_VOLUME_UP,
CMD_EVENT_VOLUME_DOWN,
CMD_EVENT_EXEC
};
typedef struct rarch_cmd rarch_cmd_t;
#ifdef HAVE_COMMAND
#if defined(HAVE_NETWORK_CMD) && defined(HAVE_NETPLAY)
bool command_network_send(const char *cmd_);
#endif
#endif
typedef struct rarch_cmd_handle
{
rarch_cmd_t *handle;
unsigned id;
} rarch_cmd_handle_t;
bool command_network_new(
command_t *handle,
bool stdin_enable,
bool network_enable,
uint16_t port);
rarch_cmd_t *rarch_cmd_new(bool stdin_enable,
bool network_enable, uint16_t port);
command_t *command_new(bool local_enable);
bool rarch_cmd_ctl(enum rarch_cmd_ctl_state state, void *data);
bool command_poll(command_t *handle);
bool command_get(command_handle_t *handle);
bool command_set(command_handle_t *handle);
bool command_free(command_t *handle);
/**
* command_event:
* @cmd : Command index.
*
* Performs RetroArch command with index @cmd.
*
* Returns: true (1) on success, otherwise false (0).
**/
bool command_event(enum event_command action, void *data);
#ifdef __cplusplus
}

File diff suppressed because it is too large Load Diff

View File

@ -1,225 +0,0 @@
/* RetroArch - A frontend for libretro.
* Copyright (C) 2011-2016 - Daniel De Matteis
*
* RetroArch is free software: you can redistribute it and/or modify it under the terms
* of the GNU General Public License as published by the Free Software Found-
* ation, either version 3 of the License, or (at your option) any later version.
*
* RetroArch is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
* PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with RetroArch.
* If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef COMMAND_EVENT_H__
#define COMMAND_EVENT_H__
#include <stdint.h>
#include <boolean.h>
#ifdef __cplusplus
extern "C" {
#endif
enum event_command
{
EVENT_CMD_NONE = 0,
/* Resets RetroArch. */
EVENT_CMD_RESET,
/* Loads content file. */
EVENT_CMD_LOAD_CONTENT,
EVENT_CMD_LOAD_CONTENT_PERSIST,
#ifdef HAVE_FFMPEG
EVENT_CMD_LOAD_CONTENT_FFMPEG,
#endif
EVENT_CMD_LOAD_CONTENT_IMAGEVIEWER,
EVENT_CMD_SET_PER_GAME_RESOLUTION,
EVENT_CMD_SET_FRAME_LIMIT,
/* Loads core. */
EVENT_CMD_LOAD_CORE_DEINIT,
EVENT_CMD_LOAD_CORE,
EVENT_CMD_LOAD_CORE_PERSIST,
EVENT_CMD_UNLOAD_CORE,
EVENT_CMD_LOAD_STATE,
EVENT_CMD_SAVE_STATE,
EVENT_CMD_SAVE_STATE_DECREMENT,
EVENT_CMD_SAVE_STATE_INCREMENT,
/* Takes screenshot. */
EVENT_CMD_TAKE_SCREENSHOT,
/* Quits RetroArch. */
EVENT_CMD_QUIT,
/* Reinitialize all drivers. */
EVENT_CMD_REINIT,
/* Toggles cheevos hardcore mode. */
EVENT_CMD_CHEEVOS_HARDCORE_MODE_TOGGLE,
/* Deinitialize rewind. */
EVENT_CMD_REWIND_DEINIT,
/* Initializes rewind. */
EVENT_CMD_REWIND_INIT,
/* Toggles rewind. */
EVENT_CMD_REWIND_TOGGLE,
/* Deinitializes autosave. */
EVENT_CMD_AUTOSAVE_DEINIT,
/* Initializes autosave. */
EVENT_CMD_AUTOSAVE_INIT,
EVENT_CMD_AUTOSAVE_STATE,
/* Stops audio. */
EVENT_CMD_AUDIO_STOP,
/* Starts audio. */
EVENT_CMD_AUDIO_START,
/* Mutes audio. */
EVENT_CMD_AUDIO_MUTE_TOGGLE,
/* Initializes overlay. */
EVENT_CMD_OVERLAY_INIT,
/* Deinitializes overlay. */
EVENT_CMD_OVERLAY_DEINIT,
/* Sets current scale factor for overlay. */
EVENT_CMD_OVERLAY_SET_SCALE_FACTOR,
/* Sets current alpha modulation for overlay. */
EVENT_CMD_OVERLAY_SET_ALPHA_MOD,
/* Cycle to next overlay. */
EVENT_CMD_OVERLAY_NEXT,
/* Deinitializes overlay. */
EVENT_CMD_DSP_FILTER_INIT,
/* Deinitializes graphics filter. */
EVENT_CMD_DSP_FILTER_DEINIT,
/* Deinitializes GPU recoring. */
EVENT_CMD_GPU_RECORD_DEINIT,
/* Initializes recording system. */
EVENT_CMD_RECORD_INIT,
/* Deinitializes recording system. */
EVENT_CMD_RECORD_DEINIT,
/* Deinitializes history playlist. */
EVENT_CMD_HISTORY_DEINIT,
/* Initializes history playlist. */
EVENT_CMD_HISTORY_INIT,
/* Deinitializes core information. */
EVENT_CMD_CORE_INFO_DEINIT,
/* Initializes core information. */
EVENT_CMD_CORE_INFO_INIT,
/* Deinitializes core. */
EVENT_CMD_CORE_DEINIT,
/* Initializes core. */
EVENT_CMD_CORE_INIT,
/* Set audio blocking state. */
EVENT_CMD_AUDIO_SET_BLOCKING_STATE,
/* Set audio nonblocking state. */
EVENT_CMD_AUDIO_SET_NONBLOCKING_STATE,
/* Apply video state changes. */
EVENT_CMD_VIDEO_APPLY_STATE_CHANGES,
/* Set video blocking state. */
EVENT_CMD_VIDEO_SET_BLOCKING_STATE,
/* Set video nonblocking state. */
EVENT_CMD_VIDEO_SET_NONBLOCKING_STATE,
/* Sets current aspect ratio index. */
EVENT_CMD_VIDEO_SET_ASPECT_RATIO,
EVENT_CMD_RESET_CONTEXT,
/* Restarts RetroArch. */
EVENT_CMD_RESTART_RETROARCH,
/* Force-quit RetroArch. */
EVENT_CMD_QUIT_RETROARCH,
/* Shutdown the OS */
EVENT_CMD_SHUTDOWN,
/* Reboot the OS */
EVENT_CMD_REBOOT,
/* Resume RetroArch when in menu. */
EVENT_CMD_RESUME,
/* Toggles pause. */
EVENT_CMD_PAUSE_TOGGLE,
/* Pauses RetroArch. */
EVENT_CMD_UNPAUSE,
/* Unpauses retroArch. */
EVENT_CMD_PAUSE,
EVENT_CMD_PAUSE_CHECKS,
EVENT_CMD_MENU_SAVE_CURRENT_CONFIG,
EVENT_CMD_MENU_SAVE_CONFIG,
EVENT_CMD_MENU_PAUSE_LIBRETRO,
/* Toggles menu on/off. */
EVENT_CMD_MENU_TOGGLE,
EVENT_CMD_MENU_REFRESH,
/* Applies shader changes. */
EVENT_CMD_SHADERS_APPLY_CHANGES,
/* Initializes shader directory. */
EVENT_CMD_SHADER_DIR_INIT,
/* Deinitializes shader directory. */
EVENT_CMD_SHADER_DIR_DEINIT,
/* Initializes controllers. */
EVENT_CMD_CONTROLLERS_INIT,
EVENT_CMD_SAVEFILES,
/* Initializes savefiles. */
EVENT_CMD_SAVEFILES_INIT,
/* Deinitializes savefiles. */
EVENT_CMD_SAVEFILES_DEINIT,
/* Initializes cheats. */
EVENT_CMD_CHEATS_INIT,
/* Deinitializes cheats. */
EVENT_CMD_CHEATS_DEINIT,
/* Apply cheats. */
EVENT_CMD_CHEATS_APPLY,
/* Deinitializes network system. */
EVENT_CMD_NETWORK_DEINIT,
/* Initializes network system. */
EVENT_CMD_NETWORK_INIT,
/* Initializes netplay system. */
EVENT_CMD_NETPLAY_INIT,
/* Deinitializes netplay system. */
EVENT_CMD_NETPLAY_DEINIT,
/* Flip netplay players. */
EVENT_CMD_NETPLAY_FLIP_PLAYERS,
/* Initializes BSV movie. */
EVENT_CMD_BSV_MOVIE_INIT,
/* Deinitializes BSV movie. */
EVENT_CMD_BSV_MOVIE_DEINIT,
/* Initializes command interface. */
EVENT_CMD_COMMAND_INIT,
/* Deinitialize command interface. */
EVENT_CMD_COMMAND_DEINIT,
/* Initializes remote gamepad interface. */
EVENT_CMD_REMOTE_INIT,
/* Deinitializes remote gamepad interface. */
EVENT_CMD_REMOTE_DEINIT,
/* Reinitializes audio driver. */
EVENT_CMD_AUDIO_REINIT,
/* Resizes windowed scale. Will reinitialize video driver. */
EVENT_CMD_RESIZE_WINDOWED_SCALE,
/* Deinitializes temporary content. */
EVENT_CMD_TEMPORARY_CONTENT_DEINIT,
EVENT_CMD_SUBSYSTEM_FULLPATHS_DEINIT,
EVENT_CMD_LOG_FILE_DEINIT,
/* Toggles disk eject. */
EVENT_CMD_DISK_EJECT_TOGGLE,
/* Cycle to next disk. */
EVENT_CMD_DISK_NEXT,
/* Cycle to previous disk. */
EVENT_CMD_DISK_PREV,
/* Appends disk image to disk image list. */
EVENT_CMD_DISK_APPEND_IMAGE,
/* Stops rumbling. */
EVENT_CMD_RUMBLE_STOP,
/* Toggles mouse grab. */
EVENT_CMD_GRAB_MOUSE_TOGGLE,
/* Toggles fullscreen mode. */
EVENT_CMD_FULLSCREEN_TOGGLE,
EVENT_CMD_PERFCNT_REPORT_FRONTEND_LOG,
EVENT_CMD_VOLUME_UP,
EVENT_CMD_VOLUME_DOWN,
EVENT_CMD_EXEC
};
/**
* event_command:
* @cmd : Command index.
*
* Performs RetroArch command with index @cmd.
*
* Returns: true (1) on success, otherwise false (0).
**/
bool event_cmd_ctl(enum event_command action, void *data);
#ifdef __cplusplus
}
#endif
#endif

View File

@ -512,13 +512,19 @@ static bool default_block_config_read = true;
static unsigned xmb_scale_factor = 100;
static unsigned xmb_alpha_factor = 75;
static unsigned xmb_theme = 0;
static unsigned xmb_gradient = 0;
static bool xmb_shadows_enable = false;
#if defined(HAVE_OPENGLES2)
static unsigned xmb_ribbon_enable = 1;
#ifdef HAVE_LAKKA
static bool xmb_shadows_enable = false;
#else
static unsigned xmb_ribbon_enable = 0;
static bool xmb_shadows_enable = true;
#endif
static unsigned menu_background_gradient = 4;
#if defined(HAVE_OPENGLES2) || defined(OSX_PPC)
static unsigned menu_shader_pipeline = 1;
#else
static unsigned menu_shader_pipeline = 2;
#endif
static bool show_advanced_settings = true;
@ -774,6 +780,8 @@ static const unsigned input_max_users = 5;
static const unsigned input_poll_type_behavior = 2;
static const unsigned menu_thumbnails_default = 3;
#ifdef IOS
static const bool ui_companion_start_on_boot = false;
#else

View File

@ -24,6 +24,7 @@
#include <retro_assert.h>
#include <string/stdstring.h>
#include "file_path_special.h"
#include "audio/audio_driver.h"
#include "configuration.h"
#include "config.def.h"
@ -32,7 +33,7 @@
#include "input/input_remapping.h"
#include "defaults.h"
#include "general.h"
#include "libretro_version_1.h"
#include "core.h"
#include "retroarch.h"
#include "system.h"
#include "verbosity.h"
@ -485,9 +486,9 @@ static void config_set_defaults(void)
settings->menu.xmb_scale_factor = xmb_scale_factor;
settings->menu.xmb_alpha_factor = xmb_alpha_factor;
settings->menu.xmb_theme = xmb_theme;
settings->menu.xmb_gradient = xmb_gradient;
settings->menu.background_gradient= menu_background_gradient;
settings->menu.xmb_shadows_enable = xmb_shadows_enable;
settings->menu.xmb_ribbon_enable = xmb_ribbon_enable;
settings->menu.shader_pipeline = menu_shader_pipeline;
settings->menu.xmb_font[0] = '\0';
settings->menu.throttle_framerate = true;
settings->menu.linear_filter = true;
@ -621,7 +622,7 @@ static void config_set_defaults(void)
settings->menu.timedate_enable = true;
settings->menu.core_enable = true;
settings->menu.dynamic_wallpaper_enable = false;
settings->menu.thumbnails = 0;
settings->menu.thumbnails = menu_thumbnails_default;
settings->menu.show_advanced_settings = show_advanced_settings;
settings->menu.entry_normal_color = menu_entry_normal_color;
settings->menu.entry_hover_color = menu_entry_hover_color;
@ -719,7 +720,7 @@ static void config_set_defaults(void)
settings->set_supports_no_game_enable = true;
video_driver_ctl(RARCH_DISPLAY_CTL_RESET_CUSTOM_VIEWPORT, NULL);
video_driver_reset_custom_viewport();
/* Make sure settings from other configs carry over into defaults
* for another config. */
@ -802,7 +803,7 @@ static void config_set_defaults(void)
global->console.sound.system_bgm_enable = false;
video_driver_ctl(RARCH_DISPLAY_CTL_DEFAULT_SETTINGS, NULL);
video_driver_default_settings();
if (*g_defaults.dir.wallpapers)
strlcpy(settings->directory.dynamic_wallpapers,
@ -950,19 +951,10 @@ static void config_set_defaults(void)
**/
static config_file_t *open_default_config_file(void)
{
char application_data[PATH_MAX_LENGTH];
char conf_path[PATH_MAX_LENGTH] = {0};
char app_path[PATH_MAX_LENGTH] = {0};
const char *xdg = NULL;
const char *home = NULL;
config_file_t *conf = NULL;
bool saved = false;
global_t *global = global_get_ptr();
(void)conf_path;
(void)app_path;
(void)saved;
(void)xdg;
(void)home;
#if defined(_WIN32) && !defined(_XBOX)
fill_pathname_application_path(app_path, sizeof(app_path));
@ -973,11 +965,10 @@ static config_file_t *open_default_config_file(void)
if (!conf)
{
const char *appdata = getenv("APPDATA");
if (appdata)
if (fill_pathname_application_data(application_data,
sizeof(application_data)))
{
fill_pathname_join(conf_path, appdata,
fill_pathname_join(conf_path, application_data,
"retroarch.cfg", sizeof(conf_path));
conf = config_file_new(conf_path);
}
@ -985,9 +976,12 @@ static config_file_t *open_default_config_file(void)
if (!conf)
{
bool saved = false;
/* Try to create a new config file. */
conf = config_file_new(NULL);
if (conf)
{
/* Since this is a clean config file, we can
@ -1010,21 +1004,20 @@ static config_file_t *open_default_config_file(void)
RARCH_WARN("Created new config file in: \"%s\".\n", conf_path);
}
#elif defined(OSX)
home = getenv("HOME");
if (!home)
if (!fill_pathname_application_data(application_data,
sizeof(application_data)))
return NULL;
fill_pathname_join(conf_path, home,
"Library/Application Support/RetroArch", sizeof(conf_path));
path_mkdir(conf_path);
path_mkdir(application_data);
fill_pathname_join(conf_path, conf_path,
fill_pathname_join(conf_path, application_data,
"retroarch.cfg", sizeof(conf_path));
conf = config_file_new(conf_path);
if (!conf)
{
bool saved = false;
conf = config_file_new(NULL);
if (conf)
@ -1045,63 +1038,42 @@ static config_file_t *open_default_config_file(void)
RARCH_WARN("Created new config file in: \"%s\".\n", conf_path);
}
#elif !defined(__CELLOS_LV2__) && !defined(_XBOX)
xdg = getenv("XDG_CONFIG_HOME");
home = getenv("HOME");
#elif !defined(RARCH_CONSOLE)
bool has_application_data = fill_pathname_application_data(application_data,
sizeof(application_data));
/* XDG_CONFIG_HOME falls back to $HOME/.config. */
if (xdg)
fill_pathname_join(conf_path, xdg,
"retroarch/retroarch.cfg", sizeof(conf_path));
else if (home)
#ifdef __HAIKU__
fill_pathname_join(conf_path, home,
"config/settings/retroarch/retroarch.cfg", sizeof(conf_path));
#else
fill_pathname_join(conf_path, home,
".config/retroarch/retroarch.cfg", sizeof(conf_path));
#endif
if (xdg || home)
if (has_application_data)
{
fill_pathname_join(conf_path, application_data,
"retroarch.cfg", sizeof(conf_path));
RARCH_LOG("Looking for config in: \"%s\".\n", conf_path);
conf = config_file_new(conf_path);
}
/* Fallback to $HOME/.retroarch.cfg. */
if (!conf && home)
if (!conf && getenv("HOME"))
{
fill_pathname_join(conf_path, home,
fill_pathname_join(conf_path, getenv("HOME"),
".retroarch.cfg", sizeof(conf_path));
RARCH_LOG("Looking for config in: \"%s\".\n", conf_path);
conf = config_file_new(conf_path);
}
if (!conf)
{
if (home || xdg)
if (!conf && has_application_data)
{
char basedir[PATH_MAX_LENGTH] = {0};
/* Try to create a new config file. */
/* XDG_CONFIG_HOME falls back to $HOME/.config. */
if (xdg)
fill_pathname_join(conf_path, xdg,
"retroarch/retroarch.cfg", sizeof(conf_path));
else if (home)
#ifdef __HAIKU__
fill_pathname_join(conf_path, home,
"config/settings/retroarch/retroarch.cfg", sizeof(conf_path));
#else
fill_pathname_join(conf_path, home,
".config/retroarch/retroarch.cfg", sizeof(conf_path));
#endif
strlcpy(conf_path, application_data, sizeof(conf_path));
fill_pathname_basedir(basedir, conf_path, sizeof(basedir));
fill_pathname_join(conf_path, conf_path, "retroarch.cfg", sizeof(conf_path));
if (path_mkdir(basedir))
{
bool saved = false;
char skeleton_conf[PATH_MAX_LENGTH] = {0};
fill_pathname_join(skeleton_conf, GLOBAL_CONFIG_DIR,
@ -1131,18 +1103,22 @@ static config_file_t *open_default_config_file(void)
RARCH_WARN("Config: Created new config file in: \"%s\".\n", conf_path);
}
}
}
#endif
if (!conf)
return NULL;
strlcpy(global->path.config, conf_path,
sizeof(global->path.config));
(void)application_data;
(void)conf_path;
(void)app_path;
if (conf)
{
global_t *global = global_get_ptr();
strlcpy(global->path.config, conf_path, sizeof(global->path.config));
return conf;
}
return NULL;
}
static void read_keybinds_keyboard(config_file_t *conf, unsigned user,
unsigned idx, struct retro_keybind *bind)
{
@ -1430,7 +1406,7 @@ static bool config_load_file(const char *path, bool set_defaults)
* important that it works for consoles right now */
config_get_bool(conf, "custom_bgm_enable",
&global->console.sound.system_bgm_enable);
video_driver_ctl(RARCH_DISPLAY_CTL_LOAD_SETTINGS, conf);
video_driver_load_settings(conf);
#endif
CONFIG_GET_INT_BASE(conf, settings, state_slot, "state_slot");
@ -1549,9 +1525,9 @@ static bool config_load_file(const char *path, bool set_defaults)
CONFIG_GET_INT_BASE(conf, settings, menu.xmb_scale_factor, "xmb_scale_factor");
CONFIG_GET_INT_BASE(conf, settings, menu.xmb_alpha_factor, "xmb_alpha_factor");
CONFIG_GET_INT_BASE(conf, settings, menu.xmb_theme, "xmb_theme");
CONFIG_GET_INT_BASE(conf, settings, menu.xmb_gradient, "xmb_gradient");
CONFIG_GET_INT_BASE(conf, settings, menu.background_gradient, "menu_background_gradient");
CONFIG_GET_BOOL_BASE(conf, settings, menu.xmb_shadows_enable, "xmb_shadows_enable");
CONFIG_GET_INT_BASE(conf, settings, menu.xmb_ribbon_enable, "xmb_ribbon_enable");
CONFIG_GET_INT_BASE(conf, settings, menu.shader_pipeline, "menu_shader_pipeline");
config_get_path(conf, "xmb_font", settings->menu.xmb_font, sizeof(settings->menu.xmb_font));
#endif
config_get_array(conf, "video_context_driver", settings->video.context_driver, sizeof(settings->video.context_driver));
@ -2444,7 +2420,7 @@ void config_load(void)
config_save_file(global->path.core_specific_config);
/* Flush out some states that could have been set by core environment variables */
core_ctl(CORE_CTL_UNSET_INPUT_DESCRIPTORS, NULL);
core_unset_input_descriptors();
if (!rarch_ctl(RARCH_CTL_IS_BLOCK_CONFIG_READ, NULL))
{
@ -2817,9 +2793,9 @@ bool config_save_file(const char *path)
config_set_int(conf, "xmb_scale_factor", settings->menu.xmb_scale_factor);
config_set_int(conf, "xmb_alpha_factor", settings->menu.xmb_alpha_factor);
config_set_int(conf, "xmb_theme", settings->menu.xmb_theme);
config_set_int(conf, "xmb_gradient", settings->menu.xmb_gradient);
config_set_int(conf, "menu_background_gradient", settings->menu.background_gradient);
config_set_bool(conf, "xmb_shadows_enable", settings->menu.xmb_shadows_enable);
config_set_int(conf, "xmb_ribbon_enable", settings->menu.xmb_ribbon_enable);
config_set_int(conf, "menu_shader_pipeline", settings->menu.shader_pipeline);
config_set_path(conf, "xmb_font",
!string_is_empty(settings->menu.xmb_font) ? settings->menu.xmb_font : "");
config_set_bool(conf, "rgui_show_start_screen",
@ -2870,7 +2846,7 @@ bool config_save_file(const char *path)
config_set_int(conf, "custom_viewport_y",
settings->video_viewport_custom.y);
video_driver_ctl(RARCH_DISPLAY_CTL_SAVE_SETTINGS, conf);
video_driver_save_settings(conf);
config_set_float(conf, "video_font_size", settings->video.font_size);

View File

@ -161,9 +161,9 @@ typedef struct settings
unsigned xmb_scale_factor;
unsigned xmb_alpha_factor;
unsigned xmb_theme;
unsigned xmb_gradient;
unsigned background_gradient;
bool xmb_shadows_enable;
unsigned xmb_ribbon_enable;
unsigned shader_pipeline;
char xmb_font[PATH_MAX_LENGTH];
bool throttle_framerate;
bool linear_filter;

214
content.c
View File

@ -61,8 +61,9 @@
#include "patch.h"
#include "system.h"
#include "retroarch.h"
#include "command_event.h"
#include "libretro_version_1.h"
#include "command.h"
#include "file_path_special.h"
#include "core.h"
#include "verbosity.h"
#ifdef HAVE_7ZIP
@ -89,6 +90,20 @@ struct sram_block
size_t size;
};
typedef struct content_stream
{
uint32_t a;
const uint8_t *b;
size_t c;
uint32_t crc;
} content_stream_t;
static const struct file_archive_file_backend *stream_backend = NULL;
static struct string_list *temporary_content = NULL;
static bool _content_is_inited = false;
static bool core_does_not_need_content = false;
static uint32_t content_crc = 0;
#ifdef HAVE_COMPRESSION
#ifdef HAVE_7ZIP
@ -848,9 +863,10 @@ static void content_load_init_wrap(
* If no content file can be loaded, will start up RetroArch
* as-is.
*
* Returns: false (0) if rarch_main_init failed, otherwise true (1).
* Returns: false (0) if retroarch_main_init failed,
* otherwise true (1).
**/
static bool content_load(content_ctx_info_t *info)
bool content_load(content_ctx_info_t *info)
{
unsigned i;
bool retval = true;
@ -884,7 +900,7 @@ static bool content_load(content_ctx_info_t *info)
wrap_args->argc = *rarch_argc_ptr;
wrap_args->argv = rarch_argv_ptr;
if (!rarch_ctl(RARCH_CTL_MAIN_INIT, wrap_args))
if (!retroarch_main_init(wrap_args->argc, wrap_args->argv))
{
retval = false;
goto error;
@ -893,9 +909,9 @@ static bool content_load(content_ctx_info_t *info)
#ifdef HAVE_MENU
menu_driver_ctl(RARCH_MENU_CTL_SHADER_MANAGER_INIT, NULL);
#endif
event_cmd_ctl(EVENT_CMD_HISTORY_INIT, NULL);
event_cmd_ctl(EVENT_CMD_RESUME, NULL);
event_cmd_ctl(EVENT_CMD_VIDEO_SET_ASPECT_RATIO, NULL);
command_event(CMD_EVENT_HISTORY_INIT, NULL);
command_event(CMD_EVENT_RESUME, NULL);
command_event(CMD_EVENT_VIDEO_SET_ASPECT_RATIO, NULL);
check_default_dirs();
@ -947,17 +963,18 @@ static bool read_content_file(unsigned i, const char *path, void **buf,
patch_content(&ret_buf, length);
#ifdef HAVE_ZLIB
content_ctl(CONTENT_CTL_GET_CRC, &content_crc_ptr);
content_get_crc(&content_crc_ptr);
stream_info.a = 0;
stream_info.b = ret_buf;
stream_info.c = *length;
content_ctl(CONTENT_CTL_STREAM_CRC_CALCULATE, &stream_info);
if (!stream_backend)
stream_backend = file_archive_get_default_file_backend();
stream_info.crc = stream_backend->stream_crc_calculate(
stream_info.a, stream_info.b, stream_info.c);
*content_crc_ptr = stream_info.crc;
RARCH_LOG("CRC32: 0x%x .\n", (unsigned)*content_crc_ptr);
#endif
*buf = ret_buf;
@ -978,19 +995,15 @@ static bool dump_to_file_desperate(const void *data,
{
time_t time_;
char timebuf[256];
char application_data[PATH_MAX_LENGTH];
char path[PATH_MAX_LENGTH];
#if defined(_WIN32) && !defined(_XBOX)
const char *base = getenv("APPDATA");
#elif defined(__CELLOS_LV2__) || defined(_XBOX)
const char *base = NULL;
#else
const char *base = getenv("HOME");
#endif
if (!base)
if (!fill_pathname_application_data(application_data,
sizeof(application_data)))
return false;
snprintf(path, sizeof(path), "%s/RetroArch-recovery-%u", base, type);
snprintf(path, sizeof(path), "%s/RetroArch-recovery-%u",
application_data, type);
time(&time_);
@ -1013,14 +1026,14 @@ static bool dump_to_file_desperate(const void *data,
*
* Returns: true if successful, false otherwise.
**/
static bool content_save_state(const char *path)
bool content_save_state(const char *path)
{
retro_ctx_serialize_info_t serial_info;
retro_ctx_size_info_t info;
bool ret = false;
void *data = NULL;
core_ctl(CORE_CTL_RETRO_SERIALIZE_SIZE, &info);
core_serialize_size(&info);
RARCH_LOG("%s: \"%s\".\n",
msg_hash_to_str(MSG_SAVING_STATE),
@ -1041,7 +1054,7 @@ static bool content_save_state(const char *path)
serial_info.data = data;
serial_info.size = info.size;
ret = core_ctl(CORE_CTL_RETRO_SERIALIZE, &serial_info);
ret = core_serialize(&serial_info);
if (ret)
ret = filestream_write_file(path, data, info.size);
@ -1065,7 +1078,7 @@ static bool content_save_state(const char *path)
*
* Returns: true if successful, false otherwise.
**/
static bool content_load_state(const char *path)
bool content_load_state(const char *path)
{
unsigned i;
ssize_t size;
@ -1111,7 +1124,7 @@ static bool content_load_state(const char *path)
retro_ctx_memory_info_t mem_info;
mem_info.id = blocks[i].type;
core_ctl(CORE_CTL_RETRO_GET_MEMORY, &mem_info);
core_get_memory(&mem_info);
blocks[i].size = mem_info.size;
}
@ -1130,7 +1143,7 @@ static bool content_load_state(const char *path)
mem_info.id = blocks[i].type;
core_ctl(CORE_CTL_RETRO_GET_MEMORY, &mem_info);
core_get_memory(&mem_info);
ptr = mem_info.data;
if (ptr)
@ -1140,7 +1153,7 @@ static bool content_load_state(const char *path)
serial_info.data_const = buf;
serial_info.size = size;
ret = core_ctl(CORE_CTL_RETRO_UNSERIALIZE, &serial_info);
ret = core_unserialize(&serial_info);
/* Flush back. */
for (i = 0; i < num_blocks; i++)
@ -1152,7 +1165,7 @@ static bool content_load_state(const char *path)
mem_info.id = blocks[i].type;
core_ctl(CORE_CTL_RETRO_GET_MEMORY, &mem_info);
core_get_memory(&mem_info);
ptr = mem_info.data;
if (ptr)
@ -1178,25 +1191,24 @@ error:
}
/**
* load_ram_file:
* content_load_ram_file:
* @path : path of RAM state that will be loaded from.
* @type : type of memory
*
* Load a RAM state from disk to memory.
*/
static bool load_ram_file(void *data)
bool content_load_ram_file(ram_type_t *ram)
{
ssize_t rc;
retro_ctx_memory_info_t mem_info;
void *buf = NULL;
ram_type_t *ram = (ram_type_t*)data;
if (!ram)
return false;
mem_info.id = ram->type;
core_ctl(CORE_CTL_RETRO_GET_MEMORY, &mem_info);
core_get_memory(&mem_info);
if (mem_info.size == 0 || !mem_info.data)
return false;
@ -1226,14 +1238,14 @@ static bool load_ram_file(void *data)
}
/**
* save_ram_file:
* content_save_ram_file:
* @path : path of RAM state that shall be written to.
* @type : type of memory
*
* Save a RAM state from memory to disk.
*
*/
static bool save_ram_file(ram_type_t *ram)
bool content_save_ram_file(ram_type_t *ram)
{
retro_ctx_memory_info_t mem_info;
@ -1242,7 +1254,7 @@ static bool save_ram_file(ram_type_t *ram)
mem_info.id = ram->type;
core_ctl(CORE_CTL_RETRO_GET_MEMORY, &mem_info);
core_get_memory(&mem_info);
if (!mem_info.data || mem_info.size == 0)
return false;
@ -1433,7 +1445,7 @@ static bool load_content(
load_info.special = special;
load_info.info = info;
if (!core_ctl(CORE_CTL_RETRO_LOAD_GAME, &load_info))
if (!core_load_game(&load_info))
{
RARCH_ERR("%s.\n", msg_hash_to_str(MSG_FAILED_TO_LOAD_CONTENT));
return false;
@ -1444,11 +1456,11 @@ static bool load_content(
{
const void *load_data = NULL;
cheevos_ctl(CHEEVOS_CTL_SET_CHEATS, NULL);
cheevos_set_cheats();
if (*content->elems[0].data)
load_data = info;
cheevos_ctl(CHEEVOS_CTL_LOAD, (void*)load_data);
cheevos_load(load_data);
}
#endif
@ -1594,9 +1606,9 @@ static bool init_content_file_set_attribs(
attr.i = system->info.block_extract;
attr.i |= system->info.need_fullpath << 1;
attr.i |= (!content_ctl(CONTENT_CTL_DOES_NOT_NEED_CONTENT, NULL)) << 2;
attr.i |= (!content_does_not_need_content()) << 2;
if (content_ctl(CONTENT_CTL_DOES_NOT_NEED_CONTENT, NULL)
if (content_does_not_need_content()
&& settings->set_supports_no_game_enable)
string_list_append(content, "", attr);
else
@ -1697,98 +1709,58 @@ static bool content_file_free(struct string_list *temporary_content)
return true;
}
bool content_ctl(enum content_ctl_state state, void *data)
bool content_does_not_need_content(void)
{
static const struct file_archive_file_backend *stream_backend = NULL;
static struct string_list *temporary_content = NULL;
static bool content_is_inited = false;
static bool core_does_not_need_content = false;
static uint32_t content_crc = 0;
switch(state)
{
case CONTENT_CTL_LOAD_RAM_FILE:
return load_ram_file(data);
case CONTENT_CTL_SAVE_RAM_FILE:
return save_ram_file((ram_type_t*)data);
case CONTENT_CTL_DOES_NOT_NEED_CONTENT:
return core_does_not_need_content;
case CONTENT_CTL_SET_DOES_NOT_NEED_CONTENT:
core_does_not_need_content = true;
break;
case CONTENT_CTL_UNSET_DOES_NOT_NEED_CONTENT:
core_does_not_need_content = false;
break;
case CONTENT_CTL_GET_CRC:
}
void content_set_does_not_need_content(void)
{
core_does_not_need_content = true;
}
void content_unset_does_not_need_content(void)
{
core_does_not_need_content = false;
}
bool content_get_crc(uint32_t **content_crc_ptr)
{
uint32_t **content_crc_ptr = (uint32_t**)data;
if (!content_crc_ptr)
return false;
*content_crc_ptr = &content_crc;
}
break;
case CONTENT_CTL_LOAD_STATE:
{
const char *path = (const char*)data;
if (!path)
return false;
return content_load_state(path);
}
case CONTENT_CTL_SAVE_STATE:
{
const char *path = (const char*)data;
if (!path)
return false;
return content_save_state(path);
}
case CONTENT_CTL_IS_INITED:
return content_is_inited;
case CONTENT_CTL_DEINIT:
content_ctl(CONTENT_CTL_TEMPORARY_FREE, NULL);
content_crc = 0;
content_is_inited = false;
core_does_not_need_content = false;
break;
case CONTENT_CTL_INIT:
content_is_inited = false;
temporary_content = string_list_new();
if (!temporary_content)
return false;
if (content_file_init(temporary_content))
{
content_is_inited = true;
return true;
}
content_ctl(CONTENT_CTL_DEINIT, NULL);
return false;
case CONTENT_CTL_TEMPORARY_FREE:
bool content_is_inited(void)
{
return _content_is_inited;
}
void content_deinit(void)
{
content_file_free(temporary_content);
temporary_content = NULL;
break;
case CONTENT_CTL_STREAM_INIT:
#ifdef HAVE_ZLIB
if (!stream_backend)
stream_backend = file_archive_get_default_file_backend();
#endif
break;
case CONTENT_CTL_STREAM_CRC_CALCULATE:
content_crc = 0;
_content_is_inited = false;
core_does_not_need_content = false;
}
/* Initializes and loads a content file for the currently
* selected libretro core. */
bool content_init(void)
{
content_stream_t *stream = NULL;
content_ctl(CONTENT_CTL_STREAM_INIT, NULL);
temporary_content = string_list_new();
if (!temporary_content)
goto error;
stream = (content_stream_t*)data;
#ifdef HAVE_ZLIB
stream->crc = stream_backend->stream_crc_calculate(
stream->a, stream->b, stream->c);
#endif
}
break;
case CONTENT_CTL_LOAD:
return content_load((content_ctx_info_t*)data);
case CONTENT_CTL_NONE:
default:
break;
}
if (!content_file_init(temporary_content))
goto error;
_content_is_inited = true;
return true;
error:
content_deinit();
return false;
}

View File

@ -30,65 +30,12 @@
extern "C" {
#endif
enum content_ctl_state
{
CONTENT_CTL_NONE = 0,
CONTENT_CTL_IS_INITED,
CONTENT_CTL_DOES_NOT_NEED_CONTENT,
CONTENT_CTL_SET_DOES_NOT_NEED_CONTENT,
CONTENT_CTL_UNSET_DOES_NOT_NEED_CONTENT,
/* Initializes and loads a content file for the currently
* selected libretro core. */
CONTENT_CTL_INIT,
CONTENT_CTL_DEINIT,
/* Loads content file and starts up RetroArch.
* If no content file can be loaded, will start up RetroArch
* as-is. */
CONTENT_CTL_LOAD,
CONTENT_CTL_GET_CRC,
/* Load a RAM state from disk to memory. */
CONTENT_CTL_LOAD_RAM_FILE,
/* Save a RAM state from memory to disk. */
CONTENT_CTL_SAVE_RAM_FILE,
/* Load a state from disk to memory. */
CONTENT_CTL_LOAD_STATE,
/* Save a state from memory to disk. */
CONTENT_CTL_SAVE_STATE,
/* Frees temporary content handle. */
CONTENT_CTL_TEMPORARY_FREE,
CONTENT_CTL_STREAM_INIT,
CONTENT_CTL_STREAM_CRC_CALCULATE
};
typedef struct ram_type
{
const char *path;
int type;
} ram_type_t;
typedef struct content_stream
{
uint32_t a;
const uint8_t *b;
size_t c;
uint32_t crc;
} content_stream_t;
typedef struct content_ctx_info
{
int argc; /* Argument count. */
@ -100,7 +47,38 @@ typedef struct content_ctx_info
void content_push_to_history_playlist(bool do_push,
const char *path, void *data);
bool content_ctl(enum content_ctl_state state, void *data);
/* Load a RAM state from disk to memory. */
bool content_load_ram_file(ram_type_t *ram);
/* Save a RAM state from memory to disk. */
bool content_save_ram_file(ram_type_t *ram);
/* Load a state from disk to memory. */
bool content_load_state(const char *path);
/* Save a state from memory to disk. */
bool content_save_state(const char *path);
/* Loads content file and starts up RetroArch.
* If no content file can be loaded, will start up RetroArch
* as-is. */
bool content_load(content_ctx_info_t *info);
bool content_does_not_need_content(void);
void content_set_does_not_need_content(void);
void content_unset_does_not_need_content(void);
bool content_get_crc(uint32_t **content_crc_ptr);
bool content_is_inited(void);
void content_deinit(void);
/* Initializes and loads a content file for the currently
* selected libretro core. */
bool content_init(void);
#ifdef __cplusplus
}

View File

@ -15,16 +15,17 @@
* If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef _RETRO_IMPLEMENTATION_V1_H
#define _RETRO_IMPLEMENTATION_V1_H
#ifndef _LIBRETRO_CORE_IMPL_H
#define _LIBRETRO_CORE_IMPL_H
#ifdef __cplusplus
extern "C" {
#endif
#include <boolean.h>
#include <libretro.h>
#include "libretro.h"
#include "core_type.h"
enum
{
@ -40,83 +41,6 @@ enum
POLL_TYPE_LATE
};
enum core_ctl_state
{
CORE_CTL_NONE = 0,
CORE_CTL_INIT,
CORE_CTL_DEINIT,
CORE_CTL_SET_CBS,
CORE_CTL_SET_CBS_REWIND,
CORE_CTL_SET_POLL_TYPE,
/* Runs the core for one frame. */
CORE_CTL_RETRO_RUN,
CORE_CTL_RETRO_INIT,
CORE_CTL_RETRO_DEINIT,
CORE_CTL_RETRO_UNLOAD_GAME,
CORE_CTL_RETRO_RESET,
CORE_CTL_RETRO_GET_SYSTEM_AV_INFO,
CORE_CTL_RETRO_CTX_FRAME_CB,
CORE_CTL_RETRO_CTX_POLL_CB,
CORE_CTL_RETRO_SET_ENVIRONMENT,
CORE_CTL_RETRO_SERIALIZE_SIZE,
CORE_CTL_RETRO_SERIALIZE,
CORE_CTL_RETRO_UNSERIALIZE,
CORE_CTL_RETRO_SYMBOLS_INIT,
CORE_CTL_RETRO_CHEAT_SET,
CORE_CTL_RETRO_CHEAT_RESET,
CORE_CTL_RETRO_SET_INPUT_STATE,
CORE_CTL_RETRO_API_VERSION,
/* Compare libretro core API version against API version
* used by RetroArch.
*
* TODO - when libretro v2 gets added, allow for switching
* between libretro version backend dynamically.
*/
CORE_CTL_VERIFY_API_VERSION,
CORE_CTL_RETRO_GET_MEMORY,
/* Initialize system A/V information. */
CORE_CTL_INIT_SYSTEM_AV_INFO,
/* Get system A/V information. */
CORE_CTL_RETRO_GET_SYSTEM_INFO,
CORE_CTL_RETRO_LOAD_GAME,
CORE_CTL_RETRO_SET_CONTROLLER_PORT_DEVICE,
CORE_CTL_HAS_SET_INPUT_DESCRIPTORS,
CORE_CTL_SET_INPUT_DESCRIPTORS,
CORE_CTL_UNSET_INPUT_DESCRIPTORS
};
typedef struct retro_ctx_input_state_info
{
retro_input_state_t cb;
@ -188,7 +112,76 @@ typedef struct retro_callbacks
retro_input_poll_t poll_cb;
} retro_callbacks_t;
bool core_ctl(enum core_ctl_state state, void *data);
bool core_load(void);
bool core_unload(void);
bool core_set_default_callbacks(void *data);
bool core_set_rewind_callbacks(void);
bool core_set_poll_type(unsigned *type);
/* Runs the core for one frame. */
bool core_run(void);
bool core_init(void);
bool core_deinit(void *data);
bool core_unload_game(void);
bool core_reset(void);
bool core_frame(retro_ctx_frame_info_t *info);
bool core_poll(void);
bool core_set_environment(retro_ctx_environ_info_t *info);
bool core_serialize_size(retro_ctx_size_info_t *info);
bool core_serialize(retro_ctx_serialize_info_t *info);
bool core_unserialize(retro_ctx_serialize_info_t *info);
bool core_init_symbols(enum rarch_core_type *type);
bool core_set_cheat(retro_ctx_cheat_info_t *info);
bool core_reset_cheat(void);
bool core_api_version(retro_ctx_api_info_t *api);
/* Compare libretro core API version against API version
* used by RetroArch.
*
* TODO - when libretro v2 gets added, allow for switching
* between libretro version backend dynamically.
*/
bool core_verify_api_version(void);
bool core_get_memory(retro_ctx_memory_info_t *info);
/* Initialize system A/V information. */
bool core_get_system_av_info(struct retro_system_av_info *av_info);
/* Get system A/V information. */
bool core_get_system_info(struct retro_system_info *system);
bool core_load_game(retro_ctx_load_content_info_t *load_info);
bool core_set_controller_port_device(retro_ctx_controller_info_t *pad);
bool core_has_set_input_descriptor(void);
void core_set_input_descriptors(void);
void core_unset_input_descriptors(void);
bool core_uninit_libretro_callbacks(void);
void core_set_input_state(retro_ctx_input_state_info_t *info);
#ifdef __cplusplus
}

405
core_impl.c Normal file
View File

@ -0,0 +1,405 @@
/* RetroArch - A frontend for libretro.
* Copyright (C) 2010-2014 - Hans-Kristian Arntzen
* Copyright (C) 2011-2016 - Daniel De Matteis
* Copyright (C) 2012-2015 - Michael Lelli
*
* RetroArch is free software: you can redistribute it and/or modify it under the terms
* of the GNU General Public License as published by the Free Software Found-
* ation, either version 3 of the License, or (at your option) any later version.
*
* RetroArch is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
* PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with RetroArch.
* If not, see <http://www.gnu.org/licenses/>.
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#include <errno.h>
#include <retro_inline.h>
#include <boolean.h>
#include <lists/string_list.h>
#include <libretro.h>
#include "dynamic.h"
#include "core.h"
#include "general.h"
#include "msg_hash.h"
#include "managers/state_manager.h"
#include "system.h"
#include "gfx/video_driver.h"
#include "audio/audio_driver.h"
#ifdef HAVE_NETPLAY
#include "network/netplay.h"
#endif
static struct retro_core_t core;
static unsigned core_poll_type;
static bool core_input_polled;
static bool core_has_set_input_descriptors = false;
static struct retro_callbacks retro_ctx;
static void core_input_state_poll_maybe(void)
{
if (core_poll_type == POLL_TYPE_NORMAL)
input_poll();
}
static int16_t core_input_state_poll(unsigned port,
unsigned device, unsigned idx, unsigned id)
{
if (core_poll_type == POLL_TYPE_LATE)
{
if (!core_input_polled)
input_poll();
core_input_polled = true;
}
return input_state(port, device, idx, id);
}
void core_set_input_state(retro_ctx_input_state_info_t *info)
{
core.retro_set_input_state(info->cb);
}
/**
* core_init_libretro_cbs:
* @data : pointer to retro_callbacks object
*
* Initializes libretro callbacks, and binds the libretro callbacks
* to default callback functions.
**/
static bool core_init_libretro_cbs(void *data)
{
struct retro_callbacks *cbs = (struct retro_callbacks*)data;
#ifdef HAVE_NETPLAY
global_t *global = global_get_ptr();
#endif
if (!cbs)
return false;
core.retro_set_video_refresh(video_driver_frame);
core.retro_set_audio_sample(audio_driver_sample);
core.retro_set_audio_sample_batch(audio_driver_sample_batch);
core.retro_set_input_state(core_input_state_poll);
core.retro_set_input_poll(core_input_state_poll_maybe);
core_set_default_callbacks(cbs);
#ifdef HAVE_NETPLAY
if (!netplay_driver_ctl(RARCH_NETPLAY_CTL_IS_DATA_INITED, NULL))
return true;
/* Force normal poll type for netplay. */
core_poll_type = POLL_TYPE_NORMAL;
if (global->netplay.is_spectate)
{
core.retro_set_input_state(
(global->netplay.is_client ?
input_state_spectate_client : input_state_spectate)
);
}
else
{
core.retro_set_video_refresh(video_frame_net);
core.retro_set_audio_sample(audio_sample_net);
core.retro_set_audio_sample_batch(audio_sample_batch_net);
core.retro_set_input_state(input_state_net);
}
#endif
return true;
}
/**
* core_set_default_callbacks:
* @data : pointer to retro_callbacks object
*
* Binds the libretro callbacks to default callback functions.
**/
bool core_set_default_callbacks(void *data)
{
struct retro_callbacks *cbs = (struct retro_callbacks*)data;
if (!cbs)
return false;
cbs->frame_cb = video_driver_frame;
cbs->sample_cb = audio_driver_sample;
cbs->sample_batch_cb = audio_driver_sample_batch;
cbs->state_cb = core_input_state_poll;
cbs->poll_cb = input_poll;
return true;
}
bool core_deinit(void *data)
{
struct retro_callbacks *cbs = (struct retro_callbacks*)data;
if (!cbs)
return false;
cbs->frame_cb = NULL;
cbs->sample_cb = NULL;
cbs->sample_batch_cb = NULL;
cbs->state_cb = NULL;
cbs->poll_cb = NULL;
return true;
}
bool core_uninit_libretro_callbacks(void)
{
return core_deinit(&retro_ctx);
}
/**
* core_set_rewind_callbacks:
*
* Sets the audio sampling callbacks based on whether or not
* rewinding is currently activated.
**/
bool core_set_rewind_callbacks(void)
{
if (state_manager_frame_is_reversed())
{
core.retro_set_audio_sample(audio_driver_sample_rewind);
core.retro_set_audio_sample_batch(audio_driver_sample_batch_rewind);
}
else
{
core.retro_set_audio_sample(audio_driver_sample);
core.retro_set_audio_sample_batch(audio_driver_sample_batch);
}
return true;
}
bool core_set_cheat(retro_ctx_cheat_info_t *info)
{
core.retro_cheat_set(info->index, info->enabled, info->code);
return true;
}
bool core_reset_cheat(void)
{
core.retro_cheat_reset();
return true;
}
bool core_api_version(retro_ctx_api_info_t *api)
{
if (!api)
return false;
api->version = core.retro_api_version();
return true;
}
bool core_set_poll_type(unsigned *type)
{
core_poll_type = *type;
return true;
}
bool core_init_symbols(enum rarch_core_type *type)
{
if (!type)
return false;
init_libretro_sym(*type, &core);
return true;
}
bool core_set_controller_port_device(retro_ctx_controller_info_t *pad)
{
if (!pad)
return false;
core.retro_set_controller_port_device(pad->port, pad->device);
return true;
}
bool core_get_memory(retro_ctx_memory_info_t *info)
{
if (!info)
return false;
info->size = core.retro_get_memory_size(info->id);
info->data = core.retro_get_memory_data(info->id);
return true;
}
bool core_load_game(retro_ctx_load_content_info_t *load_info)
{
if (!load_info)
return false;
if (load_info->special)
return core.retro_load_game_special(load_info->special->id, load_info->info, load_info->content->size);
return core.retro_load_game(*load_info->content->elems[0].data ? load_info->info : NULL);
}
bool core_get_system_info(struct retro_system_info *system)
{
if (!system)
return false;
core.retro_get_system_info(system);
return true;
}
bool core_unserialize(retro_ctx_serialize_info_t *info)
{
if (!info)
return false;
if (!core.retro_unserialize(info->data_const, info->size))
return false;
return true;
}
bool core_serialize(retro_ctx_serialize_info_t *info)
{
if (!info)
return false;
if (!core.retro_serialize(info->data, info->size))
return false;
return true;
}
bool core_serialize_size(retro_ctx_size_info_t *info)
{
if (!info)
return false;
info->size = core.retro_serialize_size();
return true;
}
bool core_frame(retro_ctx_frame_info_t *info)
{
if (!info || !retro_ctx.frame_cb)
return false;
retro_ctx.frame_cb(
info->data, info->width, info->height, info->pitch);
return true;
}
bool core_poll(void)
{
if (!retro_ctx.poll_cb)
return false;
retro_ctx.poll_cb();
return true;
}
bool core_set_environment(retro_ctx_environ_info_t *info)
{
if (!info)
return false;
core.retro_set_environment(info->env);
return true;
}
bool core_get_system_av_info(struct retro_system_av_info *av_info)
{
if (!av_info)
return false;
core.retro_get_system_av_info(av_info);
return true;
}
bool core_reset(void)
{
core.retro_reset();
return true;
}
bool core_init(void)
{
core.retro_init();
return true;
}
bool core_unload(void)
{
core.retro_deinit();
uninit_libretro_sym(&core);
return true;
}
bool core_unload_game(void)
{
video_driver_deinit_hw_context();
audio_driver_stop();
core.retro_unload_game();
return true;
}
bool core_run(void)
{
switch (core_poll_type)
{
case POLL_TYPE_EARLY:
input_poll();
break;
case POLL_TYPE_LATE:
core_input_polled = false;
break;
}
if (core.retro_run)
core.retro_run();
if (core_poll_type == POLL_TYPE_LATE && !core_input_polled)
input_poll();
return true;
}
bool core_load(void)
{
settings_t *settings = config_get_ptr();
core_poll_type = settings->input.poll_type_behavior;
if (!core_verify_api_version())
return false;
if (!core_init_libretro_cbs(&retro_ctx))
return false;
core_get_system_av_info(video_viewport_get_system_av_info());
runloop_ctl(RUNLOOP_CTL_SET_FRAME_LIMIT, NULL);
return true;
}
bool core_verify_api_version(void)
{
unsigned api_version = core.retro_api_version();
RARCH_LOG("Version of libretro API: %u\n", api_version);
RARCH_LOG("Compiled against API: %u\n", RETRO_API_VERSION);
if (api_version != RETRO_API_VERSION)
{
RARCH_WARN("%s\n", msg_hash_to_str(MSG_LIBRETRO_ABI_BREAK));
return false;
}
return true;
}
bool core_has_set_input_descriptor(void)
{
return core_has_set_input_descriptors;
}
void core_set_input_descriptors(void)
{
core_has_set_input_descriptors = true;
}
void core_unset_input_descriptors(void)
{
core_has_set_input_descriptors = false;
}

View File

@ -33,6 +33,8 @@
static const char *core_info_tmp_path = NULL;
static const struct string_list *core_info_tmp_list = NULL;
static core_info_t *core_info_current = NULL;
static core_info_list_t *core_info_curr_list = NULL;
static void core_info_list_resolve_all_extensions(
core_info_list_t *core_info_list)
@ -188,57 +190,6 @@ static config_file_t *core_info_list_iterate(
return config_file_new(info_path);
}
void core_info_get_name(const char *path, char *s, size_t len)
{
size_t i;
core_info_t *core_info = NULL;
core_info_list_t *core_info_list = NULL;
struct string_list *contents = dir_list_new_special(
NULL, DIR_LIST_CORES, NULL);
if (!contents)
return;
core_info_list = (core_info_list_t*)calloc(1, sizeof(*core_info_list));
if (!core_info_list)
goto error;
core_info = (core_info_t*)calloc(contents->size, sizeof(*core_info));
if (!core_info)
goto error;
core_info_list->list = core_info;
core_info_list->count = contents->size;
for (i = 0; i < contents->size; i++)
{
config_file_t *conf = NULL;
if (!string_is_equal(contents->elems[i].data, path))
continue;
conf = core_info_list_iterate(contents, i);
if (conf)
{
config_get_string(conf, "corename",
&core_info[i].core_name);
core_info[i].config_data = (void*)conf;
}
core_info[i].path = strdup(contents->elems[i].data);
strlcpy(s, core_info[i].core_name, len);
}
error:
if (contents)
dir_list_free(contents);
contents = NULL;
core_info_list_free(core_info_list);
}
static core_info_list_t *core_info_list_new(void)
{
size_t i;
@ -346,6 +297,370 @@ error:
return NULL;
}
/* Shallow-copies internal state.
*
* Data in *info is invalidated when the
* core_info_list is freed. */
static bool core_info_list_get_info(core_info_list_t *core_info_list,
core_info_t *out_info, const char *path)
{
size_t i;
if (!core_info_list || !out_info)
return false;
memset(out_info, 0, sizeof(*out_info));
for (i = 0; i < core_info_list->count; i++)
{
const core_info_t *info = &core_info_list->list[i];
if (string_is_equal(path_basename(info->path),
path_basename(path)))
{
*out_info = *info;
return true;
}
}
return false;
}
static bool core_info_does_support_any_file(const core_info_t *core,
const struct string_list *list)
{
size_t i;
if (!list || !core || !core->supported_extensions_list)
return false;
for (i = 0; i < list->size; i++)
if (string_list_find_elem_prefix(core->supported_extensions_list,
".", path_get_extension(list->elems[i].data)))
return true;
return false;
}
static bool core_info_does_support_file(
const core_info_t *core, const char *path)
{
if (!path || !core || !core->supported_extensions_list)
return false;
return string_list_find_elem_prefix(
core->supported_extensions_list, ".", path_get_extension(path));
}
/* qsort_r() is not in standard C, sadly. */
static int core_info_qsort_cmp(const void *a_, const void *b_)
{
const core_info_t *a = (const core_info_t*)a_;
const core_info_t *b = (const core_info_t*)b_;
int support_a =
core_info_does_support_any_file(a, core_info_tmp_list)
|| core_info_does_support_file(a, core_info_tmp_path);
int support_b =
core_info_does_support_any_file(b, core_info_tmp_list)
|| core_info_does_support_file(b, core_info_tmp_path);
if (support_a != support_b)
return support_b - support_a;
return strcasecmp(a->display_name, b->display_name);
}
static core_info_t *core_info_find_internal(
core_info_list_t *list,
const char *core)
{
size_t i;
for (i = 0; i < list->count; i++)
{
core_info_t *info = core_info_get(list, i);
if (!info)
continue;
if (string_is_equal(info->path, core))
return info;
}
return NULL;
}
static bool core_info_list_update_missing_firmware_internal(
core_info_list_t *core_info_list,
const char *core,
const char *systemdir)
{
size_t i;
char path[PATH_MAX_LENGTH] = {0};
core_info_t *info = NULL;
if (!core_info_list || !core)
return false;
info = core_info_find_internal(core_info_list, core);
if (!info)
return false;
for (i = 0; i < info->firmware_count; i++)
{
if (!info->firmware[i].path)
continue;
fill_pathname_join(path, systemdir,
info->firmware[i].path, sizeof(path));
info->firmware[i].missing = !path_file_exists(path);
}
return true;
}
#if 0
static int core_info_firmware_cmp(const void *a_, const void *b_)
{
const core_info_firmware_t *a = (const core_info_firmware_t*)a_;
const core_info_firmware_t *b = (const core_info_firmware_t*)b_;
int order = b->missing - a->missing;
if (order)
return order;
return strcasecmp(a->path, b->path);
}
/* Non-reentrant, does not allocate. Returns pointer to internal state. */
static void core_info_list_get_missing_firmware(
core_info_list_t *core_info_list,
const char *core, const char *systemdir,
const core_info_firmware_t **firmware, size_t *num_firmware)
{
size_t i;
char path[PATH_MAX_LENGTH] = {0};
core_info_t *info = NULL;
if (!core_info_list || !core)
return;
*firmware = NULL;
*num_firmware = 0;
if (!(info = core_info_find_internal(core_info_list, core)))
return;
*firmware = info->firmware;
for (i = 1; i < info->firmware_count; i++)
{
fill_pathname_join(path, systemdir,
info->firmware[i].path, sizeof(path));
info->firmware[i].missing = !path_file_exists(path);
*num_firmware += info->firmware[i].missing;
}
qsort(info->firmware, info->firmware_count, sizeof(*info->firmware),
core_info_firmware_cmp);
}
#endif
void core_info_free_current_core(void)
{
if (core_info_current)
free(core_info_current);
core_info_current = NULL;
}
bool core_info_init_current_core(void)
{
core_info_current = (core_info_t*)calloc(1, sizeof(core_info_t));
if (!core_info_current)
return false;
return true;
}
bool core_info_get_current_core(core_info_t **core)
{
if (!core)
return false;
*core = core_info_current;
return true;
}
void core_info_deinit_list(void)
{
if (core_info_curr_list)
core_info_list_free(core_info_curr_list);
core_info_curr_list = NULL;
}
bool core_info_init_list(void)
{
core_info_curr_list = core_info_list_new();
if (!core_info_curr_list)
return false;
return true;
}
bool core_info_get_list(core_info_list_t **core)
{
if (!core)
return false;
*core = core_info_curr_list;
return true;
}
bool core_info_list_update_missing_firmware(core_info_ctx_firmware_t *info)
{
if (!info)
return false;
return core_info_list_update_missing_firmware_internal(
core_info_curr_list,
info->path, info->directory.system);
}
bool core_info_load(core_info_ctx_find_t *info)
{
core_info_t *core_info = NULL;
if (!info)
return false;
core_info_get_current_core(&core_info);
if (!core_info_curr_list)
return false;
if (!core_info_list_get_info(core_info_curr_list,
core_info, info->path))
return false;
return true;
}
bool core_info_find(core_info_ctx_find_t *info)
{
if (!info || !core_info_curr_list)
return false;
info->inf = core_info_find_internal(core_info_curr_list, info->path);
if (!info->inf)
return false;
return true;
}
core_info_t *core_info_get(core_info_list_t *list, size_t i)
{
core_info_t *info = NULL;
if (!list)
return NULL;
info = (core_info_t*)&list->list[i];
if (!info || !info->path)
return NULL;
return info;
}
void core_info_list_get_supported_cores(core_info_list_t *core_info_list,
const char *path, const core_info_t **infos, size_t *num_infos)
{
#ifdef HAVE_ZLIB
struct string_list *list = NULL;
#endif
size_t supported = 0, i;
if (!core_info_list)
return;
core_info_tmp_path = path;
#ifdef HAVE_ZLIB
if (string_is_equal_noncase(path_get_extension(path), "zip"))
list = file_archive_get_file_list(path, NULL);
core_info_tmp_list = list;
#endif
/* Let supported core come first in list so we can return
* a pointer to them. */
qsort(core_info_list->list, core_info_list->count,
sizeof(core_info_t), core_info_qsort_cmp);
for (i = 0; i < core_info_list->count; i++, supported++)
{
const core_info_t *core = &core_info_list->list[i];
if (!core)
continue;
if (core_info_does_support_file(core, path))
continue;
#ifdef HAVE_ZLIB
if (core_info_does_support_any_file(core, list))
continue;
#endif
break;
}
#ifdef HAVE_ZLIB
if (list)
string_list_free(list);
#endif
*infos = core_info_list->list;
*num_infos = supported;
}
void core_info_get_name(const char *path, char *s, size_t len)
{
size_t i;
core_info_t *core_info = NULL;
core_info_list_t *core_info_list = NULL;
struct string_list *contents = dir_list_new_special(
NULL, DIR_LIST_CORES, NULL);
if (!contents)
return;
core_info_list = (core_info_list_t*)calloc(1, sizeof(*core_info_list));
if (!core_info_list)
goto error;
core_info = (core_info_t*)calloc(contents->size, sizeof(*core_info));
if (!core_info)
goto error;
core_info_list->list = core_info;
core_info_list->count = contents->size;
for (i = 0; i < contents->size; i++)
{
config_file_t *conf = NULL;
if (!string_is_equal(contents->elems[i].data, path))
continue;
conf = core_info_list_iterate(contents, i);
if (conf)
{
config_get_string(conf, "corename",
&core_info[i].core_name);
core_info[i].config_data = (void*)conf;
}
core_info[i].path = strdup(contents->elems[i].data);
strlcpy(s, core_info[i].core_name, len);
}
error:
if (contents)
dir_list_free(contents);
contents = NULL;
core_info_list_free(core_info_list);
}
size_t core_info_list_num_info_files(core_info_list_t *core_info_list)
{
@ -425,317 +740,3 @@ error:
free(core_name);
return false;
}
/* Shallow-copies internal state.
*
* Data in *info is invalidated when the
* core_info_list is freed. */
static bool core_info_list_get_info(core_info_list_t *core_info_list,
core_info_t *out_info, const char *path)
{
size_t i;
if (!core_info_list || !out_info)
return false;
memset(out_info, 0, sizeof(*out_info));
for (i = 0; i < core_info_list->count; i++)
{
const core_info_t *info = &core_info_list->list[i];
if (string_is_equal(path_basename(info->path),
path_basename(path)))
{
*out_info = *info;
return true;
}
}
return false;
}
static bool core_info_does_support_any_file(const core_info_t *core,
const struct string_list *list)
{
size_t i;
if (!list || !core || !core->supported_extensions_list)
return false;
for (i = 0; i < list->size; i++)
if (string_list_find_elem_prefix(core->supported_extensions_list,
".", path_get_extension(list->elems[i].data)))
return true;
return false;
}
static bool core_info_does_support_file(
const core_info_t *core, const char *path)
{
if (!path || !core || !core->supported_extensions_list)
return false;
return string_list_find_elem_prefix(
core->supported_extensions_list, ".", path_get_extension(path));
}
/* qsort_r() is not in standard C, sadly. */
static int core_info_qsort_cmp(const void *a_, const void *b_)
{
const core_info_t *a = (const core_info_t*)a_;
const core_info_t *b = (const core_info_t*)b_;
int support_a =
core_info_does_support_any_file(a, core_info_tmp_list)
|| core_info_does_support_file(a, core_info_tmp_path);
int support_b =
core_info_does_support_any_file(b, core_info_tmp_list)
|| core_info_does_support_file(b, core_info_tmp_path);
if (support_a != support_b)
return support_b - support_a;
return strcasecmp(a->display_name, b->display_name);
}
void core_info_list_get_supported_cores(core_info_list_t *core_info_list,
const char *path, const core_info_t **infos, size_t *num_infos)
{
#ifdef HAVE_ZLIB
struct string_list *list = NULL;
#endif
size_t supported = 0, i;
if (!core_info_list)
return;
core_info_tmp_path = path;
#ifdef HAVE_ZLIB
if (string_is_equal_noncase(path_get_extension(path), "zip"))
list = file_archive_get_file_list(path, NULL);
core_info_tmp_list = list;
#endif
/* Let supported core come first in list so we can return
* a pointer to them. */
qsort(core_info_list->list, core_info_list->count,
sizeof(core_info_t), core_info_qsort_cmp);
for (i = 0; i < core_info_list->count; i++, supported++)
{
const core_info_t *core = &core_info_list->list[i];
if (!core)
continue;
if (core_info_does_support_file(core, path))
continue;
#ifdef HAVE_ZLIB
if (core_info_does_support_any_file(core, list))
continue;
#endif
break;
}
#ifdef HAVE_ZLIB
if (list)
string_list_free(list);
#endif
*infos = core_info_list->list;
*num_infos = supported;
}
core_info_t *core_info_get(core_info_list_t *list, size_t i)
{
core_info_t *info = NULL;
if (!list)
return NULL;
info = (core_info_t*)&list->list[i];
if (!info || !info->path)
return NULL;
return info;
}
static core_info_t *core_info_find(core_info_list_t *list,
const char *core)
{
size_t i;
for (i = 0; i < list->count; i++)
{
core_info_t *info = core_info_get(list, i);
if (!info)
continue;
if (string_is_equal(info->path, core))
return info;
}
return NULL;
}
static bool core_info_list_update_missing_firmware(
core_info_list_t *core_info_list,
const char *core, const char *systemdir)
{
size_t i;
char path[PATH_MAX_LENGTH] = {0};
core_info_t *info = NULL;
if (!core_info_list || !core)
return false;
info = core_info_find(core_info_list, core);
if (!info)
return false;
for (i = 0; i < info->firmware_count; i++)
{
if (!info->firmware[i].path)
continue;
fill_pathname_join(path, systemdir,
info->firmware[i].path, sizeof(path));
info->firmware[i].missing = !path_file_exists(path);
}
return true;
}
#if 0
static int core_info_firmware_cmp(const void *a_, const void *b_)
{
const core_info_firmware_t *a = (const core_info_firmware_t*)a_;
const core_info_firmware_t *b = (const core_info_firmware_t*)b_;
int order = b->missing - a->missing;
if (order)
return order;
return strcasecmp(a->path, b->path);
}
/* Non-reentrant, does not allocate. Returns pointer to internal state. */
static void core_info_list_get_missing_firmware(
core_info_list_t *core_info_list,
const char *core, const char *systemdir,
const core_info_firmware_t **firmware, size_t *num_firmware)
{
size_t i;
char path[PATH_MAX_LENGTH] = {0};
core_info_t *info = NULL;
if (!core_info_list || !core)
return;
*firmware = NULL;
*num_firmware = 0;
if (!(info = core_info_find(core_info_list, core)))
return;
*firmware = info->firmware;
for (i = 1; i < info->firmware_count; i++)
{
fill_pathname_join(path, systemdir,
info->firmware[i].path, sizeof(path));
info->firmware[i].missing = !path_file_exists(path);
*num_firmware += info->firmware[i].missing;
}
qsort(info->firmware, info->firmware_count, sizeof(*info->firmware),
core_info_firmware_cmp);
}
#endif
bool core_info_ctl(enum core_info_state state, void *data)
{
static core_info_t *core_info_current = NULL;
static core_info_list_t *core_info_curr_list = NULL;
switch (state)
{
case CORE_INFO_CTL_CURRENT_CORE_FREE:
if (core_info_current)
free(core_info_current);
core_info_current = NULL;
break;
case CORE_INFO_CTL_CURRENT_CORE_INIT:
core_info_current = (core_info_t*)calloc(1, sizeof(core_info_t));
if (!core_info_current)
return false;
break;
case CORE_INFO_CTL_CURRENT_CORE_GET:
{
core_info_t **core = (core_info_t**)data;
if (!core)
return false;
*core = core_info_current;
}
break;
case CORE_INFO_CTL_LIST_DEINIT:
if (core_info_curr_list)
core_info_list_free(core_info_curr_list);
core_info_curr_list = NULL;
break;
case CORE_INFO_CTL_LIST_INIT:
core_info_curr_list = core_info_list_new();
break;
case CORE_INFO_CTL_LIST_GET:
{
core_info_list_t **core = (core_info_list_t**)data;
if (!core)
return false;
*core = core_info_curr_list;
}
break;
case CORE_INFO_CTL_LIST_UPDATE_MISSING_FIRMWARE:
{
core_info_ctx_firmware_t *info = (core_info_ctx_firmware_t*)data;
if (!info)
return false;
return core_info_list_update_missing_firmware(core_info_curr_list,
info->path, info->directory.system);
}
case CORE_INFO_CTL_FIND:
{
core_info_ctx_find_t *info = (core_info_ctx_find_t*)data;
if (!info || !core_info_curr_list)
return false;
info->inf = core_info_find(core_info_curr_list, info->path);
if (!info->inf)
return false;
}
break;
case CORE_INFO_CTL_LOAD:
{
core_info_t *core_info = NULL;
core_info_ctx_find_t *info = (core_info_ctx_find_t*)data;
if (!info)
return false;
core_info_ctl(CORE_INFO_CTL_CURRENT_CORE_GET, &core_info);
if (!core_info_curr_list)
return false;
if (!core_info_list_get_info(core_info_curr_list,
core_info, info->path))
return false;
}
break;
case CORE_INFO_CTL_NONE:
default:
break;
}
return true;
}

View File

@ -26,20 +26,6 @@
extern "C" {
#endif
enum core_info_state
{
CORE_INFO_CTL_NONE = 0,
CORE_INFO_CTL_LIST_DEINIT,
CORE_INFO_CTL_LIST_INIT,
CORE_INFO_CTL_LIST_GET,
CORE_INFO_CTL_LIST_UPDATE_MISSING_FIRMWARE,
CORE_INFO_CTL_CURRENT_CORE_FREE,
CORE_INFO_CTL_CURRENT_CORE_INIT,
CORE_INFO_CTL_CURRENT_CORE_GET,
CORE_INFO_CTL_LOAD,
CORE_INFO_CTL_FIND
};
typedef struct
{
char *path;
@ -116,7 +102,23 @@ void core_info_get_name(const char *path, char *s, size_t len);
core_info_t *core_info_get(core_info_list_t *list, size_t i);
bool core_info_ctl(enum core_info_state action, void *data);
void core_info_free_current_core(void);
bool core_info_init_current_core(void);
bool core_info_get_current_core(core_info_t **core);
void core_info_deinit_list(void);
bool core_info_init_list(void);
bool core_info_get_list(core_info_list_t **core);
bool core_info_list_update_missing_firmware(core_info_ctx_firmware_t *info);
bool core_info_find(core_info_ctx_find_t *info);
bool core_info_load(core_info_ctx_find_t *info);
#ifdef __cplusplus
}

View File

@ -19,8 +19,9 @@
#include <stdlib.h>
#include <string.h>
#include <libretro.h>
#include "internal_cores.h"
#include "../libretro.h"
static uint16_t *frame_buf;

View File

@ -19,7 +19,7 @@
#define INTERNAL_CORES_H__
#include <boolean.h>
#include "../libretro.h"
#include <libretro.h>
void libretro_dummy_retro_init(void);

View File

@ -42,7 +42,7 @@ extern "C" {
#include <rthreads/rthreads.h>
#include <queues/fifo_queue.h>
#include "libretro.h"
#include <libretro.h>
#ifdef RARCH_INTERNAL
#include "internal_cores.h"
#define CORE_PREFIX(s) libretro_ffmpeg_##s

View File

@ -1 +0,0 @@
#include "../../libretro.h"

View File

@ -22,12 +22,12 @@
#include "../../deps/stb/stb_image.h"
#include <libretro.h>
#ifdef RARCH_INTERNAL
#include "internal_cores.h"
#include "../../libretro.h"
#define IMAGE_CORE_PREFIX(s) libretro_imageviewer_##s
#else
#include "libretro.h"
#define IMAGE_CORE_PREFIX(s) s
#endif

View File

@ -6,7 +6,7 @@
#include <glsym/glsym.h>
#include "../../libretro.h"
#include <libretro.h>
#define ARRAY_SIZE(a) (sizeof(a) / sizeof((a)[0]))
static struct retro_hw_render_callback hw_render;

View File

@ -6,7 +6,7 @@
#include <glsym/glsym.h>
#include "../../libretro.h"
#include <libretro.h>
#define ARRAY_SIZE(a) (sizeof(a) / sizeof((a)[0]))
static struct retro_hw_render_callback hw_render;

View File

@ -7,7 +7,7 @@
#include <retro_miscellaneous.h>
#include "../../libretro.h"
#include <libretro.h>
static uint32_t *frame_buf;
static struct retro_log_callback logging;

146
cores/retropad/Makefile Normal file
View File

@ -0,0 +1,146 @@
STATIC_LINKING := 0
AR := ar
ifeq ($(platform),)
platform = unix
ifeq ($(shell uname -a),)
platform = win
else ifneq ($(findstring MINGW,$(shell uname -a)),)
platform = win
else ifneq ($(findstring Darwin,$(shell uname -a)),)
platform = osx
else ifneq ($(findstring win,$(shell uname -a)),)
platform = win
endif
endif
# system platform
system_platform = unix
ifeq ($(shell uname -a),)
EXE_EXT = .exe
system_platform = win
else ifneq ($(findstring Darwin,$(shell uname -a)),)
system_platform = osx
arch = intel
ifeq ($(shell uname -p),powerpc)
arch = ppc
endif
else ifneq ($(findstring MINGW,$(shell uname -a)),)
system_platform = win
endif
TARGET_NAME := retropad
LIBM = -lm
ifeq ($(ARCHFLAGS),)
ifeq ($(archs),ppc)
ARCHFLAGS = -arch ppc -arch ppc64
else
ARCHFLAGS = -arch i386 -arch x86_64
endif
endif
ifeq ($(platform), osx)
ifndef ($(NOUNIVERSAL))
CFLAGS += $(ARCHFLAGS)
LFLAGS += $(ARCHFLAGS)
endif
endif
ifeq ($(STATIC_LINKING), 1)
EXT := a
endif
ifeq ($(platform), unix)
EXT ?= so
TARGET := $(TARGET_NAME)_libretro.$(EXT)
fpic := -fPIC
SHARED := -shared -Wl,--version-script=link.T -Wl,--no-undefined
else ifeq ($(platform), linux-portable)
TARGET := $(TARGET_NAME)_libretro.$(EXT)
fpic := -fPIC -nostdlib
SHARED := -shared -Wl,--version-script=link.T
LIBM :=
else ifneq (,$(findstring osx,$(platform)))
TARGET := $(TARGET_NAME)_libretro.dylib
fpic := -fPIC
SHARED := -dynamiclib
else ifneq (,$(findstring ios,$(platform)))
TARGET := $(TARGET_NAME)_libretro_ios.dylib
fpic := -fPIC
SHARED := -dynamiclib
ifeq ($(IOSSDK),)
IOSSDK := $(shell xcodebuild -version -sdk iphoneos Path)
endif
DEFINES := -DIOS
CC = cc -arch armv7 -isysroot $(IOSSDK)
ifeq ($(platform),ios9)
CC += -miphoneos-version-min=8.0
CFLAGS += -miphoneos-version-min=8.0
else
CC += -miphoneos-version-min=5.0
CFLAGS += -miphoneos-version-min=5.0
endif
else ifneq (,$(findstring qnx,$(platform)))
TARGET := $(TARGET_NAME)_libretro_qnx.so
fpic := -fPIC
SHARED := -shared -Wl,--version-script=link.T -Wl,--no-undefined
else ifeq ($(platform), emscripten)
TARGET := $(TARGET_NAME)_libretro_emscripten.bc
fpic := -fPIC
SHARED := -shared -Wl,--version-script=link.T -Wl,--no-undefined
else ifeq ($(platform), vita)
TARGET := $(TARGET_NAME)_vita.a
CC = arm-vita-eabi-gcc
AR = arm-vita-eabi-ar
CFLAGS += -Wl,-q -Wall -O3
STATIC_LINKING = 1
else
CC = gcc
TARGET := $(TARGET_NAME)_libretro.dll
SHARED := -shared -static-libgcc -static-libstdc++ -s -Wl,--version-script=link.T -Wl,--no-undefined
endif
LDFLAGS += $(LIBM)
ifeq ($(platform), win)
LDFLAGS += -lws2_32
endif
ifeq ($(DEBUG), 1)
CFLAGS += -O0 -g
else
CFLAGS += -O3
endif
OBJECTS := ../../libretro-common/net/net_compat.o ../../libretro-common/net/net_socket.o retropad.o
CFLAGS += -I../../libretro-common/include -Wall -pedantic $(fpic)
ifneq (,$(findstring qnx,$(platform)))
CFLAGS += -Wc,-std=c99
else
CFLAGS += -std=gnu99
endif
CFLAGS += -I../../libretro-common/include
all: $(TARGET)
$(TARGET): $(OBJECTS)
ifeq ($(STATIC_LINKING), 1)
$(AR) rcs $@ $(OBJECTS)
else
$(CC) $(fpic) $(SHARED) $(INCLUDES) -o $@ $(OBJECTS) $(LDFLAGS)
endif
%.o: %.c
$(CC) $(CFLAGS) -c -o $@ $<
clean:
rm -f $(OBJECTS) $(TARGET)
.PHONY: clean

View File

@ -0,0 +1,25 @@
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
APP_DIR := ../../src
LOCAL_MODULE := retro
ifeq ($(TARGET_ARCH),arm)
LOCAL_CFLAGS += -DANDROID_ARM
endif
ifeq ($(TARGET_ARCH),x86)
LOCAL_CFLAGS += -DANDROID_X86
endif
ifeq ($(TARGET_ARCH),mips)
LOCAL_CFLAGS += -DANDROID_MIPS -D__mips__ -D__MIPSEL__
endif
LOCAL_SRC_FILES += ../libretro-test.c
LOCAL_CFLAGS += -O3 -std=gnu99 -ffast-math -funroll-loops
include $(BUILD_SHARED_LIBRARY)

View File

@ -0,0 +1 @@
APP_ABI := all

5
cores/retropad/link.T Normal file
View File

@ -0,0 +1,5 @@
{
global: retro_*;
local: *;
};

325
cores/retropad/retropad.c Normal file
View File

@ -0,0 +1,325 @@
/* RetroArch - A frontend for libretro.
* Copyright (C) 2010-2014 - Hans-Kristian Arntzen
* Copyright (C) 2011-2015 - Daniel De Matteis
* Copyright (C) 2016 - Andrés Suárez
*
* RetroArch is free software: you can redistribute it and/or modify it under the terms
* of the GNU General Public License as published by the Free Software Found-
* ation, either version 3 of the License, or (at your option) any later version.
*
* RetroArch is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
* PURPOSE. See the GNU General Public License for more details.
* You should have received a copy of the GNU General Public License along with RetroArch.
* If not, see <http://www.gnu.org/licenses/>.
*/
/*
* To-do:
* - Analog support
* - Some sort of connection control, it only sends packets
* but there is no acknoledgement of a connection o keepalives
* - Send player name
* - Render something on-screen maybe a gui to configure IP and port
instead of the ridiculously long strings we're using now
* - Allow changing IP address and port in runtime
* - Support other platforms
* - Input recording / Combos
*/
#include <stdio.h>
#include <stdint.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>
#include <math.h>
#include <net/net_compat.h>
#include <net/net_socket.h>
#include <retro_miscellaneous.h>
#include <libretro.h>
#ifndef SOCKET_ERROR
#define SOCKET_ERROR -1
#endif
int s;
int port;
char message[64];
char server[64];
struct sockaddr_in si_other;
struct retro_log_callback logger;
retro_log_printf_t log_cb;
static uint16_t *frame_buf;
int input_state = 0;
void retro_init(void)
{
frame_buf = (uint16_t*)calloc(320 * 240, sizeof(uint16_t));
log_cb(RETRO_LOG_INFO, "Initialising sockets...\n");
network_init();
}
void retro_deinit(void)
{
if (frame_buf)
free(frame_buf);
frame_buf = NULL;
}
unsigned retro_api_version(void)
{
return RETRO_API_VERSION;
}
void retro_set_controller_port_device(
unsigned port, unsigned device)
{
(void)port;
(void)device;
}
void retro_get_system_info(
struct retro_system_info *info)
{
memset(info, 0, sizeof(*info));
info->library_name = "RetroPad Remote";
info->library_version = "0.01";
info->need_fullpath = false;
info->valid_extensions = ""; /* Nothing. */
}
void retro_get_system_av_info(
struct retro_system_av_info *info)
{
info->timing.fps = 60.0;
info->timing.sample_rate = 30000.0;
info->geometry.base_width = 320;
info->geometry.base_height = 240;
info->geometry.max_width = 320;
info->geometry.max_height = 240;
info->geometry.aspect_ratio = 4.0 / 3.0;
}
static retro_video_refresh_t video_cb;
static retro_audio_sample_t audio_cb;
static retro_audio_sample_batch_t audio_batch_cb;
static retro_environment_t environ_cb;
static retro_input_poll_t input_poll_cb;
static retro_input_state_t input_state_cb;
void update_input()
{
input_state = 0;
input_poll_cb();
if (input_state_cb(0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_B))
input_state += 1;
if (input_state_cb(0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_A))
input_state += 2;
if (input_state_cb(0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_SELECT))
input_state += pow(2, 2);
if (input_state_cb(0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_START))
input_state += pow(2, 3);
if (input_state_cb(0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_UP))
input_state += pow(2, 4);
if (input_state_cb(0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_DOWN))
input_state += pow(2, 5);
if (input_state_cb(0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_LEFT))
input_state += pow(2, 6);
if (input_state_cb(0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_RIGHT))
input_state += pow(2, 7);
if (input_state_cb(0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_Y))
input_state += pow(2, 8);
if (input_state_cb(0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_X))
input_state += pow(2, 9);
if (input_state_cb(0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_L))
input_state += pow(2, 10);
if (input_state_cb(0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_R))
input_state += pow(2, 11);
}
void retro_set_environment(retro_environment_t cb)
{
static const struct retro_variable vars[] = {
{ "port", "Port; 55400|55401|55402|55403|55404|55405|55406|55407|55408|55409|55410|55411|55412|55413|55414|55415|55416|55417|55418|55419|55420" },
{ "ip_octet1", "IP address part 1; 0|1|2|3|4|5|6|7|8|9|10|11|12|13|14|15|16|17|18|19|20|21|22|23|24|25|26|27|28|29|30|31|32|33|35|35|36|37|38|39|40|41|42|43|44|45|46|47|48|49|50|51|52|53|54|55|56|57|58|59|60|61|62|63|64|65|66|67|68|69|70|71|72|73|74|75|76|77|78|79|80|81|82|83|84|85|86|87|88|89|90|91|92|93|94|95|96|97|98|99|100|101|102|103|104|105|106|107|108|109|110|111|112|113|114|115|116|117|118|119|120|121|122|123|124|125|126|127|128|129|130|131|132|133|135|135|136|137|138|139|140|141|142|143|144|145|146|147|148|149|150|151|152|153|154|155|156|157|158|159|160|161|162|163|164|165|166|167|168|169|170|171|172|173|174|175|176|177|178|179|180|181|182|183|184|185|186|187|188|189|190|191|192|193|194|195|196|197|198|199|200|201|202|203|204|205|206|207|208|209|210|211|212|213|214|215|216|217|218|219|220|221|222|223|224|225|226|227|228|229|230|231|232|233|235|235|236|237|238|239|240|241|242|243|244|245|246|247|248|249|250|251|252|253|254|255" },
{ "ip_octet2", "IP address part 2; 0|1|2|3|4|5|6|7|8|9|10|11|12|13|14|15|16|17|18|19|20|21|22|23|24|25|26|27|28|29|30|31|32|33|35|35|36|37|38|39|40|41|42|43|44|45|46|47|48|49|50|51|52|53|54|55|56|57|58|59|60|61|62|63|64|65|66|67|68|69|70|71|72|73|74|75|76|77|78|79|80|81|82|83|84|85|86|87|88|89|90|91|92|93|94|95|96|97|98|99|100|101|102|103|104|105|106|107|108|109|110|111|112|113|114|115|116|117|118|119|120|121|122|123|124|125|126|127|128|129|130|131|132|133|135|135|136|137|138|139|140|141|142|143|144|145|146|147|148|149|150|151|152|153|154|155|156|157|158|159|160|161|162|163|164|165|166|167|168|169|170|171|172|173|174|175|176|177|178|179|180|181|182|183|184|185|186|187|188|189|190|191|192|193|194|195|196|197|198|199|200|201|202|203|204|205|206|207|208|209|210|211|212|213|214|215|216|217|218|219|220|221|222|223|224|225|226|227|228|229|230|231|232|233|235|235|236|237|238|239|240|241|242|243|244|245|246|247|248|249|250|251|252|253|254|255" },
{ "ip_octet3", "IP address part 3; 0|1|2|3|4|5|6|7|8|9|10|11|12|13|14|15|16|17|18|19|20|21|22|23|24|25|26|27|28|29|30|31|32|33|35|35|36|37|38|39|40|41|42|43|44|45|46|47|48|49|50|51|52|53|54|55|56|57|58|59|60|61|62|63|64|65|66|67|68|69|70|71|72|73|74|75|76|77|78|79|80|81|82|83|84|85|86|87|88|89|90|91|92|93|94|95|96|97|98|99|100|101|102|103|104|105|106|107|108|109|110|111|112|113|114|115|116|117|118|119|120|121|122|123|124|125|126|127|128|129|130|131|132|133|135|135|136|137|138|139|140|141|142|143|144|145|146|147|148|149|150|151|152|153|154|155|156|157|158|159|160|161|162|163|164|165|166|167|168|169|170|171|172|173|174|175|176|177|178|179|180|181|182|183|184|185|186|187|188|189|190|191|192|193|194|195|196|197|198|199|200|201|202|203|204|205|206|207|208|209|210|211|212|213|214|215|216|217|218|219|220|221|222|223|224|225|226|227|228|229|230|231|232|233|235|235|236|237|238|239|240|241|242|243|244|245|246|247|248|249|250|251|252|253|254|255" },
{ "ip_octet4", "IP address part 4; 0|1|2|3|4|5|6|7|8|9|10|11|12|13|14|15|16|17|18|19|20|21|22|23|24|25|26|27|28|29|30|31|32|33|35|35|36|37|38|39|40|41|42|43|44|45|46|47|48|49|50|51|52|53|54|55|56|57|58|59|60|61|62|63|64|65|66|67|68|69|70|71|72|73|74|75|76|77|78|79|80|81|82|83|84|85|86|87|88|89|90|91|92|93|94|95|96|97|98|99|100|101|102|103|104|105|106|107|108|109|110|111|112|113|114|115|116|117|118|119|120|121|122|123|124|125|126|127|128|129|130|131|132|133|135|135|136|137|138|139|140|141|142|143|144|145|146|147|148|149|150|151|152|153|154|155|156|157|158|159|160|161|162|163|164|165|166|167|168|169|170|171|172|173|174|175|176|177|178|179|180|181|182|183|184|185|186|187|188|189|190|191|192|193|194|195|196|197|198|199|200|201|202|203|204|205|206|207|208|209|210|211|212|213|214|215|216|217|218|219|220|221|222|223|224|225|226|227|228|229|230|231|232|233|235|235|236|237|238|239|240|241|242|243|244|245|246|247|248|249|250|251|252|253|254|255" },
{ NULL, NULL },
};
cb(RETRO_ENVIRONMENT_SET_VARIABLES, (void*)vars);
enum retro_pixel_format fmt = RETRO_PIXEL_FORMAT_RGB565;
environ_cb = cb;
bool no_content = true;
cb(RETRO_ENVIRONMENT_SET_SUPPORT_NO_GAME, &no_content);
environ_cb(RETRO_ENVIRONMENT_SET_PIXEL_FORMAT, &fmt);
if (cb(RETRO_ENVIRONMENT_GET_LOG_INTERFACE, &logger))
log_cb = logger.log;
}
static void check_variables(void)
{
struct retro_variable var, var2, var3, var4, port_var;
var.key = "ip_octet1";
var2.key = "ip_octet2";
var3.key = "ip_octet3";
var4.key = "ip_octet4";
port_var.key = "port";
environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var);
environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var2);
environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var3);
environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var4);
environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &port_var);
snprintf(server, sizeof(server), "%s.%s.%s.%s", var.value, var2.value, var3.value, var4.value);
port = atoi(port_var.value);
}
void retro_set_audio_sample(retro_audio_sample_t cb)
{
audio_cb = cb;
}
void retro_set_audio_sample_batch(
retro_audio_sample_batch_t cb)
{
audio_batch_cb = cb;
}
void retro_set_input_poll(retro_input_poll_t cb)
{
input_poll_cb = cb;
}
void retro_set_input_state(retro_input_state_t cb)
{
input_state_cb = cb;
}
void retro_set_video_refresh(retro_video_refresh_t cb)
{
video_cb = cb;
}
void retro_reset(void)
{}
void retro_run(void)
{
unsigned i;
update_input();
snprintf(message, sizeof(message), "%d", input_state);
/* send the message */
if (sendto(s, message, strlen(message) , 0 , (struct sockaddr *) &si_other, sizeof(si_other))==-1)
log_cb(RETRO_LOG_INFO, "Error sending data\n");
for (i = 0; i < 320 * 240; i++)
frame_buf[i] = 4 << 5;
video_cb(frame_buf, 320, 240, 640);
}
bool retro_load_game(const struct retro_game_info *info)
{
socket_target_t in_target;
check_variables();
s = socket_create(
"retropad",
SOCKET_DOMAIN_INET,
SOCKET_TYPE_DATAGRAM,
SOCKET_PROTOCOL_UDP);
if (s == SOCKET_ERROR)
log_cb(RETRO_LOG_INFO, "socket failed");
/* setup address structure */
memset((char *) &si_other, 0, sizeof(si_other));
in_target.port = port;
in_target.server = server;
in_target.domain = SOCKET_DOMAIN_INET;
socket_set_target(&si_other, &in_target);
log_cb(RETRO_LOG_INFO, "Server IP Address: %s\n" , server);
return true;
}
void retro_unload_game(void)
{}
unsigned retro_get_region(void)
{
return RETRO_REGION_NTSC;
}
bool retro_load_game_special(unsigned type,
const struct retro_game_info *info, size_t num)
{
(void)type;
(void)info;
(void)num;
return false;
}
size_t retro_serialize_size(void)
{
return 0;
}
bool retro_serialize(void *data, size_t size)
{
(void)data;
(void)size;
return false;
}
bool retro_unserialize(const void *data,
size_t size)
{
(void)data;
(void)size;
return false;
}
void *retro_get_memory_data(unsigned id)
{
(void)id;
return NULL;
}
size_t retro_get_memory_size(unsigned id)
{
(void)id;
return 0;
}
void retro_cheat_reset(void)
{}
void retro_cheat_set(unsigned idx,
bool enabled, const char *code)
{
(void)idx;
(void)enabled;
(void)code;
}

1
deps/SPIRV-Cross vendored Submodule

@ -0,0 +1 @@
Subproject commit 44ef367141f9935bc719c9cc25693a9055f61efa

1
deps/spir2cross vendored

@ -1 +0,0 @@
Subproject commit 0ae2bcc3d0edc60e03180f6080a168f78edc82ca

View File

@ -1,6 +1,6 @@
#!/bin/sh
RARCH_VERSION=1.3.3
RARCH_VERSION=1.3.4
PLATFORM=$1
SALAMANDER=no
MAKEFILE_GRIFFIN=no

View File

@ -151,7 +151,7 @@ The video input is scaled with point filtering before being encoded at the corre
.TP
\fB--bsvplay PATH, -P PATH\fR
Play back a movie recorded in the .bsv format (bSNES). Cart ROM and movie file need to correspond.
Play back a movie recorded in the .bsv format (bsnes). Cart ROM and movie file need to correspond.
It also requires to play back with the same libretro backend that was used for recording.
.TP

View File

@ -17,6 +17,7 @@
#include <compat/posix_string.h>
#include <string/stdstring.h>
#include "command.h"
#include "general.h"
#include "msg_hash.h"
#include "system.h"
@ -26,7 +27,7 @@
#include "camera/camera_driver.h"
#include "record/record_driver.h"
#include "location/location_driver.h"
#include "libretro_version_1.h"
#include "core.h"
#ifdef HAVE_MENU
#include "menu/menu_driver.h"
@ -200,14 +201,14 @@ bool driver_find_next(const char *label, char *s, size_t len)
static void driver_adjust_system_rates(void)
{
audio_driver_ctl(RARCH_AUDIO_CTL_MONITOR_ADJUST_SYSTEM_RATES, NULL);
video_driver_ctl(RARCH_DISPLAY_CTL_MONITOR_ADJUST_SYSTEM_RATES, NULL);
audio_driver_monitor_adjust_system_rates();
video_driver_monitor_adjust_system_rates();
if (!video_driver_get_ptr(false))
return;
if (runloop_ctl(RUNLOOP_CTL_IS_NONBLOCK_FORCED, NULL))
event_cmd_ctl(EVENT_CMD_VIDEO_SET_NONBLOCKING_STATE, NULL);
command_event(CMD_EVENT_VIDEO_SET_NONBLOCKING_STATE, NULL);
else
driver_ctl(RARCH_DRIVER_CTL_SET_NONBLOCK_STATE, NULL);
}
@ -223,19 +224,17 @@ static void driver_adjust_system_rates(void)
static void driver_set_nonblock_state(void)
{
settings_t *settings = config_get_ptr();
bool enable = input_driver_ctl(
RARCH_INPUT_CTL_IS_NONBLOCK_STATE, NULL);
bool enable = input_driver_is_nonblock_state();
/* Only apply non-block-state for video if we're using vsync. */
if (video_driver_ctl(RARCH_DISPLAY_CTL_IS_ACTIVE, NULL)
&& video_driver_get_ptr(false))
if (video_driver_is_active() && video_driver_get_ptr(false))
{
bool video_nonblock = enable;
if ( !settings->video.vsync
|| runloop_ctl(RUNLOOP_CTL_IS_NONBLOCK_FORCED, NULL))
video_nonblock = true;
video_driver_ctl(RARCH_DISPLAY_CTL_SET_NONBLOCK_STATE, &video_nonblock);
video_driver_set_nonblock_state(video_nonblock);
}
audio_driver_set_nonblocking_state(enable);
@ -256,7 +255,7 @@ static bool driver_update_system_av_info(const struct retro_system_av_info *info
struct retro_system_av_info *av_info = video_viewport_get_system_av_info();
memcpy(av_info, info, sizeof(*av_info));
event_cmd_ctl(EVENT_CMD_REINIT, NULL);
command_event(CMD_EVENT_REINIT, NULL);
/* Cannot continue recording with different parameters.
* Take the easiest route out and just restart the recording. */
@ -265,8 +264,8 @@ static bool driver_update_system_av_info(const struct retro_system_av_info *info
runloop_msg_queue_push(
msg_hash_to_str(MSG_RESTARTING_RECORDING_DUE_TO_DRIVER_REINIT),
2, 180, false);
event_cmd_ctl(EVENT_CMD_RECORD_DEINIT, NULL);
event_cmd_ctl(EVENT_CMD_RECORD_INIT, NULL);
command_event(CMD_EVENT_RECORD_DEINIT, NULL);
command_event(CMD_EVENT_RECORD_INIT, NULL);
}
return true;
@ -288,8 +287,8 @@ static void menu_update_libretro_info(void)
if (!info)
return;
event_cmd_ctl(EVENT_CMD_CORE_INFO_INIT, NULL);
event_cmd_ctl(EVENT_CMD_LOAD_CORE_PERSIST, NULL);
command_event(CMD_EVENT_CORE_INFO_INIT, NULL);
command_event(CMD_EVENT_LOAD_CORE_PERSIST, NULL);
}
#endif
@ -303,11 +302,11 @@ static void menu_update_libretro_info(void)
static void init_drivers(int flags)
{
if (flags & DRIVER_VIDEO)
video_driver_ctl(RARCH_DISPLAY_CTL_UNSET_OWN_DRIVER, NULL);
video_driver_unset_own_driver();
if (flags & DRIVER_AUDIO)
audio_driver_ctl(RARCH_AUDIO_CTL_UNSET_OWN_DRIVER, NULL);
audio_driver_unset_own_driver();
if (flags & DRIVER_INPUT)
input_driver_ctl(RARCH_INPUT_CTL_UNSET_OWN_DRIVER, NULL);
input_driver_unset_own_driver();
if (flags & DRIVER_CAMERA)
camera_driver_ctl(RARCH_CAMERA_CTL_UNSET_OWN_DRIVER, NULL);
if (flags & DRIVER_LOCATION)
@ -323,24 +322,24 @@ static void init_drivers(int flags)
if (flags & DRIVER_VIDEO)
{
struct retro_hw_render_callback *hwr = NULL;
video_driver_ctl(RARCH_DISPLAY_CTL_HW_CONTEXT_GET, &hwr);
struct retro_hw_render_callback *hwr =
video_driver_get_hw_context();
video_driver_ctl(RARCH_DISPLAY_CTL_MONITOR_RESET, NULL);
video_driver_ctl(RARCH_DISPLAY_CTL_INIT, NULL);
video_driver_monitor_reset();
video_driver_init();
if (!video_driver_ctl(RARCH_DISPLAY_CTL_IS_VIDEO_CACHE_CONTEXT_ACK, NULL)
if (!video_driver_is_video_cache_context_ack()
&& hwr->context_reset)
hwr->context_reset();
video_driver_ctl(RARCH_DISPLAY_CTL_UNSET_VIDEO_CACHE_CONTEXT_ACK, NULL);
video_driver_unset_video_cache_context_ack();
runloop_ctl(RUNLOOP_CTL_SET_FRAME_TIME_LAST, NULL);
}
if (flags & DRIVER_AUDIO)
{
audio_driver_ctl(RARCH_AUDIO_CTL_INIT, NULL);
audio_driver_ctl(RARCH_AUDIO_CTL_DEVICES_LIST_NEW, NULL);
audio_driver_init();
audio_driver_new_devices_list();
}
/* Only initialize camera driver if we're ever going to use it. */
@ -364,7 +363,7 @@ static void init_drivers(int flags)
if (flags & (DRIVER_VIDEO | DRIVER_AUDIO))
{
/* Keep non-throttled state as good as possible. */
if (input_driver_ctl(RARCH_INPUT_CTL_IS_NONBLOCK_STATE, NULL))
if (input_driver_is_nonblock_state())
driver_ctl(RARCH_DRIVER_CTL_SET_NONBLOCK_STATE, NULL);
}
}
@ -408,19 +407,19 @@ static void uninit_drivers(int flags)
camera_driver_ctl(RARCH_CAMERA_CTL_DEINIT, NULL);
if (flags & DRIVER_AUDIO)
audio_driver_ctl(RARCH_AUDIO_CTL_DEINIT, NULL);
audio_driver_deinit();
if (flags & DRIVERS_VIDEO_INPUT)
video_driver_ctl(RARCH_DISPLAY_CTL_DEINIT, NULL);
video_driver_deinit();
if ((flags & DRIVER_VIDEO) && !video_driver_ctl(RARCH_DISPLAY_CTL_OWNS_DRIVER, NULL))
video_driver_ctl(RARCH_DISPLAY_CTL_DESTROY_DATA, NULL);
if ((flags & DRIVER_VIDEO) && !video_driver_owns_driver())
video_driver_destroy_data();
if ((flags & DRIVER_INPUT) && !input_driver_ctl(RARCH_INPUT_CTL_OWNS_DRIVER, NULL))
input_driver_ctl(RARCH_INPUT_CTL_DESTROY_DATA, NULL);
if ((flags & DRIVER_INPUT) && !input_driver_owns_driver())
input_driver_destroy_data();
if ((flags & DRIVER_AUDIO) && !audio_driver_ctl(RARCH_AUDIO_CTL_OWNS_DRIVER, NULL))
audio_driver_ctl(RARCH_AUDIO_CTL_DESTROY_DATA, NULL);
if ((flags & DRIVER_AUDIO) && !audio_driver_owns_driver())
audio_driver_destroy_data();
}
bool driver_ctl(enum driver_ctl_state state, void *data)
@ -428,15 +427,15 @@ bool driver_ctl(enum driver_ctl_state state, void *data)
switch (state)
{
case RARCH_DRIVER_CTL_DEINIT:
video_driver_ctl(RARCH_DISPLAY_CTL_DESTROY, NULL);
audio_driver_ctl(RARCH_AUDIO_CTL_DESTROY, NULL);
input_driver_ctl(RARCH_INPUT_CTL_DESTROY, NULL);
video_driver_destroy();
audio_driver_destroy();
input_driver_destroy();
#ifdef HAVE_MENU
menu_driver_ctl(RARCH_MENU_CTL_DESTROY, NULL);
#endif
location_driver_ctl(RARCH_LOCATION_CTL_DESTROY, NULL);
camera_driver_ctl(RARCH_CAMERA_CTL_DESTROY, NULL);
core_ctl(CORE_CTL_DEINIT, NULL);
core_uninit_libretro_callbacks();
break;
case RARCH_DRIVER_CTL_UNINIT:
{
@ -465,9 +464,9 @@ bool driver_ctl(enum driver_ctl_state state, void *data)
return driver_ctl(RARCH_DRIVER_CTL_INIT, &flags);
}
case RARCH_DRIVER_CTL_INIT_PRE:
audio_driver_ctl(RARCH_AUDIO_CTL_FIND_DRIVER, NULL);
video_driver_ctl(RARCH_DISPLAY_CTL_FIND_DRIVER, NULL);
input_driver_ctl(RARCH_INPUT_CTL_FIND_DRIVER, NULL);
audio_driver_find_driver();
video_driver_find_driver();
input_driver_find_driver();
camera_driver_ctl(RARCH_CAMERA_CTL_FIND_DRIVER, NULL);
find_location_driver();
#ifdef HAVE_MENU
@ -478,7 +477,7 @@ bool driver_ctl(enum driver_ctl_state state, void *data)
{
float *hz = (float*)data;
video_monitor_set_refresh_rate(*hz);
audio_driver_ctl(RARCH_AUDIO_CTL_MONITOR_SET_REFRESH_RATE, NULL);
audio_driver_monitor_set_rate();
driver_adjust_system_rates();
}
break;

244
dynamic.c
View File

@ -25,24 +25,30 @@
#include <string/stdstring.h>
#include <retro_assert.h>
#include <features/features_cpu.h>
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include "dynamic.h"
#include "command_event.h"
#include "command.h"
#include "audio/audio_driver.h"
#include "camera/camera_driver.h"
#include "location/location_driver.h"
#include "record/record_driver.h"
#include "libretro_version_1.h"
#include "performance.h"
#include "core.h"
#include "performance_counters.h"
#include "system.h"
#include "gfx/video_context_driver.h"
#include "cores/internal_cores.h"
#include "frontend/frontend_driver.h"
#include "content.h"
#ifdef HAVE_CHEEVOS
#include "cheevos.h"
#endif
#include "retroarch.h"
#include "configuration.h"
#include "general.h"
@ -53,7 +59,7 @@
#define SYMBOL(x) do { \
function_t func = dylib_proc(lib_handle, #x); \
memcpy(&current_core->x, &func, sizeof(func)); \
if (current_core->x == NULL) { RARCH_ERR("Failed to load symbol: \"%s\"\n", #x); retro_fail(1, "init_libretro_sym()"); } \
if (current_core->x == NULL) { RARCH_ERR("Failed to load symbol: \"%s\"\n", #x); retroarch_fail(1, "init_libretro_sym()"); } \
} while (0)
static dylib_t lib_handle;
@ -306,14 +312,14 @@ static void load_dynamic_core(void)
RARCH_ERR("This could happen if other modules RetroArch depends on "
"link against libretro directly.\n");
RARCH_ERR("Proceeding could cause a crash. Aborting ...\n");
retro_fail(1, "init_libretro_sym()");
retroarch_fail(1, "init_libretro_sym()");
}
if (!*settings->path.libretro)
{
RARCH_ERR("RetroArch is built for dynamic libretro cores, but "
"libretro_path is not set. Cannot continue.\n");
retro_fail(1, "init_libretro_sym()");
retroarch_fail(1, "init_libretro_sym()");
}
/* Need to use absolute path for this setting. It can be
@ -329,7 +335,7 @@ static void load_dynamic_core(void)
RARCH_ERR("Failed to open libretro core: \"%s\"\n",
settings->path.libretro);
RARCH_ERR("Error(s): %s\n", dylib_error());
retro_fail(1, "load_dynamic()");
retroarch_fail(1, "load_dynamic()");
}
}
#endif
@ -513,7 +519,7 @@ void libretro_get_current_core_pathname(char *name, size_t size)
if (size == 0)
return;
core_ctl(CORE_CTL_RETRO_GET_SYSTEM_INFO, &info);
core_get_system_info(&info);
if (info.library_name)
id = info.library_name;
@ -620,6 +626,106 @@ static void rarch_log_libretro(enum retro_log_level level,
va_end(vp);
}
static size_t mmap_add_bits_down(size_t n)
{
n |= n >> 1;
n |= n >> 2;
n |= n >> 4;
n |= n >> 8;
n |= n >> 16;
/* double shift to avoid warnings on 32bit (it's dead code, but compilers suck) */
if (sizeof(size_t) > 4)
n |= n >> 16 >> 16;
return n;
}
static size_t mmap_inflate(size_t addr, size_t mask)
{
while (mask)
{
size_t tmp = (mask - 1) & ~mask;
/* to put in an 1 bit instead, OR in tmp+1 */
addr = ((addr & ~tmp) << 1) | (addr & tmp);
mask = mask & (mask - 1);
}
return addr;
}
static size_t mmap_reduce(size_t addr, size_t mask)
{
while (mask)
{
size_t tmp = (mask - 1) & ~mask;
addr = (addr & tmp) | ((addr >> 1) & ~tmp);
mask = (mask & (mask - 1)) >> 1;
}
return addr;
}
static size_t mmap_highest_bit(size_t n)
{
n = mmap_add_bits_down(n);
return n ^ (n >> 1);
}
static bool mmap_preprocess_descriptors(struct retro_memory_descriptor *first, unsigned count)
{
struct retro_memory_descriptor *desc;
const struct retro_memory_descriptor *end;
size_t top_addr, disconnect_mask;
end = first + count;
top_addr = 1;
for (desc = first; desc < end; desc++)
{
if (desc->select != 0)
top_addr |= desc->select;
else
top_addr |= desc->start + desc->len - 1;
}
top_addr = mmap_add_bits_down(top_addr);
for (desc = first; desc < end; desc++)
{
if (desc->select == 0)
{
if (desc->len == 0)
return false;
if ((desc->len & (desc->len - 1)) != 0)
return false;
desc->select = top_addr & ~mmap_inflate(mmap_add_bits_down(desc->len - 1), desc->disconnect);
}
if (desc->len == 0)
desc->len = mmap_add_bits_down(mmap_reduce(top_addr & ~desc->select, desc->disconnect)) + 1;
if (desc->start & ~desc->select)
return false;
while (mmap_reduce(top_addr & ~desc->select, desc->disconnect) >> 1 > desc->len - 1)
desc->disconnect |= mmap_highest_bit(top_addr & ~desc->select & ~desc->disconnect);
disconnect_mask = mmap_add_bits_down(desc->len - 1);
desc->disconnect &= disconnect_mask;
while ((~disconnect_mask) >> 1 & desc->disconnect)
{
disconnect_mask >>= 1;
desc->disconnect &= disconnect_mask;
}
}
return true;
}
/**
* rarch_environment_cb:
* @cmd : Identifier of command.
@ -739,7 +845,7 @@ bool rarch_environment_cb(unsigned cmd, void *data)
break;
case RETRO_ENVIRONMENT_GET_SAVE_DIRECTORY:
*(const char**)data = rarch_get_current_savefile_dir();
*(const char**)data = retroarch_get_current_savefile_dir();
break;
case RETRO_ENVIRONMENT_GET_USERNAME:
@ -874,7 +980,7 @@ bool rarch_environment_cb(unsigned cmd, void *data)
}
}
core_ctl(CORE_CTL_SET_INPUT_DESCRIPTORS, NULL);
core_set_input_descriptors();
break;
}
@ -910,7 +1016,7 @@ bool rarch_environment_cb(unsigned cmd, void *data)
struct retro_hw_render_callback *cb =
(struct retro_hw_render_callback*)data;
video_driver_ctl(RARCH_DISPLAY_CTL_HW_CONTEXT_GET, &hwr);
hwr = video_driver_get_hw_context();
RARCH_LOG("Environ SET_HW_RENDER.\n");
@ -970,8 +1076,16 @@ bool rarch_environment_cb(unsigned cmd, void *data)
break;
case RETRO_HW_CONTEXT_OPENGL_CORE:
{
gfx_ctx_flags_t flags;
flags.flags = 0;
BIT32_SET(flags.flags, GFX_CTX_FLAGS_GL_CORE_CONTEXT);
video_context_driver_set_flags(&flags);
RARCH_LOG("Requesting core OpenGL context (%u.%u).\n",
cb->version_major, cb->version_minor);
}
break;
#endif
@ -997,9 +1111,9 @@ bool rarch_environment_cb(unsigned cmd, void *data)
RARCH_LOG("Environ SET_SUPPORT_NO_GAME: %s.\n", state ? "yes" : "no");
if (state)
content_ctl(CONTENT_CTL_SET_DOES_NOT_NEED_CONTENT, NULL);
content_set_does_not_need_content();
else
content_ctl(CONTENT_CTL_UNSET_DOES_NOT_NEED_CONTENT, NULL);
content_unset_does_not_need_content();
break;
}
@ -1013,17 +1127,14 @@ bool rarch_environment_cb(unsigned cmd, void *data)
break;
}
/* FIXME - PS3 audio driver needs to be fixed so that threaded
* audio works correctly (audio is already on a thread for PS3
* audio driver so that's probably the problem) */
#if defined(HAVE_THREADS) && !defined(__CELLOS_LV2__)
case RETRO_ENVIRONMENT_SET_AUDIO_CALLBACK:
#if defined(HAVE_THREADS) && !defined(__CELLOS_LV2__)
{
RARCH_LOG("Environ SET_AUDIO_CALLBACK.\n");
audio_driver_ctl(RARCH_AUDIO_CTL_SET_CALLBACK, data);
break;
audio_driver_set_callback(data);
}
#endif
break;
case RETRO_ENVIRONMENT_SET_FRAME_TIME_CALLBACK:
{
@ -1047,7 +1158,7 @@ bool rarch_environment_cb(unsigned cmd, void *data)
uint64_t *mask = (uint64_t*)data;
RARCH_LOG("Environ GET_INPUT_DEVICE_CAPABILITIES.\n");
if (input_driver_ctl(RARCH_INPUT_CTL_HAS_CAPABILITIES, NULL))
if (input_driver_has_capabilities())
*mask = input_driver_get_capabilities();
else
return false;
@ -1112,9 +1223,9 @@ bool rarch_environment_cb(unsigned cmd, void *data)
struct retro_perf_callback *cb = (struct retro_perf_callback*)data;
RARCH_LOG("Environ GET_PERF_INTERFACE.\n");
cb->get_time_usec = retro_get_time_usec;
cb->get_cpu_features = retro_get_cpu_features;
cb->get_perf_counter = retro_get_perf_counter;
cb->get_time_usec = cpu_features_get_time_usec;
cb->get_cpu_features = cpu_features_get;
cb->get_perf_counter = cpu_features_get_perf_counter;
cb->perf_register = retro_perf_register;
cb->perf_start = retro_perf_start;
@ -1204,6 +1315,74 @@ bool rarch_environment_cb(unsigned cmd, void *data)
break;
}
case RETRO_ENVIRONMENT_SET_MEMORY_MAPS:
{
unsigned i;
struct retro_memory_descriptor *descriptors;
const struct retro_memory_map *mmaps =
(const struct retro_memory_map*)data;
free((void*)system->mmaps.descriptors);
system->mmaps.num_descriptors = 0;
descriptors = (struct retro_memory_descriptor*)
calloc(mmaps->num_descriptors, sizeof(*system->mmaps.descriptors));
if (!descriptors)
return false;
system->mmaps.descriptors = descriptors;
memcpy((void*)system->mmaps.descriptors, mmaps->descriptors,
mmaps->num_descriptors * sizeof(*system->mmaps.descriptors));
system->mmaps.num_descriptors = mmaps->num_descriptors;
mmap_preprocess_descriptors(descriptors, mmaps->num_descriptors);
RARCH_LOG("Environ SET_MEMORY_MAPS.\n");
if (sizeof(void *) == 8)
RARCH_LOG(" ndx flags ptr offset start select disconn len addrspace\n");
else
RARCH_LOG(" ndx flags ptr offset start select disconn len addrspace\n");
for (i = 0; i < system->mmaps.num_descriptors; i++)
{
const struct retro_memory_descriptor *desc =
&system->mmaps.descriptors[i];
char flags[7];
flags[0] = 'M';
if ((desc->flags & RETRO_MEMDESC_MINSIZE_8) == RETRO_MEMDESC_MINSIZE_8)
flags[1] = '8';
else if ((desc->flags & RETRO_MEMDESC_MINSIZE_4) == RETRO_MEMDESC_MINSIZE_4)
flags[1] = '4';
else if ((desc->flags & RETRO_MEMDESC_MINSIZE_2) == RETRO_MEMDESC_MINSIZE_2)
flags[1] = '2';
else
flags[1] = '1';
flags[2] = 'A';
if ((desc->flags & RETRO_MEMDESC_ALIGN_8) == RETRO_MEMDESC_ALIGN_8)
flags[3] = '8';
else if ((desc->flags & RETRO_MEMDESC_ALIGN_4) == RETRO_MEMDESC_ALIGN_4)
flags[3] = '4';
else if ((desc->flags & RETRO_MEMDESC_ALIGN_2) == RETRO_MEMDESC_ALIGN_2)
flags[3] = '2';
else
flags[3] = '1';
flags[4] = (desc->flags & RETRO_MEMDESC_BIGENDIAN) ? 'B' : 'b';
flags[5] = (desc->flags & RETRO_MEMDESC_CONST) ? 'C' : 'c';
flags[6] = 0;
RARCH_LOG(" %03u %s %p %08X %08X %08X %08X %08X %s\n",
i + 1, flags, desc->ptr, desc->offset, desc->start,
desc->select, desc->disconnect, desc->len,
desc->addrspace ? desc->addrspace : "");
}
break;
}
case RETRO_ENVIRONMENT_SET_GEOMETRY:
{
const struct retro_game_geometry *in_geom = NULL;
@ -1236,7 +1415,7 @@ bool rarch_environment_cb(unsigned cmd, void *data)
/* Forces recomputation of aspect ratios if
* using core-dependent aspect ratios. */
event_cmd_ctl(EVENT_CMD_VIDEO_SET_ASPECT_RATIO, NULL);
command_event(CMD_EVENT_VIDEO_SET_ASPECT_RATIO, NULL);
/* TODO: Figure out what to do, if anything, with recording. */
}
@ -1244,17 +1423,22 @@ bool rarch_environment_cb(unsigned cmd, void *data)
}
case RETRO_ENVIRONMENT_GET_CURRENT_SOFTWARE_FRAMEBUFFER:
return video_driver_ctl(
RARCH_DISPLAY_CTL_GET_CURRENT_SOFTWARE_FRAMEBUFFER,
return video_driver_get_current_software_framebuffer(
(struct retro_framebuffer*)data);
case RETRO_ENVIRONMENT_GET_HW_RENDER_INTERFACE:
return video_driver_ctl(
RARCH_DISPLAY_CTL_GET_HW_RENDER_INTERFACE,
return video_driver_get_hw_render_interface(
(const struct retro_hw_render_interface**)data);
/* Private extensions for internal use, not part of libretro API. */
/* None yet. */
case RETRO_ENVIRONMENT_SET_SUPPORT_ACHIEVEMENTS:
#ifdef HAVE_CHEEVOS
{
bool state = *(const bool*)data;
RARCH_LOG("Environ SET_SUPPORT_ACHIEVEMENTS: %s.\n", state ? "yes" : "no");
cheevos_set_support_cheevos(state);
}
#endif
break;
/* Default */
default:

View File

@ -18,9 +18,9 @@
#define __DYNAMIC_H
#include <boolean.h>
#include <libretro.h>
#include "core_type.h"
#include "libretro.h"
#ifdef HAVE_CONFIG_H
#include "config.h"

View File

@ -13,6 +13,10 @@
* If not, see <http://www.gnu.org/licenses/>.
*/
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include <stdlib.h>
#include <boolean.h>
#include <string.h>
@ -137,6 +141,53 @@ void fill_pathname_abbreviate_special(char *out_path,
retro_assert(strlcpy(out_path, in_path, size) < size);
}
bool fill_pathname_application_data(char *s, size_t len)
{
#if defined(_WIN32) && !defined(_XBOX)
const char *appdata = getenv("APPDATA");
if (appdata)
{
strlcpy(s, appdata, len);
return true;
}
#elif defined(OSX)
const char *appdata = getenv("HOME");
if (appdata)
{
fill_pathname_join(s, appdata,
"Library/Application Support/RetroArch", len);
return true;
}
#elif !defined(RARCH_CONSOLE)
const char *xdg = getenv("XDG_CONFIG_HOME");
const char *appdata = getenv("HOME");
/* XDG_CONFIG_HOME falls back to $HOME/.config. */
if (xdg)
{
fill_pathname_join(s, xdg, "retroarch", len);
return true;
}
if (appdata)
{
#ifdef __HAIKU__
fill_pathname_join(s, appdata,
"config/settings/retroarch/", len);
#else
fill_pathname_join(s, appdata,
".config/retroarch/", len);
#endif
return true;
}
#endif
return false;
}
#if !defined(RARCH_CONSOLE)
void fill_pathname_application_path(char *s, size_t len)
{

27
file_path_special.h Normal file
View File

@ -0,0 +1,27 @@
/* RetroArch - A frontend for libretro.
* Copyright (C) 2010-2014 - Hans-Kristian Arntzen
* Copyright (C) 2011-2016 - Daniel De Matteis
*
* RetroArch is free software: you can redistribute it and/or modify it under the terms
* of the GNU General Public License as published by the Free Software Found-
* ation, either version 3 of the License, or (at your option) any later version.
*
* RetroArch is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
* PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with RetroArch.
* If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef _FILE_PATH_SPECIAL_H
#define _FILE_PATH_SPECIAL_H
#include <stdint.h>
#include <stddef.h>
#include <boolean.h>
bool fill_pathname_application_data(char *s, size_t len);
#endif

View File

@ -74,8 +74,10 @@ static void frontend_ctr_get_environment_settings(int *argc, char *argv[],
"system", sizeof(g_defaults.dir.system));
fill_pathname_join(g_defaults.dir.playlist, g_defaults.dir.core,
"playlists", sizeof(g_defaults.dir.playlist));
fill_pathname_join(g_defaults.dir.menu_config, g_defaults.dir.port,
"config", sizeof(g_defaults.dir.menu_config));
fill_pathname_join(g_defaults.dir.remap, g_defaults.dir.port,
"remaps", sizeof(g_defaults.dir.remap));
"config/remaps", sizeof(g_defaults.dir.remap));
fill_pathname_join(g_defaults.dir.video_filter, g_defaults.dir.port,
"filters", sizeof(g_defaults.dir.remap));
fill_pathname_join(g_defaults.path.config, g_defaults.dir.port,
@ -93,7 +95,7 @@ static void frontend_ctr_deinit(void *data)
*verbose = true;
#ifdef HAVE_FILE_LOGGER
event_cmd_ctl(EVENT_CMD_LOG_FILE_DEINIT, NULL);
command_event(CMD_EVENT_LOG_FILE_DEINIT, NULL);
#endif
if(gfxBottomFramebuffers[0] == (u8*)currentConsole->frameBuffer)

View File

@ -46,6 +46,7 @@
#include <rhash.h>
#include "../frontend_driver.h"
#include "../../file_path_special.h"
#include "../../defaults.h"
#include "../../general.h"
#include "../../verbosity.h"
@ -360,33 +361,43 @@ static void frontend_darwin_get_environment_settings(int *argc, char *argv[],
fill_pathname_join(g_defaults.dir.core_assets, home_dir_buf, "downloads", sizeof(g_defaults.dir.core_assets));
fill_pathname_join(g_defaults.dir.assets, home_dir_buf, "assets", sizeof(g_defaults.dir.assets));
fill_pathname_join(g_defaults.dir.system, home_dir_buf, "system", sizeof(g_defaults.dir.system));
fill_pathname_join(g_defaults.dir.menu_config, home_dir_buf, "configs", sizeof(g_defaults.dir.menu_config));
fill_pathname_join(g_defaults.dir.menu_config, home_dir_buf, "config", sizeof(g_defaults.dir.menu_config));
fill_pathname_join(g_defaults.path.config, g_defaults.dir.menu_config, "retroarch.cfg", sizeof(g_defaults.path.config));
fill_pathname_join(g_defaults.dir.remap, g_defaults.dir.menu_config, "remaps", sizeof(g_defaults.dir.remap));
fill_pathname_join(g_defaults.dir.database, home_dir_buf, "database/rdb", sizeof(g_defaults.dir.database));
fill_pathname_join(g_defaults.dir.cursor, home_dir_buf, "database/cursors", sizeof(g_defaults.dir.cursor));
fill_pathname_join(g_defaults.dir.cheats, home_dir_buf, "cht", sizeof(g_defaults.dir.cheats));
fill_pathname_join(g_defaults.dir.thumbnails, home_dir_buf, "thumbnails", sizeof(g_defaults.dir.thumbnails));
fill_pathname_join(g_defaults.dir.sram, home_dir_buf, "saves", sizeof(g_defaults.dir.sram));
fill_pathname_join(g_defaults.dir.savestate, home_dir_buf, "states", sizeof(g_defaults.dir.savestate));
fill_pathname_join(g_defaults.dir.remap, home_dir_buf, "remaps", sizeof(g_defaults.dir.remap));
fill_pathname_join(g_defaults.dir.menu_config, home_dir_buf, "config", sizeof(g_defaults.dir.menu_config));
#if defined(IOS)
fill_pathname_join(g_defaults.dir.playlist, home_dir_buf, "playlists", sizeof(g_defaults.dir.playlist));
#endif
#if defined(OSX)
char application_data[PATH_MAX_LENGTH];
fill_pathname_application_data(application_data, sizeof(application_data));
#ifdef HAVE_CG
fill_pathname_join(g_defaults.dir.shader, home_dir_buf, "shaders_cg", sizeof(g_defaults.dir.shader));
#endif
fill_pathname_join(g_defaults.dir.audio_filter, home_dir_buf, "audio_filters", sizeof(g_defaults.dir.audio_filter));
fill_pathname_join(g_defaults.dir.video_filter, home_dir_buf, "video_filters", sizeof(g_defaults.dir.video_filter));
fill_pathname_join(g_defaults.dir.playlist, home_dir_buf, "playlists", sizeof(g_defaults.dir.playlist));
fill_pathname_join(g_defaults.dir.playlist, application_data, "playlists", sizeof(g_defaults.dir.playlist));
fill_pathname_join(g_defaults.dir.thumbnails, application_data, "thumbnails", sizeof(g_defaults.dir.thumbnails));
fill_pathname_join(g_defaults.dir.menu_config, application_data, "config", sizeof(g_defaults.dir.menu_config));
fill_pathname_join(g_defaults.path.config, g_defaults.dir.menu_config, "retroarch.cfg", sizeof(g_defaults.path.config));
fill_pathname_join(g_defaults.dir.remap, g_defaults.dir.menu_config, "remaps", sizeof(g_defaults.dir.remap));
fill_pathname_join(g_defaults.dir.core_assets, application_data, "downloads", sizeof(g_defaults.dir.core_assets));
fill_pathname_join(g_defaults.dir.screenshot, application_data, "screenshots", sizeof(g_defaults.dir.screenshot));
#if defined(RELEASE_BUILD)
fill_pathname_join(g_defaults.dir.remap, bundle_path_buf, "Contents/Resources/remaps", sizeof(g_defaults.dir.remap));
fill_pathname_join(g_defaults.dir.playlist, bundle_path_buf, "Contents/Resources/playlists", sizeof(g_defaults.dir.playlist));
fill_pathname_join(g_defaults.dir.shader, bundle_path_buf, "Contents/Resources/shaders", sizeof(g_defaults.dir.shader));
fill_pathname_join(g_defaults.dir.core, bundle_path_buf, "Contents/Resources/cores", sizeof(g_defaults.dir.core));
fill_pathname_join(g_defaults.dir.core_info, bundle_path_buf, "Contents/Resources/info", sizeof(g_defaults.dir.core_info));
fill_pathname_join(g_defaults.dir.overlay, bundle_path_buf, "Contents/Resources/overlays", sizeof(g_defaults.dir.overlay));
fill_pathname_join(g_defaults.dir.autoconfig, bundle_path_buf, "Contents/Resources/autoconfig", sizeof(g_defaults.dir.autoconfig));
fill_pathname_join(g_defaults.dir.core_assets, bundle_path_buf, "Contents/Resources/downloads", sizeof(g_defaults.dir.core_assets));
fill_pathname_join(g_defaults.dir.assets, bundle_path_buf, "Contents/Resources/assets", sizeof(g_defaults.dir.assets));
fill_pathname_join(g_defaults.dir.menu_config, bundle_path_buf, "Contents/Resources/configs", sizeof(g_defaults.dir.menu_config));
fill_pathname_join(g_defaults.path.config, g_defaults.dir.menu_config, "retroarch.cfg", sizeof(g_defaults.path.config));
fill_pathname_join(g_defaults.dir.database, bundle_path_buf, "Contents/Resources/database/rdb", sizeof(g_defaults.dir.database));
fill_pathname_join(g_defaults.dir.cursor, bundle_path_buf, "Contents/Resources/database/cursors", sizeof(g_defaults.dir.cursor));
fill_pathname_join(g_defaults.dir.cheats, bundle_path_buf, "Contents/Resources/cht", sizeof(g_defaults.dir.cheats));

View File

@ -26,7 +26,7 @@
#include "../../retroarch.h"
#include "../../runloop.h"
#include "../frontend_driver.h"
#include "../../command_event.h"
#include "../../command.h"
static void emscripten_mainloop(void)
{
@ -34,7 +34,7 @@ static void emscripten_mainloop(void)
int ret = runloop_iterate(&sleep_ms);
if (ret == 1 && sleep_ms > 0)
retro_sleep(sleep_ms);
runloop_ctl(RUNLOOP_CTL_DATA_ITERATE, NULL);
runloop_iterate_data();
if (ret != -1)
return;
@ -44,22 +44,22 @@ static void emscripten_mainloop(void)
void cmd_savefiles(void)
{
event_cmd_ctl(EVENT_CMD_SAVEFILES, NULL);
command_event(CMD_EVENT_SAVEFILES, NULL);
}
void cmd_save_state(void)
{
event_cmd_ctl(EVENT_CMD_SAVE_STATE, NULL);
command_event(CMD_EVENT_SAVE_STATE, NULL);
}
void cmd_load_state(void)
{
event_cmd_ctl(EVENT_CMD_LOAD_STATE, NULL);
command_event(CMD_EVENT_LOAD_STATE, NULL);
}
void cmd_take_screenshot(void)
{
event_cmd_ctl(EVENT_CMD_TAKE_SCREENSHOT, NULL);
command_event(CMD_EVENT_TAKE_SCREENSHOT, NULL);
}

View File

@ -172,6 +172,24 @@ static void frontend_gx_get_environment_settings(
#elif defined(HAVE_FILE_LOGGER)
retro_main_log_file_init("/retroarch-log.txt");
#endif
/* This situation can happen on some loaders so we really need some
fake args or else retroarch will just crash on parsing NULL pointers */
if(*argc == 0 || argv == NULL)
{
struct rarch_main_wrap *args = (struct rarch_main_wrap*)params_data;
if (args)
{
args->touched = true;
args->no_content = false;
args->verbose = false;
args->config_path = NULL;
args->sram_path = NULL;
args->state_path = NULL;
args->content_path = NULL;
args->libretro_path = NULL;
}
}
#endif
#ifdef HW_DOL
@ -408,7 +426,7 @@ static bool frontend_gx_set_fork(enum frontend_fork fork_mode)
case FRONTEND_FORK_RESTART:
RARCH_LOG("FRONTEND_FORK_RESTART\n");
gx_fork_mode = fork_mode;
rarch_ctl(RARCH_CTL_FORCE_QUIT, NULL);
command_event(CMD_EVENT_QUIT, NULL);
break;
case FRONTEND_FORK_NONE:
default:

View File

@ -48,399 +48,43 @@
#include "../frontend_driver.h"
#include "../../defaults.h"
#include "../../general.h"
#include "../../retroarch.h"
#include "../../verbosity.h"
#include "platform_linux.h"
/* This small data type is used to represent a CPU list / mask,
* as read from sysfs on Linux.
*
* See http://www.kernel.org/doc/Documentation/cputopology.txt
*
* For now, we don't expect more than 32 cores on mobile devices,
* so keep everything simple.
*/
typedef struct
#ifdef ANDROID
enum
{
uint32_t mask;
} CpuList;
/* Internal SDCARD writable */
INT_SD_WRITABLE = 1,
/* Internal SDCARD not writable but the private app dir is */
INT_SD_APPDIR_WRITABLE,
/* Internal SDCARD not writable at all */
INT_SD_NOT_WRITABLE
};
static bool cpu_inited_once;
static enum cpu_family g_cpuFamily;
static uint64_t g_cpuFeatures;
static int g_cpuCount;
struct android_app *g_android;
static pthread_key_t thread_key;
static char screenshot_dir[PATH_MAX_LENGTH];
static char downloads_dir[PATH_MAX_LENGTH];
static char apk_dir[PATH_MAX_LENGTH];
static char app_dir[PATH_MAX_LENGTH];
static char int_sd_dir[PATH_MAX_LENGTH];
static char int_sd_app_dir[PATH_MAX_LENGTH];
#else
static const char *proc_apm_path = "/proc/apm";
static const char *proc_acpi_battery_path = "/proc/acpi/battery";
static const char *proc_acpi_sysfs_ac_adapter_path = "/sys/class/power_supply/ACAD";
static const char *proc_acpi_sysfs_battery_path = "/sys/class/power_supply";
static const char *proc_acpi_ac_adapter_path = "/proc/acpi/ac_adapter";
#endif
#ifndef HAVE_DYNAMIC
static enum frontend_fork linux_fork_mode = FRONTEND_FORK_NONE;
#endif
#ifdef __arm__
# define DEFAULT_CPU_FAMILY CPU_FAMILY_ARM
#elif defined __i386__
# define DEFAULT_CPU_FAMILY CPU_FAMILY_X86
#else
# define DEFAULT_CPU_FAMILY CPU_FAMILY_UNKNOWN
#endif
#ifdef __i386__
void x86_cpuid(int func, int flags[4]);
#endif
#ifdef __ARM_ARCH__
/* Extract the content of a the first occurrence of a given field in
* the content of /proc/cpuinfo and return it as a heap-allocated
* string that must be freed by the caller.
*
* Return NULL if not found
*/
static char *extract_cpuinfo_field(char* buffer,
ssize_t length, const char* field)
{
int len;
const char *q;
int fieldlen = strlen(field);
char* bufend = buffer + length;
char* result = NULL;
/* Look for first field occurrence,
* and ensures it starts the line. */
const char *p = buffer;
for (;;)
{
p = memmem(p, bufend-p, field, fieldlen);
if (p == NULL)
return result;
if (p == buffer || p[-1] == '\n')
break;
p += fieldlen;
}
/* Skip to the first column followed by a space */
p += fieldlen;
p = memchr(p, ':', bufend-p);
if (p == NULL || p[1] != ' ')
return result;
/* Find the end of the line */
p += 2;
q = memchr(p, '\n', bufend-p);
if (q == NULL)
q = bufend;
/* Copy the line into a heap-allocated buffer */
len = q-p;
result = malloc(len+1);
if (result == NULL)
return result;
memcpy(result, p, len);
result[len] = '\0';
return result;
}
/* Checks that a space-separated list of items
* contains one given 'item'.
* Returns 1 if found, 0 otherwise.
*/
static int has_list_item(const char* list, const char* item)
{
const char* p = list;
int itemlen = strlen(item);
if (list == NULL)
return 0;
while (*p)
{
const char* q;
/* skip spaces */
while (*p == ' ' || *p == '\t')
p++;
/* find end of current list item */
q = p;
while (*q && *q != ' ' && *q != '\t')
q++;
if (itemlen == q-p && !memcmp(p, item, itemlen))
return 1;
/* skip to next item */
p = q;
}
return 0;
}
#endif
/* Parse an decimal integer starting from 'input', but not going further
* than 'limit'. Return the value into '*result'.
*
* NOTE: Does not skip over leading spaces, or deal with sign characters.
* NOTE: Ignores overflows.
*
* The function returns NULL in case of error (bad format), or the new
* position after the decimal number in case of success (which will always
* be <= 'limit').
*/
static const char *parse_decimal(const char* input,
const char* limit, int* result)
{
const char* p = input;
int val = 0;
while (p < limit)
{
int d = (*p - '0');
if ((unsigned)d >= 10U)
break;
val = val*10 + d;
p++;
}
if (p == input)
return NULL;
*result = val;
return p;
}
/* Parse a textual list of cpus and store the result inside a CpuList object.
* Input format is the following:
* - comma-separated list of items (no spaces)
* - each item is either a single decimal number (cpu index), or a range made
* of two numbers separated by a single dash (-). Ranges are inclusive.
*
* Examples: 0
* 2,4-127,128-143
* 0-1
*/
static void cpulist_parse(CpuList* list, char **buf, ssize_t length)
{
const char* p = (const char*)buf;
const char* end = p + length;
/* NOTE: the input line coming from sysfs typically contains a
* trailing newline, so take care of it in the code below
*/
while (p < end && *p != '\n')
{
int val, start_value, end_value;
/* Find the end of current item, and put it into 'q' */
const char *q = (const char*)memchr(p, ',', end-p);
if (!q)
q = end;
/* Get first value */
p = parse_decimal(p, q, &start_value);
if (p == NULL)
return;
end_value = start_value;
/* If we're not at the end of the item, expect a dash and
* and integer; extract end value.
*/
if (p < q && *p == '-')
{
p = parse_decimal(p+1, q, &end_value);
if (p == NULL)
return;
}
/* Set bits CPU list bits */
for (val = start_value; val <= end_value; val++)
{
if ((unsigned)val < 32)
list->mask |= (uint32_t)(1U << val);
}
/* Jump to next item */
p = q;
if (p < end)
p++;
}
}
/* Read a CPU list from one sysfs file */
static void cpulist_read_from(CpuList* list, const char* filename)
{
ssize_t length;
char *buf = NULL;
list->mask = 0;
if (filestream_read_file(filename, (void**)&buf, &length) != 1)
{
RARCH_ERR("Could not read %s: %s\n", filename, strerror(errno));
return;
}
cpulist_parse(list, &buf, length);
if (buf)
free(buf);
buf = NULL;
}
/* Return the number of cpus present on a given device.
*
* To handle all weird kernel configurations, we need to compute the
* intersection of the 'present' and 'possible' CPU lists and count
* the result.
*/
static int get_cpu_count(void)
{
CpuList cpus_present[1];
CpuList cpus_possible[1];
cpulist_read_from(cpus_present, "/sys/devices/system/cpu/present");
cpulist_read_from(cpus_possible, "/sys/devices/system/cpu/possible");
/* Compute the intersection of both sets to get the actual number of
* CPU cores that can be used on this device by the kernel.
*/
cpus_present->mask &= cpus_possible->mask;
return __builtin_popcount(cpus_present->mask);
}
static void linux_cpu_init(void)
{
ssize_t length;
void *buf = NULL;
g_cpuFamily = DEFAULT_CPU_FAMILY;
g_cpuFeatures = 0;
g_cpuCount = 1;
if (filestream_read_file("/proc/cpuinfo", &buf, &length) != 1)
return;
/* Count the CPU cores, the value may be 0 for single-core CPUs */
g_cpuCount = get_cpu_count();
if (g_cpuCount == 0)
g_cpuCount = 1;
RARCH_LOG("found cpuCount = %d\n", g_cpuCount);
#ifdef __ARM_ARCH__
/* Extract architecture from the "CPU Architecture" field.
* The list is well-known, unlike the the output of
* the 'Processor' field which can vary greatly.
*
* See the definition of the 'proc_arch' array in
* $KERNEL/arch/arm/kernel/setup.c and the 'c_show' function in
* same file.
*/
char* cpu_arch = extract_cpuinfo_field(buf, length, "CPU architecture");
if (cpu_arch)
{
char* end;
int has_armv7 = 0;
/* read the initial decimal number, ignore the rest */
long arch_number = strtol(cpu_arch, &end, 10);
RARCH_LOG("Found CPU architecture = '%s'\n", cpu_arch);
/* Here we assume that ARMv8 will be upwards compatible with v7
* in the future. Unfortunately, there is no 'Features' field to
* indicate that Thumb-2 is supported.
*/
if (end > cpu_arch && arch_number >= 7)
has_armv7 = 1;
/* Unfortunately, it seems that certain ARMv6-based CPUs
* report an incorrect architecture number of 7!
*
* See http://code.google.com/p/android/issues/detail?id=10812
*
* We try to correct this by looking at the 'elf_format'
* field reported by the 'Processor' field, which is of the
* form of "(v7l)" for an ARMv7-based CPU, and "(v6l)" for
* an ARMv6-one.
*/
if (has_armv7)
{
char *cpu_proc = extract_cpuinfo_field(buf, length,
"Processor");
if (cpu_proc != NULL)
{
RARCH_LOG("found cpu_proc = '%s'\n", cpu_proc);
if (has_list_item(cpu_proc, "(v6l)"))
{
RARCH_ERR("CPU processor and architecture mismatch!!\n");
has_armv7 = 0;
}
free(cpu_proc);
}
}
if (has_armv7)
g_cpuFeatures |= CPU_ARM_FEATURE_ARMv7;
/* The LDREX / STREX instructions are available from ARMv6 */
if (arch_number >= 6)
g_cpuFeatures |= CPU_ARM_FEATURE_LDREX_STREX;
free(cpu_arch);
}
/* Extract the list of CPU features from 'Features' field */
char* cpu_features = extract_cpuinfo_field(buf, length, "Features");
if (cpu_features)
{
RARCH_LOG("found cpu_features = '%s'\n", cpu_features);
if (has_list_item(cpu_features, "vfpv3"))
g_cpuFeatures |= CPU_ARM_FEATURE_VFPv3;
else if (has_list_item(cpu_features, "vfpv3d16"))
g_cpuFeatures |= CPU_ARM_FEATURE_VFPv3;
/* Note: Certain kernels only report NEON but not VFPv3
* in their features list. However, ARM mandates
* that if NEON is implemented, so must be VFPv3
* so always set the flag.
*/
if (has_list_item(cpu_features, "neon"))
g_cpuFeatures |= CPU_ARM_FEATURE_NEON | CPU_ARM_FEATURE_VFPv3;
free(cpu_features);
}
#endif /* __ARM_ARCH__ */
#ifdef __i386__
g_cpuFamily = CPU_FAMILY_X86;
#elif defined(_MIPS_ARCH)
g_cpuFamily = CPU_FAMILY_MIPS;
#endif
if (buf)
free(buf);
buf = NULL;
}
enum cpu_family linux_get_cpu_platform(void)
{
return g_cpuFamily;
}
uint64_t linux_get_cpu_features(void)
{
return g_cpuFeatures;
}
int linux_get_cpu_count(void)
{
return g_cpuCount;
}
int system_property_get(const char *command,
const char *args, char *value)
{
@ -484,21 +128,6 @@ error:
}
#ifdef ANDROID
#define SDCARD_ROOT_WRITABLE 1
#define SDCARD_EXT_DIR_WRITABLE 2
#define SDCARD_NOT_WRITABLE 3
struct android_app *g_android;
static pthread_key_t thread_key;
char screenshot_dir[PATH_MAX_LENGTH];
char downloads_dir[PATH_MAX_LENGTH];
char apk_path[PATH_MAX_LENGTH];
char sdcard_dir[PATH_MAX_LENGTH];
char app_dir[PATH_MAX_LENGTH];
char ext_dir[PATH_MAX_LENGTH];
/* forward declaration */
bool android_run_events(void *data);
@ -739,7 +368,7 @@ static void android_app_entry(void *data)
if (ret == 1 && sleep_ms > 0)
retro_sleep(sleep_ms);
runloop_ctl(RUNLOOP_CTL_DATA_ITERATE, NULL);
runloop_iterate_data();
}while (ret != -1);
main_exit(data);
@ -933,12 +562,6 @@ static void frontend_android_shutdown(bool unused)
}
#else
static const char *proc_apm_path = "/proc/apm";
static const char *proc_acpi_battery_path = "/proc/acpi/battery";
static const char *proc_acpi_sysfs_ac_adapter_path= "/sys/class/power_supply/ACAD";
static const char *proc_acpi_sysfs_battery_path= "/sys/class/power_supply";
static const char *proc_acpi_ac_adapter_path = "/proc/acpi/ac_adapter";
static bool make_proc_acpi_key_val(char **_ptr, char **_key, char **_val)
{
@ -1009,6 +632,9 @@ static void check_proc_acpi_battery(const char * node, bool * have_battery,
snprintf(path, sizeof(path), "%s/%s/%s", base, node, "state");
if (!path_file_exists(path))
goto end;
if (!filestream_read_file(path, (void**)&buf, &length))
goto end;
@ -1134,6 +760,8 @@ static void check_proc_acpi_sysfs_battery(const char *node,
return;
snprintf(path, sizeof(path), "%s/%s/%s", base, node, "status");
if (!path_file_exists(path))
return;
if (filestream_read_file(path, (void**)&buf, &length) != 1)
return;
@ -1167,6 +795,8 @@ static void check_proc_acpi_ac_adapter(const char * node, bool *have_ac)
ssize_t length = 0;
snprintf(path, sizeof(path), "%s/%s/%s", base, node, "state");
if (!path_file_exists(path))
return;
if (filestream_read_file(path, (void**)&buf, &length) != 1)
return;
@ -1194,6 +824,8 @@ static void check_proc_acpi_sysfs_ac_adapter(const char * node, bool *have_ac)
const char *base = proc_acpi_sysfs_ac_adapter_path;
snprintf(path, sizeof(path), "%s/%s", base, "online");
if (!path_file_exists(path))
return;
if (filestream_read_file(path, (void**)&buf, &length) != 1)
return;
@ -1249,6 +881,8 @@ static bool frontend_linux_powerstate_check_apm(
char *buf = NULL;
char *str = NULL;
if (!path_file_exists(proc_apm_path))
goto error;
if (filestream_read_file(proc_apm_path, (void**)&buf, &length) != 1)
goto error;
@ -1671,15 +1305,15 @@ static void frontend_linux_get_env(int *argc,
{
const char *argv = (*env)->GetStringUTFChars(env, jstr, 0);
*sdcard_dir = '\0';
*int_sd_dir = '\0';
if (argv && *argv)
strlcpy(sdcard_dir, argv, sizeof(sdcard_dir));
strlcpy(int_sd_dir, argv, sizeof(int_sd_dir));
(*env)->ReleaseStringUTFChars(env, jstr, argv);
if (*sdcard_dir)
if (*int_sd_dir)
{
RARCH_LOG("External storage location [%s]\n", sdcard_dir);
RARCH_LOG("External storage location [%s]\n", int_sd_dir);
/* TODO base dir handler */
}
}
@ -1733,15 +1367,15 @@ static void frontend_linux_get_env(int *argc,
{
const char *argv = (*env)->GetStringUTFChars(env, jstr, 0);
*apk_path = '\0';
*apk_dir = '\0';
if (argv && *argv)
strlcpy(apk_path, argv, sizeof(apk_path));
strlcpy(apk_dir, argv, sizeof(apk_dir));
(*env)->ReleaseStringUTFChars(env, jstr, argv);
if (*apk_path)
if (*apk_dir)
{
RARCH_LOG("APK location [%s].\n", apk_path);
RARCH_LOG("APK location [%s].\n", apk_dir);
}
}
@ -1752,15 +1386,15 @@ static void frontend_linux_get_env(int *argc,
{
const char *argv = (*env)->GetStringUTFChars(env, jstr, 0);
*ext_dir = '\0';
*int_sd_app_dir = '\0';
if (argv && *argv)
strlcpy(ext_dir, argv, sizeof(ext_dir));
strlcpy(int_sd_app_dir, argv, sizeof(int_sd_app_dir));
(*env)->ReleaseStringUTFChars(env, jstr, argv);
if (*ext_dir)
if (*int_sd_app_dir)
{
RARCH_LOG("External files location [%s]\n", ext_dir);
RARCH_LOG("External files location [%s]\n", int_sd_app_dir);
}
}
@ -1779,20 +1413,20 @@ static void frontend_linux_get_env(int *argc,
strlcpy(app_dir, argv, sizeof(app_dir));
(*env)->ReleaseStringUTFChars(env, jstr, argv);
//set paths depending on the ability to write to sdcard_dir
//set paths depending on the ability to write to int_sd_dir
if(*sdcard_dir)
if(*int_sd_dir)
{
if(test_permissions(sdcard_dir))
perms = SDCARD_ROOT_WRITABLE;
if(test_permissions(int_sd_dir))
perms = INT_SD_WRITABLE;
}
else if(*ext_dir)
else if(*int_sd_app_dir)
{
if(test_permissions(ext_dir))
perms = SDCARD_EXT_DIR_WRITABLE;
if(test_permissions(int_sd_app_dir))
perms = INT_SD_APPDIR_WRITABLE;
}
else
perms = SDCARD_NOT_WRITABLE;
perms = INT_SD_NOT_WRITABLE;
RARCH_LOG("SD permissions: %d",perms);
@ -1829,16 +1463,8 @@ static void frontend_linux_get_env(int *argc,
app_dir, "database/rdb", sizeof(g_defaults.dir.database));
fill_pathname_join(g_defaults.dir.cursor,
app_dir, "database/cursors", sizeof(g_defaults.dir.cursor));
fill_pathname_join(g_defaults.dir.cheats,
app_dir, "cheats", sizeof(g_defaults.dir.cheats));
fill_pathname_join(g_defaults.dir.playlist,
app_dir, "playlists", sizeof(g_defaults.dir.playlist));
fill_pathname_join(g_defaults.dir.remap,
app_dir, "remaps", sizeof(g_defaults.dir.remap));
fill_pathname_join(g_defaults.dir.wallpapers,
app_dir, "wallpapers", sizeof(g_defaults.dir.wallpapers));
fill_pathname_join(g_defaults.dir.thumbnails,
app_dir, "thumbnails", sizeof(g_defaults.dir.thumbnails));
app_dir, "assets/wallpapers", sizeof(g_defaults.dir.wallpapers));
if(*downloads_dir && test_permissions(downloads_dir))
{
fill_pathname_join(g_defaults.dir.core_assets,
@ -1869,68 +1495,110 @@ static void frontend_linux_get_env(int *argc,
switch (perms)
{
case SDCARD_EXT_DIR_WRITABLE:
case INT_SD_APPDIR_WRITABLE:
fill_pathname_join(g_defaults.dir.sram,
ext_dir, "saves", sizeof(g_defaults.dir.sram));
path_mkdir(g_defaults.dir.sram);
int_sd_app_dir, "saves", sizeof(g_defaults.dir.sram));
fill_pathname_join(g_defaults.dir.savestate,
ext_dir, "states", sizeof(g_defaults.dir.savestate));
path_mkdir(g_defaults.dir.savestate);
int_sd_app_dir, "states", sizeof(g_defaults.dir.savestate));
fill_pathname_join(g_defaults.dir.system,
ext_dir, "system", sizeof(g_defaults.dir.system));
path_mkdir(g_defaults.dir.system);
int_sd_app_dir, "system", sizeof(g_defaults.dir.system));
fill_pathname_join(g_defaults.dir.menu_config,
ext_dir, "config", sizeof(g_defaults.dir.menu_config));
path_mkdir(g_defaults.dir.menu_config);
int_sd_app_dir, "config", sizeof(g_defaults.dir.menu_config));
fill_pathname_join(g_defaults.dir.remap,
g_defaults.dir.menu_config, "remaps", sizeof(g_defaults.dir.remap));
fill_pathname_join(g_defaults.dir.thumbnails,
int_sd_app_dir, "thumbnails", sizeof(g_defaults.dir.thumbnails));
fill_pathname_join(g_defaults.dir.playlist,
int_sd_app_dir, "playlists", sizeof(g_defaults.dir.playlist));
fill_pathname_join(g_defaults.dir.cheats,
int_sd_app_dir, "cheats", sizeof(g_defaults.dir.cheats));
/* TODO/FIXME - Test if this is needed at all, as far as I know,
* every directory we set in g_defaults already gets created if it
* doesn't exist already */
path_mkdir(g_defaults.dir.sram);
path_mkdir(g_defaults.dir.savestate);
path_mkdir(g_defaults.dir.system);
path_mkdir(g_defaults.dir.menu_config);
path_mkdir(g_defaults.dir.remap);
path_mkdir(g_defaults.dir.thumbnails);
path_mkdir(g_defaults.dir.playlist);
path_mkdir(g_defaults.dir.cheats);
break;
case SDCARD_NOT_WRITABLE:
case INT_SD_NOT_WRITABLE:
fill_pathname_join(g_defaults.dir.sram,
app_dir, "saves", sizeof(g_defaults.dir.sram));
path_mkdir(g_defaults.dir.sram);
fill_pathname_join(g_defaults.dir.savestate,
app_dir, "states", sizeof(g_defaults.dir.savestate));
path_mkdir(g_defaults.dir.savestate);
fill_pathname_join(g_defaults.dir.system,
app_dir, "system", sizeof(g_defaults.dir.system));
path_mkdir(g_defaults.dir.system);
fill_pathname_join(g_defaults.dir.menu_config,
app_dir, "config", sizeof(g_defaults.dir.menu_config));
fill_pathname_join(g_defaults.dir.remap,
g_defaults.dir.menu_config, "remaps", sizeof(g_defaults.dir.remap));
fill_pathname_join(g_defaults.dir.thumbnails,
app_dir, "thumbnails", sizeof(g_defaults.dir.thumbnails));
fill_pathname_join(g_defaults.dir.playlist,
app_dir, "playlists", sizeof(g_defaults.dir.playlist));
fill_pathname_join(g_defaults.dir.cheats,
app_dir, "cheats", sizeof(g_defaults.dir.cheats));
/* TODO/FIXME - Test if this is needed at all, as far as I know,
* every directory we set in g_defaults already gets created if it
* doesn't exist already */
path_mkdir(g_defaults.dir.sram);
path_mkdir(g_defaults.dir.savestate);
path_mkdir(g_defaults.dir.system);
path_mkdir(g_defaults.dir.menu_config);
path_mkdir(g_defaults.dir.remap);
path_mkdir(g_defaults.dir.thumbnails);
path_mkdir(g_defaults.dir.playlist);
path_mkdir(g_defaults.dir.cheats);
break;
case SDCARD_ROOT_WRITABLE:
case INT_SD_WRITABLE:
fill_pathname_join(g_defaults.dir.menu_config,
int_sd_dir, "RetroArch/config", sizeof(g_defaults.dir.menu_config));
fill_pathname_join(g_defaults.dir.remap,
g_defaults.dir.menu_config, "remaps", sizeof(g_defaults.dir.remap));
fill_pathname_join(g_defaults.dir.thumbnails,
int_sd_dir, "RetroArch/thumbnails", sizeof(g_defaults.dir.thumbnails));
fill_pathname_join(g_defaults.dir.playlist,
int_sd_dir, "RetroArch/playlists", sizeof(g_defaults.dir.playlist));
fill_pathname_join(g_defaults.dir.cheats,
int_sd_dir, "RetroArch/cheats", sizeof(g_defaults.dir.cheats));
/* TODO/FIXME - Test if this is needed at all, as far as I know,
* every directory we set in g_defaults already gets created if it
* doesn't exist already */
path_mkdir(g_defaults.dir.menu_config);
path_mkdir(g_defaults.dir.remap);
path_mkdir(g_defaults.dir.thumbnails);
path_mkdir(g_defaults.dir.playlist);
path_mkdir(g_defaults.dir.cheats);
default:
break;
}
/* create save and system directories in the internal dir too */
fill_pathname_join(buf,
app_dir, "saves", sizeof(buf));
fill_pathname_join(buf, app_dir, "saves", sizeof(buf));
path_mkdir(buf);
fill_pathname_join(buf,
app_dir, "states", sizeof(buf));
fill_pathname_join(buf, app_dir, "states", sizeof(buf));
path_mkdir(buf);
fill_pathname_join(buf,
app_dir, "system", sizeof(buf));
fill_pathname_join(buf, app_dir, "system", sizeof(buf));
path_mkdir(buf);
/* create save and system directories in the internal sd too */
fill_pathname_join(buf,
ext_dir, "saves", sizeof(buf));
fill_pathname_join(buf, int_sd_app_dir, "saves", sizeof(buf));
path_mkdir(buf);
fill_pathname_join(buf,
ext_dir, "states", sizeof(buf));
fill_pathname_join(buf, int_sd_app_dir, "states", sizeof(buf));
path_mkdir(buf);
fill_pathname_join(buf,
ext_dir, "system", sizeof(buf));
fill_pathname_join(buf, int_sd_app_dir, "system", sizeof(buf));
path_mkdir(buf);
RARCH_LOG("Default savefile folder: [%s]", g_defaults.dir.sram);
@ -1964,9 +1632,7 @@ static void frontend_linux_get_env(int *argc,
* for gamepad-like/console devices. */
if (device_is_game_console(device_model))
{
snprintf(g_defaults.settings.menu, sizeof(g_defaults.settings.menu), "xmb");
}
#else
char base_path[PATH_MAX];
@ -1987,11 +1653,13 @@ static void frontend_linux_get_env(int *argc,
fill_pathname_join(g_defaults.dir.core_info, base_path,
"cores", sizeof(g_defaults.dir.core_info));
fill_pathname_join(g_defaults.dir.autoconfig, base_path,
"autoconf", sizeof(g_defaults.dir.autoconfig));
"autoconfig", sizeof(g_defaults.dir.autoconfig));
fill_pathname_join(g_defaults.dir.assets, base_path,
"assets", sizeof(g_defaults.dir.assets));
fill_pathname_join(g_defaults.dir.remap, base_path,
"remap", sizeof(g_defaults.dir.remap));
fill_pathname_join(g_defaults.dir.menu_config, base_path,
"config", sizeof(g_defaults.dir.menu_config));
fill_pathname_join(g_defaults.dir.remap, g_defaults.dir.menu_config,
"remaps", sizeof(g_defaults.dir.remap));
fill_pathname_join(g_defaults.dir.playlist, base_path,
"playlists", sizeof(g_defaults.dir.playlist));
fill_pathname_join(g_defaults.dir.cursor, base_path,
@ -2128,11 +1796,6 @@ static void frontend_linux_init(void *data)
"getStringExtra", "(Ljava/lang/String;)Ljava/lang/String;");
#endif
if (!cpu_inited_once)
{
linux_cpu_init();
cpu_inited_once = true;
}
}
#ifdef ANDROID
@ -2144,9 +1807,9 @@ static int frontend_android_parse_drive_list(void *data)
menu_entries_add(list,
app_dir, "Application Dir", MENU_FILE_DIRECTORY, 0, 0);
menu_entries_add(list,
ext_dir, "External Application Dir", MENU_FILE_DIRECTORY, 0, 0);
int_sd_app_dir, "External Application Dir", MENU_FILE_DIRECTORY, 0, 0);
menu_entries_add(list,
sdcard_dir, "Internal Memory", MENU_FILE_DIRECTORY, 0, 0);
int_sd_dir, "Internal Memory", MENU_FILE_DIRECTORY, 0, 0);
menu_entries_add(list, "/", "",
MENU_FILE_DIRECTORY, 0, 0);
@ -2156,7 +1819,6 @@ static int frontend_android_parse_drive_list(void *data)
#endif
#ifndef HAVE_DYNAMIC
#include "../../retroarch.h"
static bool frontend_linux_set_fork(enum frontend_fork fork_mode)
{
@ -2181,7 +1843,7 @@ static bool frontend_linux_set_fork(enum frontend_fork fork_mode)
fill_pathname_application_path(executable_path, sizeof(executable_path));
strlcpy(settings->path.libretro, executable_path, sizeof(settings->path.libretro));
}
rarch_ctl(RARCH_CTL_FORCE_QUIT, NULL);
command_event(CMD_EVENT_QUIT, NULL);
break;
case FRONTEND_FORK_NONE:
default:

View File

@ -23,31 +23,6 @@
#include <boolean.h>
enum cpu_family
{
CPU_FAMILY_UNKNOWN = 0,
CPU_FAMILY_ARM,
CPU_FAMILY_X86,
CPU_FAMILY_MIPS,
CPU_FAMILY_MAX /* do not remove */
};
enum
{
CPU_ARM_FEATURE_ARMv7 = (1 << 0),
CPU_ARM_FEATURE_VFPv3 = (1 << 1),
CPU_ARM_FEATURE_NEON = (1 << 2),
CPU_ARM_FEATURE_LDREX_STREX = (1 << 3)
};
enum
{
CPU_X86_FEATURE_SSSE3 = (1 << 0),
CPU_X86_FEATURE_POPCNT = (1 << 1),
CPU_X86_FEATURE_MOVBE = (1 << 2)
};
#ifndef MAX_PADS
#define MAX_PADS 8
#endif
@ -56,12 +31,6 @@ enum
#define MAX_AXIS 10
#endif
enum cpu_family linux_get_cpu_family(void);
uint64_t linux_get_cpu_features(void);
int linux_get_cpu_count(void);
#ifdef ANDROID
#include <jni.h>
#include <poll.h>

View File

@ -163,7 +163,7 @@ static void frontend_psp_deinit(void *data)
*verbose = false;
#ifdef HAVE_FILE_LOGGER
event_cmd_ctl(EVENT_CMD_LOG_FILE_DEINIT, NULL);
command_event(CMD_EVENT_LOG_FILE_DEINIT, NULL);
#endif
#endif

View File

@ -21,6 +21,7 @@
#include <retro_miscellaneous.h>
#include <dynamic/dylib.h>
#include <lists/file_list.h>
#include <file/file_path.h>
#include "../frontend_driver.h"
#include "../../general.h"
@ -110,6 +111,9 @@ static void frontend_win32_get_os(char *s, size_t len, int *major, int *minor)
switch (*major)
{
case 10:
strlcpy(s, "Windows 10", len);
break;
case 6:
switch (*minor)
{
@ -237,28 +241,63 @@ static void frontend_win32_environment_get(int *argc, char *argv[],
{
gfx_set_dwm();
strlcpy(g_defaults.dir.assets, ":\\assets", sizeof(g_defaults.dir.assets));
strlcpy(g_defaults.dir.audio_filter, ":\\filters\\audio", sizeof(g_defaults.dir.audio_filter));
strlcpy(g_defaults.dir.video_filter, ":\\filters\\video", sizeof(g_defaults.dir.video_filter));
strlcpy(g_defaults.dir.cheats, ":\\cheats", sizeof(g_defaults.dir.cheats));
strlcpy(g_defaults.dir.database, ":\\database\\rdb", sizeof(g_defaults.dir.database));
strlcpy(g_defaults.dir.cursor, ":\\database\\cursors", sizeof(g_defaults.dir.cursor));
strlcpy(g_defaults.dir.playlist, ":\\playlists", sizeof(g_defaults.dir.playlist));
strlcpy(g_defaults.dir.remap, ":\\config\\remap", sizeof(g_defaults.dir.remap));
strlcpy(g_defaults.dir.wallpapers, ":\\wallpapers", sizeof(g_defaults.dir.wallpapers));
strlcpy(g_defaults.dir.thumbnails, ":\\thumbnails", sizeof(g_defaults.dir.thumbnails));
strlcpy(g_defaults.dir.overlay, ":\\overlays", sizeof(g_defaults.dir.overlay));
strlcpy(g_defaults.dir.osk_overlay, ":\\overlays", sizeof(g_defaults.dir.osk_overlay));
strlcpy(g_defaults.dir.core, ":\\cores", sizeof(g_defaults.dir.core));
strlcpy(g_defaults.dir.core_info, ":\\info", sizeof(g_defaults.dir.core_info));
strlcpy(g_defaults.dir.autoconfig, ":\\autoconf", sizeof(g_defaults.dir.autoconfig));
strlcpy(g_defaults.dir.system, ":\\system", sizeof(g_defaults.dir.system));
strlcpy(g_defaults.dir.sram, ":\\saves", sizeof(g_defaults.dir.sram));
strlcpy(g_defaults.dir.savestate, ":\\states", sizeof(g_defaults.dir.savestate));
strlcpy(g_defaults.dir.menu_config, ":\\config", sizeof(g_defaults.dir.menu_config));
strlcpy(g_defaults.dir.shader, ":\\shaders", sizeof(g_defaults.dir.shader));
strlcpy(g_defaults.dir.core_assets, ":\\downloads", sizeof(g_defaults.dir.core_assets));
strlcpy(g_defaults.dir.screenshot, ":\\screenshots", sizeof(g_defaults.dir.screenshot));
fill_pathname_expand_special(g_defaults.dir.assets,
":/assets", sizeof(g_defaults.dir.assets));
fill_pathname_expand_special(g_defaults.dir.audio_filter,
":/filters/audio", sizeof(g_defaults.dir.audio_filter));
fill_pathname_expand_special(g_defaults.dir.video_filter,
":/filters/video", sizeof(g_defaults.dir.video_filter));
fill_pathname_expand_special(g_defaults.dir.cheats,
":/cheats", sizeof(g_defaults.dir.cheats));
fill_pathname_expand_special(g_defaults.dir.database,
":/database/rdb", sizeof(g_defaults.dir.database));
fill_pathname_expand_special(g_defaults.dir.cursor,
":/database/cursors", sizeof(g_defaults.dir.cursor));
fill_pathname_expand_special(g_defaults.dir.playlist,
":/playlists", sizeof(g_defaults.dir.assets));
fill_pathname_expand_special(g_defaults.dir.menu_config,
":/config", sizeof(g_defaults.dir.menu_config));
fill_pathname_expand_special(g_defaults.dir.remap,
":/config/remaps", sizeof(g_defaults.dir.remap));
fill_pathname_expand_special(g_defaults.dir.wallpapers,
":/assets/wallpapers", sizeof(g_defaults.dir.wallpapers));
fill_pathname_expand_special(g_defaults.dir.thumbnails,
":/thumbnails", sizeof(g_defaults.dir.thumbnails));
fill_pathname_expand_special(g_defaults.dir.overlay,
":/overlays", sizeof(g_defaults.dir.overlay));
fill_pathname_expand_special(g_defaults.dir.osk_overlay,
":/overlays", sizeof(g_defaults.dir.osk_overlay));
fill_pathname_expand_special(g_defaults.dir.osk_overlay,
":/overlays", sizeof(g_defaults.dir.osk_overlay));
fill_pathname_expand_special(g_defaults.dir.core,
":/cores", sizeof(g_defaults.dir.core));
fill_pathname_expand_special(g_defaults.dir.core_info,
":/info", sizeof(g_defaults.dir.core_info));
fill_pathname_expand_special(g_defaults.dir.autoconfig,
":/autoconfig", sizeof(g_defaults.dir.autoconfig));
fill_pathname_expand_special(g_defaults.dir.shader,
":/shaders", sizeof(g_defaults.dir.shader));
fill_pathname_expand_special(g_defaults.dir.core_assets,
":/downloads", sizeof(g_defaults.dir.core_assets));
fill_pathname_expand_special(g_defaults.dir.screenshot,
":/screenshots", sizeof(g_defaults.dir.screenshot));
/* don't force this in the driver anymore, these will be handled by
a dummy config file so they can be reset to content dir
fill_pathname_expand_special(g_defaults.dir.sram,
":/saves", sizeof(g_defaults.dir.sram));
fill_pathname_expand_special(g_defaults.dir.savestate,
":/states", sizeof(g_defaults.dir.savestate));
fill_pathname_expand_special(g_defaults.dir.system,
":/system", sizeof(g_defaults.dir.system));
*/
#ifdef HAVE_MENU
#if defined(HAVE_OPENGL) || defined(HAVE_OPENGLES)
snprintf(g_defaults.settings.menu, sizeof(g_defaults.settings.menu), "xmb");
#endif
#endif
}
frontend_ctx_driver_t frontend_ctx_win32 = {

View File

@ -59,7 +59,7 @@ void main_exit(void *args)
{
settings_t *settings = config_get_ptr();
event_cmd_ctl(EVENT_CMD_MENU_SAVE_CURRENT_CONFIG, NULL);
command_event(CMD_EVENT_MENU_SAVE_CURRENT_CONFIG, NULL);
#ifdef HAVE_MENU
/* Do not want menu context to live any more. */
@ -67,7 +67,7 @@ void main_exit(void *args)
#endif
rarch_ctl(RARCH_CTL_MAIN_DEINIT, NULL);
event_cmd_ctl(EVENT_CMD_PERFCNT_REPORT_FRONTEND_LOG, NULL);
command_event(CMD_EVENT_PERFCNT_REPORT_FRONTEND_LOG, NULL);
#if defined(HAVE_LOGGER) && !defined(ANDROID)
logger_shutdown();
@ -126,14 +126,14 @@ int rarch_main(int argc, char *argv[], void *data)
info.args = args;
info.environ_get = frontend_driver_environment_get_ptr();
if (!content_ctl(CONTENT_CTL_LOAD, &info))
if (!content_load(&info))
return 0;
}
runloop_ctl(RUNLOOP_CTL_SYSTEM_INFO_GET, &system);
runloop_ctl(RUNLOOP_CTL_GET_CONTENT_PATH, &fullpath);
if (content_ctl(CONTENT_CTL_IS_INITED, NULL) || content_ctl(CONTENT_CTL_DOES_NOT_NEED_CONTENT, NULL))
if (content_is_inited() || content_does_not_need_content())
{
char tmp[PATH_MAX_LENGTH];
struct retro_system_info *info = system ? &system->info : NULL;
@ -149,7 +149,7 @@ int rarch_main(int argc, char *argv[], void *data)
if (rarch_ctl(RARCH_CTL_IS_DUMMY_CORE, NULL) || !info)
content_push_to_history_playlist(
content_ctl(CONTENT_CTL_DOES_NOT_NEED_CONTENT, NULL) || *tmp,
content_does_not_need_content() || *tmp,
*tmp ? tmp : NULL,
info);
}
@ -164,7 +164,7 @@ int rarch_main(int argc, char *argv[], void *data)
if (ret == 1 && sleep_ms > 0)
retro_sleep(sleep_ms);
runloop_ctl(RUNLOOP_CTL_DATA_ITERATE, NULL);
runloop_iterate_data();
}while(ret != -1);
main_exit(args);

View File

@ -30,7 +30,7 @@
#endif
#ifndef PACKAGE_VERSION
#define PACKAGE_VERSION "1.3.3"
#define PACKAGE_VERSION "1.3.4"
#endif
#endif

View File

@ -16,14 +16,7 @@
#include "gl_common.h"
extern void gl_load_texture_data(uint32_t id_data,
enum gfx_wrap_type wrap_type,
enum texture_filter_type filter_type,
unsigned alignment,
unsigned width, unsigned height,
const void *frame, unsigned base_size);
void gl_ff_vertex(const struct gfx_coords *coords)
void gl_ff_vertex(const struct video_coords *coords)
{
#ifndef NO_GL_FF_VERTEX
/* Fall back to fixed function-style if needed and possible. */
@ -53,52 +46,3 @@ void gl_ff_matrix(const math_matrix_4x4 *mat)
glLoadMatrixf(ident.data);
#endif
}
bool gl_load_luts(const struct video_shader *shader,
GLuint *textures_lut)
{
unsigned i;
unsigned num_luts = MIN(shader->luts, GFX_MAX_TEXTURES);
if (!shader->luts)
return true;
glGenTextures(num_luts, textures_lut);
for (i = 0; i < num_luts; i++)
{
struct texture_image img = {0};
enum texture_filter_type filter_type = TEXTURE_FILTER_LINEAR;
RARCH_LOG("Loading texture image from: \"%s\" ...\n",
shader->lut[i].path);
if (!video_texture_image_load(&img, shader->lut[i].path))
{
RARCH_ERR("Failed to load texture image from: \"%s\"\n",
shader->lut[i].path);
return false;
}
if (shader->lut[i].filter == RARCH_FILTER_NEAREST)
filter_type = TEXTURE_FILTER_NEAREST;
if (shader->lut[i].mipmap)
{
if (filter_type == TEXTURE_FILTER_NEAREST)
filter_type = TEXTURE_FILTER_MIPMAP_NEAREST;
else
filter_type = TEXTURE_FILTER_MIPMAP_LINEAR;
}
gl_load_texture_data(textures_lut[i],
shader->lut[i].wrap,
filter_type, 4,
img.width, img.height,
img.pixels, sizeof(uint32_t));
video_texture_image_free(&img);
}
glBindTexture(GL_TEXTURE_2D, 0);
return true;
}

View File

@ -181,8 +181,8 @@ typedef struct gl
GLuint texture[GFX_MAX_TEXTURES];
unsigned tex_index; /* For use with PREV. */
unsigned textures;
struct gfx_tex_info tex_info;
struct gfx_tex_info prev_info[GFX_MAX_TEXTURES];
struct video_tex_info tex_info;
struct video_tex_info prev_info[GFX_MAX_TEXTURES];
GLuint tex_mag_filter;
GLuint tex_min_filter;
bool tex_mipmap;
@ -196,7 +196,7 @@ typedef struct gl
/* Render-to-texture, multipass shaders. */
GLuint fbo[GFX_MAX_SHADERS];
GLuint fbo_texture[GFX_MAX_SHADERS];
struct gfx_fbo_rect fbo_rect[GFX_MAX_SHADERS];
struct video_fbo_rect fbo_rect[GFX_MAX_SHADERS];
struct gfx_fbo_scale fbo_scale[GFX_MAX_SHADERS];
int fbo_pass;
bool fbo_inited;
@ -231,7 +231,7 @@ typedef struct gl
unsigned tex_w, tex_h;
math_matrix_4x4 mvp, mvp_no_rot;
struct gfx_coords coords;
struct video_coords coords;
const float *vertex_ptr;
const float *white_color_ptr;
@ -339,7 +339,7 @@ static INLINE unsigned gl_wrap_type_to_enum(enum gfx_wrap_type type)
return 0;
}
void gl_ff_vertex(const struct gfx_coords *coords);
void gl_ff_vertex(const struct video_coords *coords);
void gl_ff_matrix(const math_matrix_4x4 *mat);
#endif

View File

@ -481,7 +481,9 @@ struct vk_texture vulkan_create_texture(vk_t *vk,
submit_info.commandBufferCount = 1;
submit_info.pCommandBuffers = &staging;
#ifdef HAVE_THREADS
slock_lock(vk->context->queue_lock);
#endif
VKFUNC(vkQueueSubmit)(vk->context->queue,
1, &submit_info, VK_NULL_HANDLE);
@ -489,7 +491,9 @@ struct vk_texture vulkan_create_texture(vk_t *vk,
* during init, so waiting for GPU to complete transfer
* and blocking isn't a big deal. */
VKFUNC(vkQueueWaitIdle)(vk->context->queue);
#ifdef HAVE_THREADS
slock_unlock(vk->context->queue_lock);
#endif
VKFUNC(vkFreeCommandBuffers)(vk->context->device, vk->staging_pool, 1, &staging);
vulkan_destroy_texture(
@ -523,14 +527,9 @@ static void vulkan_write_quad_descriptors(
const struct vk_texture *texture,
VkSampler sampler)
{
VkDescriptorImageInfo image_info;
VkDescriptorBufferInfo buffer_info;
VkWriteDescriptorSet write = { VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET };
image_info.sampler = sampler;
image_info.imageView = texture->view;
image_info.imageLayout = texture->layout;
buffer_info.buffer = buffer;
buffer_info.offset = offset;
buffer_info.range = range;
@ -542,6 +541,14 @@ static void vulkan_write_quad_descriptors(
write.pBufferInfo = &buffer_info;
VKFUNC(vkUpdateDescriptorSets)(device, 1, &write, 0, NULL);
if (texture)
{
VkDescriptorImageInfo image_info;
image_info.sampler = sampler;
image_info.imageView = texture->view;
image_info.imageLayout = texture->layout;
write.dstSet = set;
write.dstBinding = 1;
write.descriptorCount = 1;
@ -549,6 +556,7 @@ static void vulkan_write_quad_descriptors(
write.pImageInfo = &image_info;
VKFUNC(vkUpdateDescriptorSets)(device, 1, &write, 0, NULL);
}
}
void vulkan_transition_texture(vk_t *vk, struct vk_texture *texture)
{
@ -606,6 +614,7 @@ static void vulkan_check_dynamic_state(
void vulkan_draw_triangles(vk_t *vk, const struct vk_draw_triangles *call)
{
if (call->texture)
vulkan_transition_texture(vk, call->texture);
if (call->pipeline != vk->tracker.pipeline)
@ -624,26 +633,24 @@ void vulkan_draw_triangles(vk_t *vk, const struct vk_draw_triangles *call)
{
VkDescriptorSet set;
if (memcmp(call->mvp, &vk->tracker.mvp, sizeof(*call->mvp))
|| (call->texture->view != vk->tracker.view)
|| (call->sampler != vk->tracker.sampler))
{
/* Upload UBO */
struct vk_buffer_range range;
if (!vulkan_buffer_chain_alloc(vk->context, &vk->chain->ubo,
sizeof(*call->mvp), &range))
call->uniform_size, &range))
return;
memcpy(range.data, call->mvp, sizeof(*call->mvp));
memcpy(range.data, call->uniform, call->uniform_size);
set = vulkan_descriptor_manager_alloc(
vk->context->device,
&vk->chain->descriptor_manager);
vulkan_write_quad_descriptors(
vk->context->device,
set,
range.buffer,
range.offset,
sizeof(*call->mvp),
call->uniform_size,
call->texture,
call->sampler);
@ -651,10 +658,9 @@ void vulkan_draw_triangles(vk_t *vk, const struct vk_draw_triangles *call)
vk->pipelines.layout, 0,
1, &set, 0, NULL);
vk->tracker.view = call->texture->view;
vk->tracker.sampler = call->sampler;
vk->tracker.mvp = *call->mvp;
}
vk->tracker.view = VK_NULL_HANDLE;
vk->tracker.sampler = VK_NULL_HANDLE;
memset(&vk->tracker.mvp, 0, sizeof(vk->tracker.mvp));
}
/* VBO is already uploaded. */
@ -1371,7 +1377,7 @@ bool vulkan_context_init(gfx_ctx_vulkan_data_t *vk,
vk->context.device = cached_device;
cached_device = NULL;
video_driver_ctl(RARCH_DISPLAY_CTL_SET_VIDEO_CACHE_CONTEXT_ACK, NULL);
video_driver_set_video_cache_context_ack();
RARCH_LOG("[Vulkan]: Using cached Vulkan context.\n");
}
else if (VKFUNC(vkCreateDevice)(vk->context.gpu, &device_info,
@ -1421,9 +1427,11 @@ bool vulkan_context_init(gfx_ctx_vulkan_data_t *vk,
break;
}
#ifdef HAVE_THREADS
vk->context.queue_lock = slock_new();
if (!vk->context.queue_lock)
return false;
#endif
return true;
}
@ -1575,7 +1583,9 @@ void vulkan_present(gfx_ctx_vulkan_data_t *vk, unsigned index)
present.pWaitSemaphores = &vk->context.swapchain_semaphores[index];
/* Better hope QueuePresent doesn't block D: */
#ifdef HAVE_THREADS
slock_lock(vk->context.queue_lock);
#endif
err = VKFUNC(vkQueuePresentKHR)(vk->context.queue, &present);
if (err != VK_SUCCESS || result != VK_SUCCESS)
@ -1584,7 +1594,9 @@ void vulkan_present(gfx_ctx_vulkan_data_t *vk, unsigned index)
vk->context.invalid_swapchain = true;
}
#ifdef HAVE_THREADS
slock_unlock(vk->context.queue_lock);
#endif
}
void vulkan_context_destroy(gfx_ctx_vulkan_data_t *vk,
@ -1612,7 +1624,7 @@ void vulkan_context_destroy(gfx_ctx_vulkan_data_t *vk,
vk->context.swapchain_fences[i], NULL);
}
if (video_driver_ctl(RARCH_DISPLAY_CTL_IS_VIDEO_CACHE_CONTEXT, NULL))
if (video_driver_is_video_cache_context())
{
cached_device = vk->context.device;
cached_instance = vk->context.instance;

View File

@ -38,14 +38,14 @@
#include <rthreads/rthreads.h>
#include <formats/image.h>
#include <libretro.h>
#include <libretro_vulkan.h>
#include "../../driver.h"
#include "../../performance.h"
#include "../../libretro.h"
#include "../../general.h"
#include "../../retroarch.h"
#include "../font_driver.h"
#include "../video_context_driver.h"
#include "../../libretro_vulkan.h"
#include "../drivers_shader/shader_vulkan.h"
typedef struct vulkan_filter_chain vulkan_filter_chain_t;
@ -249,7 +249,9 @@ struct vk_draw_triangles
VkPipeline pipeline;
struct vk_texture *texture;
VkSampler sampler;
const math_matrix_4x4 *mvp;
const void *uniform;
size_t uniform_size;
const struct vk_buffer_range *vbo;
unsigned vertices;
@ -312,7 +314,7 @@ typedef struct vk
struct
{
bool blend;
VkPipeline pipelines[4];
VkPipeline pipelines[8];
struct vk_texture blank_texture;
} display;

View File

@ -141,18 +141,21 @@ void x11_set_window_attr(Display *dpy, Window win)
x11_set_window_class(dpy, win);
}
void x11_suspend_screensaver(Window wnd)
void x11_suspend_screensaver(Window wnd, bool enable)
{
int ret;
char cmd[64] = {0};
static bool screensaver_na = false;
if (!enable)
return;
if (screensaver_na)
return;
RARCH_LOG("Suspending screensaver (X11).\n");
snprintf(cmd, sizeof(cmd), "xdg-screensaver suspend %d", (int)wnd);
snprintf(cmd, sizeof(cmd), "xdg-screensaver suspend 0x%x", (int)wnd);
ret = system(cmd);
if (ret == -1)
@ -551,8 +554,7 @@ void x11_update_window_title(void *data)
char buf_fps[128] = {0};
settings_t *settings = config_get_ptr();
if (video_monitor_get_fps(buf, sizeof(buf),
buf_fps, sizeof(buf_fps)))
if (video_monitor_get_fps(buf, sizeof(buf), buf_fps, sizeof(buf_fps)))
XStoreName(g_x11_dpy, g_x11_win, buf);
if (settings->fps_show)
runloop_msg_queue_push(buf_fps, 1, 1, false);

View File

@ -43,7 +43,7 @@ extern unsigned g_x11_screen;
void x11_save_last_used_monitor(Window win);
void x11_show_mouse(Display *dpy, Window win, bool state);
void x11_windowed_fullscreen(Display *dpy, Window win);
void x11_suspend_screensaver(Window win);
void x11_suspend_screensaver(Window win, bool enable);
bool x11_enter_fullscreen(Display *dpy, unsigned width,
unsigned height, XF86VidModeModeInfo *desktop_mode);

View File

@ -46,8 +46,8 @@
#include "../../menu/menu_driver.h"
#endif
#include "../../libretro_version_1.h"
#include "../../performance.h"
#include "../../core.h"
#include "../../performance_counters.h"
#include "../../defines/d3d_defines.h"
#include "../../verbosity.h"
@ -103,7 +103,7 @@ static bool d3d_init_imports(d3d_video_t *d3d)
mem_info.id = RETRO_MEMORY_SYSTEM_RAM;
core_ctl(CORE_CTL_RETRO_GET_MEMORY, &mem_info);
core_get_memory(&mem_info);
tracker_info.wram = (uint8_t*)mem_info.data;
tracker_info.info = d3d->shader.variable;
@ -544,7 +544,7 @@ void d3d_make_d3dpp(void *data,
unsigned width = 0;
unsigned height = 0;
gfx_ctx_ctl(GFX_CTL_GET_VIDEO_SIZE, &mode);
video_context_driver_get_video_size(&mode);
width = mode.width;
height = mode.height;
@ -664,7 +664,7 @@ static void d3d_calculate_rect(void *data,
aspect_data.width = *width;
aspect_data.height = *height;
gfx_ctx_ctl(GFX_CTL_TRANSLATE_ASPECT, &aspect_data);
video_context_driver_translate_aspect(&aspect_data);
*x = 0;
*y = 0;
@ -845,7 +845,7 @@ static void d3d_set_nonblock_state(void *data, bool state)
d3d->video_info.vsync = !state;
gfx_ctx_ctl(GFX_CTL_SWAP_INTERVAL, &interval);
video_context_driver_swap_interval(&interval);
#ifndef _XBOX
d3d->needs_restore = true;
d3d_restore(d3d);
@ -867,7 +867,7 @@ static bool d3d_alive(void *data)
size_data.width = &temp_width;
size_data.height = &temp_height;
if (gfx_ctx_ctl(GFX_CTL_CHECK_WINDOW, &size_data))
if (video_context_driver_check_window(&size_data))
{
if (quit)
d3d->quitting = quit;
@ -881,7 +881,7 @@ static bool d3d_alive(void *data)
mode.width = temp_width;
mode.height = temp_height;
gfx_ctx_ctl(GFX_CTL_SET_RESIZE, &mode);
video_context_driver_set_resize(&mode);
d3d_restore(d3d);
}
@ -896,46 +896,42 @@ static bool d3d_alive(void *data)
static bool d3d_focus(void *data)
{
return gfx_ctx_ctl(GFX_CTL_FOCUS, NULL);
return video_context_driver_focus();
}
static bool d3d_suppress_screensaver(void *data, bool enable)
{
bool enabled = enable;
return gfx_ctx_ctl(GFX_CTL_SUPPRESS_SCREENSAVER, &enabled);
return video_context_driver_suppress_screensaver(&enabled);
}
static bool d3d_has_windowed(void *data)
{
return gfx_ctx_ctl(GFX_CTL_HAS_WINDOWED, NULL);
return video_context_driver_has_windowed();
}
static void d3d_set_aspect_ratio(void *data, unsigned aspect_ratio_idx)
{
d3d_video_t *d3d = (d3d_video_t*)data;
enum rarch_display_ctl_state cmd = RARCH_DISPLAY_CTL_NONE;
switch (aspect_ratio_idx)
{
case ASPECT_RATIO_SQUARE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_SQUARE_PIXEL;
video_driver_set_viewport_square_pixel();
break;
case ASPECT_RATIO_CORE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CORE;
video_driver_set_viewport_core();
break;
case ASPECT_RATIO_CONFIG:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CONFIG;
video_driver_set_viewport_config();
break;
default:
break;
}
if (cmd != RARCH_DISPLAY_CTL_NONE)
video_driver_ctl(cmd, NULL);
video_driver_set_aspect_ratio_value(aspectratio_lut[aspect_ratio_idx].value);
if (!d3d)
@ -1021,7 +1017,7 @@ static bool d3d_construct(d3d_video_t *d3d,
{
gfx_ctx_mode_t mode;
gfx_ctx_ctl(GFX_CTL_GET_VIDEO_SIZE, &mode);
video_context_driver_get_video_size(&mode);
full_x = mode.width;
full_y = mode.height;
@ -1069,7 +1065,7 @@ static bool d3d_construct(d3d_video_t *d3d,
inp.input = input;
inp.input_data = input_data;
gfx_ctx_ctl(GFX_CTL_INPUT_DRIVER, &inp);
video_context_driver_input_driver(&inp);
RARCH_LOG("[D3D]: Init complete.\n");
return true;
@ -1078,7 +1074,7 @@ static bool d3d_construct(d3d_video_t *d3d,
static void d3d_set_rotation(void *data, unsigned rot)
{
d3d_video_t *d3d = (d3d_video_t*)data;
struct gfx_ortho ortho = {0, 1, 0, 1, -1, 1};
struct video_ortho ortho = {0, 1, 0, 1, -1, 1};
if (!d3d)
return;
@ -1088,7 +1084,7 @@ static void d3d_set_rotation(void *data, unsigned rot)
static void d3d_show_mouse(void *data, bool state)
{
gfx_ctx_ctl(GFX_CTL_SHOW_MOUSE, &state);
video_context_driver_show_mouse(&state);
}
static const gfx_ctx_driver_t *d3d_get_context(void *data)
@ -1104,7 +1100,7 @@ static const gfx_ctx_driver_t *d3d_get_context(void *data)
unsigned major = 9;
enum gfx_ctx_api api = GFX_CTX_DIRECT3D9_API;
#endif
return gfx_ctx_init_first(data,
return video_context_driver_init_first(data,
settings->video.context_driver,
api, major, minor, false);
}
@ -1129,7 +1125,7 @@ static void *d3d_init(const video_info_t *info,
input_driver_set(input, input_data);
video_driver_ctl(RARCH_DISPLAY_CTL_SET_OWN_DRIVER, NULL);
video_driver_set_own_driver();
return d3d;
}
}
@ -1158,7 +1154,7 @@ static void *d3d_init(const video_info_t *info,
#endif
#endif
gfx_ctx_ctl(GFX_CTL_SET, (void*)ctx_driver);
video_context_driver_set((const gfx_ctx_driver_t*)ctx_driver);
if (!d3d_construct(d3d, info, input, input_data))
{
@ -1168,14 +1164,14 @@ static void *d3d_init(const video_info_t *info,
d3d->keep_aspect = info->force_aspect;
#ifdef _XBOX
video_driver_ctl(RARCH_DISPLAY_CTL_SET_OWN_DRIVER, NULL);
video_driver_ctl(RARCH_INPUT_CTL_SET_OWN_DRIVER, NULL);
video_driver_set_own_driver();
video_input_ctl(RARCH_INPUT_CTL_SET_OWN_DRIVER, NULL);
#endif
return d3d;
error:
gfx_ctx_ctl(GFX_CTL_DESTROY, NULL);
video_context_driver_destroy();
if (d3d)
delete d3d;
return NULL;
@ -1208,7 +1204,7 @@ static void d3d_free(void *data)
d3d_free_overlays(d3d);
#endif
gfx_ctx_ctl(GFX_CTL_FREE, NULL);
video_context_driver_free();
#ifndef _XBOX
#ifdef HAVE_MENU
@ -1396,7 +1392,7 @@ static void d3d_overlay_enable(void *data, bool state)
for (i = 0; i < d3d->overlays.size(); i++)
d3d->overlays_enabled = state;
gfx_ctx_ctl(GFX_CTL_SHOW_MOUSE, &state);
video_context_driver_show_mouse(&state);
}
static void d3d_overlay_full_screen(void *data, bool enable)
@ -1541,11 +1537,11 @@ static bool d3d_frame(void *data, const void *frame,
}
#endif
gfx_ctx_ctl(GFX_CTL_UPDATE_WINDOW_TITLE, NULL);
video_context_driver_update_window_title();
retro_perf_stop(&d3d_frame);
gfx_ctx_ctl(GFX_CTL_SWAP_BUFFERS, NULL);
video_context_driver_swap_buffers();
return true;
}
@ -1735,7 +1731,7 @@ static uintptr_t d3d_load_texture(void *video_data, void *data,
break;
}
return rarch_threaded_video_texture_load(data, func);
return video_thread_texture_load(data, func);
}
video_texture_load_d3d((d3d_video_t*)video_driver_get_ptr(false), (struct texture_image*)data, filter_type, &id);

View File

@ -30,7 +30,7 @@
#include "render_chain_driver.h"
#include "../video_driver.h"
#include "../../general.h"
#include "../../performance.h"
#include "../../performance_counters.h"
#include "../../verbosity.h"
#include "d3d.h"

View File

@ -17,10 +17,11 @@
#ifndef __D3D_RENDER_CHAIN_H
#define __D3D_RENDER_CHAIN_H
#include <libretro.h>
#include "../video_driver.h"
#include "../video_shader_parse.h"
#include "../video_state_tracker.h"
#include "../../libretro.h"
#include "../../defines/d3d_defines.h"
#ifdef __cplusplus

View File

@ -50,7 +50,7 @@ static void renderchain_set_mvp(void *data, unsigned vp_width,
mvp.data = d3d;
mvp.matrix = NULL;
video_shader_driver_ctl(SHADER_CTL_SET_MVP, &mvp);
video_shadser_driver_set_mvp(&mvp);
#elif defined(HAVE_D3D8)
D3DXMATRIX p_out, p_rotate, mat;
D3DXMatrixOrthoOffCenterLH(&mat, 0, vp_width, vp_height, 0, 0.0f, 1.0f);
@ -224,7 +224,7 @@ static void renderchain_set_vertices(void *data, unsigned pass,
shader_info.idx = pass;
shader_info.set_active = true;
video_shader_driver_ctl(SHADER_CTL_USE, &shader_info);
video_shader_driver_use(&shader_info);
params.data = d3d;
params.width = vert_width;
@ -240,7 +240,7 @@ static void renderchain_set_vertices(void *data, unsigned pass,
params.fbo_info = NULL;
params.fbo_info_cnt = 0;
video_shader_driver_ctl(SHADER_CTL_SET_PARAMS, &params);
video_shader_driver_set_parameters(&params);
#endif
#endif
}
@ -398,7 +398,7 @@ static bool xdk_renderchain_render(void *data, const void *frame,
settings_t *settings = config_get_ptr();
xdk_renderchain_t *chain = (xdk_renderchain_t*)d3d->renderchain_data;
video_driver_ctl(RARCH_DISPLAY_CTL_GET_FRAME_COUNT, &frame_count);
frame_count = video_driver_get_frame_count_ptr();
video_driver_get_size(&width, &height);

View File

@ -23,12 +23,12 @@
#include "ctr_gu.h"
#include "../../command_event.h"
#include "../../command.h"
#include "../../general.h"
#include "../../driver.h"
#include "../../retroarch.h"
#include "../../performance.h"
#include "../../performance_counters.h"
#define CTR_TOP_FRAMEBUFFER_WIDTH 400
#define CTR_TOP_FRAMEBUFFER_HEIGHT 240
@ -512,13 +512,13 @@ static bool ctr_frame(void* data, const void* frame,
if(!aptMainLoop())
{
event_cmd_ctl(EVENT_CMD_QUIT, NULL);
command_event(CMD_EVENT_QUIT, NULL);
return true;
}
if (select_pressed)
{
event_cmd_ctl(EVENT_CMD_QUIT, NULL);
command_event(CMD_EVENT_QUIT, NULL);
return true;
}
@ -961,29 +961,25 @@ static void ctr_set_filtering(void* data, unsigned index, bool smooth)
static void ctr_set_aspect_ratio(void* data, unsigned aspect_ratio_idx)
{
ctr_video_t *ctr = (ctr_video_t*)data;
enum rarch_display_ctl_state cmd = RARCH_DISPLAY_CTL_NONE;
switch (aspect_ratio_idx)
{
case ASPECT_RATIO_SQUARE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_SQUARE_PIXEL;
video_driver_set_viewport_square_pixel();
break;
case ASPECT_RATIO_CORE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CORE;
video_driver_set_viewport_core();
break;
case ASPECT_RATIO_CONFIG:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CONFIG;
video_driver_set_viewport_config();
break;
default:
break;
}
if (cmd != RARCH_DISPLAY_CTL_NONE)
video_driver_ctl(cmd, NULL);
video_driver_set_aspect_ratio_value(aspectratio_lut[aspect_ratio_idx].value);
ctr->keep_aspect = true;

View File

@ -1402,29 +1402,25 @@ static void exynos_gfx_viewport_info(void *data, struct video_viewport *vp)
static void exynos_set_aspect_ratio(void *data, unsigned aspect_ratio_idx)
{
struct exynos_video *vid = (struct exynos_video*)data;
enum rarch_display_ctl_state cmd = RARCH_DISPLAY_CTL_NONE;
switch (aspect_ratio_idx)
{
case ASPECT_RATIO_SQUARE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_SQUARE_PIXEL;
video_driver_set_viewport_square_pixel();
break;
case ASPECT_RATIO_CORE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CORE;
video_driver_set_viewport_core();
break;
case ASPECT_RATIO_CONFIG:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CONFIG;
video_driver_set_viewport_config();
break;
default:
break;
}
if (cmd != RARCH_DISPLAY_CTL_NONE)
video_driver_ctl(cmd, NULL);
video_driver_set_aspect_ratio_value(aspectratio_lut[aspect_ratio_idx].value);
vid->aspect_changed = true;
}

File diff suppressed because it is too large Load Diff

View File

@ -1,11 +1,6 @@
static const char *stock_vertex_xmb =
"#if __VERSION__ >= 130\n"
"#define COMPAT_VARYING out\n"
"#define COMPAT_ATTRIBUTE in\n"
"#else\n"
static const char *stock_vertex_xmb_legacy =
"#define COMPAT_VARYING varying\n"
"#define COMPAT_ATTRIBUTE attribute\n"
"#endif\n"
"COMPAT_ATTRIBUTE vec3 VertexCoord;\n"
"uniform float time;\n"
"COMPAT_VARYING vec3 fragVertexEc;\n"

View File

@ -1,11 +1,6 @@
static const char *stock_vertex_xmb_simple =
"#if __VERSION__ >= 130\n"
"#define COMPAT_VARYING out\n"
"#define COMPAT_ATTRIBUTE in\n"
"#else\n"
static const char *stock_vertex_xmb_simple_legacy =
"#define COMPAT_VARYING varying\n"
"#define COMPAT_ATTRIBUTE attribute\n"
"#endif\n"
"COMPAT_ATTRIBUTE vec3 VertexCoord;\n"
"uniform float time;\n"
"float iqhash( float n )\n"

View File

@ -0,0 +1,45 @@
static const char *stock_vertex_xmb_modern =
"#define COMPAT_VARYING out\n"
"#define COMPAT_ATTRIBUTE in\n"
"COMPAT_ATTRIBUTE vec3 VertexCoord;\n"
"uniform float time;\n"
"COMPAT_VARYING vec3 fragVertexEc;\n"
"float iqhash( float n )\n"
"{\n"
" return fract(sin(n)*43758.5453);\n"
"}\n"
"float noise( vec3 x )\n"
"{\n"
" vec3 p = floor(x);\n"
" vec3 f = fract(x);\n"
" f = f*f*(3.0-2.0*f);\n"
" float n = p.x + p.y*57.0 + 113.0*p.z;\n"
" return mix(mix(mix( iqhash(n+0.0 ), iqhash(n+1.0 ),f.x),\n"
" mix( iqhash(n+57.0 ), iqhash(n+58.0 ),f.x),f.y),\n"
" mix(mix( iqhash(n+113.0), iqhash(n+114.0),f.x),\n"
" mix( iqhash(n+170.0), iqhash(n+171.0),f.x),f.y),f.z);\n"
"}\n"
"float xmb_noise2( vec3 x )\n"
"{\n"
" return cos((x.z*1.0)*2.0);"
"}\n"
"void main()\n"
"{\n"
" vec3 v = vec3(VertexCoord.x, 0.0, VertexCoord.y);\n"
" vec3 v2 = v;\n"
" vec3 v3 = v;\n"
" v.y = xmb_noise2(v2)/6.0;\n"
" v3.x = v3.x + time/5.0;\n"
" v3.x = v3.x / 2.0;\n"
" v3.z = v3.z + time/10.0;\n"
" v3.y = v3.y + time/100.0;\n"
" v.z = v.z + noise(v3*7.0)/15.0;\n"
" v.y = v.y + noise(v3*7.0)/15.0 + cos(v.x*2.0-time/5.0)/5.0 - 0.3;\n"
" gl_Position = vec4(v, 1.0);\n"
" fragVertexEc = gl_Position.xyz;\n"
"}\n";

View File

@ -0,0 +1,29 @@
static const char *stock_vertex_xmb_simple_modern =
"#define COMPAT_VARYING out\n"
"#define COMPAT_ATTRIBUTE in\n"
"COMPAT_ATTRIBUTE vec3 VertexCoord;\n"
"uniform float time;\n"
"float iqhash( float n )\n"
"{\n"
" return fract(sin(n)*43758.5453);\n"
"}\n"
"float noise( vec3 x )\n"
"{\n"
" vec3 p = floor(x);\n"
" vec3 f = fract(x);\n"
" f = f*f*(3.0-2.0*f);\n"
" float n = p.x + p.y*57.0 + 113.0*p.z;\n"
" return mix(mix(mix( iqhash(n+0.0 ), iqhash(n+1.0 ),f.x),\n"
" mix( iqhash(n+57.0 ), iqhash(n+58.0 ),f.x),f.y),\n"
" mix(mix( iqhash(n+113.0), iqhash(n+114.0),f.x),\n"
" mix( iqhash(n+170.0), iqhash(n+171.0),f.x),f.y),f.z);\n"
"}\n"
"void main()\n"
"{\n"
" vec3 v = vec3(VertexCoord.x, 0.0, VertexCoord.y);\n"
" vec3 v2 = v;\n"
" v2.x = v2.x + time/2.0;\n"
" v2.z = v.z * 3.0;\n"
" v.y = -cos((v.x+v.z/3.0+time)*2.0)/10.0 - noise(v2.xyz)/4.0;\n"
" gl_Position = vec4(v, 1.0);\n"
"}\n";

View File

@ -413,9 +413,9 @@ static void gx_set_video_mode(void *data, unsigned fbWidth, unsigned lines,
new_fb_pitch = new_fb_width * 2;
menu_display_ctl(MENU_DISPLAY_CTL_SET_WIDTH, &new_fb_width);
menu_display_ctl(MENU_DISPLAY_CTL_SET_HEIGHT, &new_fb_height);
menu_display_ctl(MENU_DISPLAY_CTL_SET_FB_PITCH, &new_fb_pitch);
menu_display_set_width(new_fb_width);
menu_display_set_height(new_fb_height);
menu_display_set_framebuffer_pitch(new_fb_pitch);
GX_SetViewportJitter(0, 0, gx_mode.fbWidth, gx_mode.efbHeight, 0, 1, 1);
GX_SetDispCopySrc(0, 0, gx_mode.fbWidth, gx_mode.efbHeight);
@ -472,29 +472,25 @@ static void gx_set_video_mode(void *data, unsigned fbWidth, unsigned lines,
static void gx_set_aspect_ratio(void *data, unsigned aspect_ratio_idx)
{
gx_video_t *gx = (gx_video_t*)data;
enum rarch_display_ctl_state cmd = RARCH_DISPLAY_CTL_NONE;
switch (aspect_ratio_idx)
{
case ASPECT_RATIO_SQUARE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_SQUARE_PIXEL;
video_driver_set_viewport_square_pixel();
break;
case ASPECT_RATIO_CORE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CORE;
video_driver_set_viewport_core();
break;
case ASPECT_RATIO_CONFIG:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CONFIG;
video_driver_set_viewport_config();
break;
default:
break;
}
if (cmd != RARCH_DISPLAY_CTL_NONE)
video_driver_ctl(cmd, NULL);
video_driver_set_aspect_ratio_value(
aspectratio_lut[aspect_ratio_idx].value);
@ -555,8 +551,8 @@ static void init_texture(void *data, unsigned width, unsigned height)
menu_w = 320;
menu_h = 240;
menu_display_ctl(MENU_DISPLAY_CTL_WIDTH, &menu_w);
menu_display_ctl(MENU_DISPLAY_CTL_HEIGHT, &menu_h);
menu_w = menu_display_get_width();
menu_h = menu_display_get_height();
GX_InitTexObj(fb_ptr, g_tex.data, width, height,
(gx->rgb32) ? GX_TF_RGBA8 : gx->menu_texture_enable ?
@ -1496,9 +1492,9 @@ static bool gx_frame(void *data, const void *frame,
size_t fb_pitch;
unsigned fb_width, fb_height;
menu_display_ctl(MENU_DISPLAY_CTL_WIDTH, &fb_width);
menu_display_ctl(MENU_DISPLAY_CTL_HEIGHT, &fb_height);
menu_display_ctl(MENU_DISPLAY_CTL_FB_PITCH, &fb_pitch);
fb_width = menu_display_get_width();
fb_height = menu_display_get_height();
fb_pitch = menu_display_get_framebuffer_pitch();
convert_texture16(
gx->menu_data,

View File

@ -41,6 +41,8 @@
#include "../../retroarch.h"
#include "../video_context_driver.h"
#include "../video_frame.h"
#include "../font_driver.h"
typedef struct omapfb_page
@ -1087,43 +1089,23 @@ static bool omap_gfx_read_viewport(void *data, uint8_t *buffer)
return true;
}
static void update_scaler(omap_video_t *vid, struct scaler_ctx *scaler,
enum scaler_pix_fmt format, unsigned width,
unsigned height, unsigned pitch)
{
if (
width != scaler->in_width
|| height != scaler->in_height
|| format != scaler->in_fmt
|| pitch != scaler->in_stride
)
{
scaler->in_fmt = format;
scaler->in_width = width;
scaler->in_height = height;
scaler->in_stride = pitch;
scaler->out_width = vid->width;
scaler->out_height = vid->height;
scaler->out_stride = vid->width * vid->bytes_per_pixel;
if (!scaler_ctx_gen_filter(scaler))
RARCH_ERR("[video_omap]: scaler_ctx_gen_filter failed\n");
}
}
static void omap_gfx_set_texture_frame(void *data, const void *frame, bool rgb32,
unsigned width, unsigned height, float alpha)
{
omap_video_t *vid = (omap_video_t*)data;
enum scaler_pix_fmt format = rgb32 ? SCALER_FMT_ARGB8888 : SCALER_FMT_RGBA4444;
(void) alpha;
update_scaler(vid, &vid->menu.scaler, format, width, height,
video_frame_scale(
&vid->menu.scaler,
vid->menu.frame,
frame,
format,
vid->width,
vid->height,
vid->width * vid->bytes_per_pixel,
width,
height,
width * (rgb32 ? sizeof(uint32_t) : sizeof(uint16_t)));
scaler_ctx_scale(&vid->menu.scaler, vid->menu.frame, frame);
}
static void omap_gfx_set_texture_enable(void *data, bool state, bool full_screen)

View File

@ -793,29 +793,25 @@ static void psp_set_filtering(void *data, unsigned index, bool smooth)
static void psp_set_aspect_ratio(void *data, unsigned aspect_ratio_idx)
{
psp1_video_t *psp = (psp1_video_t*)data;
enum rarch_display_ctl_state cmd = RARCH_DISPLAY_CTL_NONE;
switch (aspect_ratio_idx)
{
case ASPECT_RATIO_SQUARE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_SQUARE_PIXEL;
video_driver_set_viewport_square_pixel();
break;
case ASPECT_RATIO_CORE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CORE;
video_driver_set_viewport_core();
break;
case ASPECT_RATIO_CONFIG:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CONFIG;
video_driver_set_viewport_config();
break;
default:
break;
}
if (cmd != RARCH_DISPLAY_CTL_NONE)
video_driver_ctl(cmd, NULL);
video_driver_set_aspect_ratio_value(aspectratio_lut[aspect_ratio_idx].value);
psp->keep_aspect = true;

View File

@ -25,7 +25,7 @@
#include "../../driver.h"
#include "../../general.h"
#include "../../retroarch.h"
#include "../../performance.h"
#include "../../performance_counters.h"
#include "../../verbosity.h"
#include "../video_context_driver.h"
#include "../font_driver.h"
@ -569,7 +569,7 @@ static bool sdl2_gfx_suppress_screensaver(void *data, bool enable)
if (video_driver_display_type_get() == RARCH_DISPLAY_X11)
{
#ifdef HAVE_X11
x11_suspend_screensaver(video_driver_window_get());
x11_suspend_screensaver(video_driver_window_get(), enable);
#endif
return true;
}
@ -629,7 +629,7 @@ static bool sdl2_gfx_read_viewport(void *data, uint8_t *buffer)
rarch_perf_init(&sdl2_gfx_read_viewport, "sdl2_gfx_read_viewport");
retro_perf_start(&sdl2_gfx_read_viewport);
video_driver_ctl(RARCH_DISPLAY_CTL_CACHED_FRAME_RENDER, NULL);
video_driver_cached_frame_render();
surf = SDL_GetWindowSurface(vid->window);
bgr24 = SDL_ConvertSurfaceFormat(surf, SDL_PIXELFORMAT_BGR24, 0);
@ -658,29 +658,25 @@ static void sdl2_poke_set_filtering(void *data, unsigned index, bool smooth)
static void sdl2_poke_set_aspect_ratio(void *data, unsigned aspect_ratio_idx)
{
sdl2_video_t *vid = (sdl2_video_t*)data;
enum rarch_display_ctl_state cmd = RARCH_DISPLAY_CTL_NONE;
switch (aspect_ratio_idx)
{
case ASPECT_RATIO_SQUARE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_SQUARE_PIXEL;
video_driver_set_viewport_square_pixel();
break;
case ASPECT_RATIO_CORE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CORE;
video_driver_set_viewport_core();
break;
case ASPECT_RATIO_CONFIG:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CONFIG;
video_driver_set_viewport_config();
break;
default:
break;
}
if (cmd != RARCH_DISPLAY_CTL_NONE)
video_driver_ctl(cmd, NULL);
video_driver_set_aspect_ratio_value(aspectratio_lut[aspect_ratio_idx].value);
vid->video.force_aspect = true;

View File

@ -25,7 +25,9 @@
#include "../../driver.h"
#include "../../general.h"
#include "../../performance.h"
#include "../../performance_counters.h"
#include "../video_frame.h"
#include "../video_context_driver.h"
#include "../font_driver.h"
@ -83,30 +85,6 @@ static void sdl_gfx_free(void *data)
free(vid);
}
static void sdl_update_scaler(SDL_Surface *surf, struct scaler_ctx *scaler,
enum scaler_pix_fmt format, unsigned width,
unsigned height, unsigned pitch)
{
if (
width != (unsigned)scaler->in_width
|| height != (unsigned)scaler->in_height
|| format != scaler->in_fmt
|| pitch != (unsigned)scaler->in_stride
)
{
scaler->in_fmt = format;
scaler->in_width = width;
scaler->in_height = height;
scaler->in_stride = pitch;
scaler->out_width = surf->w;
scaler->out_height = surf->h;
scaler->out_stride = surf->pitch;
scaler_ctx_gen_filter(scaler);
}
}
static void sdl_init_font(sdl_video_t *vid, const char *font_path, unsigned font_size)
{
int r, g, b;
@ -361,14 +339,23 @@ static bool sdl_gfx_frame(void *data, const void *frame, unsigned width,
if (!frame)
return true;
sdl_update_scaler(vid->screen, &vid->scaler, vid->scaler.in_fmt, width, height, pitch);
if (SDL_MUSTLOCK(vid->screen))
SDL_LockSurface(vid->screen);
rarch_perf_init(&sdl_scale, "sdl_scale");
retro_perf_start(&sdl_scale);
scaler_ctx_scale(&vid->scaler, vid->screen->pixels, frame);
video_frame_scale(
&vid->scaler,
vid->screen->pixels,
frame,
vid->scaler.in_fmt,
vid->screen->w,
vid->screen->h,
vid->screen->pitch,
width,
height,
pitch);
retro_perf_stop(&sdl_scale);
if (vid->menu.active)
@ -414,7 +401,7 @@ static bool sdl_gfx_suppress_screensaver(void *data, bool enable)
#ifdef HAVE_X11
if (video_driver_display_type_get() == RARCH_DISPLAY_X11)
{
x11_suspend_screensaver(video_driver_window_get());
x11_suspend_screensaver(video_driver_window_get(), enable);
return true;
}
#endif
@ -446,29 +433,24 @@ static void sdl_set_filtering(void *data, unsigned index, bool smooth)
static void sdl_set_aspect_ratio(void *data, unsigned aspect_ratio_idx)
{
enum rarch_display_ctl_state cmd = RARCH_DISPLAY_CTL_NONE;
switch (aspect_ratio_idx)
{
case ASPECT_RATIO_SQUARE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_SQUARE_PIXEL;
video_driver_set_viewport_square_pixel();
break;
case ASPECT_RATIO_CORE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CORE;
video_driver_set_viewport_core();
break;
case ASPECT_RATIO_CONFIG:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CONFIG;
video_driver_set_viewport_config();
break;
default:
break;
}
if (cmd != RARCH_DISPLAY_CTL_NONE)
video_driver_ctl(cmd, NULL);
video_driver_set_aspect_ratio_value(aspectratio_lut[aspect_ratio_idx].value);
}
@ -480,15 +462,23 @@ static void sdl_apply_state_changes(void *data)
static void sdl_set_texture_frame(void *data, const void *frame, bool rgb32,
unsigned width, unsigned height, float alpha)
{
enum scaler_pix_fmt format = rgb32 ? SCALER_FMT_ARGB8888 : SCALER_FMT_RGBA4444;
enum scaler_pix_fmt format = rgb32
? SCALER_FMT_ARGB8888 : SCALER_FMT_RGBA4444;
sdl_video_t *vid = (sdl_video_t*)data;
(void)alpha;
video_frame_scale(
&vid->menu.scaler,
vid->menu.frame->pixels,
frame,
format,
vid->menu.frame->w,
vid->menu.frame->h,
vid->menu.frame->pitch,
width,
height,
width * (rgb32 ? sizeof(uint32_t) : sizeof(uint16_t))
);
sdl_update_scaler(vid->menu.frame, &vid->menu.scaler, format, width, height,
width * (rgb32 ? sizeof(uint32_t) : sizeof(uint16_t)));
scaler_ctx_scale(&vid->menu.scaler, vid->menu.frame->pixels, frame);
SDL_SetAlpha(vid->menu.frame, SDL_SRCALPHA, 255.0 * alpha);
}

View File

@ -84,7 +84,7 @@ typedef enum tag_DISP_CMD
DISP_CMD_LAYER_SET_SCN_WINDOW = 0x48,
DISP_CMD_LAYER_GET_SCN_WINDOW = 0x49,
DISP_CMD_LAYER_SET_PARA = 0x4a,
DISP_CMD_LAYER_GET_PARA = 0x4b,
DISP_CMD_LAYER_GET_PARA = 0x4b
} __disp_cmd_t;
typedef struct

View File

@ -24,13 +24,13 @@
#include <retro_inline.h>
#include <retro_assert.h>
#include <gfx/math/matrix_3x3.h>
#include <libretro.h>
#include "../video_context_driver.h"
#include "../../libretro.h"
#include "../../general.h"
#include "../../retroarch.h"
#include "../../driver.h"
#include "../../performance.h"
#include "../../performance_counters.h"
#include "../font_driver.h"
#include "../../content.h"
#include "../../runloop.h"
@ -70,7 +70,7 @@ static PFNVGCREATEEGLIMAGETARGETKHRPROC pvgCreateEGLImageTargetKHR;
static void vg_set_nonblock_state(void *data, bool state)
{
unsigned interval = state ? 0 : 1;
gfx_ctx_ctl(GFX_CTL_SWAP_INTERVAL, &interval);
video_context_driver_swap_interval(&interval);
}
static INLINE bool vg_query_extension(const char *ext)
@ -94,16 +94,16 @@ static void *vg_init(const video_info_t *video,
VGfloat clearColor[4] = {0, 0, 0, 1};
settings_t *settings = config_get_ptr();
vg_t *vg = (vg_t*)calloc(1, sizeof(vg_t));
const gfx_ctx_driver_t *ctx = gfx_ctx_init_first(
const gfx_ctx_driver_t *ctx = video_context_driver_init_first(
vg, settings->video.context_driver,
GFX_CTX_OPENVG_API, 0, 0, false);
if (!vg || !ctx)
goto error;
gfx_ctx_ctl(GFX_CTL_SET, (void*)ctx);
video_context_driver_set((void*)ctx);
gfx_ctx_ctl(GFX_CTL_GET_VIDEO_SIZE, &mode);
video_context_driver_get_video_size(&mode);
temp_width = mode.width;
temp_height = mode.height;
@ -117,8 +117,8 @@ static void *vg_init(const video_info_t *video,
interval = video->vsync ? 1 : 0;
gfx_ctx_ctl(GFX_CTL_SWAP_INTERVAL, &interval);
gfx_ctx_ctl(GFX_CTL_UPDATE_WINDOW_TITLE, NULL);
video_context_driver_swap_interval(&interval);
video_context_driver_update_window_title();
vg->mTexType = video->rgb32 ? VG_sXRGB_8888 : VG_sRGB_565;
vg->keep_aspect = video->force_aspect;
@ -137,7 +137,7 @@ static void *vg_init(const video_info_t *video,
mode.height = win_height;
mode.fullscreen = video->fullscreen;
if (!gfx_ctx_ctl(GFX_CTL_SET_VIDEO_MODE, &mode))
if (!video_context_driver_set_video_mode(&mode))
goto error;
video_driver_get_size(&temp_width, &temp_height);
@ -147,7 +147,7 @@ static void *vg_init(const video_info_t *video,
mode.width = 0;
mode.height = 0;
gfx_ctx_ctl(GFX_CTL_GET_VIDEO_SIZE, &mode);
video_context_driver_get_video_size(&mode);
temp_width = mode.width;
temp_height = mode.height;
@ -170,7 +170,7 @@ static void *vg_init(const video_info_t *video,
aspect_data.width = temp_width;
aspect_data.height = temp_height;
gfx_ctx_ctl(GFX_CTL_TRANSLATE_ASPECT, &aspect_data);
video_context_driver_translate_aspect(&aspect_data);
vgSetfv(VG_CLEAR_COLOR, 4, clearColor);
@ -182,7 +182,7 @@ static void *vg_init(const video_info_t *video,
inp.input = input;
inp.input_data = input_data;
gfx_ctx_ctl(GFX_CTL_INPUT_DRIVER, &inp);
video_context_driver_input_driver(&inp);
if ( settings->video.font_enable
&& font_renderer_create_default((const void**)&vg->font_driver, &vg->mFontRenderer,
@ -216,13 +216,13 @@ static void *vg_init(const video_info_t *video,
}
if (vg_query_extension("KHR_EGL_image")
&& gfx_ctx_ctl(GFX_CTL_IMAGE_BUFFER_INIT, (void*)video))
&& video_context_driver_init_image_buffer((void*)video))
{
gfx_ctx_proc_address_t proc_address;
proc_address.sym = "vgCreateEGLImageTargetKHR";
gfx_ctx_ctl(GFX_CTL_PROC_ADDRESS_GET, &proc_address);
video_context_driver_get_proc_address(&proc_address);
pvgCreateEGLImageTargetKHR =
(PFNVGCREATEEGLIMAGETARGETKHRPROC)proc_address.addr;
@ -245,7 +245,7 @@ static void *vg_init(const video_info_t *video,
error:
if (vg)
free(vg);
gfx_ctx_ctl(GFX_CTL_DESTROY, NULL);
video_context_driver_destroy();
return NULL;
}
@ -266,7 +266,7 @@ static void vg_free(void *data)
vgDestroyPaint(vg->mPaintBg);
}
gfx_ctx_ctl(GFX_CTL_FREE, NULL);
video_context_driver_free();
free(vg);
}
@ -343,7 +343,7 @@ static void vg_copy_frame(void *data, const void *frame,
img_info.index = 0;
img_info.handle = &img;
new_egl = gfx_ctx_ctl(GFX_CTL_IMAGE_BUFFER_WRITE, &img_info);
new_egl = video_context_driver_write_to_image_buffer(&img_info);
retro_assert(img != EGL_NO_IMAGE_KHR);
@ -413,11 +413,11 @@ static bool vg_frame(void *data, const void *frame,
vg_draw_message(vg, msg);
#endif
gfx_ctx_ctl(GFX_CTL_UPDATE_WINDOW_TITLE, NULL);
video_context_driver_update_window_title();
retro_perf_stop(&vg_fr);
gfx_ctx_ctl(GFX_CTL_SWAP_BUFFERS, NULL);
video_context_driver_swap_buffers();
return true;
}
@ -435,7 +435,7 @@ static bool vg_alive(void *data)
size_data.width = &temp_width;
size_data.height = &temp_height;
gfx_ctx_ctl(GFX_CTL_CHECK_WINDOW, &size_data);
video_context_driver_check_window(&size_data);
if (temp_width != 0 && temp_height != 0)
video_driver_set_size(&temp_width, &temp_height);
@ -445,18 +445,18 @@ static bool vg_alive(void *data)
static bool vg_focus(void *data)
{
return gfx_ctx_ctl(GFX_CTL_FOCUS, NULL);
return video_context_driver_focus();
}
static bool vg_suppress_screensaver(void *data, bool enable)
{
bool enabled = enable;
return gfx_ctx_ctl(GFX_CTL_SUPPRESS_SCREENSAVER, &enabled);
return video_context_driver_suppress_screensaver(&enabled);
}
static bool vg_has_windowed(void *data)
{
return gfx_ctx_ctl(GFX_CTL_HAS_WINDOWED, NULL);
return video_context_driver_has_windowed();
}
static bool vg_set_shader(void *data,

View File

@ -121,7 +121,8 @@ static void *vita2d_gfx_init(const video_info_t *video,
vita->vsync = video->vsync;
vita->rgb32 = video->rgb32;
vita->tex_filter = video->smooth? SCE_GXM_TEXTURE_FILTER_LINEAR : SCE_GXM_TEXTURE_FILTER_POINT;
vita->tex_filter = video->smooth
? SCE_GXM_TEXTURE_FILTER_LINEAR : SCE_GXM_TEXTURE_FILTER_POINT;
if (input && input_data)
{
@ -149,14 +150,12 @@ static void *vita2d_gfx_init(const video_info_t *video,
static void vita2d_render_overlay(void *data);
static void vita2d_free_overlay(vita_video_t *vita)
{
for (unsigned i = 0; i < vita->overlays; i++)
{
unsigned i;
for (i = 0; i < vita->overlays; i++)
vita2d_free_texture(vita->overlay[i].tex);
}
free(vita->overlay);
vita->overlay = NULL;
vita->overlays = 0;
//GX_InvalidateTexAll();
}
#endif
@ -327,8 +326,6 @@ static void vita2d_gfx_free(void *data)
{
vita_video_t *vita = (vita_video_t *)data;
RARCH_LOG("vita2d_gfx_free()\n");
vita2d_fini();
if (vita->menu.texture)
@ -492,29 +489,25 @@ static void vita_set_filtering(void *data, unsigned index, bool smooth)
static void vita_set_aspect_ratio(void *data, unsigned aspect_ratio_idx)
{
vita_video_t *vita = (vita_video_t*)data;
enum rarch_display_ctl_state cmd = RARCH_DISPLAY_CTL_NONE;
switch (aspect_ratio_idx)
{
case ASPECT_RATIO_SQUARE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_SQUARE_PIXEL;
video_driver_set_viewport_square_pixel();
break;
case ASPECT_RATIO_CORE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CORE;
video_driver_set_viewport_core();
break;
case ASPECT_RATIO_CONFIG:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CONFIG;
video_driver_set_viewport_config();
break;
default:
break;
}
if (cmd != RARCH_DISPLAY_CTL_NONE)
video_driver_ctl(cmd, NULL);
video_driver_set_aspect_ratio_value(aspectratio_lut[aspect_ratio_idx].value);
vita->keep_aspect = true;
@ -560,7 +553,9 @@ static void vita_set_texture_frame(void *data, const void *frame, bool rgb32,
vita->menu.width = width;
vita->menu.height = height;
}
vita2d_texture_set_filters(vita->menu.texture,SCE_GXM_TEXTURE_FILTER_LINEAR,SCE_GXM_TEXTURE_FILTER_LINEAR);
tex_p = vita2d_texture_get_datap(vita->menu.texture);
stride = vita2d_texture_get_stride(vita->menu.texture);
@ -670,9 +665,7 @@ static void vita2d_overlay_tex_geom(void *data, unsigned image,
float x, float y, float w, float h)
{
vita_video_t *vita = (vita_video_t*)data;
struct vita_overlay_data *o;
o = NULL;
struct vita_overlay_data *o = NULL;
if (vita)
o = (struct vita_overlay_data*)&vita->overlay[image];
@ -690,9 +683,7 @@ static void vita2d_overlay_vertex_geom(void *data, unsigned image,
float x, float y, float w, float h)
{
vita_video_t *vita = (vita_video_t*)data;
struct vita_overlay_data *o;
o = NULL;
struct vita_overlay_data *o = NULL;
/* Flipped, so we preserve top-down semantics. */
/*y = 1.0f - y;
@ -731,8 +722,10 @@ static void vita2d_overlay_set_alpha(void *data, unsigned image, float mod)
static void vita2d_render_overlay(void *data)
{
unsigned i;
vita_video_t *vita = (vita_video_t*)data;
for (unsigned i = 0; i < vita->overlays; i++)
for (i = 0; i < vita->overlays; i++)
{
vita2d_draw_texture_tint_part_scale(vita->overlay[i].tex,
vita->overlay[i].x,
@ -744,7 +737,6 @@ static void vita2d_render_overlay(void *data)
vita->overlay[i].w,
vita->overlay[i].h,
RGBA8(0xFF,0xFF,0xFF,(uint8_t)(vita->overlay[i].alpha_mod * 255.0f)));
//RGBA8(0x00, 0x00, 0x00, (uint8_t)(vita->overlay[i].alpha_mod * 255.0f)));
}
}

View File

@ -13,28 +13,33 @@
* If not, see <http://www.gnu.org/licenses/>.
*/
#include "../common/vulkan_common.h"
#include "vulkan_shaders/alpha_blend.vert.inc"
#include "vulkan_shaders/alpha_blend.frag.inc"
#include "vulkan_shaders/font.frag.inc"
#include <stdio.h>
#include <stdint.h>
#include <math.h>
#include <string.h>
#include <compat/strl.h>
#include <gfx/scaler/scaler.h>
#include <formats/image.h>
#include <retro_inline.h>
#include <retro_miscellaneous.h>
#include <retro_assert.h>
#include <libretro.h>
#include "../common/vulkan_common.h"
#include "vulkan_shaders/alpha_blend.vert.inc"
#include "vulkan_shaders/alpha_blend.frag.inc"
#include "vulkan_shaders/font.frag.inc"
#include "vulkan_shaders/ribbon.vert.inc"
#include "vulkan_shaders/ribbon.frag.inc"
#include "vulkan_shaders/ribbon_simple.vert.inc"
#include "vulkan_shaders/ribbon_simple.frag.inc"
#include "../../driver.h"
#include "../../record/record_driver.h"
#include "../../performance.h"
#include "../../performance_counters.h"
#include "../../libretro.h"
#include "../../general.h"
#include "../../retroarch.h"
@ -66,7 +71,8 @@ static const gfx_ctx_driver_t *vulkan_get_context(vk_t *vk)
settings_t *settings = config_get_ptr();
enum gfx_ctx_api api = GFX_CTX_VULKAN_API;
return gfx_ctx_init_first(vk, settings->video.context_driver,
return video_context_driver_init_first(
vk, settings->video.context_driver,
api, major, minor, false);
}
@ -172,7 +178,7 @@ static void vulkan_init_pipeline_layout(
bindings[0].binding = 0;
bindings[0].descriptorType = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER;
bindings[0].descriptorCount = 1;
bindings[0].stageFlags = VK_SHADER_STAGE_VERTEX_BIT;
bindings[0].stageFlags = VK_SHADER_STAGE_VERTEX_BIT | VK_SHADER_STAGE_FRAGMENT_BIT;
bindings[0].pImmutableSamplers = NULL;
bindings[1].binding = 1;
@ -360,6 +366,49 @@ static void vulkan_init_pipelines(
VKFUNC(vkDestroyShaderModule)(vk->context->device, shader_stages[0].module, NULL);
VKFUNC(vkDestroyShaderModule)(vk->context->device, shader_stages[1].module, NULL);
/* Other menu pipelines. */
for (i = 0; i < 4; i++)
{
if (i & 2)
{
module_info.codeSize = ribbon_simple_vert_spv_len;
module_info.pCode = (const uint32_t*)ribbon_simple_vert_spv;
}
else
{
module_info.codeSize = ribbon_vert_spv_len;
module_info.pCode = (const uint32_t*)ribbon_vert_spv;
}
shader_stages[0].stage = VK_SHADER_STAGE_VERTEX_BIT;
shader_stages[0].pName = "main";
VKFUNC(vkCreateShaderModule)(vk->context->device,
&module_info, NULL, &shader_stages[0].module);
if (i & 2)
{
module_info.codeSize = ribbon_simple_frag_spv_len;
module_info.pCode = (const uint32_t*)ribbon_simple_frag_spv;
}
else
{
module_info.codeSize = ribbon_frag_spv_len;
module_info.pCode = (const uint32_t*)ribbon_frag_spv;
}
shader_stages[1].stage = VK_SHADER_STAGE_FRAGMENT_BIT;
shader_stages[1].pName = "main";
VKFUNC(vkCreateShaderModule)(vk->context->device,
&module_info, NULL, &shader_stages[1].module);
input_assembly.topology = i & 1 ?
VK_PRIMITIVE_TOPOLOGY_TRIANGLE_STRIP :
VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST;
VKFUNC(vkCreateGraphicsPipelines)(vk->context->device, vk->pipelines.cache,
1, &pipe, NULL, &vk->display.pipelines[4 + i]);
}
}
static void vulkan_init_command_buffers(vk_t *vk)
@ -550,7 +599,7 @@ static void vulkan_deinit_pipelines(vk_t *vk)
VKFUNC(vkDestroyPipeline)(vk->context->device,
vk->pipelines.font, NULL);
for (i = 0; i < 4; i++)
for (i = 0; i < 8; i++)
VKFUNC(vkDestroyPipeline)(vk->context->device,
vk->display.pipelines[i], NULL);
}
@ -762,7 +811,7 @@ static void vulkan_free(void *data)
if (vk->filter_chain)
vulkan_filter_chain_free(vk->filter_chain);
gfx_ctx_ctl(GFX_CTL_FREE, NULL);
video_context_driver_free();
}
scaler_ctx_gen_reset(&vk->readback.scaler);
@ -836,21 +885,25 @@ static void vulkan_set_command_buffers(void *handle, uint32_t num_cmd,
static void vulkan_lock_queue(void *handle)
{
vk_t *vk = (vk_t*)handle;
#ifdef HAVE_THREADS
slock_lock(vk->context->queue_lock);
#endif
}
static void vulkan_unlock_queue(void *handle)
{
vk_t *vk = (vk_t*)handle;
#ifdef HAVE_THREADS
slock_unlock(vk->context->queue_lock);
#endif
}
static void vulkan_init_hw_render(vk_t *vk)
{
struct retro_hw_render_interface_vulkan *iface =
&vk->hw.iface;
struct retro_hw_render_callback *hwr = NULL;
video_driver_ctl(RARCH_DISPLAY_CTL_HW_CONTEXT_GET, &hwr);
struct retro_hw_render_callback *hwr =
video_driver_get_hw_context();
if (hwr->context_type != RETRO_HW_CONTEXT_VULKAN)
return;
@ -932,9 +985,9 @@ static void *vulkan_init(const video_info_t *video,
if (!ctx_driver)
goto error;
gfx_ctx_ctl(GFX_CTL_SET, (void*)ctx_driver);
video_context_driver_set((const gfx_ctx_driver_t*)ctx_driver);
gfx_ctx_ctl(GFX_CTL_GET_VIDEO_SIZE, &mode);
video_context_driver_get_video_size(&mode);
full_x = mode.width;
full_y = mode.height;
mode.width = 0;
@ -942,7 +995,7 @@ static void *vulkan_init(const video_info_t *video,
RARCH_LOG("Detecting screen resolution %ux%u.\n", full_x, full_y);
interval = video->vsync ? settings->video.swap_interval : 0;
gfx_ctx_ctl(GFX_CTL_SWAP_INTERVAL, &interval);
video_context_driver_swap_interval(&interval);
win_width = video->width;
win_height = video->height;
@ -956,10 +1009,10 @@ static void *vulkan_init(const video_info_t *video,
mode.width = win_width;
mode.height = win_height;
mode.fullscreen = video->fullscreen;
if (!gfx_ctx_ctl(GFX_CTL_SET_VIDEO_MODE, &mode))
if (!video_context_driver_set_video_mode(&mode))
goto error;
gfx_ctx_ctl(GFX_CTL_GET_VIDEO_SIZE, &mode);
video_context_driver_get_video_size(&mode);
temp_width = mode.width;
temp_height = mode.height;
@ -969,7 +1022,7 @@ static void *vulkan_init(const video_info_t *video,
RARCH_LOG("Vulkan: Using resolution %ux%u\n", temp_width, temp_height);
gfx_ctx_ctl(GFX_CTL_GET_CONTEXT_DATA, &vk->context);
video_context_driver_get_context_data(&vk->context);
vk->vsync = video->vsync;
vk->fullscreen = video->fullscreen;
@ -993,7 +1046,7 @@ static void *vulkan_init(const video_info_t *video,
inp.input = input;
inp.input_data = input_data;
gfx_ctx_ctl(GFX_CTL_INPUT_DRIVER, &inp);
video_context_driver_input_driver(&inp);
if (settings->video.font_enable)
{
@ -1050,7 +1103,7 @@ static void vulkan_set_nonblock_state(void *data, bool state)
RARCH_LOG("[Vulkan]: VSync => %s\n", state ? "off" : "on");
interval = state ? 0 : settings->video.swap_interval;
gfx_ctx_ctl(GFX_CTL_SWAP_INTERVAL, &interval);
video_context_driver_swap_interval(&interval);
/* Changing vsync might require recreating the swapchain, which means new VkImages
* to render into. */
@ -1074,7 +1127,7 @@ static bool vulkan_alive(void *data)
size_data.width = &temp_width;
size_data.height = &temp_height;
if (gfx_ctx_ctl(GFX_CTL_CHECK_WINDOW, &size_data))
if (video_context_driver_check_window(&size_data))
{
if (quit)
vk->quitting = true;
@ -1093,20 +1146,20 @@ static bool vulkan_alive(void *data)
static bool vulkan_focus(void *data)
{
(void)data;
return gfx_ctx_ctl(GFX_CTL_FOCUS, NULL);
return video_context_driver_focus();
}
static bool vulkan_suppress_screensaver(void *data, bool enable)
{
(void)data;
bool enabled = enable;
return gfx_ctx_ctl(GFX_CTL_SUPPRESS_SCREENSAVER, &enabled);
return video_context_driver_suppress_screensaver(&enabled);
}
static bool vulkan_has_windowed(void *data)
{
(void)data;
return gfx_ctx_ctl(GFX_CTL_HAS_WINDOWED, NULL);
return video_context_driver_has_windowed();
}
static bool vulkan_set_shader(void *data,
@ -1143,7 +1196,7 @@ static bool vulkan_set_shader(void *data,
}
static void vulkan_set_projection(vk_t *vk,
struct gfx_ortho *ortho, bool allow_rotate)
struct video_ortho *ortho, bool allow_rotate)
{
math_matrix_4x4 rot;
@ -1164,7 +1217,7 @@ static void vulkan_set_projection(vk_t *vk,
static void vulkan_set_rotation(void *data, unsigned rotation)
{
vk_t *vk = (vk_t*)data;
struct gfx_ortho ortho = {0, 1, 0, 1, -1, 1};
struct video_ortho ortho = {0, 1, 0, 1, -1, 1};
if (!vk)
return;
@ -1184,7 +1237,7 @@ static void vulkan_set_video_mode(void *data,
mode.height = height;
mode.fullscreen = fullscreen;
gfx_ctx_ctl(GFX_CTL_SET_VIDEO_MODE, &mode);
video_context_driver_set_video_mode(&mode);
}
static void vulkan_set_viewport(void *data, unsigned viewport_width,
@ -1195,7 +1248,7 @@ static void vulkan_set_viewport(void *data, unsigned viewport_width,
int x = 0;
int y = 0;
float device_aspect = (float)viewport_width / viewport_height;
struct gfx_ortho ortho = {0, 1, 0, 1, -1, 1};
struct video_ortho ortho = {0, 1, 0, 1, -1, 1};
settings_t *settings = config_get_ptr();
vk_t *vk = (vk_t*)data;
@ -1205,7 +1258,7 @@ static void vulkan_set_viewport(void *data, unsigned viewport_width,
aspect_data.width = viewport_width;
aspect_data.height = viewport_height;
gfx_ctx_ctl(GFX_CTL_TRANSLATE_ASPECT, &aspect_data);
video_context_driver_translate_aspect(&aspect_data);
if (settings->video.scale_integer && !force_full)
{
@ -1692,17 +1745,21 @@ static bool vulkan_frame(void *data, const void *frame,
retro_perf_start(&queue_submit);
#ifdef HAVE_THREADS
slock_lock(vk->context->queue_lock);
#endif
VKFUNC(vkQueueSubmit)(vk->context->queue, 1,
&submit_info, vk->context->swapchain_fences[frame_index]);
#ifdef HAVE_THREADS
slock_unlock(vk->context->queue_lock);
#endif
retro_perf_stop(&queue_submit);
retro_perf_start(&swapbuffers);
gfx_ctx_ctl(GFX_CTL_SWAP_BUFFERS, NULL);
video_context_driver_swap_buffers();
retro_perf_stop(&swapbuffers);
gfx_ctx_ctl(GFX_CTL_UPDATE_WINDOW_TITLE, NULL);
video_context_driver_update_window_title();
/* Handle spurious swapchain invalidations as soon as we can,
* i.e. right after swap buffers. */
@ -1711,7 +1768,7 @@ static bool vulkan_frame(void *data, const void *frame,
gfx_ctx_mode_t mode;
mode.width = width;
mode.height = height;
gfx_ctx_ctl(GFX_CTL_SET_RESIZE, &mode);
video_context_driver_set_resize(&mode);
vk->should_resize = false;
}
@ -1723,29 +1780,25 @@ static bool vulkan_frame(void *data, const void *frame,
static void vulkan_set_aspect_ratio(void *data, unsigned aspect_ratio_idx)
{
vk_t *vk = (vk_t*)data;
enum rarch_display_ctl_state cmd = RARCH_DISPLAY_CTL_NONE;
switch (aspect_ratio_idx)
{
case ASPECT_RATIO_SQUARE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_SQUARE_PIXEL;
video_driver_set_viewport_square_pixel();
break;
case ASPECT_RATIO_CORE:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CORE;
video_driver_set_viewport_core();
break;
case ASPECT_RATIO_CONFIG:
cmd = RARCH_DISPLAY_CTL_SET_VIEWPORT_CONFIG;
video_driver_set_viewport_config();
break;
default:
break;
}
if (cmd != RARCH_DISPLAY_CTL_NONE)
video_driver_ctl(cmd, NULL);
video_driver_set_aspect_ratio_value(
aspectratio_lut[aspect_ratio_idx].value);
@ -1766,7 +1819,7 @@ static void vulkan_apply_state_changes(void *data)
static void vulkan_show_mouse(void *data, bool state)
{
(void)data;
gfx_ctx_ctl(GFX_CTL_SHOW_MOUSE, &state);
video_context_driver_show_mouse(&state);
}
static struct video_shader *vulkan_get_current_shader(void *data)
@ -1963,7 +2016,9 @@ static const video_poke_interface_t vulkan_poke_interface = {
NULL,
NULL,
#endif
#ifdef HAVE_MENU
vulkan_set_osd_msg,
#endif
vulkan_show_mouse,
NULL,
vulkan_get_current_shader,
@ -2034,7 +2089,7 @@ static bool vulkan_read_viewport(void *data, uint8_t *buffer)
* with conversion. */
vk->readback.pending = true;
video_driver_ctl(RARCH_DISPLAY_CTL_CACHED_FRAME_RENDER, NULL);
video_driver_cached_frame_render();
VKFUNC(vkQueueWaitIdle)(vk->context->queue);
if (!staging->mapped)
@ -2073,7 +2128,7 @@ static void vulkan_overlay_enable(void *data, bool enable)
vk->overlay.enable = enable;
if (vk->fullscreen)
gfx_ctx_ctl(GFX_CTL_SHOW_MOUSE, &enable);
video_context_driver_show_mouse(&enable);
}
static void vulkan_overlay_full_screen(void *data, bool enable)
@ -2149,7 +2204,8 @@ static void vulkan_render_overlay(vk_t *vk)
call.pipeline = vk->display.pipelines[3]; /* Strip with blend */
call.texture = &vk->overlay.images[i];
call.sampler = vk->samplers.linear;
call.mvp = &vk->mvp;
call.uniform = &vk->mvp;
call.uniform_size = sizeof(vk->mvp);
call.vbo = &range;
call.vertices = 4;
vulkan_draw_triangles(vk, &call);
@ -2215,9 +2271,13 @@ static bool vulkan_overlay_load(void *data,
if (!vk)
return false;
#ifdef HAVE_THREADS
slock_lock(vk->context->queue_lock);
#endif
VKFUNC(vkQueueWaitIdle)(vk->context->queue);
#ifdef HAVE_THREADS
slock_unlock(vk->context->queue_lock);
#endif
vulkan_overlay_free(vk);
vk->overlay.images = (struct vk_texture*)

View File

@ -0,0 +1,21 @@
#version 310 es
precision highp float;
layout(std140, set = 0, binding = 0) uniform UBO
{
float time;
} constants;
layout(location = 0) in vec3 vEC;
layout(location = 0) out vec4 FragColor;
void main()
{
const vec3 up = vec3(0.0, 0.0, 1.0);
vec3 x = dFdx(vEC);
vec3 y = dFdy(vEC);
vec3 normal = normalize(cross(x, y));
float c = 1.0 - dot(normal, up);
c = (1.0 - cos(c * c)) / 3.0;
FragColor = vec4(1.0, 1.0, 1.0, c);
}

View File

@ -0,0 +1,101 @@
unsigned char ribbon_frag_spv[] = {
0x03, 0x02, 0x23, 0x07, 0x00, 0x00, 0x01, 0x00, 0x01, 0x00, 0x08, 0x00,
0x2d, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x11, 0x00, 0x02, 0x00,
0x01, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x06, 0x00, 0x01, 0x00, 0x00, 0x00,
0x47, 0x4c, 0x53, 0x4c, 0x2e, 0x73, 0x74, 0x64, 0x2e, 0x34, 0x35, 0x30,
0x00, 0x00, 0x00, 0x00, 0x0e, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00,
0x01, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x07, 0x00, 0x04, 0x00, 0x00, 0x00,
0x04, 0x00, 0x00, 0x00, 0x6d, 0x61, 0x69, 0x6e, 0x00, 0x00, 0x00, 0x00,
0x0b, 0x00, 0x00, 0x00, 0x27, 0x00, 0x00, 0x00, 0x10, 0x00, 0x03, 0x00,
0x04, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x03, 0x00, 0x03, 0x00,
0x01, 0x00, 0x00, 0x00, 0x36, 0x01, 0x00, 0x00, 0x05, 0x00, 0x04, 0x00,
0x04, 0x00, 0x00, 0x00, 0x6d, 0x61, 0x69, 0x6e, 0x00, 0x00, 0x00, 0x00,
0x05, 0x00, 0x03, 0x00, 0x09, 0x00, 0x00, 0x00, 0x78, 0x00, 0x00, 0x00,
0x05, 0x00, 0x03, 0x00, 0x0b, 0x00, 0x00, 0x00, 0x76, 0x45, 0x43, 0x00,
0x05, 0x00, 0x03, 0x00, 0x0e, 0x00, 0x00, 0x00, 0x79, 0x00, 0x00, 0x00,
0x05, 0x00, 0x04, 0x00, 0x11, 0x00, 0x00, 0x00, 0x6e, 0x6f, 0x72, 0x6d,
0x61, 0x6c, 0x00, 0x00, 0x05, 0x00, 0x03, 0x00, 0x17, 0x00, 0x00, 0x00,
0x63, 0x00, 0x00, 0x00, 0x05, 0x00, 0x05, 0x00, 0x27, 0x00, 0x00, 0x00,
0x46, 0x72, 0x61, 0x67, 0x43, 0x6f, 0x6c, 0x6f, 0x72, 0x00, 0x00, 0x00,
0x05, 0x00, 0x03, 0x00, 0x2a, 0x00, 0x00, 0x00, 0x55, 0x42, 0x4f, 0x00,
0x06, 0x00, 0x05, 0x00, 0x2a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x74, 0x69, 0x6d, 0x65, 0x00, 0x00, 0x00, 0x00, 0x05, 0x00, 0x05, 0x00,
0x2c, 0x00, 0x00, 0x00, 0x63, 0x6f, 0x6e, 0x73, 0x74, 0x61, 0x6e, 0x74,
0x73, 0x00, 0x00, 0x00, 0x47, 0x00, 0x04, 0x00, 0x0b, 0x00, 0x00, 0x00,
0x1e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x47, 0x00, 0x04, 0x00,
0x27, 0x00, 0x00, 0x00, 0x1e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x48, 0x00, 0x05, 0x00, 0x2a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x23, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x47, 0x00, 0x03, 0x00,
0x2a, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x47, 0x00, 0x04, 0x00,
0x2c, 0x00, 0x00, 0x00, 0x22, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x47, 0x00, 0x04, 0x00, 0x2c, 0x00, 0x00, 0x00, 0x21, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x13, 0x00, 0x02, 0x00, 0x02, 0x00, 0x00, 0x00,
0x21, 0x00, 0x03, 0x00, 0x03, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
0x16, 0x00, 0x03, 0x00, 0x06, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00,
0x17, 0x00, 0x04, 0x00, 0x07, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00,
0x03, 0x00, 0x00, 0x00, 0x20, 0x00, 0x04, 0x00, 0x08, 0x00, 0x00, 0x00,
0x07, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x04, 0x00,
0x0a, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00,
0x3b, 0x00, 0x04, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x00, 0x00,
0x01, 0x00, 0x00, 0x00, 0x20, 0x00, 0x04, 0x00, 0x16, 0x00, 0x00, 0x00,
0x07, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x2b, 0x00, 0x04, 0x00,
0x06, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x3f,
0x2b, 0x00, 0x04, 0x00, 0x06, 0x00, 0x00, 0x00, 0x1a, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x2c, 0x00, 0x06, 0x00, 0x07, 0x00, 0x00, 0x00,
0x1b, 0x00, 0x00, 0x00, 0x1a, 0x00, 0x00, 0x00, 0x1a, 0x00, 0x00, 0x00,
0x18, 0x00, 0x00, 0x00, 0x2b, 0x00, 0x04, 0x00, 0x06, 0x00, 0x00, 0x00,
0x23, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x40, 0x17, 0x00, 0x04, 0x00,
0x25, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00,
0x20, 0x00, 0x04, 0x00, 0x26, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
0x25, 0x00, 0x00, 0x00, 0x3b, 0x00, 0x04, 0x00, 0x26, 0x00, 0x00, 0x00,
0x27, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x1e, 0x00, 0x03, 0x00,
0x2a, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x20, 0x00, 0x04, 0x00,
0x2b, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x2a, 0x00, 0x00, 0x00,
0x3b, 0x00, 0x04, 0x00, 0x2b, 0x00, 0x00, 0x00, 0x2c, 0x00, 0x00, 0x00,
0x02, 0x00, 0x00, 0x00, 0x36, 0x00, 0x05, 0x00, 0x02, 0x00, 0x00, 0x00,
0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
0xf8, 0x00, 0x02, 0x00, 0x05, 0x00, 0x00, 0x00, 0x3b, 0x00, 0x04, 0x00,
0x08, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00,
0x3b, 0x00, 0x04, 0x00, 0x08, 0x00, 0x00, 0x00, 0x0e, 0x00, 0x00, 0x00,
0x07, 0x00, 0x00, 0x00, 0x3b, 0x00, 0x04, 0x00, 0x08, 0x00, 0x00, 0x00,
0x11, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x3b, 0x00, 0x04, 0x00,
0x16, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00,
0x3d, 0x00, 0x04, 0x00, 0x07, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00,
0x0b, 0x00, 0x00, 0x00, 0xcf, 0x00, 0x04, 0x00, 0x07, 0x00, 0x00, 0x00,
0x0d, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x3e, 0x00, 0x03, 0x00,
0x09, 0x00, 0x00, 0x00, 0x0d, 0x00, 0x00, 0x00, 0x3d, 0x00, 0x04, 0x00,
0x07, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x00, 0x00,
0xd0, 0x00, 0x04, 0x00, 0x07, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00,
0x0f, 0x00, 0x00, 0x00, 0x3e, 0x00, 0x03, 0x00, 0x0e, 0x00, 0x00, 0x00,
0x10, 0x00, 0x00, 0x00, 0x3d, 0x00, 0x04, 0x00, 0x07, 0x00, 0x00, 0x00,
0x12, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x3d, 0x00, 0x04, 0x00,
0x07, 0x00, 0x00, 0x00, 0x13, 0x00, 0x00, 0x00, 0x0e, 0x00, 0x00, 0x00,
0x0c, 0x00, 0x07, 0x00, 0x07, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00,
0x01, 0x00, 0x00, 0x00, 0x44, 0x00, 0x00, 0x00, 0x12, 0x00, 0x00, 0x00,
0x13, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x06, 0x00, 0x07, 0x00, 0x00, 0x00,
0x15, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x45, 0x00, 0x00, 0x00,
0x14, 0x00, 0x00, 0x00, 0x3e, 0x00, 0x03, 0x00, 0x11, 0x00, 0x00, 0x00,
0x15, 0x00, 0x00, 0x00, 0x3d, 0x00, 0x04, 0x00, 0x07, 0x00, 0x00, 0x00,
0x19, 0x00, 0x00, 0x00, 0x11, 0x00, 0x00, 0x00, 0x94, 0x00, 0x05, 0x00,
0x06, 0x00, 0x00, 0x00, 0x1c, 0x00, 0x00, 0x00, 0x19, 0x00, 0x00, 0x00,
0x1b, 0x00, 0x00, 0x00, 0x83, 0x00, 0x05, 0x00, 0x06, 0x00, 0x00, 0x00,
0x1d, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x1c, 0x00, 0x00, 0x00,
0x3e, 0x00, 0x03, 0x00, 0x17, 0x00, 0x00, 0x00, 0x1d, 0x00, 0x00, 0x00,
0x3d, 0x00, 0x04, 0x00, 0x06, 0x00, 0x00, 0x00, 0x1e, 0x00, 0x00, 0x00,
0x17, 0x00, 0x00, 0x00, 0x3d, 0x00, 0x04, 0x00, 0x06, 0x00, 0x00, 0x00,
0x1f, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x85, 0x00, 0x05, 0x00,
0x06, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x1e, 0x00, 0x00, 0x00,
0x1f, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x06, 0x00, 0x06, 0x00, 0x00, 0x00,
0x21, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x0e, 0x00, 0x00, 0x00,
0x20, 0x00, 0x00, 0x00, 0x83, 0x00, 0x05, 0x00, 0x06, 0x00, 0x00, 0x00,
0x22, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x21, 0x00, 0x00, 0x00,
0x88, 0x00, 0x05, 0x00, 0x06, 0x00, 0x00, 0x00, 0x24, 0x00, 0x00, 0x00,
0x22, 0x00, 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, 0x3e, 0x00, 0x03, 0x00,
0x17, 0x00, 0x00, 0x00, 0x24, 0x00, 0x00, 0x00, 0x3d, 0x00, 0x04, 0x00,
0x06, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00,
0x50, 0x00, 0x07, 0x00, 0x25, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x00,
0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00,
0x28, 0x00, 0x00, 0x00, 0x3e, 0x00, 0x03, 0x00, 0x27, 0x00, 0x00, 0x00,
0x29, 0x00, 0x00, 0x00, 0xfd, 0x00, 0x01, 0x00, 0x38, 0x00, 0x01, 0x00
};
unsigned int ribbon_frag_spv_len = 1176;

Some files were not shown because too many files have changed in this diff Show More