Add enhanced core options
authorretro-wertz <retro-wertz@users.noreply.github.com>
Mon, 29 Jul 2019 13:00:29 +0000 (21:00 +0800)
committerretro-wertz <retro-wertz@users.noreply.github.com>
Mon, 29 Jul 2019 13:00:29 +0000 (21:00 +0800)
Makefile
frontend/libretro.c
frontend/libretro_core_options.h [new file with mode: 0644]
libretro-common/include/libretro.h [moved from frontend/libretro.h with 90% similarity, mode: 0644]
libretro-common/include/retro_inline.h [new file with mode: 0644]

index a278519..7f8356b 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -274,6 +274,7 @@ LDFLAGS += `pkg-config --libs glib-2.0 libosso dbus-1 hildon-fm-2`
 endif
 ifeq "$(PLATFORM)" "libretro"
 OBJS += frontend/libretro.o
+CFLAGS += -Ilibretro-common/include
 CFLAGS += -DFRONTEND_SUPPORTS_RGB565
 CFLAGS += -DHAVE_LIBRETRO
 
index 992da60..f5522a3 100644 (file)
@@ -33,7 +33,9 @@
 #include "plugin_lib.h"
 #include "arm_features.h"
 #include "revision.h"
-#include "libretro.h"
+
+#include <libretro.h>
+#include "libretro_core_options.h"
 
 #ifdef _3DS
 #include "3ds/3ds_utils.h"
@@ -485,65 +487,12 @@ void out_register_libretro(struct out_driver *drv)
 /* libretro */
 void retro_set_environment(retro_environment_t cb)
 {
-   static const struct retro_variable vars[] = {
-      { "pcsx_rearmed_frameskip", "Frameskip; 0|1|2|3" },
-      { "pcsx_rearmed_bios", "Use BIOS; auto|HLE" },
-      { "pcsx_rearmed_region", "Region; auto|NTSC|PAL" },
-      { "pcsx_rearmed_memcard2", "Enable second memory card; disabled|enabled" },
-      { "pcsx_rearmed_pad1type", "Pad 1 Type; standard|analog|dualshock|negcon|none" },
-      { "pcsx_rearmed_pad2type", "Pad 2 Type; standard|analog|dualshock|negcon|none" },
-      { "pcsx_rearmed_pad3type", "Pad 3 Type; none|standard|analog|dualshock|negcon" },
-      { "pcsx_rearmed_pad4type", "Pad 4 Type; none|standard|analog|dualshock|negcon" },
-      { "pcsx_rearmed_pad5type", "Pad 5 Type; none|standard|analog|dualshock|negcon" },
-      { "pcsx_rearmed_pad6type", "Pad 6 Type; none|standard|analog|dualshock|negcon" },
-      { "pcsx_rearmed_pad7type", "Pad 7 Type; none|standard|analog|dualshock|negcon" },
-      { "pcsx_rearmed_pad8type", "Pad 8 Type; none|standard|analog|dualshock|negcon" },
-      { "pcsx_rearmed_multitap1", "Multitap 1; auto|disabled|enabled" },
-      { "pcsx_rearmed_multitap2", "Multitap 2; auto|disabled|enabled" },
-      { "pcsx_rearmed_negcon_deadzone", "NegCon Twist Deadzone (percent); 0|5|10|15|20|25|30" },
-      { "pcsx_rearmed_negcon_response", "NegCon Twist Response; linear|quadratic|cubic" },
-      { "pcsx_rearmed_vibration", "Enable Vibration; enabled|disabled" },
-      { "pcsx_rearmed_dithering", "Enable Dithering; enabled|disabled" },
-#ifndef DRC_DISABLE
-      { "pcsx_rearmed_drc", "Dynamic recompiler; enabled|disabled" },
-#ifdef HAVE_PRE_ARMV7
-      { "pcsx_rearmed_psxclock", "PSX cpu clock (default 50); 50|51|52|53|54|55|5657|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|30|31|32|33|34|35|36|37|38|39|40|41|42|43|44|45|46|47|48|49" },
-#else
-      { "pcsx_rearmed_psxclock", "PSX cpu clock (default 57); 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|30|31|32|33|34|35|36|37|38|39|40|41|42|43|44|45|46|47|48|49|50|51|52|53|54|55|56" },
-#endif
-#endif
-#ifdef __ARM_NEON__
-      { "pcsx_rearmed_neon_interlace_enable", "Enable interlacing mode(s); disabled|enabled" },
-      { "pcsx_rearmed_neon_enhancement_enable", "Enhanced resolution (slow); disabled|enabled" },
-      { "pcsx_rearmed_neon_enhancement_no_main", "Enhanced resolution speed hack; disabled|enabled" },
-#endif
-      { "pcsx_rearmed_duping_enable", "Frame duping; enabled|disabled" },
-      { "pcsx_rearmed_display_internal_fps", "Display Internal FPS; disabled|enabled" },
-      { "pcsx_rearmed_show_bios_bootlogo", "Show Bios Bootlogo(Breaks some games); disabled|enabled" },
-      { "pcsx_rearmed_spu_reverb", "Sound: Reverb; enabled|disabled" },
-      { "pcsx_rearmed_spu_interpolation", "Sound: Interpolation; simple|gaussian|cubic|off" },
-      { "pcsx_rearmed_idiablofix", "Diablo Music Fix; disabled|enabled" },
-      { "pcsx_rearmed_pe2_fix", "Parasite Eve 2/Vandal Hearts 1/2 Fix; disabled|enabled" },
-      { "pcsx_rearmed_inuyasha_fix", "InuYasha Sengoku Battle Fix; disabled|enabled" },
-
-      /* Advance options */
-      { "pcsx_rearmed_noxadecoding", "XA Decoding; enabled|disabled" },
-      { "pcsx_rearmed_nocdaudio", "CD Audio; enabled|disabled" },
-#ifndef DRC_DISABLE
-      { "pcsx_rearmed_nosmccheck", "(Speed Hack) Disable SMC Checks; disabled|enabled" },
-      { "pcsx_rearmed_gteregsunneeded", "(Speed Hack) Assume GTE Regs Unneeded; disabled|enabled" },
-      { "pcsx_rearmed_nogteflags", "(Speed Hack) Disable GTE Flags; disabled|enabled" },
-#endif
-
-      { NULL, NULL }
-   };
-
-    if (cb(RETRO_ENVIRONMENT_GET_LOG_INTERFACE, &logging))
-        log_cb = logging.log;
-
    environ_cb = cb;
 
-   cb(RETRO_ENVIRONMENT_SET_VARIABLES, (void*)vars);
+   if (cb(RETRO_ENVIRONMENT_GET_LOG_INTERFACE, &logging))
+      log_cb = logging.log;
+
+   libretro_set_core_options(environ_cb);
 }
 
 void retro_set_video_refresh(retro_video_refresh_t cb) { video_cb = cb; }
diff --git a/frontend/libretro_core_options.h b/frontend/libretro_core_options.h
new file mode 100644 (file)
index 0000000..66f1b0c
--- /dev/null
@@ -0,0 +1,787 @@
+#ifndef LIBRETRO_CORE_OPTIONS_H__
+#define LIBRETRO_CORE_OPTIONS_H__
+
+#include <stdlib.h>
+#include <string.h>
+
+#include <libretro.h>
+#include <retro_inline.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/*
+ ********************************
+ * Core Option Definitions
+ ********************************
+*/
+
+/* RETRO_LANGUAGE_ENGLISH */
+
+/* Default language:
+ * - All other languages must include the same keys and values
+ * - Will be used as a fallback in the event that frontend language
+ *   is not available
+ * - Will be used as a fallback for any missing entries in
+ *   frontend language definition
+ */
+
+#ifdef HAVE_PRE_ARMV7
+#define PSX_CLOCK_DEFAULT "50"
+#define PSX_CLOCK_LABEL "Overclock or underclock the PSX clock. Default is 50"
+#else
+#define PSX_CLOCK_DEFAULT "57"
+#define PSX_CLOCK_LABEL "Overclock or underclock the PSX clock. Default is 57"
+#endif
+
+struct retro_core_option_definition option_defs_us[] = {
+   {
+      "pcsx_rearmed_frameskip",
+      "Frameskip",
+      "Choose how much frames should be skipped to improve performance at the expense of visual smoothness.",
+      {
+         { "0", NULL },
+         { "1", NULL },
+         { "2", NULL },
+         { "3", NULL },
+         { NULL, NULL},
+      },
+      "0",
+   },
+   {
+      "pcsx_rearmed_bios",
+      "Use BIOS",
+      "Allows you to use real bios file (if available) or emulated bios (HLE). Its recommended to use official bios file for better compatibility.",
+      {
+         { "auto", "auto" },
+         { "HLE", "hle" },
+         { NULL, NULL},
+      },
+      "auto",
+   },
+   {
+      "pcsx_rearmed_region",
+      "Region",
+      "Choose what region the system is from. 60 Hz for NTSC, 50 Hz for PAL.",
+      {
+         { "auto", "auto" },
+         { "NTSC", "ntsc" },
+         { "PAL", "pal" },
+         { NULL, NULL},
+      },
+      "auto",
+   },
+   {
+      "pcsx_rearmed_memcard2",
+      "Enable second memory card (shared)",
+      "Enabled the memory card slot 2. This is shared amongs all games.",
+      {
+         { "disable",  NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "disable",
+   },
+   {
+      "pcsx_rearmed_pad1type",
+      "Pad 1 Type",
+      "Pad type for player 1",
+      {
+         { "standard", NULL },
+         { "analog", NULL },
+         { "dualshock", NULL },
+         { "negcon", NULL },
+         { "none", NULL },
+         { NULL, NULL},
+      },
+      "standard",
+   },
+   {
+      "pcsx_rearmed_pad2type",
+      "Pad 2 Type",
+      "Pad type for player 2",
+      {
+         { "standard", NULL },
+         { "analog", NULL },
+         { "dualshock", NULL },
+         { "negcon", NULL },
+         { "none", NULL },
+         { NULL, NULL},
+      },
+      "standard",
+   },
+   {
+      "pcsx_rearmed_pad3type",
+      "Pad 3 Type",
+      "Pad type for player 3",
+      {
+         { "standard", NULL },
+         { "analog", NULL },
+         { "dualshock", NULL },
+         { "negcon", NULL },
+         { "none", NULL },
+         { NULL, NULL},
+      },
+      "none",
+   },
+   {
+      "pcsx_rearmed_pad4type",
+      "Pad 4 Type",
+      "Pad type for player 4",
+      {
+         { "standard", NULL },
+         { "analog", NULL },
+         { "dualshock", NULL },
+         { "negcon", NULL },
+         { "none", NULL },
+         { NULL, NULL},
+      },
+      "none",
+   },
+   {
+      "pcsx_rearmed_pad5type",
+      "Pad 5 Type",
+      "Pad type for player 5",
+      {
+         { "standard", NULL },
+         { "analog",  NULL },
+         { "dualshock", NULL },
+         { "negcon", NULL },
+         { "none", NULL },
+         { NULL, NULL},
+      },
+      "none",
+   },{
+      "pcsx_rearmed_pad6type",
+      "Pad 6 Type",
+      "Pad type for player 6",
+      {
+         { "standard", NULL },
+         { "analog",  NULL },
+         { "dualshock", NULL },
+         { "negcon", NULL },
+         { "none", NULL },
+         { NULL, NULL},
+      },
+      "none",
+   },{
+      "pcsx_rearmed_pad7type",
+      "Pad 7 Type",
+      "Pad type for player 7",
+      {
+         { "standard", NULL },
+         { "analog",  NULL },
+         { "dualshock", NULL },
+         { "negcon", NULL },
+         { "none", NULL },
+         { NULL, NULL},
+      },
+      "none",
+   },{
+      "pcsx_rearmed_pad8type",
+      "Pad 8 Type",
+      "Pad type for player 8",
+      {
+         { "standard", NULL },
+         { "analog",  NULL },
+         { "dualshock", NULL },
+         { "negcon", NULL },
+         { "none", NULL },
+         { NULL, NULL},
+      },
+      "none",
+   },
+   {
+      "pcsx_rearmed_multitap1",
+      "Multitap 1",
+      "Enables/Disables multitap on port 1, allowing upto 5 players in games that permit it.",
+      {
+         { "auto", NULL },
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "auto",
+   },
+   {
+      "pcsx_rearmed_multitap2",
+      "Multitap 2",
+      "Enables/Disables multitap on port 2, allowing upto 8 players in games that permit it. Multitap 1 has to be enabled for this to work.",
+      {
+         { "auto", NULL },
+         { "disabled",  NULL },
+         { "enabled",   NULL },
+         { NULL, NULL},
+      },
+      "auto",
+   },
+   {
+      "pcsx_rearmed_negcon_deadzone",
+      "NegCon Twist Deadzone (percent)",
+      "Sets the deadzone of the RetroPad left analog stick when simulating the 'twist' action of emulated neGcon Controllers. Used to eliminate drift/unwanted input.",
+      {
+         { "0",  NULL },
+         { "5",  NULL },
+         { "10", NULL },
+         { "15", NULL },
+         { "20", NULL },
+         { "25", NULL },
+         { "30", NULL },
+         { NULL, NULL},
+      },
+      "0",
+   },
+   {
+      "pcsx_rearmed_negcon_response",
+      "NegCon Twist Response",
+      "Specifies the analog response when using a RetroPad left analog stick to simulate the 'twist' action of emulated neGcon Controllers.",
+      {
+         { "linear", NULL },
+         { "quadratic", NULL },
+         { "cubic", NULL },
+         { NULL, NULL},
+      },
+      "linear",
+   },
+   {
+      "pcsx_rearmed_vibration",
+      "Enable Vibration",
+      "Enables Vibration feedback for controllers that supports vibration features.",
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "enabled",
+   },
+   {
+      "pcsx_rearmed_dithering",
+      "Enable Dithering",
+      "If Off, disables the dithering pattern the PSX applies to combat color banding.",
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "enabled",
+   },
+
+#ifndef DRC_DISABLE
+   {
+      "pcsx_rearmed_drc",
+      "Dynamic recompiler",
+      "Enables core to use dynamic recompiler or interpreter (slower) cpu instructions.",
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "enabled",
+   },
+   {
+      "pcsx_rearmed_psxclock",
+      "PSX CPU clock",
+      PSX_CLOCK_LABEL,
+      {
+         { "30", NULL },
+         { "31", NULL },
+         { "32", NULL },
+         { "33", NULL },
+         { "34", NULL },
+         { "35", NULL },
+         { "36", NULL },
+         { "37", NULL },
+         { "38", NULL },
+         { "39", NULL },
+         { "40", NULL },
+         { "41", NULL },
+         { "42", NULL },
+         { "43", NULL },
+         { "44", NULL },
+         { "45", NULL },
+         { "46", NULL },
+         { "47", NULL },
+         { "48", NULL },
+         { "49", NULL },
+         { "50", NULL },
+         { "51", NULL },
+         { "52", NULL },
+         { "53", NULL },
+         { "54", NULL },
+         { "55", NULL },
+         { "56", NULL },
+         { "57", NULL },
+         { "58", NULL },
+         { "59", NULL },
+         { "60", NULL },
+         { "61", NULL },
+         { "62", NULL },
+         { "63", NULL },
+         { "64", NULL },
+         { "65", NULL },
+         { "66", NULL },
+         { "67", NULL },
+         { "68", NULL },
+         { "69", NULL },
+         { "70", NULL },
+         { "71", NULL },
+         { "72", NULL },
+         { "73", NULL },
+         { "74", NULL },
+         { "75", NULL },
+         { "76", NULL },
+         { "77", NULL },
+         { "78", NULL },
+         { "79", NULL },
+         { "80", NULL },
+         { "81", NULL },
+         { "82", NULL },
+         { "83", NULL },
+         { "84", NULL },
+         { "85", NULL },
+         { "86", NULL },
+         { "87", NULL },
+         { "88", NULL },
+         { "89", NULL },
+         { "90", NULL },
+         { "91", NULL },
+         { "92", NULL },
+         { "93", NULL },
+         { "94", NULL },
+         { "95", NULL },
+         { "96", NULL },
+         { "97", NULL },
+         { "98", NULL },
+         { "99", NULL },
+         { "100", NULL },
+         { NULL, NULL},
+      },
+      PSX_CLOCK_DEFAULT,
+   },
+#endif /* DRC_DISABLE */
+
+#ifdef __ARM_NEON__
+   {
+      "pcsx_rearmed_neon_interlace_enable",
+      "Enable interlacing mode(s)",
+      "Enables fake scanlines effect.",
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "disabled",
+   },
+   {
+      "pcsx_rearmed_neon_enhancement_enable",
+      "Enhanced resolution (slow)",
+      "Renders in double resolution at the cost of lower performance",
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "disabled",
+   },
+   {
+      "pcsx_rearmed_neon_enhancement_no_main",
+      "Enhanced resolution speed hack",
+      "Speed hack for Enhanced resolution option (glitches some games).",
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "disabled",
+   },
+#endif /* __ARM_NEON__ */
+
+   {
+      "pcsx_rearmed_duping_enable",
+      "Frame duping",
+      "A speedup, redraws/reuses the last frame if there was no new data.",
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "enabled",
+   },
+   {
+      "pcsx_rearmed_display_internal_fps",
+      "Display Internal FPS",
+      "Shows an on-screen frames per second counter when enabled.",
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "disabled",
+   },
+   {
+      "pcsx_rearmed_show_bios_bootlogo",
+      "Show Bios Bootlogo",
+      "When enabled, shows the playstation logo when starting or resetting. (Breaks some games).",
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "disabled",
+   },
+   {
+      "pcsx_rearmed_spu_reverb",
+      "Sound Reverb",
+      "Enables or disables audio reverb effect.",
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "enabled",
+   },
+   {
+      "pcsx_rearmed_spu_interpolation",
+      "Sound: Interpolation",
+      NULL,
+      {
+         { "simple", NULL },
+         { "gaussian", NULL },
+         { "cubic", NULL },
+         { "off", NULL },
+         { NULL, NULL},
+      },
+      "simple",
+   },
+   {
+      "pcsx_rearmed_idiablofix",
+      "Diablo Music Fix",
+      NULL,
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "disabled",
+   },
+   {
+      "pcsx_rearmed_pe2_fix",
+      "Parasite Eve 2/Vandal Hearts 1/2 Fix",
+      NULL,
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "disabled",
+   },
+   {
+      "pcsx_rearmed_inuyasha_fix",
+      "InuYasha Sengoku Battle Fix",
+      NULL,
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "disabled",
+   },
+
+   /* ADVANCED OPTIONS */
+   {
+      "pcsx_rearmed_noxadecoding",
+      "XA Decoding",
+      NULL,
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "enabled",
+   },
+   {
+      "pcsx_rearmed_nocdaudio",
+      "CD Audio",
+      NULL,
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "enabled",
+   },
+
+#ifndef DRC_DISABLE
+   {
+      "pcsx_rearmed_nosmccheck",
+      "(Speed Hack) Disable SMC Checks",
+      "Will cause crashes when loading, break memcards.",
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "disabled",
+   },
+   {
+      "pcsx_rearmed_gteregsunneeded",
+      "(Speed Hack) Assume GTE Regs Unneeded",
+      "May cause graphical glitches.",
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "disabled",
+   },
+   {
+      "pcsx_rearmed_nogteflags",
+      "(Speed Hack) Disable GTE Flags",
+      "Will cause graphical glitches.",
+      {
+         { "disabled", NULL },
+         { "enabled",  NULL },
+         { NULL, NULL},
+      },
+      "disabled",
+   },
+#endif /* DRC_DISABLE */
+
+   { NULL, NULL, NULL, { NULL, NULL }, NULL },
+};
+
+/* RETRO_LANGUAGE_JAPANESE */
+
+/* RETRO_LANGUAGE_FRENCH */
+
+/* RETRO_LANGUAGE_SPANISH */
+
+/* RETRO_LANGUAGE_GERMAN */
+
+/* RETRO_LANGUAGE_ITALIAN */
+
+/* RETRO_LANGUAGE_DUTCH */
+
+/* RETRO_LANGUAGE_PORTUGUESE_BRAZIL */
+
+/* RETRO_LANGUAGE_PORTUGUESE_PORTUGAL */
+
+/* RETRO_LANGUAGE_RUSSIAN */
+
+/* RETRO_LANGUAGE_KOREAN */
+
+/* RETRO_LANGUAGE_CHINESE_TRADITIONAL */
+
+/* RETRO_LANGUAGE_CHINESE_SIMPLIFIED */
+
+/* RETRO_LANGUAGE_ESPERANTO */
+
+/* RETRO_LANGUAGE_POLISH */
+
+/* RETRO_LANGUAGE_VIETNAMESE */
+
+/* RETRO_LANGUAGE_ARABIC */
+
+/* RETRO_LANGUAGE_GREEK */
+
+/* RETRO_LANGUAGE_TURKISH */
+
+/*
+ ********************************
+ * Language Mapping
+ ********************************
+*/
+
+struct retro_core_option_definition *option_defs_intl[RETRO_LANGUAGE_LAST] = {
+   option_defs_us, /* RETRO_LANGUAGE_ENGLISH */
+   NULL,           /* RETRO_LANGUAGE_JAPANESE */
+   NULL,           /* RETRO_LANGUAGE_FRENCH */
+   NULL,           /* RETRO_LANGUAGE_SPANISH */
+   NULL,           /* RETRO_LANGUAGE_GERMAN */
+   NULL,           /* RETRO_LANGUAGE_ITALIAN */
+   NULL,           /* RETRO_LANGUAGE_DUTCH */
+   NULL,           /* RETRO_LANGUAGE_PORTUGUESE_BRAZIL */
+   NULL,           /* RETRO_LANGUAGE_PORTUGUESE_PORTUGAL */
+   NULL,           /* RETRO_LANGUAGE_RUSSIAN */
+   NULL,           /* RETRO_LANGUAGE_KOREAN */
+   NULL,           /* RETRO_LANGUAGE_CHINESE_TRADITIONAL */
+   NULL,           /* RETRO_LANGUAGE_CHINESE_SIMPLIFIED */
+   NULL,           /* RETRO_LANGUAGE_ESPERANTO */
+   NULL,           /* RETRO_LANGUAGE_POLISH */
+   NULL,           /* RETRO_LANGUAGE_VIETNAMESE */
+   NULL,           /* RETRO_LANGUAGE_ARABIC */
+   NULL,           /* RETRO_LANGUAGE_GREEK */
+   NULL,           /* RETRO_LANGUAGE_TURKISH */
+};
+
+/*
+ ********************************
+ * Functions
+ ********************************
+*/
+
+/* Handles configuration/setting of core options.
+ * Should only be called inside retro_set_environment().
+ * > We place the function body in the header to avoid the
+ *   necessity of adding more .c files (i.e. want this to
+ *   be as painless as possible for core devs)
+ */
+
+static INLINE void libretro_set_core_options(retro_environment_t environ_cb)
+{
+   unsigned version = 0;
+
+   if (!environ_cb)
+      return;
+
+   if (environ_cb(RETRO_ENVIRONMENT_GET_CORE_OPTIONS_VERSION, &version) && (version == 1))
+   {
+      struct retro_core_options_intl core_options_intl;
+      unsigned language = 0;
+
+      core_options_intl.us    = option_defs_us;
+      core_options_intl.local = NULL;
+
+      if (environ_cb(RETRO_ENVIRONMENT_GET_LANGUAGE, &language) &&
+          (language < RETRO_LANGUAGE_LAST) && (language != RETRO_LANGUAGE_ENGLISH))
+         core_options_intl.local = option_defs_intl[language];
+
+      environ_cb(RETRO_ENVIRONMENT_SET_CORE_OPTIONS_INTL, &core_options_intl);
+   }
+   else
+   {
+      size_t i;
+      size_t option_index              = 0;
+      size_t num_options               = 0;
+      struct retro_variable *variables = NULL;
+      char **values_buf                = NULL;
+
+      /* Determine number of options
+       * > Note: We are going to skip a number of irrelevant
+       *   core options when building the retro_variable array,
+       *   but we'll allocate space for all of them. The difference
+       *   in resource usage is negligible, and this allows us to
+       *   keep the code 'cleaner' */
+      while (true)
+      {
+         if (option_defs_us[num_options].key)
+            num_options++;
+         else
+            break;
+      }
+
+      /* Allocate arrays */
+      variables  = (struct retro_variable *)calloc(num_options + 1, sizeof(struct retro_variable));
+      values_buf = (char **)calloc(num_options, sizeof(char *));
+
+      if (!variables || !values_buf)
+         goto error;
+
+      /* Copy parameters from option_defs_us array */
+      for (i = 0; i < num_options; i++)
+      {
+         const char *key                        = option_defs_us[i].key;
+         const char *desc                       = option_defs_us[i].desc;
+         const char *default_value              = option_defs_us[i].default_value;
+         struct retro_core_option_value *values = option_defs_us[i].values;
+         size_t buf_len                         = 3;
+         size_t default_index                   = 0;
+
+         values_buf[i] = NULL;
+
+         /* Skip options that are irrelevant when using the
+          * old style core options interface */
+         if ((strcmp(key, "fceumm_advance_sound_options") == 0))
+            continue;
+
+         if (desc)
+         {
+            size_t num_values = 0;
+
+            /* Determine number of values */
+            while (true)
+            {
+               if (values[num_values].value)
+               {
+                  /* Check if this is the default value */
+                  if (default_value)
+                     if (strcmp(values[num_values].value, default_value) == 0)
+                        default_index = num_values;
+
+                  buf_len += strlen(values[num_values].value);
+                  num_values++;
+               }
+               else
+                  break;
+            }
+
+            /* Build values string */
+            if (num_values > 1)
+            {
+               size_t j;
+
+               buf_len += num_values - 1;
+               buf_len += strlen(desc);
+
+               values_buf[i] = (char *)calloc(buf_len, sizeof(char));
+               if (!values_buf[i])
+                  goto error;
+
+               strcpy(values_buf[i], desc);
+               strcat(values_buf[i], "; ");
+
+               /* Default value goes first */
+               strcat(values_buf[i], values[default_index].value);
+
+               /* Add remaining values */
+               for (j = 0; j < num_values; j++)
+               {
+                  if (j != default_index)
+                  {
+                     strcat(values_buf[i], "|");
+                     strcat(values_buf[i], values[j].value);
+                  }
+               }
+            }
+         }
+
+         variables[option_index].key   = key;
+         variables[option_index].value = values_buf[i];
+         option_index++;
+      }
+
+      /* Set variables */
+      environ_cb(RETRO_ENVIRONMENT_SET_VARIABLES, variables);
+
+error:
+
+      /* Clean up */
+      if (values_buf)
+      {
+         for (i = 0; i < num_options; i++)
+         {
+            if (values_buf[i])
+            {
+               free(values_buf[i]);
+               values_buf[i] = NULL;
+            }
+         }
+
+         free(values_buf);
+         values_buf = NULL;
+      }
+
+      if (variables)
+      {
+         free(variables);
+         variables = NULL;
+      }
+   }
+}
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
old mode 100755 (executable)
new mode 100644 (file)
similarity index 90%
rename from frontend/libretro.h
rename to libretro-common/include/libretro.h
index 8daec83..1fd2f5b
@@ -614,7 +614,7 @@ enum retro_mod
                                             * Afterward it may be called again for the core to communicate
                                             * updated options to the frontend, but the number of core
                                             * options must not change from the number in the initial call.
-                                           *
+                                            *
                                             * 'data' points to an array of retro_variable structs
                                             * terminated by a { NULL, NULL } element.
                                             * retro_variable::key should be namespaced to not collide
@@ -1106,6 +1106,148 @@ enum retro_mod
                                             * It will return a bitmask of all the digital buttons.
                                             */
 
+#define RETRO_ENVIRONMENT_GET_CORE_OPTIONS_VERSION 52
+                                           /* unsigned * --
+                                            * Unsigned value is the API version number of the core options
+                                            * interface supported by the frontend. If callback return false,
+                                            * API version is assumed to be 0.
+                                            *
+                                            * In legacy code, core options are set by passing an array of
+                                            * retro_variable structs to RETRO_ENVIRONMENT_SET_VARIABLES.
+                                            * This may be still be done regardless of the core options
+                                            * interface version.
+                                            *
+                                            * If version is 1 however, core options may instead be set by
+                                            * passing an array of retro_core_option_definition structs to
+                                            * RETRO_ENVIRONMENT_SET_CORE_OPTIONS, or a 2D array of
+                                            * retro_core_option_definition structs to RETRO_ENVIRONMENT_SET_CORE_OPTIONS_INTL.
+                                            * This allows the core to additionally set option sublabel information
+                                            * and/or provide localisation support.
+                                            */
+
+#define RETRO_ENVIRONMENT_SET_CORE_OPTIONS 53
+                                           /* const struct retro_core_option_definition ** --
+                                            * Allows an implementation to signal the environment
+                                            * which variables it might want to check for later using
+                                            * GET_VARIABLE.
+                                            * This allows the frontend to present these variables to
+                                            * a user dynamically.
+                                            * This should only be called if RETRO_ENVIRONMENT_GET_ENHANCED_CORE_OPTIONS
+                                            * returns an API version of 1.
+                                            * This should be called instead of RETRO_ENVIRONMENT_SET_VARIABLES.
+                                            * This should be called the first time as early as
+                                            * possible (ideally in retro_set_environment).
+                                            * Afterwards it may be called again for the core to communicate
+                                            * updated options to the frontend, but the number of core
+                                            * options must not change from the number in the initial call.
+                                            *
+                                            * 'data' points to an array of retro_core_option_definition structs
+                                            * terminated by a { NULL, NULL, NULL, {{0}}, NULL } element.
+                                            * retro_core_option_definition::key should be namespaced to not collide
+                                            * with other implementations' keys. e.g. A core called
+                                            * 'foo' should use keys named as 'foo_option'.
+                                            * retro_core_option_definition::desc should contain a human readable
+                                            * description of the key.
+                                            * retro_core_option_definition::info should contain any additional human
+                                            * readable information text that a typical user may need to
+                                            * understand the functionality of the option.
+                                            * retro_core_option_definition::values is an array of retro_core_option_value
+                                            * structs terminated by a { NULL, NULL } element.
+                                            * > retro_core_option_definition::values[index].value is an expected option
+                                            *   value.
+                                            * > retro_core_option_definition::values[index].label is a human readable
+                                            *   label used when displaying the value on screen. If NULL,
+                                            *   the value itself is used.
+                                            * retro_core_option_definition::default_value is the default core option
+                                            * setting. It must match one of the expected option values in the
+                                            * retro_core_option_definition::values array. If it does not, or the
+                                            * default value is NULL, the first entry in the
+                                            * retro_core_option_definition::values array is treated as the default.
+                                            *
+                                            * The number of possible options should be very limited,
+                                            * and must be less than RETRO_NUM_CORE_OPTION_VALUES_MAX.
+                                            * i.e. it should be feasible to cycle through options
+                                            * without a keyboard.
+                                            *
+                                            * First entry should be treated as a default.
+                                            *
+                                            * Example entry:
+                                            * {
+                                            *     "foo_option",
+                                            *     "Speed hack coprocessor X",
+                                            *     "Provides increased performance at the expense of reduced accuracy",
+                                            *    {
+                                            *         { "false",    NULL },
+                                            *         { "true",     NULL },
+                                            *         { "unstable", "Turbo (Unstable)" },
+                                            *         { NULL, NULL },
+                                            *     },
+                                            *     "false"
+                                            * }
+                                            *
+                                            * Only strings are operated on. The possible values will
+                                            * generally be displayed and stored as-is by the frontend.
+                                            */
+
+#define RETRO_ENVIRONMENT_SET_CORE_OPTIONS_INTL 54
+                                           /* const struct retro_core_options_intl * --
+                                            * Allows an implementation to signal the environment
+                                            * which variables it might want to check for later using
+                                            * GET_VARIABLE.
+                                            * This allows the frontend to present these variables to
+                                            * a user dynamically.
+                                            * This should only be called if RETRO_ENVIRONMENT_GET_ENHANCED_CORE_OPTIONS
+                                            * returns an API version of 1.
+                                            * This should be called instead of RETRO_ENVIRONMENT_SET_VARIABLES.
+                                            * This should be called the first time as early as
+                                            * possible (ideally in retro_set_environment).
+                                            * Afterwards it may be called again for the core to communicate
+                                            * updated options to the frontend, but the number of core
+                                            * options must not change from the number in the initial call.
+                                            *
+                                            * This is fundamentally the same as RETRO_ENVIRONMENT_SET_CORE_OPTIONS,
+                                            * with the addition of localisation support. The description of the
+                                            * RETRO_ENVIRONMENT_SET_CORE_OPTIONS callback should be consulted
+                                            * for further details.
+                                            *
+                                            * 'data' points to a retro_core_options_intl struct.
+                                            *
+                                            * retro_core_options_intl::us is a pointer to an array of
+                                            * retro_core_option_definition structs defining the US English
+                                            * core options implementation. It must point to a valid array.
+                                            *
+                                            * retro_core_options_intl::local is a pointer to an array of
+                                            * retro_core_option_definition structs defining core options for
+                                            * the current frontend language. It may be NULL (in which case
+                                            * retro_core_options_intl::us is used by the frontend). Any items
+                                            * missing from this array will be read from retro_core_options_intl::us
+                                            * instead.
+                                            *
+                                            * NOTE: Default core option values are always taken from the
+                                            * retro_core_options_intl::us array. Any default values in
+                                            * retro_core_options_intl::local array will be ignored.
+                                            */
+
+#define RETRO_ENVIRONMENT_SET_CORE_OPTIONS_DISPLAY 55
+                                           /* struct retro_core_option_display * --
+                                            *
+                                            * Allows an implementation to signal the environment to show
+                                            * or hide a variable when displaying core options. This is
+                                            * considered a *suggestion*. The frontend is free to ignore
+                                            * this callback, and its implementation not considered mandatory.
+                                            *
+                                            * 'data' points to a retro_core_option_display struct
+                                            *
+                                            * retro_core_option_display::key is a variable identifier
+                                            * which has already been set by SET_VARIABLES/SET_CORE_OPTIONS.
+                                            *
+                                            * retro_core_option_display::visible is a boolean, specifying
+                                            * whether variable should be displayed
+                                            *
+                                            * Note that all core option variables will be set visible by
+                                            * default when calling SET_VARIABLES/SET_CORE_OPTIONS.
+                                            */
+
 /* VFS functionality */
 
 /* File paths:
@@ -2351,6 +2493,64 @@ struct retro_variable
    const char *value;
 };
 
+struct retro_core_option_display
+{
+   /* Variable to configure in RETRO_ENVIRONMENT_SET_CORE_OPTIONS_DISPLAY */
+   const char *key;
+
+   /* Specifies whether variable should be displayed
+    * when presenting core options to the user */
+   bool visible;
+};
+
+/* Maximum number of values permitted for a core option
+ * NOTE: This may be increased on a core-by-core basis
+ * if required (doing so has no effect on the frontend) */
+#define RETRO_NUM_CORE_OPTION_VALUES_MAX 128
+
+struct retro_core_option_value
+{
+   /* Expected option value */
+   const char *value;
+
+   /* Human-readable value label. If NULL, value itself
+    * will be displayed by the frontend */
+   const char *label;
+};
+
+struct retro_core_option_definition
+{
+   /* Variable to query in RETRO_ENVIRONMENT_GET_VARIABLE. */
+   const char *key;
+
+   /* Human-readable core option description (used as menu label) */
+   const char *desc;
+
+   /* Human-readable core option information (used as menu sublabel) */
+   const char *info;
+
+   /* Array of retro_core_option_value structs, terminated by NULL */
+   struct retro_core_option_value values[RETRO_NUM_CORE_OPTION_VALUES_MAX];
+
+   /* Default core option value. Must match one of the values
+    * in the retro_core_option_value array, otherwise will be
+    * ignored */
+   const char *default_value;
+};
+
+struct retro_core_options_intl
+{
+   /* Pointer to an array of retro_core_option_definition structs
+    * - US English implementation
+    * - Must point to a valid array */
+   struct retro_core_option_definition *us;
+
+   /* Pointer to an array of retro_core_option_definition structs
+    * - Implementation for current frontend language
+    * - May be NULL */
+   struct retro_core_option_definition *local;
+};
+
 struct retro_game_info
 {
    const char *path;       /* Path to game, UTF-8 encoded.
diff --git a/libretro-common/include/retro_inline.h b/libretro-common/include/retro_inline.h
new file mode 100644 (file)
index 0000000..e4a21f6
--- /dev/null
@@ -0,0 +1,39 @@
+/* Copyright  (C) 2010-2018 The RetroArch team
+ *
+ * ---------------------------------------------------------------------------------------
+ * The following license statement only applies to this file (retro_inline.h).
+ * ---------------------------------------------------------------------------------------
+ *
+ * Permission is hereby granted, free of charge,
+ * to any person obtaining a copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation the rights to
+ * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software,
+ * and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
+ * INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+ * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
+ * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef __LIBRETRO_SDK_INLINE_H
+#define __LIBRETRO_SDK_INLINE_H
+
+#ifndef INLINE
+
+#if defined(_WIN32) || defined(__INTEL_COMPILER)
+#define INLINE __inline
+#elif defined(__STDC_VERSION__) && __STDC_VERSION__>=199901L
+#define INLINE inline
+#elif defined(__GNUC__)
+#define INLINE __inline__
+#else
+#define INLINE
+#endif
+
+#endif
+#endif