From 7b3bbda18b94c68816730a436cf608a7ecade0e5 Mon Sep 17 00:00:00 2001 From: Brandon Wright Date: Fri, 25 May 2018 16:56:02 -0500 Subject: [PATCH] Update libretro port. --- libretro/Makefile | 628 ++++++++---- libretro/Makefile.common | 14 +- libretro/control | 10 + libretro/jni/Android.mk | 34 +- .../libretro-common/include/compat/msvc.h | 104 ++ .../include/compat/msvc/stdint.h | 254 +++++ libretro/libretro-win32.vcproj | 794 ++++++++++++++++ libretro/libretro-win32.vcxproj | 303 ------ libretro/libretro-win32.vcxproj.filters | 348 ------- libretro/libretro.cpp | 428 ++++++--- libretro/libretro.def | 39 + libretro/libretro.h | 891 +++++++++++------- libretro/msvc/msvc-2010.bat | 124 +++ libretro/msvc/msvc-2010.sln | 20 + libretro/msvc/msvc-2010/libretro.def | 27 + libretro/msvc/msvc-2010/msvc-2010.vcxproj | 140 +++ .../msvc/msvc-2010/msvc-2010.vcxproj.filters | 193 ++++ port.h | 18 +- 18 files changed, 3062 insertions(+), 1307 deletions(-) create mode 100644 libretro/control create mode 100644 libretro/libretro-common/include/compat/msvc.h create mode 100644 libretro/libretro-common/include/compat/msvc/stdint.h create mode 100644 libretro/libretro-win32.vcproj delete mode 100644 libretro/libretro-win32.vcxproj delete mode 100644 libretro/libretro-win32.vcxproj.filters create mode 100644 libretro/libretro.def mode change 100755 => 100644 libretro/libretro.h create mode 100644 libretro/msvc/msvc-2010.bat create mode 100644 libretro/msvc/msvc-2010.sln create mode 100644 libretro/msvc/msvc-2010/libretro.def create mode 100644 libretro/msvc/msvc-2010/msvc-2010.vcxproj create mode 100644 libretro/msvc/msvc-2010/msvc-2010.vcxproj.filters diff --git a/libretro/Makefile b/libretro/Makefile index ea9c93ca..e6ea40eb 100644 --- a/libretro/Makefile +++ b/libretro/Makefile @@ -1,213 +1,460 @@ DEBUG = 0 HAVE_EXCEPTIONS = 0 +LAGFIX=1 + +SPACE := +SPACE := $(SPACE) $(SPACE) +BACKSLASH := +BACKSLASH := \$(BACKSLASH) +filter_out1 = $(filter-out $(firstword $1),$1) +filter_out2 = $(call filter_out1,$(call filter_out1,$1)) ifeq ($(platform),) - platform = unix - ifeq ($(shell uname -a),) - platform = win - else ifneq ($(findstring Darwin,$(shell uname -a)),) - platform = osx - arch = intel - ifeq ($(shell uname -p),powerpc) - arch = ppc - endif - else ifneq ($(findstring MINGW,$(shell uname -a)),) - platform = win - else ifneq ($(findstring win,$(shell uname -a)),) - platform = win - endif + platform = unix + ifeq ($(shell uname -s),) + platform = win + else ifneq ($(findstring MINGW,$(shell uname -s)),) + platform = win + else ifneq ($(findstring Darwin,$(shell uname -s)),) + platform = osx + arch = intel + ifeq ($(shell uname -p),powerpc) + arch = ppc + endif + else ifneq ($(findstring win,$(shell uname -s)),) + platform = win + endif +else ifneq (,$(findstring armv,$(platform))) + override platform += unix +else ifneq (,$(findstring rpi,$(platform))) + override platform += unix endif -CXX ?= g++ -CC ?= gcc TARGET_NAME = snes9x -LIBM = -lm + +LIBS = + +ifeq (,$(findstring msvc,$(platform))) +LIBS += -lm +endif + +GIT_VERSION := " $(shell git rev-parse --short HEAD || echo unknown)" +ifneq ($(GIT_VERSION)," unknown") + CXXFLAGS += -DGIT_VERSION=\"$(GIT_VERSION)\" +endif + +ifeq ($(LAGFIX),1) + CFLAGS += -DLAGFIX + CXXFLAGS += -DLAGFIX +endif # Unix -ifeq ($(platform), unix) - TARGET := $(TARGET_NAME)_libretro.so - fpic := -fPIC - SHARED := -shared -Wl,--version-script=link.T - ifneq ($(findstring Haiku,$(shell uname -a)),) - LIBM := - endif +ifneq (,$(findstring unix,$(platform))) + TARGET := $(TARGET_NAME)_libretro.so + fpic := -fPIC + ifneq ($(findstring SunOS,$(shell uname -a)),) + CC = gcc + SHARED := -shared -z defs + else + SHARED := -shared -Wl,--version-script=link.T + endif + ifneq ($(findstring Haiku,$(shell uname -a)),) + LIBS := + endif + + # ARM + ifneq (,$(findstring armv,$(platform))) + CXXFLAGS += -DARM + # Raspberry Pi + else ifneq (,$(findstring rpi,$(platform))) + CXXFLAGS += -DARM + endif # OS X else ifeq ($(platform), osx) - TARGET := $(TARGET_NAME)_libretro.dylib - fpic := -fPIC - SHARED := -dynamiclib - - arch = intel - ifeq ($(shell uname -p),powerpc) - arch = ppc - endif - - ifeq ($(arch),ppc) - CXXFLAGS += -DBLARGG_BIG_ENDIAN=1 -D__ppc__ - endif - OSXVER = `sw_vers -productVersion | cut -d. -f 2` - OSX_LT_MAVERICKS = `(( $(OSXVER) <= 9)) && echo "YES"` - fpic += -mmacosx-version-min=10.1 + TARGET := $(TARGET_NAME)_libretro.dylib + fpic := -fPIC + SHARED := -dynamiclib + arch = intel + ifeq ($(shell uname -p),powerpc) + arch = ppc + endif + ifeq ($(arch),ppc) + CXXFLAGS += -DBLARGG_BIG_ENDIAN=1 -D__ppc__ + endif + OSXVER = `sw_vers -productVersion | cut -d. -f 2` + OSX_LT_MAVERICKS = `(( $(OSXVER) <= 9)) && echo "YES"` + fpic += -mmacosx-version-min=10.1 # iOS else ifneq (,$(findstring ios,$(platform))) - TARGET := $(TARGET_NAME)_libretro_ios.dylib - fpic := -fPIC - SHARED := -dynamiclib + TARGET := $(TARGET_NAME)_libretro_ios.dylib + fpic := -fPIC + SHARED := -dynamiclib + ifeq ($(IOSSDK),) + IOSSDK := $(shell xcodebuild -version -sdk iphoneos Path) + endif + ifeq ($(platform),ios-arm64) + CC = clang -arch arm64 -isysroot $(IOSSDK) + CXX = clang++ -arch arm64 -isysroot $(IOSSDK) + else + CC = clang -arch armv7 -isysroot $(IOSSDK) + CXX = clang++ -arch armv7 -isysroot $(IOSSDK) + endif + CXXFLAGS += -DIOS + CXXFLAGS += -DARM + ifeq ($(platform),$(filter $(platform),ios9 ios-arm64)) + CC += -miphoneos-version-min=8.0 + CXX += -miphoneos-version-min=8.0 + CFLAGS += -miphoneos-version-min=8.0 + CXXFLAGS += -miphoneos-version-min=8.0 + else + CC += -miphoneos-version-min=5.0 + CXX += -miphoneos-version-min=5.0 + CFLAGS += -miphoneos-version-min=5.0 + CXXFLAGS += -miphoneos-version-min=5.0 + endif - ifeq ($(IOSSDK),) - IOSSDK := $(shell xcodebuild -version -sdk iphoneos Path) - endif - - CC = clang -arch armv7 -isysroot $(IOSSDK) - CXX = clang++ -arch armv7 -isysroot $(IOSSDK) - CXXFLAGS += -DIOS - CXXFLAGS += -DARM -ifeq ($(platform),ios9) - CC += -miphoneos-version-min=8.0 - CXX += -miphoneos-version-min=8.0 - CFLAGS += -miphoneos-version-min=8.0 - CXXFLAGS += -miphoneos-version-min=8.0 -else - CC += -miphoneos-version-min=5.0 - CXX += -miphoneos-version-min=5.0 - CFLAGS += -miphoneos-version-min=5.0 - CXXFLAGS += -miphoneos-version-min=5.0 -endif +# Theos else ifeq ($(platform), theos_ios) -DEPLOYMENT_IOSVERSION = 5.0 -TARGET = iphone:latest:$(DEPLOYMENT_IOSVERSION) -ARCHS = armv7 armv7s -TARGET_IPHONEOS_DEPLOYMENT_VERSION=$(DEPLOYMENT_IOSVERSION) -THEOS_BUILD_DIR := objs -include $(THEOS)/makefiles/common.mk - -LIBRARY_NAME = $(TARGET_NAME)_libretro_ios + DEPLOYMENT_IOSVERSION = 5.0 + TARGET = iphone:latest:$(DEPLOYMENT_IOSVERSION) + ARCHS = armv7 armv7s + TARGET_IPHONEOS_DEPLOYMENT_VERSION=$(DEPLOYMENT_IOSVERSION) + THEOS_BUILD_DIR := objs + include $(THEOS)/makefiles/common.mk + LIBRARY_NAME = $(TARGET_NAME)_libretro_ios # QNX else ifeq ($(platform), qnx) - TARGET := $(TARGET_NAME)_libretro_$(platform).so - fpic := -fPIC + TARGET := $(TARGET_NAME)_libretro_$(platform).so + fpic := -fPIC SHARED := -shared -Wl,--version-script=link.T - CC = qcc -Vgcc_notarmv7le - CXX = QCC -Vgcc_notarmv7le - AR = QCC -Vgcc_ntoarmv7le - CXXFLAGS += -D__BLACKBERRY_QNX__ - CXXFLAGS += -DARM - HAVE_EXCEPTIONS = 1 + CC = qcc -Vgcc_notarmv7le + CXX = QCC -Vgcc_notarmv7le + AR = QCC -Vgcc_ntoarmv7le + CXXFLAGS += -D__BLACKBERRY_QNX__ + CXXFLAGS += -DARM + HAVE_EXCEPTIONS = 1 # Vita else ifeq ($(platform), vita) - TARGET := $(TARGET_NAME)_libretro_$(platform).so - fpic := -fPIC - CC = arm-vita-eabi-gcc$(EXE_EXT) - CXX = arm-vita-eabi-g++$(EXE_EXT) - AR = arm-vita-eabi-ar$(EXE_EXT) - CXXFLAGS += -DVITA - HAVE_EXCEPTIONS = 1 + TARGET := $(TARGET_NAME)_libretro_$(platform).so + fpic := -fPIC + CC = arm-vita-eabi-gcc$(EXE_EXT) + CXX = arm-vita-eabi-g++$(EXE_EXT) + AR = arm-vita-eabi-ar$(EXE_EXT) + CXXFLAGS += -DVITA + HAVE_EXCEPTIONS = 1 # PS3 -else ifeq ($(platform), ps3) - TARGET := $(TARGET_NAME)_libretro_$(platform).a - CC = $(CELL_SDK)/host-win32/ppu/bin/ppu-lv2-gcc.exe - CXX = $(CELL_SDK)/host-win32/ppu/bin/ppu-lv2-g++.exe - AR = $(CELL_SDK)/host-win32/ppu/bin/ppu-lv2-ar.exe - CXXFLAGS += -DBLARGG_BIG_ENDIAN=1 -D__ppc__ - STATIC_LINKING = 1 +else ifneq (,$(filter $(platform), ps3 sncps3 psl1ght)) + TARGET := $(TARGET_NAME)_libretro_$(platform).a + CXXFLAGS += -DBLARGG_BIG_ENDIAN=1 -D__ppc__ + STATIC_LINKING = 1 -# sncps3 -else ifeq ($(platform), sncps3) - TARGET := $(TARGET_NAME)_libretro_ps3.a - CC = $(CELL_SDK)/host-win32/sn/bin/ps3ppusnc.exe - CXX = $(CELL_SDK)/host-win32/sn/bin/ps3ppusnc.exe - AR = $(CELL_SDK)/host-win32/sn/bin/ps3snarl.exe - CXXFLAGS += -DBLARGG_BIG_ENDIAN=1 -D__ppc__ - STATIC_LINKING = 1 + # sncps3 + ifneq (,$(findstring sncps3,$(platform))) + TARGET := $(TARGET_NAME)_libretro_ps3.a + CC = $(CELL_SDK)/host-win32/sn/bin/ps3ppusnc.exe + CXX = $(CC) + AR = $(CELL_SDK)/host-win32/sn/bin/ps3snarl.exe -# Lightweight PS3 Homebrew SDK -else ifeq ($(platform), psl1ght) - TARGET := $(TARGET_NAME)_libretro_$(platform).a - CC = $(PS3DEV)/ppu/bin/ppu-gcc$(EXE_EXT) - CXX = $(PS3DEV)/ppu/bin/ppu-g++$(EXE_EXT) - AR = $(PS3DEV)/ppu/bin/ppu-ar$(EXE_EXT) - CXXFLAGS += -DBLARGG_BIG_ENDIAN=1 -D__ppc__ - STATIC_LINKING = 1 + # PS3 + else ifneq (,$(findstring ps3,$(platform))) + CC = $(CELL_SDK)/host-win32/ppu/bin/ppu-lv2-gcc.exe + CXX = $(CELL_SDK)/host-win32/ppu/bin/ppu-lv2-g++.exe + AR = $(CELL_SDK)/host-win32/ppu/bin/ppu-lv2-ar.exe + + # Lightweight PS3 Homebrew SDK + else ifneq (,$(findstring psl1ght,$(platform))) + CC = $(PS3DEV)/ppu/bin/ppu-gcc$(EXE_EXT) + CXX = $(PS3DEV)/ppu/bin/ppu-g++$(EXE_EXT) + AR = $(PS3DEV)/ppu/bin/ppu-ar$(EXE_EXT) + endif # Xbox 360 else ifeq ($(platform), xenon) - TARGET := $(TARGET_NAME)_libretro_xenon360.a - CC = xenon-gcc$(EXE_EXT) - CXX = xenon-g++$(EXE_EXT) - AR = xenon-ar$(EXE_EXT) - CXXFLAGS += -D__LIBXENON__ -m32 -D__ppc__ - STATIC_LINKING = 1 + TARGET := $(TARGET_NAME)_libretro_xenon360.a + CC = xenon-gcc$(EXE_EXT) + CXX = xenon-g++$(EXE_EXT) + AR = xenon-ar$(EXE_EXT) + CXXFLAGS += -D__LIBXENON__ -m32 -D__ppc__ + STATIC_LINKING = 1 -# Nintendo Wii -else ifeq ($(platform), wii) - TARGET := $(TARGET_NAME)_libretro_$(platform).a - CC = $(DEVKITPPC)/bin/powerpc-eabi-gcc$(EXE_EXT) - CXX = $(DEVKITPPC)/bin/powerpc-eabi-g++$(EXE_EXT) - AR = $(DEVKITPPC)/bin/powerpc-eabi-ar$(EXE_EXT) - CXXFLAGS += -DGEKKO -mrvl -mcpu=750 -meabi -mhard-float -DBLARGG_BIG_ENDIAN=1 -D__ppc__ - STATIC_LINKING = 1 +# Nintendo Game Cube / Wii / WiiU +else ifneq (,$(filter $(platform), ngc wii wiiu)) + TARGET := $(TARGET_NAME)_libretro_$(platform).a + CC = $(DEVKITPPC)/bin/powerpc-eabi-gcc$(EXE_EXT) + CXX = $(DEVKITPPC)/bin/powerpc-eabi-g++$(EXE_EXT) + AR = $(DEVKITPPC)/bin/powerpc-eabi-ar$(EXE_EXT) + CXXFLAGS += -mcpu=750 -meabi -mhard-float -DBLARGG_BIG_ENDIAN=1 -D__ppc__ + CXXFLAGS += -U__INT32_TYPE__ -U __UINT32_TYPE__ -D__INT32_TYPE__=int + STATIC_LINKING = 1 + # Nintendo WiiU + ifneq (,$(findstring wiiu,$(platform))) + CXXFLAGS += -mwup + + # Nintendo Wii + else ifneq (,$(findstring wii,$(platform))) + CXXFLAGS += -DGEKKO -mrvl + + # Nintendo Game Cube + else ifneq (,$(findstring ngc,$(platform))) + CXXFLAGS += -DGEKKO -mrvl + endif + +# Emscripten else ifeq ($(platform), emscripten) - TARGET := $(TARGET_NAME)_libretro_$(platform).bc - STATIC_LINKING = 1 + TARGET := $(TARGET_NAME)_libretro_$(platform).bc + STATIC_LINKING = 1 -# ARM -else ifneq (,$(findstring armv,$(platform))) - TARGET := $(TARGET_NAME)_libretro.so - SHARED := -shared -Wl,--no-undefined - fpic := -fPIC - CC ?= gcc - CXX ?= g++ - ifneq (,$(findstring cortexa8,$(platform))) - CXXFLAGS += -marm -mcpu=cortex-a8 - else ifneq (,$(findstring cortexa9,$(platform))) - CXXFLAGS += -marm -mcpu=cortex-a9 - else ifneq (,$(findstring cortexa53,$(platform))) - CXXFLAGS += -marm -mcpu=cortex-a53 - endif - CXXFLAGS += -marm - ifneq (,$(findstring neon,$(platform))) - CXXFLAGS += -mfpu=neon - HAVE_NEON = 1 - endif - ifneq (,$(findstring softfloat,$(platform))) - CXXFLAGS += -mfloat-abi=softfp - else ifneq (,$(findstring hardfloat,$(platform))) - CXXFLAGS += -mfloat-abi=hard - endif - CXXFLAGS += -DARM +# Windows MSVC 2003 Xbox 1 +else ifeq ($(platform), xbox1_msvc2003) +TARGET := $(TARGET_NAME)_libretro_xdk1.lib +MSVCBINDIRPREFIX = $(XDK)/xbox/bin/vc71 +CC = "$(MSVCBINDIRPREFIX)/CL.exe" +CXX = "$(MSVCBINDIRPREFIX)/CL.exe" +LD = "$(MSVCBINDIRPREFIX)/lib.exe" -# Android -else ifneq (,$(findstring android,$(platform))) - TARGET := $(TARGET_NAME)_libretro_android.so - SHARED := -shared -Wl,--no-undefined -march=armv7-a -Wl,--fix-cortex-a8 - fpic := -fPIC - CXXFLAGS += -marm -march=armv7-a -mfloat-abi=softfp -mfpu=neon -DANDROID -DARM - HAVE_NEON = 1 +export INCLUDE := $(XDK)/xbox/include +export LIB := $(XDK)/xbox/lib +PSS_STYLE :=2 +CFLAGS += -D_XBOX -D_XBOX1 +CXXFLAGS += -D_XBOX -D_XBOX1 +STATIC_LINKING=1 +HAS_GCC := 0 +# Windows MSVC 2010 Xbox 360 +else ifeq ($(platform), xbox360_msvc2010) +TARGET := $(TARGET_NAME)_libretro_xdk360.lib +MSVCBINDIRPREFIX = $(XEDK)/bin/win32 +CC = "$(MSVCBINDIRPREFIX)/cl.exe" +CXX = "$(MSVCBINDIRPREFIX)/cl.exe" +LD = "$(MSVCBINDIRPREFIX)/lib.exe" +export INCLUDE := $(XEDK)/include/xbox +export LIB := $(XEDK)/lib/xbox +PSS_STYLE :=2 +CFLAGS += -D_XBOX -D_XBOX360 +CXXFLAGS += -D_XBOX -D_XBOX360 +STATIC_LINKING=1 +HAS_GCC := 0 + +# Windows MSVC 2017 all architectures +else ifneq (,$(findstring windows_msvc2017,$(platform))) + + PlatformSuffix = $(subst windows_msvc2017_,,$(platform)) + ifneq (,$(findstring desktop,$(PlatformSuffix))) + WinPartition = desktop + MSVC2017CompileFlags = -DWINAPI_FAMILY=WINAPI_FAMILY_DESKTOP_APP + LDFLAGS += -MANIFEST -LTCG:incremental -NXCOMPAT -DYNAMICBASE -DEBUG -OPT:REF -INCREMENTAL:NO -SUBSYSTEM:WINDOWS -MANIFESTUAC:"level='asInvoker' uiAccess='false'" -OPT:ICF -ERRORREPORT:PROMPT -NOLOGO -TLBID:1 + LIBS += kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib + else ifneq (,$(findstring uwp,$(PlatformSuffix))) + WinPartition = uwp + MSVC2017CompileFlags = -DWINAPI_FAMILY=WINAPI_FAMILY_APP -DWINDLL -D_UNICODE -DUNICODE -DWRL_NO_DEFAULT_LIB + LDFLAGS += -APPCONTAINER -NXCOMPAT -DYNAMICBASE -MANIFEST:NO -LTCG -OPT:REF -SUBSYSTEM:CONSOLE -MANIFESTUAC:NO -OPT:ICF -ERRORREPORT:PROMPT -NOLOGO -TLBID:1 -DEBUG:FULL -WINMD:NO + LIBS += WindowsApp.lib + endif + + CFLAGS += $(MSVC2017CompileFlags) + CXXFLAGS += $(MSVC2017CompileFlags) + + TargetArchMoniker = $(subst $(WinPartition)_,,$(PlatformSuffix)) + + CC = cl.exe + CXX = cl.exe + + reg_query = $(call filter_out2,$(subst $2,,$(shell reg query "$2" -v "$1" 2>nul))) + fix_path = $(subst $(SPACE),\ ,$(subst \,/,$1)) + + ProgramFiles86w := $(shell cmd /c "echo %PROGRAMFILES(x86)%") + ProgramFiles86 := $(shell cygpath "$(ProgramFiles86w)") + + WindowsSdkDir ?= $(call reg_query,InstallationFolder,HKEY_LOCAL_MACHINE\SOFTWARE\Wow6432Node\Microsoft\Microsoft SDKs\Windows\v10.0) + WindowsSdkDir ?= $(call reg_query,InstallationFolder,HKEY_CURRENT_USER\SOFTWARE\Wow6432Node\Microsoft\Microsoft SDKs\Windows\v10.0) + WindowsSdkDir ?= $(call reg_query,InstallationFolder,HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Microsoft SDKs\Windows\v10.0) + WindowsSdkDir ?= $(call reg_query,InstallationFolder,HKEY_CURRENT_USER\SOFTWARE\Microsoft\Microsoft SDKs\Windows\v10.0) + WindowsSdkDir := $(WindowsSdkDir) + + WindowsSDKVersion ?= $(firstword $(foreach folder,$(subst $(subst \,/,$(WindowsSdkDir)Include/),,$(wildcard $(call fix_path,$(WindowsSdkDir)Include\*))),$(if $(wildcard $(call fix_path,$(WindowsSdkDir)Include/$(folder)/um/Windows.h)),$(folder),)))$(BACKSLASH) + WindowsSDKVersion := $(WindowsSDKVersion) + + VsInstallBuildTools = $(ProgramFiles86)/Microsoft Visual Studio/2017/BuildTools + VsInstallEnterprise = $(ProgramFiles86)/Microsoft Visual Studio/2017/Enterprise + VsInstallProfessional = $(ProgramFiles86)/Microsoft Visual Studio/2017/Professional + VsInstallCommunity = $(ProgramFiles86)/Microsoft Visual Studio/2017/Community + + VsInstallRoot ?= $(shell if [ -d "$(VsInstallBuildTools)" ]; then echo "$(VsInstallBuildTools)"; fi) + ifeq ($(VsInstallRoot), ) + VsInstallRoot = $(shell if [ -d "$(VsInstallEnterprise)" ]; then echo "$(VsInstallEnterprise)"; fi) + endif + ifeq ($(VsInstallRoot), ) + VsInstallRoot = $(shell if [ -d "$(VsInstallProfessional)" ]; then echo "$(VsInstallProfessional)"; fi) + endif + ifeq ($(VsInstallRoot), ) + VsInstallRoot = $(shell if [ -d "$(VsInstallCommunity)" ]; then echo "$(VsInstallCommunity)"; fi) + endif + VsInstallRoot := $(VsInstallRoot) + + VcCompilerToolsVer := $(shell cat "$(VsInstallRoot)/VC/Auxiliary/Build/Microsoft.VCToolsVersion.default.txt" | grep -o '[0-9\.]*') + VcCompilerToolsDir := $(VsInstallRoot)/VC/Tools/MSVC/$(VcCompilerToolsVer) + + WindowsSDKSharedIncludeDir := $(shell cygpath -w "$(WindowsSdkDir)\Include\$(WindowsSDKVersion)\shared") + WindowsSDKUCRTIncludeDir := $(shell cygpath -w "$(WindowsSdkDir)\Include\$(WindowsSDKVersion)\ucrt") + WindowsSDKUMIncludeDir := $(shell cygpath -w "$(WindowsSdkDir)\Include\$(WindowsSDKVersion)\um") + WindowsSDKUCRTLibDir := $(shell cygpath -w "$(WindowsSdkDir)\Lib\$(WindowsSDKVersion)\ucrt\$(TargetArchMoniker)") + WindowsSDKUMLibDir := $(shell cygpath -w "$(WindowsSdkDir)\Lib\$(WindowsSDKVersion)\um\$(TargetArchMoniker)") + + # For some reason the HostX86 compiler doesn't like compiling for x64 + # ("no such file" opening a shared library), and vice-versa. + # Work around it for now by using the strictly x86 compiler for x86, and x64 for x64. + # NOTE: What about ARM? + ifneq (,$(findstring x64,$(TargetArchMoniker))) + VCCompilerToolsBinDir := $(VcCompilerToolsDir)\bin\HostX64 + else + VCCompilerToolsBinDir := $(VcCompilerToolsDir)\bin\HostX86 + endif + + PATH := $(shell IFS=$$'\n'; cygpath "$(VCCompilerToolsBinDir)/$(TargetArchMoniker)"):$(PATH) + PATH := $(PATH):$(shell IFS=$$'\n'; cygpath "$(VsInstallRoot)/Common7/IDE") + INCLUDE := $(shell IFS=$$'\n'; cygpath -w "$(VcCompilerToolsDir)/include") + LIB := $(shell IFS=$$'\n'; cygpath -w "$(VcCompilerToolsDir)/lib/$(TargetArchMoniker)") + + export INCLUDE := $(INCLUDE);$(WindowsSDKSharedIncludeDir);$(WindowsSDKUCRTIncludeDir);$(WindowsSDKUMIncludeDir) + export LIB := $(LIB);$(WindowsSDKUCRTLibDir);$(WindowsSDKUMLibDir) + TARGET := $(TARGET_NAME)_libretro.dll + PSS_STYLE :=2 + LDFLAGS += -DLL + +# Windows MSVC 2010 x64 +else ifeq ($(platform), windows_msvc2010_x64) + CC = cl.exe + CXX = cl.exe + +PATH := $(shell IFS=$$'\n'; cygpath "$(VS100COMNTOOLS)../../VC/bin/amd64"):$(PATH) +PATH := $(PATH):$(shell IFS=$$'\n'; cygpath "$(VS100COMNTOOLS)../IDE") +LIB := $(shell IFS=$$'\n'; cygpath "$(VS100COMNTOOLS)../../VC/lib/amd64") +INCLUDE := $(shell IFS=$$'\n'; cygpath "$(VS100COMNTOOLS)../../VC/include") + +WindowsSdkDir := $(shell reg query "HKLM\SOFTWARE\Microsoft\Microsoft SDKs\Windows\v7.0A" -v "InstallationFolder" | grep -o '[A-Z]:\\.*')lib/x64 +WindowsSdkDir ?= $(shell reg query "HKLM\SOFTWARE\Microsoft\Microsoft SDKs\Windows\v7.1A" -v "InstallationFolder" | grep -o '[A-Z]:\\.*')lib/x64 + +WindowsSdkDirInc := $(shell reg query "HKLM\SOFTWARE\Microsoft\Microsoft SDKs\Windows\v7.0A" -v "InstallationFolder" | grep -o '[A-Z]:\\.*')Include +WindowsSdkDirInc ?= $(shell reg query "HKLM\SOFTWARE\Microsoft\Microsoft SDKs\Windows\v7.1A" -v "InstallationFolder" | grep -o '[A-Z]:\\.*')Include + + +INCFLAGS_PLATFORM = -I"$(WindowsSdkDirInc)" +export INCLUDE := $(INCLUDE) +export LIB := $(LIB);$(WindowsSdkDir) +TARGET := $(TARGET_NAME)_libretro.dll +PSS_STYLE :=2 +LDFLAGS += -DLL +LIBS := +# Windows MSVC 2010 x86 +else ifeq ($(platform), windows_msvc2010_x86) + CC = cl.exe + CXX = cl.exe + +PATH := $(shell IFS=$$'\n'; cygpath "$(VS100COMNTOOLS)../../VC/bin"):$(PATH) +PATH := $(PATH):$(shell IFS=$$'\n'; cygpath "$(VS100COMNTOOLS)../IDE") +LIB := $(shell IFS=$$'\n'; cygpath -w "$(VS100COMNTOOLS)../../VC/lib") +INCLUDE := $(shell IFS=$$'\n'; cygpath "$(VS100COMNTOOLS)../../VC/include") + +WindowsSdkDir := $(shell reg query "HKLM\SOFTWARE\Microsoft\Microsoft SDKs\Windows\v7.0A" -v "InstallationFolder" | grep -o '[A-Z]:\\.*')lib +WindowsSdkDir ?= $(shell reg query "HKLM\SOFTWARE\Microsoft\Microsoft SDKs\Windows\v7.1A" -v "InstallationFolder" | grep -o '[A-Z]:\\.*')lib + +WindowsSdkDirInc := $(shell reg query "HKLM\SOFTWARE\Microsoft\Microsoft SDKs\Windows\v7.0A" -v "InstallationFolder" | grep -o '[A-Z]:\\.*')Include +WindowsSdkDirInc ?= $(shell reg query "HKLM\SOFTWARE\Microsoft\Microsoft SDKs\Windows\v7.1A" -v "InstallationFolder" | grep -o '[A-Z]:\\.*')Include + + +INCFLAGS_PLATFORM = -I"$(WindowsSdkDirInc)" +export INCLUDE := $(INCLUDE) +export LIB := $(LIB);$(WindowsSdkDir) +TARGET := $(TARGET_NAME)_libretro.dll +PSS_STYLE :=2 +LDFLAGS += -DLL +LIBS := + +# Windows MSVC 2003 x86 +else ifeq ($(platform), windows_msvc2003_x86) + CC = cl.exe + CXX = cl.exe + +PATH := $(shell IFS=$$'\n'; cygpath "$(VS71COMNTOOLS)../../Vc7/bin"):$(PATH) +PATH := $(PATH):$(shell IFS=$$'\n'; cygpath "$(VS71COMNTOOLS)../IDE") +INCLUDE := $(shell IFS=$$'\n'; cygpath "$(VS71COMNTOOLS)../../Vc7/include") +LIB := $(shell IFS=$$'\n'; cygpath -w "$(VS71COMNTOOLS)../../Vc7/lib") +BIN := $(shell IFS=$$'\n'; cygpath "$(VS71COMNTOOLS)../../Vc7/bin") + +WindowsSdkDir := $(INETSDK) + +export INCLUDE := $(INCLUDE);$(INETSDK)/Include;src/drivers/libretro/msvc/msvc-2005 +export LIB := $(LIB);$(WindowsSdkDir);$(INETSDK)/Lib +TARGET := $(TARGET_NAME)_libretro.dll +PSS_STYLE :=2 +LDFLAGS += -DLL +CFLAGS += -D_CRT_SECURE_NO_DEPRECATE + +# Windows MSVC 2005 x86 +else ifeq ($(platform), windows_msvc2005_x86) + CC = cl.exe + CXX = cl.exe + +PATH := $(shell IFS=$$'\n'; cygpath "$(VS80COMNTOOLS)../../VC/bin"):$(PATH) +PATH := $(PATH):$(shell IFS=$$'\n'; cygpath "$(VS80COMNTOOLS)../IDE") +INCLUDE := $(shell IFS=$$'\n'; cygpath "$(VS80COMNTOOLS)../../VC/include") +LIB := $(shell IFS=$$'\n'; cygpath -w "$(VS80COMNTOOLS)../../VC/lib") +BIN := $(shell IFS=$$'\n'; cygpath "$(VS80COMNTOOLS)../../VC/bin") + +WindowsSdkDir := $(INETSDK) + +export INCLUDE := $(INCLUDE);$(INETSDK)/Include;libretro-common/include/compat/msvc +export LIB := $(LIB);$(WindowsSdkDir);$(INETSDK)/Lib +TARGET := $(TARGET_NAME)_libretro.dll +PSS_STYLE :=2 +LDFLAGS += -DLL +CFLAGS += -D_CRT_SECURE_NO_DEPRECATE # Windows else - TARGET := $(TARGET_NAME)_libretro.dll - CC = gcc - CXX = g++ - SHARED := -shared -static-libgcc -static-libstdc++ -s -Wl,--version-script=link.T - CXXFLAGS += -D__WIN32__ -D__WIN32_LIBSNES__ - + TARGET := $(TARGET_NAME)_libretro.dll + CC = gcc + CXX = g++ + SHARED := -shared -static-libgcc -static-libstdc++ -s -Wl,--version-script=link.T + CXXFLAGS += -D__WIN32__ endif CORE_DIR := .. ifeq ($(DEBUG), 1) - CXXFLAGS += -O0 -g - CFLAGS += -O0 -g + ifneq (,$(findstring msvc,$(platform))) + CFLAGS += -Od -Zi -DDEBUG -D_DEBUG + CXXFLAGS += -Od -Zi -DDEBUG -D_DEBUG + + ifeq ($(STATIC_LINKING),1) + CFLAGS += -MTd + CXXFLAGS += -MTd + else + CFLAGS += -MDd + CXXFLAGS += -MDd + endif + else + CFLAGS += -O0 -g -DDEBUG + CXXFLAGS += -O0 -g -DDEBUG + endif else - CXXFLAGS += -O3 -DNDEBUG - CFLAGS += -O3 -DNDEBUG + CFLAGS += -O2 -DNDEBUG + CXXFLAGS += -O2 -DNDEBUG + + ifneq (,$(findstring msvc,$(platform))) + ifeq ($(STATIC_LINKING),1) + CFLAGS += -MT + CXXFLAGS += -MT + else + CFLAGS += -MD + CXXFLAGS += -MD + endif + endif endif include Makefile.common @@ -215,21 +462,46 @@ include Makefile.common OBJECTS := $(SOURCES_CXX:.cpp=.o) $(SOURCES_C:.c=.o) ifeq ($(platform), sncps3) - WARNINGS_DEFINES = - CODE_DEFINES = + WARNINGS_DEFINES = + CODE_DEFINES = +else ifneq (,$(findstring msvc,$(platform))) + WARNINGS_DEFINES = + CODE_DEFINES = else - WARNINGS_DEFINES = -Wall -W -Wno-unused-parameter - CODE_DEFINES = -fomit-frame-pointer + WARNINGS_DEFINES = -Wall -W -Wno-unused-parameter + CODE_DEFINES = -fomit-frame-pointer endif -ifneq ($(HAVE_EXCEPTIONS), 1) -CXXFLAGS += -fno-exceptions -endif - -CXXFLAGS += $(CODE_DEFINES) -fno-rtti -pedantic $(WARNINGS_DEFINES) $(fpic) -CXXFLAGS += -DHAVE_STRINGS_H -DHAVE_STDINT_H -DRIGHTSHIFT_IS_SAR -D__LIBRETRO__ +CXXFLAGS += $(CODE_DEFINES) $(WARNINGS_DEFINES) $(fpic) +CXXFLAGS += -DRIGHTSHIFT_IS_SAR -D__LIBRETRO__ CFLAGS = $(CXXFLAGS) +ifeq (,$(findstring msvc,$(platform))) +CXXFLAGS += -DHAVE_STRINGS_H +CXXFLAGS += -fno-rtti -pedantic +ifneq ($(HAVE_EXCEPTIONS), 1) + CXXFLAGS += -fno-exceptions +endif +endif + +OBJOUT = -o +LINKOUT = -o + +ifneq (,$(findstring msvc,$(platform))) + OBJOUT = -Fo + LINKOUT = -out: +ifeq ($(STATIC_LINKING),1) + LD ?= lib.exe + STATIC_LINKING=0 +else + LD = link.exe +endif +else + LD = $(CXX) +endif + +INCFLAGS += $(INCFLAGS_PLATFORM) + ifeq ($(platform), theos_ios) COMMON_FLAGS := -DIOS -DARM $(COMMON_DEFINES) $(INCFLAGS) -I$(THEOS_INCLUDE_PATH) -Wno-error $(LIBRARY_NAME)_CFLAGS += $(CFLAGS) $(COMMON_FLAGS) @@ -243,14 +515,14 @@ $(TARGET): $(OBJECTS) ifeq ($(STATIC_LINKING), 1) $(AR) rcs $@ $(OBJECTS) else - $(CXX) $(fpic) $(SHARED) $(INCFLAGS) -o $@ $(OBJECTS) $(LIBM) + $(LD) $(fpic) $(SHARED) $(LINKOUT)$@ $(OBJECTS) $(LDFLAGS) $(LIBS) endif %.o: %.cpp - $(CXX) $(INCFLAGS) $(CXXFLAGS) -c -o $@ $< + $(CXX) $(INCFLAGS) $(CPPFLAGS) $(CXXFLAGS) -c $(OBJOUT)$@ $< %.o: %.c - $(CC) $(INCFLAGS) $(CFLAGS) -c -o $@ $< + $(CC) $(INCFLAGS) $(CPPFLAGS) $(CFLAGS) -c $(OBJOUT)$@ $< clean: rm -f $(OBJECTS) $(TARGET) diff --git a/libretro/Makefile.common b/libretro/Makefile.common index 3e921d26..dd47ed3d 100644 --- a/libretro/Makefile.common +++ b/libretro/Makefile.common @@ -1,12 +1,16 @@ +LIBRETRO_COMM_DIR = $(CORE_DIR)/libretro/libretro-common INCFLAGS = -I$(CORE_DIR)/libretro -I$(CORE_DIR) -I$(CORE_DIR)/apu/ -I$(CORE_DIR)/apu/bapu +ifneq (,$(findstring msvc2003,$(platform))) +INCFLAGS += -I$(LIBRETRO_COMM_DIR)/include/compat/msvc +endif + SOURCES_C := SOURCES_CXX := $(CORE_DIR)/apu/apu.cpp \ $(CORE_DIR)/apu/bapu/dsp/sdsp.cpp \ $(CORE_DIR)/apu/bapu/dsp/SPC_DSP.cpp \ $(CORE_DIR)/apu/bapu/smp/smp.cpp \ $(CORE_DIR)/apu/bapu/smp/smp_state.cpp \ - $(CORE_DIR)/bml.cpp \ $(CORE_DIR)/bsx.cpp \ $(CORE_DIR)/c4.cpp \ $(CORE_DIR)/c4emu.cpp \ @@ -31,24 +35,24 @@ SOURCES_CXX := $(CORE_DIR)/apu/apu.cpp \ $(CORE_DIR)/globals.cpp \ $(CORE_DIR)/logger.cpp \ $(CORE_DIR)/memmap.cpp \ - $(CORE_DIR)/movie.cpp \ - $(CORE_DIR)/msu1.cpp \ $(CORE_DIR)/obc1.cpp \ + $(CORE_DIR)/msu1.cpp \ $(CORE_DIR)/ppu.cpp \ $(CORE_DIR)/stream.cpp \ $(CORE_DIR)/sa1.cpp \ $(CORE_DIR)/sa1cpu.cpp \ - $(CORE_DIR)/screenshot.cpp \ $(CORE_DIR)/sdd1.cpp \ $(CORE_DIR)/sdd1emu.cpp \ $(CORE_DIR)/seta.cpp \ $(CORE_DIR)/seta010.cpp \ $(CORE_DIR)/seta011.cpp \ $(CORE_DIR)/seta018.cpp \ - $(CORE_DIR)/sha256.cpp \ $(CORE_DIR)/snapshot.cpp \ $(CORE_DIR)/snes9x.cpp \ $(CORE_DIR)/spc7110.cpp \ $(CORE_DIR)/srtc.cpp \ $(CORE_DIR)/tile.cpp \ + $(CORE_DIR)/sha256.cpp \ + $(CORE_DIR)/bml.cpp \ + $(CORE_DIR)/movie.cpp \ $(CORE_DIR)/libretro/libretro.cpp diff --git a/libretro/control b/libretro/control new file mode 100644 index 00000000..8a835c8b --- /dev/null +++ b/libretro/control @@ -0,0 +1,10 @@ +Package: com.libretro.snes9x +Name: snes9x +Depends: +Version: 0.0.1 +Architecture: iphoneos-arm +Description: Libretro iOS core of SNES9x +Maintainer: libretro +Author: libretro +Section: System +Tag: role::developer diff --git a/libretro/jni/Android.mk b/libretro/jni/Android.mk index 7ec6d3db..d59e3614 100644 --- a/libretro/jni/Android.mk +++ b/libretro/jni/Android.mk @@ -1,23 +1,19 @@ LOCAL_PATH := $(call my-dir) +CORE_DIR := $(LOCAL_PATH)/../.. + +include $(CORE_DIR)/libretro/Makefile.common + +COREFLAGS := -DANDROID -D__LIBRETRO__ -DHAVE_STRINGS_H -DRIGHTSHIFT_IS_SAR $(INCFLAGS) + +GIT_VERSION := " $(shell git rev-parse --short HEAD || echo unknown)" +ifneq ($(GIT_VERSION)," unknown") + COREFLAGS += -DGIT_VERSION=\"$(GIT_VERSION)\" +endif + include $(CLEAR_VARS) - -ifeq ($(TARGET_ARCH),arm) -LOCAL_CFLAGS += -DANDROID_ARM -LOCAL_ARM_MODE := arm -endif - -ifeq ($(TARGET_ARCH),x86) -LOCAL_CFLAGS += -DANDROID_X86 -endif - -ifeq ($(TARGET_ARCH),mips) -LOCAL_CFLAGS += -DANDROID_MIPS -endif - -LOCAL_MODULE := libretro -LOCAL_SRC_FILES = ../../apu/apu.cpp ../../apu/bapu/dsp/sdsp.cpp ../../apu/bapu/dsp/SPC_DSP.cpp ../../apu/bapu/smp/smp.cpp ../../apu/bapu/smp/smp_state.cpp ../../bsx.cpp ../../c4.cpp ../../c4emu.cpp ../../cheats.cpp ../../cheats2.cpp ../../clip.cpp ../../conffile.cpp ../../controls.cpp ../../cpu.cpp ../../cpuexec.cpp ../../cpuops.cpp ../../crosshairs.cpp ../../dma.cpp ../../dsp.cpp ../../dsp1.cpp ../../dsp2.cpp ../../dsp3.cpp ../../dsp4.cpp ../../fxinst.cpp ../../fxemu.cpp ../../gfx.cpp ../../globals.cpp ../../logger.cpp ../../memmap.cpp ../../movie.cpp ../../obc1.cpp ../../ppu.cpp ../../stream.cpp ../../sa1.cpp ../../sa1cpu.cpp ../../screenshot.cpp ../../sdd1.cpp ../../sdd1emu.cpp ../../seta.cpp ../../seta010.cpp ../../seta011.cpp ../../seta018.cpp ../../snapshot.cpp ../../snes9x.cpp ../../spc7110.cpp ../../srtc.cpp ../../tile.cpp ../libretro.cpp -LOCAL_CXXFLAGS = -DANDROID -DARM -D__LIBRETRO__ -DHAVE_STRINGS_H -DHAVE_STDINT_H -DRIGHTSHIFT_IS_SAR -LOCAL_C_INCLUDES = ../../ ../../apu/bapu/ - +LOCAL_MODULE := retro +LOCAL_SRC_FILES := $(SOURCES_CXX) +LOCAL_CXXFLAGS := $(COREFLAGS) +LOCAL_LDFLAGS := -Wl,-version-script=$(CORE_DIR)/libretro/link.T include $(BUILD_SHARED_LIBRARY) diff --git a/libretro/libretro-common/include/compat/msvc.h b/libretro/libretro-common/include/compat/msvc.h new file mode 100644 index 00000000..57ca291b --- /dev/null +++ b/libretro/libretro-common/include/compat/msvc.h @@ -0,0 +1,104 @@ +/* Copyright (C) 2010-2016 The RetroArch team + * + * --------------------------------------------------------------------------------------- + * The following license statement only applies to this file (msvc_compat.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_COMPAT_MSVC_H +#define __LIBRETRO_SDK_COMPAT_MSVC_H + +#ifdef _MSC_VER + +#ifdef __cplusplus +extern "C" { +#endif + +/* Pre-MSVC 2015 compilers don't implement snprintf in a cross-platform manner. */ +#if _MSC_VER < 1900 + #include + #ifndef snprintf + #define snprintf c99_snprintf_retro__ + #endif + + int c99_snprintf_retro__(char *outBuf, size_t size, const char *format, ...); +#endif + +/* Pre-MSVC 2010 compilers don't implement vsnprintf in a cross-platform manner? Not sure about this one. */ +#if _MSC_VER < 1600 + #include + #include + #ifndef vsnprintf + #define vsnprintf c99_vsnprintf_retro__ + #endif + int c99_vsnprintf_retro__(char *outBuf, size_t size, const char *format, va_list ap); +#endif + +#ifdef __cplusplus +} +#endif + +#undef UNICODE /* Do not bother with UNICODE at this time. */ +#include +#include +#include + +/* Python headers defines ssize_t and sets HAVE_SSIZE_T. + * Cannot duplicate these efforts. + */ +#ifndef HAVE_SSIZE_T +#if defined(_WIN64) +typedef __int64 ssize_t; +#elif defined(_WIN32) +typedef int ssize_t; +#endif +#endif + +#define mkdir(dirname, unused) _mkdir(dirname) +#define strtoull _strtoui64 +#undef strcasecmp +#define strcasecmp _stricmp +#undef strncasecmp +#define strncasecmp _strnicmp + +/* Disable some of the annoying warnings. */ +#pragma warning(disable : 4800) +#pragma warning(disable : 4805) +#pragma warning(disable : 4244) +#pragma warning(disable : 4305) +#pragma warning(disable : 4146) +#pragma warning(disable : 4267) +#pragma warning(disable : 4723) +#pragma warning(disable : 4996) + +/* roundf is available since MSVC 2013 */ +#if _MSC_VER < 1800 +#define roundf(in) (in >= 0.0f ? floorf(in + 0.5f) : ceilf(in - 0.5f)) +#endif + +#ifndef PATH_MAX +#define PATH_MAX _MAX_PATH +#endif + +#ifndef SIZE_MAX +#define SIZE_MAX _UI32_MAX +#endif + +#endif +#endif + diff --git a/libretro/libretro-common/include/compat/msvc/stdint.h b/libretro/libretro-common/include/compat/msvc/stdint.h new file mode 100644 index 00000000..403e1f73 --- /dev/null +++ b/libretro/libretro-common/include/compat/msvc/stdint.h @@ -0,0 +1,254 @@ +/* ISO C9x compliant stdint.h for Microsoft Visual Studio + * Based on ISO/IEC 9899:TC2 Committee draft (May 6, 2005) WG14/N1124 + * + * Copyright (c) 2006-2008 Alexander Chemeris + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. The name of the author may be used to endorse or promote products + * derived from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO + * EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; + * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, + * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR + * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF + * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef __RARCH_STDINT_H +#define __RARCH_STDINT_H + +#if _MSC_VER && (_MSC_VER < 1600) +/* Pre-MSVC 2010 needs an implementation of stdint.h. */ + +#if _MSC_VER > 1000 +#pragma once +#endif + +#include + +/* For Visual Studio 6 in C++ mode and for many Visual Studio versions when + * compiling for ARM we should wrap include with 'extern "C++" {}' + * or compiler give many errors like this: + * + * error C2733: second C linkage of overloaded function 'wmemchr' not allowed + */ +#ifdef __cplusplus +extern "C" { +#endif +# include +#ifdef __cplusplus +} +#endif + +/* Define _W64 macros to mark types changing their size, like intptr_t. */ +#ifndef _W64 +# if !defined(__midl) && (defined(_X86_) || defined(_M_IX86)) && _MSC_VER >= 1300 +# define _W64 __w64 +# else +# define _W64 +# endif +#endif + + +/* 7.18.1 Integer types. */ + +/* 7.18.1.1 Exact-width integer types. */ + +/* Visual Studio 6 and Embedded Visual C++ 4 doesn't + * realize that, e.g. char has the same size as __int8 + * so we give up on __intX for them. + */ +#if (_MSC_VER < 1300) + typedef signed char int8_t; + typedef signed short int16_t; + typedef signed int int32_t; + typedef unsigned char uint8_t; + typedef unsigned short uint16_t; + typedef unsigned int uint32_t; +#else + typedef signed __int8 int8_t; + typedef signed __int16 int16_t; + typedef signed __int32 int32_t; + typedef unsigned __int8 uint8_t; + typedef unsigned __int16 uint16_t; + typedef unsigned __int32 uint32_t; +#endif +typedef signed __int64 int64_t; +typedef unsigned __int64 uint64_t; + + +/* 7.18.1.2 Minimum-width integer types. */ +typedef int8_t int_least8_t; +typedef int16_t int_least16_t; +typedef int32_t int_least32_t; +typedef int64_t int_least64_t; +typedef uint8_t uint_least8_t; +typedef uint16_t uint_least16_t; +typedef uint32_t uint_least32_t; +typedef uint64_t uint_least64_t; + +/* 7.18.1.3 Fastest minimum-width integer types. */ +typedef int8_t int_fast8_t; +typedef int16_t int_fast16_t; +typedef int32_t int_fast32_t; +typedef int64_t int_fast64_t; +typedef uint8_t uint_fast8_t; +typedef uint16_t uint_fast16_t; +typedef uint32_t uint_fast32_t; +typedef uint64_t uint_fast64_t; + +/* 7.18.1.4 Integer types capable of holding object pointers. */ +#ifdef _WIN64 /* [ */ + typedef signed __int64 intptr_t; + typedef unsigned __int64 uintptr_t; +#else /* _WIN64 ][ */ + typedef _W64 signed int intptr_t; + typedef _W64 unsigned int uintptr_t; +#endif /* _WIN64 ] */ + +/* 7.18.1.5 Greatest-width integer types. */ +typedef int64_t intmax_t; +typedef uint64_t uintmax_t; + +/* 7.18.2 Limits of specified-width integer types. */ + +#if !defined(__cplusplus) || defined(__STDC_LIMIT_MACROS) +/* [ See footnote 220 at page 257 and footnote 221 at page 259. */ + +/* 7.18.2.1 Limits of exact-width integer types. */ +#define INT8_MIN ((int8_t)_I8_MIN) +#define INT8_MAX _I8_MAX +#define INT16_MIN ((int16_t)_I16_MIN) +#define INT16_MAX _I16_MAX +#define INT32_MIN ((int32_t)_I32_MIN) +#define INT32_MAX _I32_MAX +#define INT64_MIN ((int64_t)_I64_MIN) +#define INT64_MAX _I64_MAX +#define UINT8_MAX _UI8_MAX +#define UINT16_MAX _UI16_MAX +#define UINT32_MAX _UI32_MAX +#define UINT64_MAX _UI64_MAX + +/* 7.18.2.2 Limits of minimum-width integer types. */ +#define INT_LEAST8_MIN INT8_MIN +#define INT_LEAST8_MAX INT8_MAX +#define INT_LEAST16_MIN INT16_MIN +#define INT_LEAST16_MAX INT16_MAX +#define INT_LEAST32_MIN INT32_MIN +#define INT_LEAST32_MAX INT32_MAX +#define INT_LEAST64_MIN INT64_MIN +#define INT_LEAST64_MAX INT64_MAX +#define UINT_LEAST8_MAX UINT8_MAX +#define UINT_LEAST16_MAX UINT16_MAX +#define UINT_LEAST32_MAX UINT32_MAX +#define UINT_LEAST64_MAX UINT64_MAX + +/* 7.18.2.3 Limits of fastest minimum-width integer types. */ +#define INT_FAST8_MIN INT8_MIN +#define INT_FAST8_MAX INT8_MAX +#define INT_FAST16_MIN INT16_MIN +#define INT_FAST16_MAX INT16_MAX +#define INT_FAST32_MIN INT32_MIN +#define INT_FAST32_MAX INT32_MAX +#define INT_FAST64_MIN INT64_MIN +#define INT_FAST64_MAX INT64_MAX +#define UINT_FAST8_MAX UINT8_MAX +#define UINT_FAST16_MAX UINT16_MAX +#define UINT_FAST32_MAX UINT32_MAX +#define UINT_FAST64_MAX UINT64_MAX + +/* 7.18.2.4 Limits of integer types capable of holding object pointers. */ +#ifdef _WIN64 /* [ */ +# define INTPTR_MIN INT64_MIN +# define INTPTR_MAX INT64_MAX +# define UINTPTR_MAX UINT64_MAX +#else /* _WIN64 ][ */ +# define INTPTR_MIN INT32_MIN +# define INTPTR_MAX INT32_MAX +# define UINTPTR_MAX UINT32_MAX +#endif /* _WIN64 ] */ + +/* 7.18.2.5 Limits of greatest-width integer types */ +#define INTMAX_MIN INT64_MIN +#define INTMAX_MAX INT64_MAX +#define UINTMAX_MAX UINT64_MAX + +/* 7.18.3 Limits of other integer types */ + +#ifdef _WIN64 /* [ */ +# define PTRDIFF_MIN _I64_MIN +# define PTRDIFF_MAX _I64_MAX +#else /* _WIN64 ][ */ +# define PTRDIFF_MIN _I32_MIN +# define PTRDIFF_MAX _I32_MAX +#endif /* _WIN64 ] */ + +#define SIG_ATOMIC_MIN INT_MIN +#define SIG_ATOMIC_MAX INT_MAX + +#ifndef SIZE_MAX /* [ */ +# ifdef _WIN64 /* [ */ +# define SIZE_MAX _UI64_MAX +# else /* _WIN64 ][ */ +# define SIZE_MAX _UI32_MAX +# endif /* _WIN64 ] */ +#endif /* SIZE_MAX ] */ + +/* WCHAR_MIN and WCHAR_MAX are also defined in */ +#ifndef WCHAR_MIN /* [ */ +# define WCHAR_MIN 0 +#endif /* WCHAR_MIN ] */ +#ifndef WCHAR_MAX // [ +# define WCHAR_MAX _UI16_MAX +#endif /* WCHAR_MAX ] */ + +#define WINT_MIN 0 +#define WINT_MAX _UI16_MAX + +#endif /* __STDC_LIMIT_MACROS ] */ + +/* 7.18.4 Limits of other integer types */ + +#if !defined(__cplusplus) || defined(__STDC_CONSTANT_MACROS) +/* [ See footnote 224 at page 260 */ + +/* 7.18.4.1 Macros for minimum-width integer constants */ + +#define INT8_C(val) val##i8 +#define INT16_C(val) val##i16 +#define INT32_C(val) val##i32 +#define INT64_C(val) val##i64 + +#define UINT8_C(val) val##ui8 +#define UINT16_C(val) val##ui16 +#define UINT32_C(val) val##ui32 +#define UINT64_C(val) val##ui64 + +/* 7.18.4.2 Macros for greatest-width integer constants */ +#define INTMAX_C INT64_C +#define UINTMAX_C UINT64_C + +#endif +/* __STDC_CONSTANT_MACROS ] */ + +#else +/* Sanity for everything else. */ +#include +#endif + +#endif + diff --git a/libretro/libretro-win32.vcproj b/libretro/libretro-win32.vcproj new file mode 100644 index 00000000..7208f1e9 --- /dev/null +++ b/libretro/libretro-win32.vcproj @@ -0,0 +1,794 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/libretro/libretro-win32.vcxproj b/libretro/libretro-win32.vcxproj deleted file mode 100644 index 884b6197..00000000 --- a/libretro/libretro-win32.vcxproj +++ /dev/null @@ -1,303 +0,0 @@ - - - - - libretro Debug - Win32 - - - libretro Debug - x64 - - - libretro Release - Win32 - - - libretro Release - x64 - - - - {4A2A7544-0547-4539-8B53-047FB9A15C75} - libretrowin32 - Win32Proj - 8.1 - - - - DynamicLibrary - v141_xp - NotSet - true - - - DynamicLibrary - v141_xp - NotSet - - - DynamicLibrary - v141_xp - NotSet - true - - - DynamicLibrary - v141_xp - NotSet - - - - - - - - - - - - - - - - - - - <_ProjectFileVersion>14.0.25431.1 - - - $(Platform)\$(Configuration)\ - $(Platform)\$(Configuration)\ - true - libretro_debug - - - $(Platform)\$(Configuration)\ - $(Platform)\$(Configuration)\ - true - libretro_debug - - - $(Platform)\$(Configuration)\ - $(Platform)\$(Configuration)\ - false - libretro - - - $(Platform)\$(Configuration)\ - $(Platform)\$(Configuration)\ - false - libretro - - - - Disabled - ../;../apu/bapu;%(AdditionalIncludeDirectories) - __WIN32__;__WIN32_LIBSNES__;%(PreprocessorDefinitions) - true - EnableFastChecks - MultiThreadedDebug - - Level2 - EditAndContinue - - - - - true - Windows - MachineX86 - - - - - X64 - - - Disabled - ../;../apu/bapu;%(AdditionalIncludeDirectories) - __WIN32__;__WIN32_LIBSNES__;%(PreprocessorDefinitions) - true - EnableFastChecks - MultiThreadedDebug - - Level2 - ProgramDatabase - - - - - true - Windows - MachineX64 - - - - - Full - AnySuitable - true - Speed - ../;../apu/bapu;%(AdditionalIncludeDirectories) - __WIN32__;__WIN32_LIBSNES__;%(PreprocessorDefinitions) - MultiThreaded - true - - Level2 - ProgramDatabase - - - - - true - Windows - true - true - MachineX86 - - - - - X64 - - - Full - AnySuitable - true - Speed - true - ../;../apu/bapu;%(AdditionalIncludeDirectories) - __WIN32__;__WIN32_LIBSNES__;%(PreprocessorDefinitions) - MultiThreadedDLL - true - - Level2 - ProgramDatabase - - - - - true - Windows - true - true - MachineX64 - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/libretro/libretro-win32.vcxproj.filters b/libretro/libretro-win32.vcxproj.filters deleted file mode 100644 index bb0a5065..00000000 --- a/libretro/libretro-win32.vcxproj.filters +++ /dev/null @@ -1,348 +0,0 @@ - - - - - {11448d42-5e46-4e58-b0be-8cb4b3b52ec0} - - - {dff4c5c7-1360-4c70-9a67-f5457847b1e9} - - - {d36ce584-8d5f-421c-9e1c-219a937e23c3} - - - {bb8b70ce-cd5a-45ab-848c-5c5379190802} - - - {7445db59-72e6-42a3-963c-c352087333b1} - - - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source\APU - - - s9x-source\APU - - - s9x-source\APU - - - s9x-source\APU - - - s9x-source\APU\DSP - - - s9x-source\APU\DSP - - - s9x-source\APU\DSP - - - s9x-source\APU\DSP - - - s9x-source\APU\DSP - - - s9x-source\APU\DSP - - - libretro - - - s9x-source - - - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source - - - s9x-source\APU - - - s9x-source\APU\SMP - - - s9x-source\APU\SMP - - - s9x-source\APU\DSP - - - s9x-source\APU\DSP - - - libretro - - - s9x-source - - - \ No newline at end of file diff --git a/libretro/libretro.cpp b/libretro/libretro.cpp index 6d874843..4f730fb0 100644 --- a/libretro/libretro.cpp +++ b/libretro/libretro.cpp @@ -9,29 +9,30 @@ #include "snapshot.h" #include "controls.h" #include "cheats.h" -#include "movie.h" #include "logger.h" #include "display.h" #include "conffile.h" #include -#ifndef __WIN32__ +#ifdef _WIN32 +#include +#else #include #endif #include #include #include -#define RETRO_DEVICE_JOYPAD_MULTITAP ((1 << 8) | RETRO_DEVICE_JOYPAD) -#define RETRO_DEVICE_LIGHTGUN_SUPER_SCOPE ((1 << 8) | RETRO_DEVICE_LIGHTGUN) -#define RETRO_DEVICE_LIGHTGUN_JUSTIFIER ((2 << 8) | RETRO_DEVICE_LIGHTGUN) -#define RETRO_DEVICE_LIGHTGUN_JUSTIFIERS ((3 << 8) | RETRO_DEVICE_LIGHTGUN) +#define RETRO_DEVICE_JOYPAD_MULTITAP ((1 << 8) | RETRO_DEVICE_JOYPAD) +#define RETRO_DEVICE_LIGHTGUN_SUPER_SCOPE ((1 << 8) | RETRO_DEVICE_LIGHTGUN) +#define RETRO_DEVICE_LIGHTGUN_JUSTIFIER ((2 << 8) | RETRO_DEVICE_LIGHTGUN) +#define RETRO_DEVICE_LIGHTGUN_JUSTIFIERS ((3 << 8) | RETRO_DEVICE_LIGHTGUN) -#define RETRO_MEMORY_SNES_BSX_RAM ((1 << 8) | RETRO_MEMORY_SAVE_RAM) -#define RETRO_MEMORY_SNES_BSX_PRAM ((2 << 8) | RETRO_MEMORY_SAVE_RAM) -#define RETRO_MEMORY_SNES_SUFAMI_TURBO_A_RAM ((3 << 8) | RETRO_MEMORY_SAVE_RAM) -#define RETRO_MEMORY_SNES_SUFAMI_TURBO_B_RAM ((4 << 8) | RETRO_MEMORY_SAVE_RAM) -#define RETRO_MEMORY_SNES_GAME_BOY_RAM ((5 << 8) | RETRO_MEMORY_SAVE_RAM) -#define RETRO_MEMORY_SNES_GAME_BOY_RTC ((6 << 8) | RETRO_MEMORY_RTC) +#define RETRO_MEMORY_SNES_BSX_RAM ((1 << 8) | RETRO_MEMORY_SAVE_RAM) +#define RETRO_MEMORY_SNES_BSX_PRAM ((2 << 8) | RETRO_MEMORY_SAVE_RAM) +#define RETRO_MEMORY_SNES_SUFAMI_TURBO_A_RAM ((3 << 8) | RETRO_MEMORY_SAVE_RAM) +#define RETRO_MEMORY_SNES_SUFAMI_TURBO_B_RAM ((4 << 8) | RETRO_MEMORY_SAVE_RAM) +#define RETRO_MEMORY_SNES_GAME_BOY_RAM ((5 << 8) | RETRO_MEMORY_SAVE_RAM) +#define RETRO_MEMORY_SNES_GAME_BOY_RTC ((6 << 8) | RETRO_MEMORY_RTC) #define RETRO_GAME_TYPE_BSX 0x101 #define RETRO_GAME_TYPE_BSX_SLOTTED 0x102 @@ -39,12 +40,14 @@ #define RETRO_GAME_TYPE_SUPER_GAME_BOY 0x104 #define SNES_4_3 4.0f / 3.0f -#define SNES_8_7 8.0f / 7.0f -char g_rom_dir[PATH_MAX]; -char g_basename[PATH_MAX]; +char g_rom_dir[1024]; +char g_basename[1024]; +bool overclock_cycles = false; +bool reduce_sprite_flicker = false; +int one_c, slow_one_c, two_c; -static retro_log_printf_t log_cb = NULL; +retro_log_printf_t log_cb = NULL; static retro_video_refresh_t video_cb = NULL; static retro_audio_sample_t audio_cb = NULL; static retro_audio_sample_batch_t audio_batch_cb = NULL; @@ -110,21 +113,9 @@ void retro_set_input_state(retro_input_state_t cb) input_state_cb = cb; } -enum overscan_mode { - OVERSCAN_CROP_ON, - OVERSCAN_CROP_OFF, - OVERSCAN_CROP_AUTO -}; -enum aspect_mode { - ASPECT_RATIO_4_3, - ASPECT_RATIO_8_7, - ASPECT_RATIO_NTSC, - ASPECT_RATIO_PAL, - ASPECT_RATIO_AUTO -}; static retro_environment_t environ_cb; -static overscan_mode crop_overscan_mode = OVERSCAN_CROP_ON; // default to crop -static aspect_mode aspect_ratio_mode = ASPECT_RATIO_4_3; // default to 4:3 +static unsigned crop_overscan_mode = 0; +static unsigned aspect_ratio_mode = 0; static bool rom_loaded = false; void retro_set_environment(retro_environment_t cb) { @@ -134,6 +125,10 @@ void retro_set_environment(retro_environment_t cb) // These variable names and possible values constitute an ABI with ZMZ (ZSNES Libretro player). // Changing "Show layer 1" is fine, but don't change "layer_1"/etc or the possible values ("Yes|No"). // Adding more variables and rearranging them is safe. + { "snes9x_up_down_allowed", "Allow Opposing Directions; disabled|enabled" }, + { "snes9x_overclock", "SuperFX Frequency; 100%|200%|400%|600%|800%|1000%" }, + //{ "snes9x_overclock_cycles", "Reduce Slowdown (Hack, Unsafe); disabled|compatible|max" }, + //{ "snes9x_reduce_sprite_flicker", "Reduce Flickering (Hack, Unsafe); disabled|enabled" }, { "snes9x_layer_1", "Show layer 1; enabled|disabled" }, { "snes9x_layer_2", "Show layer 2; enabled|disabled" }, { "snes9x_layer_3", "Show layer 3; enabled|disabled" }, @@ -141,6 +136,7 @@ void retro_set_environment(retro_environment_t cb) { "snes9x_layer_5", "Show sprite layer; enabled|disabled" }, { "snes9x_gfx_clip", "Enable graphic clip windows; enabled|disabled" }, { "snes9x_gfx_transp", "Enable transparency effects; enabled|disabled" }, + { "snes9x_gfx_hires", "Enable hires mode; enabled|disabled" }, { "snes9x_sndchan_1", "Enable sound channel 1; enabled|disabled" }, { "snes9x_sndchan_2", "Enable sound channel 2; enabled|disabled" }, { "snes9x_sndchan_3", "Enable sound channel 3; enabled|disabled" }, @@ -149,20 +145,20 @@ void retro_set_environment(retro_environment_t cb) { "snes9x_sndchan_6", "Enable sound channel 6; enabled|disabled" }, { "snes9x_sndchan_7", "Enable sound channel 7; enabled|disabled" }, { "snes9x_sndchan_8", "Enable sound channel 8; enabled|disabled" }, - { "snes9x_overscan", "Crop overscan; enabled|disabled|auto" }, - { "snes9x_aspect", "Preferred aspect ratio; 4:3|8:7|auto|ntsc|pal" }, + { "snes9x_overscan", "Crop overscan; auto|enabled|disabled" }, + { "snes9x_aspect", "Preferred aspect ratio; auto|ntsc|pal|4:3" }, { NULL, NULL }, }; environ_cb(RETRO_ENVIRONMENT_SET_VARIABLES, variables); - const struct retro_controller_description port_1[] = { + static const struct retro_controller_description port_1[] = { { "SNES Joypad", RETRO_DEVICE_JOYPAD }, { "SNES Mouse", RETRO_DEVICE_MOUSE }, { "Multitap", RETRO_DEVICE_JOYPAD_MULTITAP }, }; - const struct retro_controller_description port_2[] = { + static const struct retro_controller_description port_2[] = { { "SNES Joypad", RETRO_DEVICE_JOYPAD }, { "SNES Mouse", RETRO_DEVICE_MOUSE }, { "Multitap", RETRO_DEVICE_JOYPAD_MULTITAP }, @@ -170,10 +166,10 @@ void retro_set_environment(retro_environment_t cb) { "Justifier", RETRO_DEVICE_LIGHTGUN_JUSTIFIER }, }; - const struct retro_controller_info ports[] = { + static const struct retro_controller_info ports[] = { { port_1, 3 }, { port_2, 5 }, - { 0 }, + { 0, 0 }, }; environ_cb(RETRO_ENVIRONMENT_SET_CONTROLLER_INFO, (void*)ports); @@ -191,16 +187,67 @@ static void update_variables(void) bool geometry_update = false; char key[256]; struct retro_variable var; + var.key = "snes9x_overclock"; + var.value = NULL; - var.key=key; + if (environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var)) + { + int freq = atoi(var.value); + Settings.SuperFXClockMultiplier = freq; + } + + var.key = "snes9x_up_down_allowed"; + var.value = NULL; + + if (environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var)) + { + Settings.UpAndDown = !strcmp(var.value, "disabled") ? false : true; + } + else + Settings.UpAndDown = false; + + var.key = "snes9x_overclock_cycles"; + var.value = NULL; + + if (environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var) && var.value) + { + if (strcmp(var.value, "compatible") == 0) + { + overclock_cycles = true; + one_c = 4; + slow_one_c = 5; + two_c = 6; + } + else if (strcmp(var.value, "max") == 0) + { + overclock_cycles = true; + one_c = 3; + slow_one_c = 3; + two_c = 3; + } + else + overclock_cycles = false; + } + + var.key = "snes9x_reduce_sprite_flicker"; + var.value = NULL; + + if (environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var) && var.value) + { + if (strcmp(var.value, "enabled") == 0) + reduce_sprite_flicker = true; + else + reduce_sprite_flicker = false; + } int disabled_channels=0; strcpy(key, "snes9x_sndchan_x"); + var.key=key; for (int i=0;i<8;i++) { key[strlen("snes9x_sndchan_")]='1'+i; var.value=NULL; - if (environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var) && var.value && !strcmp("disabled", var.value)) + if (environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var) && !strcmp("disabled", var.value)) disabled_channels|=1<> 1); + while (avail >= BUFFER_SIZE) + { + //this loop will never be entered, but handle oversized sample counts just in case + S9xMixSamples((uint8*)audio_buf, BUFFER_SIZE); + audio_batch_cb(audio_buf, BUFFER_SIZE >> 1); + + avail -= BUFFER_SIZE; + } + if (avail > 0) + { + S9xMixSamples((uint8*)audio_buf, avail); + audio_batch_cb(audio_buf, avail >> 1); + } } void retro_get_system_info(struct retro_system_info *info) @@ -284,36 +345,34 @@ void retro_get_system_info(struct retro_system_info *info) memset(info,0,sizeof(retro_system_info)); info->library_name = "Snes9x"; - info->library_version = VERSION; - info->valid_extensions = "smc|sfc|swc|fig|bs"; +#ifndef GIT_VERSION +#define GIT_VERSION "" +#endif + info->library_version = VERSION GIT_VERSION; + info->valid_extensions = "smc|sfc|swc|fig"; info->need_fullpath = false; info->block_extract = false; } float get_aspect_ratio(unsigned width, unsigned height) { - if (aspect_ratio_mode == ASPECT_RATIO_4_3) + if (aspect_ratio_mode == 3) // 4:3 { return SNES_4_3; } - else if (aspect_ratio_mode == ASPECT_RATIO_8_7) - { - return SNES_8_7; - } - // OV2: not sure if these really make sense - NTSC is similar to 4:3, PAL looks weird float sample_frequency_ntsc = 135000000.0 / 11.0; float sample_frequency_pal = 14750000.0; float sample_freq = retro_get_region() == RETRO_REGION_NTSC ? sample_frequency_ntsc : sample_frequency_pal; float dot_rate = SNES::cpu.frequency / 4.0; - if (aspect_ratio_mode == ASPECT_RATIO_NTSC) // ntsc + if (aspect_ratio_mode == 1) // ntsc { sample_freq = sample_frequency_ntsc; dot_rate = NTSC_MASTER_CLOCK / 4.0; } - else if (aspect_ratio_mode == ASPECT_RATIO_PAL) // pal + else if (aspect_ratio_mode == 2) // pal { sample_freq = sample_frequency_pal; dot_rate = PAL_MASTER_CLOCK / 4.0; @@ -328,9 +387,9 @@ void retro_get_system_av_info(struct retro_system_av_info *info) memset(info,0,sizeof(retro_system_av_info)); unsigned width = SNES_WIDTH; unsigned height = PPU.ScreenHeight; - if (crop_overscan_mode == OVERSCAN_CROP_ON) + if (crop_overscan_mode == 1) // enabled height = SNES_HEIGHT; - else if (crop_overscan_mode == OVERSCAN_CROP_OFF) + else if (crop_overscan_mode == 2) // disabled height = SNES_HEIGHT_EXTENDED; info->geometry.base_width = width; @@ -356,40 +415,40 @@ void retro_reset() static unsigned snes_devices[2]; void retro_set_controller_port_device(unsigned port, unsigned device) { - if(port < 2) + if (port < 2) { - int offset = snes_devices[0] == RETRO_DEVICE_JOYPAD_MULTITAP ? 4 : 1; - switch (device) - { - case RETRO_DEVICE_JOYPAD: - S9xSetController(port, CTL_JOYPAD, port * offset, 0, 0, 0); - snes_devices[port] = RETRO_DEVICE_JOYPAD; - break; - case RETRO_DEVICE_JOYPAD_MULTITAP: - S9xSetController(port, CTL_MP5, port * offset, port * offset + 1, port * offset + 2, port * offset + 3); - snes_devices[port] = RETRO_DEVICE_JOYPAD_MULTITAP; - break; - case RETRO_DEVICE_MOUSE: - S9xSetController(port, CTL_MOUSE, 0, 0, 0, 0); - snes_devices[port] = RETRO_DEVICE_MOUSE; - break; - case RETRO_DEVICE_LIGHTGUN_SUPER_SCOPE: - S9xSetController(port, CTL_SUPERSCOPE, 0, 0, 0, 0); - snes_devices[port] = RETRO_DEVICE_LIGHTGUN_SUPER_SCOPE; - break; - case RETRO_DEVICE_LIGHTGUN_JUSTIFIER: - S9xSetController(port, CTL_JUSTIFIER, 0, 0, 0, 0); - snes_devices[port] = RETRO_DEVICE_LIGHTGUN_JUSTIFIER; - break; - default: - if (log_cb) - log_cb(RETRO_LOG_ERROR, "[libretro]: Invalid device (%d).\n", device); - } - if (!port) - retro_set_controller_port_device(1, snes_devices[1]); + int offset = snes_devices[0] == RETRO_DEVICE_JOYPAD_MULTITAP ? 4 : 1; + switch (device) + { + case RETRO_DEVICE_JOYPAD: + S9xSetController(port, CTL_JOYPAD, port * offset, 0, 0, 0); + snes_devices[port] = RETRO_DEVICE_JOYPAD; + break; + case RETRO_DEVICE_JOYPAD_MULTITAP: + S9xSetController(port, CTL_MP5, port * offset, port * offset + 1, port * offset + 2, port * offset + 3); + snes_devices[port] = RETRO_DEVICE_JOYPAD_MULTITAP; + break; + case RETRO_DEVICE_MOUSE: + S9xSetController(port, CTL_MOUSE, port, 0, 0, 0); + snes_devices[port] = RETRO_DEVICE_MOUSE; + break; + case RETRO_DEVICE_LIGHTGUN_SUPER_SCOPE: + S9xSetController(port, CTL_SUPERSCOPE, 0, 0, 0, 0); + snes_devices[port] = RETRO_DEVICE_LIGHTGUN_SUPER_SCOPE; + break; + case RETRO_DEVICE_LIGHTGUN_JUSTIFIER: + S9xSetController(port, CTL_JUSTIFIER, 0, 0, 0, 0); + snes_devices[port] = RETRO_DEVICE_LIGHTGUN_JUSTIFIER; + break; + default: + if (log_cb) + log_cb(RETRO_LOG_ERROR, "[libretro]: Invalid device.\n"); + } + if (!port) + retro_set_controller_port_device(1, snes_devices[1]); } else if(device != RETRO_DEVICE_NONE) - log_cb(RETRO_LOG_INFO, "[libretro]: Nonexistent Port (%d).\n", port); + log_cb(RETRO_LOG_INFO, "[libretro]: Nonexistent Port (%d).\n", port); } void retro_cheat_reset() @@ -432,6 +491,49 @@ void retro_cheat_set(unsigned index, bool enabled, const char *codeline) S9xCheatsEnable(); } +#define MAX_MAPS 32 +static struct retro_memory_descriptor memorydesc[MAX_MAPS]; +static unsigned memorydesc_c; + +static bool merge_mapping() +{ + if (memorydesc_c==1) return false;//can't merge the only one + struct retro_memory_descriptor * a=&memorydesc[MAX_MAPS - (memorydesc_c-1)]; + struct retro_memory_descriptor * b=&memorydesc[MAX_MAPS - memorydesc_c]; +//printf("test %x/%x\n",a->start,b->start); + if (a->flags != b->flags) return false; + if (a->disconnect != b->disconnect) return false; + if (a->len != b->len) return false; + if (a->addrspace || b->addrspace) return false;//we don't use these + if (((char*)a->ptr)+a->offset==((char*)b->ptr)+b->offset && a->select==b->select) + { +//printf("merge/mirror\n"); + a->select&=~(a->start^b->start); + memorydesc_c--; + return true; + } + uint32 len=a->len; + if (!len) len=(0x1000000 - a->select); + if (len && ((len-1) & (len | a->disconnect))==0 && ((char*)a->ptr)+a->offset+len == ((char*)b->ptr)+b->offset) + { +//printf("merge/consec\n"); + a->select &=~ len; + a->disconnect &=~ len; + memorydesc_c--; + return true; + } +//printf("nomerge\n"); + return false; +} + +void S9xAppendMapping(struct retro_memory_descriptor *desc) +{ + //do it backwards - snes9x defines the last one to win, while we define the first one to win + //printf("add %x\n",desc->start); + memcpy(&memorydesc[MAX_MAPS - (++memorydesc_c)], desc, sizeof(struct retro_memory_descriptor)); + while (merge_mapping()) {} +} + static void init_descriptors(void) { struct retro_input_descriptor desc[] = { @@ -500,15 +602,18 @@ static void init_descriptors(void) { 4, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_SELECT, "Select" }, { 4, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_START, "Start" }, - { 0 }, + { 0, 0, 0, 0, NULL }, }; environ_cb(RETRO_ENVIRONMENT_SET_INPUT_DESCRIPTORS, desc); } +static bool ChronoTriggerFrameHack; + bool retro_load_game(const struct retro_game_info *game) { init_descriptors(); + memorydesc_c = 0; update_variables(); @@ -525,19 +630,35 @@ bool retro_load_game(const struct retro_game_info *game) rom_loaded = Memory.LoadROMMem((const uint8_t*)game->data ,game->size); } - enum retro_pixel_format fmt = RETRO_PIXEL_FORMAT_RGB565; - - if(!environ_cb || !environ_cb(RETRO_ENVIRONMENT_SET_PIXEL_FORMAT, &fmt)) - { - return false; + int pixel_format = RGB555; + if(environ_cb) { + pixel_format = RGB565; + enum retro_pixel_format fmt = RETRO_PIXEL_FORMAT_RGB565; + if (!environ_cb(RETRO_ENVIRONMENT_SET_PIXEL_FORMAT, &fmt)) + pixel_format = RGB555; } - S9xGraphicsDeinit(); + S9xSetRenderPixelFormat(pixel_format); S9xGraphicsInit(); if (!rom_loaded && log_cb) log_cb(RETRO_LOG_ERROR, "[libretro]: Rom loading failed...\n"); + /* Check if Chrono Trigger is loaded, if so, we need to set a variable to + * true to get rid of an annoying mid-frame resolution switch to 256x239 + * which can cause an undesirable flicker/breakup of the screen for a + * split second - this happens whenever the game switches from normal + * mode to battle mode and vice versa. */ + ChronoTriggerFrameHack = false; + if (Memory.match_nc("CHRONO TRIGGER") || /* Chrono Trigger */ + Memory.match_id("ACT") || + Memory.match_id("AC9J") /* Chrono Trigger (Sample) */ + ) + ChronoTriggerFrameHack = true; + + struct retro_memory_map map={ memorydesc+MAX_MAPS-memorydesc_c, memorydesc_c }; + if (rom_loaded) environ_cb(RETRO_ENVIRONMENT_SET_MEMORY_MAPS, &map); + return rom_loaded; } @@ -548,6 +669,7 @@ bool retro_load_game_special(unsigned game_type, const struct retro_game_info *info, size_t num_info) { init_descriptors(); + memorydesc_c = 0; update_variables(); @@ -593,6 +715,9 @@ bool retro_load_game_special(unsigned game_type, break; } + struct retro_memory_map map={ memorydesc+MAX_MAPS-memorydesc_c, memorydesc_c }; + if (rom_loaded) environ_cb(RETRO_ENVIRONMENT_SET_MEMORY_MAPS, &map); + return rom_loaded; } @@ -605,7 +730,7 @@ static void check_system_specs(void) environ_cb(RETRO_ENVIRONMENT_SET_PERFORMANCE_LEVEL, &level); } -void retro_init() +void retro_init(void) { struct retro_log_callback log; @@ -614,6 +739,10 @@ void retro_init() else log_cb = NULL; + // State that SNES9X supports achievements. + bool achievements = true; + environ_cb(RETRO_ENVIRONMENT_SET_SUPPORT_ACHIEVEMENTS, &achievements); + memset(&Settings, 0, sizeof(Settings)); Settings.MouseMaster = TRUE; Settings.SuperScopeMaster = TRUE; @@ -631,10 +760,6 @@ void retro_init() Settings.InitialInfoStringTimeout = 120; Settings.HDMATimingHack = 100; Settings.BlockInvalidVRAMAccessMaster = TRUE; - Settings.WrongMovieStateProtection = TRUE; - Settings.DumpStreamsMaxFrames = -1; - Settings.StretchScreenshots = 0; - Settings.SnapshotScreenshots = FALSE; Settings.CartAName[0] = 0; Settings.CartBName[0] = 0; Settings.AutoSaveDelay = 1; @@ -652,9 +777,15 @@ void retro_init() exit(1); } - - S9xInitSound(1000, 0);//just give it a 1 second buffer - + //very slow devices will still pop + + //this needs to be applied to all snes9x cores + + //increasing the buffer size does not cause extra lag(tested with 1000ms buffer) + //bool8 S9xInitSound (int buffer_ms, int lag_ms) + + S9xInitSound(32, 0); //give it a 1.9 frame long buffer, or 1026 samples. The audio buffer is flushed every 128-132 samples anyway, so it won't get anywhere near there. + S9xSetSoundMute(FALSE); S9xSetSamplesAvailableCallback(S9xAudioCallback, NULL); @@ -725,6 +856,7 @@ void retro_init() #define BTN_POINTER (BTN_LAST + 1) #define BTN_POINTER2 (BTN_POINTER + 1) + static void map_buttons() { MAP_BUTTON(MAKE_BUTTON(PAD_1, BTN_A), "Joypad1 A"); @@ -875,9 +1007,26 @@ void retro_run() update_geometry(); height = PPU.ScreenHeight; } + + int result = -1; + bool okay = environ_cb(RETRO_ENVIRONMENT_GET_AUDIO_VIDEO_ENABLE, &result); + if (okay) + { + bool audioEnabled = 0 != (result & 2); + bool videoEnabled = 0 != (result & 1); + IPPU.RenderThisFrame = videoEnabled; + S9xSetSoundMute(!audioEnabled); + } + else + { + IPPU.RenderThisFrame = true; + S9xSetSoundMute(false); + } + poll_cb(); report_buttons(); S9xMainLoop(); + S9xAudioCallback(NULL); } void retro_deinit() @@ -917,6 +1066,9 @@ void* retro_get_memory_data(unsigned type) case RETRO_MEMORY_VIDEO_RAM: data = Memory.VRAM; break; + //case RETRO_MEMORY_ROM: + // data = Memory.ROM; + // break; default: data = NULL; break; @@ -948,6 +1100,9 @@ size_t retro_get_memory_size(unsigned type) case RETRO_MEMORY_VIDEO_RAM: size = 64 * 1024; break; + //case RETRO_MEMORY_ROM: + // size = Memory.CalculatedSize; + // break; default: size = 0; break; @@ -973,12 +1128,17 @@ bool retro_unserialize(const void* data, size_t size) { if (S9xUnfreezeGameMem((const uint8_t*)data,size) != SUCCESS) return false; + return true; } bool8 S9xDeinitUpdate(int width, int height) { - if (crop_overscan_mode == OVERSCAN_CROP_ON) + // Apply Chrono Trigger Framehack + if (ChronoTriggerFrameHack && (height > SNES_HEIGHT)) + height = SNES_HEIGHT; + + if (crop_overscan_mode == 1) // enabled { if (height >= SNES_HEIGHT << 1) { @@ -989,7 +1149,7 @@ bool8 S9xDeinitUpdate(int width, int height) height = SNES_HEIGHT; } } - else if (crop_overscan_mode == OVERSCAN_CROP_OFF) + else if (crop_overscan_mode == 2) // disabled { if (height > SNES_HEIGHT_EXTENDED) { @@ -1011,7 +1171,7 @@ bool8 S9xDeinitUpdate(int width, int height) bool8 S9xContinueUpdate(int width, int height) { - return true; + return S9xDeinitUpdate(width, height); } // Dummy functions that should probably be implemented correctly later. @@ -1019,6 +1179,12 @@ void S9xParsePortConfig(ConfigFile&, int) {} void S9xSyncSpeed() {} const char* S9xStringInput(const char* in) { return in; } +#ifdef _WIN32 +#define SLASH '\\' +#else +#define SLASH '/' +#endif + const char* S9xGetFilename(const char* in, s9x_getdirtype type) { static char newpath[2048]; @@ -1028,8 +1194,8 @@ const char* S9xGetFilename(const char* in, s9x_getdirtype type) switch (type) { case ROMFILENAME_DIR: - snprintf(newpath, sizeof(newpath), "%s%c%s%s", - g_rom_dir, SLASH_CHAR, g_basename, in); + sprintf(newpath, "%s%c%s%s", + g_rom_dir, SLASH, g_basename, in); return newpath; default: break; @@ -1060,13 +1226,35 @@ const char* S9xBasename(const char* in) { return in; } bool8 S9xInitUpdate() { return TRUE; } void S9xExtraUsage() {} bool8 S9xOpenSoundDevice() { return TRUE; } -void S9xMessage(int, int, const char*) {} bool S9xPollAxis(unsigned int, short*) { return FALSE; } void S9xSetPalette() {} void S9xParseArg(char**, int&, int) {} void S9xExit() {} bool S9xPollPointer(unsigned int, short*, short*) { return false; } -const char *S9xChooseMovieFilename(unsigned char) { return NULL; } + +void S9xMessage(int type, int, const char* s) +{ + if (!log_cb) return; + + switch (type) + { + case S9X_DEBUG: + log_cb(RETRO_LOG_DEBUG, "%s\n", s); + break; + case S9X_WARNING: + log_cb(RETRO_LOG_WARN, "%s\n", s); + break; + case S9X_INFO: + log_cb(RETRO_LOG_INFO, "%s\n", s); + break; + case S9X_ERROR: + log_cb(RETRO_LOG_ERROR, "%s\n", s); + break; + default: + log_cb(RETRO_LOG_DEBUG, "%s\n", s); + break; + } +} bool8 S9xOpenSnapshotFile(const char* filepath, bool8 read_only, STREAM *file) { diff --git a/libretro/libretro.def b/libretro/libretro.def new file mode 100644 index 00000000..77094e74 --- /dev/null +++ b/libretro/libretro.def @@ -0,0 +1,39 @@ +LIBRARY libretro + +EXPORTS + +retro_api_version + +retro_get_system_info +retro_get_system_av_info + +retro_set_video_refresh +retro_set_audio_sample +retro_set_audio_sample_batch +retro_set_input_poll +retro_set_input_state + +retro_set_environment + +retro_set_controller_port_device + +retro_init +retro_deinit + +retro_reset +retro_run + +retro_serialize_size +retro_serialize +retro_unserialize + +retro_cheat_reset +retro_cheat_set + +retro_load_game +retro_unload_game +retro_load_game_special + +retro_get_region +retro_get_memory_data +retro_get_memory_size \ No newline at end of file diff --git a/libretro/libretro.h b/libretro/libretro.h old mode 100755 new mode 100644 index 42aa7b52..e02741e7 --- a/libretro/libretro.h +++ b/libretro/libretro.h @@ -1,4 +1,4 @@ -/* Copyright (C) 2010-2016 The RetroArch team +/* Copyright (C) 2010-2017 The RetroArch team * * --------------------------------------------------------------------------------------- * The following license statement only applies to this libretro API header (libretro.h). @@ -23,7 +23,7 @@ #ifndef LIBRETRO_H__ #define LIBRETRO_H__ -#include +#include #include #include @@ -77,7 +77,7 @@ extern "C" { # endif #endif -/* Used for checking API/ABI mismatches that can break libretro +/* Used for checking API/ABI mismatches that can break libretro * implementations. * It is not incremented for compatible changes to the API. */ @@ -87,13 +87,13 @@ extern "C" { * Libretro's fundamental device abstractions. * * Libretro's input system consists of some standardized device types, - * such as a joypad (with/without analog), mouse, keyboard, lightgun + * such as a joypad (with/without analog), mouse, keyboard, lightgun * and a pointer. * - * The functionality of these devices are fixed, and individual cores + * The functionality of these devices are fixed, and individual cores * map their own concept of a controller to libretro's abstractions. - * This makes it possible for frontends to map the abstract types to a - * real input device, and not having to worry about binding input + * This makes it possible for frontends to map the abstract types to a + * real input device, and not having to worry about binding input * correctly to arbitrary controller layouts. */ @@ -104,43 +104,50 @@ extern "C" { /* Input disabled. */ #define RETRO_DEVICE_NONE 0 -/* The JOYPAD is called RetroPad. It is essentially a Super Nintendo - * controller, but with additional L2/R2/L3/R3 buttons, similar to a +/* The JOYPAD is called RetroPad. It is essentially a Super Nintendo + * controller, but with additional L2/R2/L3/R3 buttons, similar to a * PS1 DualShock. */ #define RETRO_DEVICE_JOYPAD 1 /* The mouse is a simple mouse, similar to Super Nintendo's mouse. * X and Y coordinates are reported relatively to last poll (poll callback). - * It is up to the libretro implementation to keep track of where the mouse + * It is up to the libretro implementation to keep track of where the mouse * pointer is supposed to be on the screen. - * The frontend must make sure not to interfere with its own hardware + * The frontend must make sure not to interfere with its own hardware * mouse pointer. */ #define RETRO_DEVICE_MOUSE 2 /* KEYBOARD device lets one poll for raw key pressed. - * It is poll based, so input callback will return with the current + * It is poll based, so input callback will return with the current * pressed state. * For event/text based keyboard input, see * RETRO_ENVIRONMENT_SET_KEYBOARD_CALLBACK. */ #define RETRO_DEVICE_KEYBOARD 3 -/* Lightgun X/Y coordinates are reported relatively to last poll, - * similar to mouse. */ +/* LIGHTGUN device is similar to Guncon-2 for PlayStation 2. + * It reports X/Y coordinates in screen space (similar to the pointer) + * in the range [-0x8000, 0x7fff] in both axes, with zero being center. + * As well as reporting on/off screen state. It features a trigger, + * start/select buttons, auxiliary action buttons and a + * directional pad. A forced off-screen shot can be requested for + * auto-reloading function in some games. + */ #define RETRO_DEVICE_LIGHTGUN 4 /* The ANALOG device is an extension to JOYPAD (RetroPad). - * Similar to DualShock it adds two analog sticks. - * This is treated as a separate device type as it returns values in the - * full analog range of [-0x8000, 0x7fff]. Positive X axis is right. - * Positive Y axis is down. - * Only use ANALOG type when polling for analog values of the axes. + * Similar to DualShock2 it adds two analog sticks and all buttons can + * be analog. This is treated as a separate device type as it returns + * axis values in the full analog range of [-0x8000, 0x7fff]. + * Positive X axis is right. Positive Y axis is down. + * Buttons are returned in the range [0, 0x7fff]. + * Only use ANALOG type when polling for analog values. */ #define RETRO_DEVICE_ANALOG 5 /* Abstracts the concept of a pointing mechanism, e.g. touch. - * This allows libretro to query in absolute coordinates where on the + * This allows libretro to query in absolute coordinates where on the * screen a mouse (or something similar) is being placed. * For a touch centric device, coordinates reported are the coordinates * of the press. @@ -148,33 +155,34 @@ extern "C" { * Coordinates in X and Y are reported as: * [-0x7fff, 0x7fff]: -0x7fff corresponds to the far left/top of the screen, * and 0x7fff corresponds to the far right/bottom of the screen. - * The "screen" is here defined as area that is passed to the frontend and + * The "screen" is here defined as area that is passed to the frontend and * later displayed on the monitor. * * The frontend is free to scale/resize this screen as it sees fit, however, - * (X, Y) = (-0x7fff, -0x7fff) will correspond to the top-left pixel of the + * (X, Y) = (-0x7fff, -0x7fff) will correspond to the top-left pixel of the * game image, etc. * - * To check if the pointer coordinates are valid (e.g. a touch display + * To check if the pointer coordinates are valid (e.g. a touch display * actually being touched), PRESSED returns 1 or 0. * - * If using a mouse on a desktop, PRESSED will usually correspond to the + * If using a mouse on a desktop, PRESSED will usually correspond to the * left mouse button, but this is a frontend decision. * PRESSED will only return 1 if the pointer is inside the game screen. * - * For multi-touch, the index variable can be used to successively query + * For multi-touch, the index variable can be used to successively query * more presses. * If index = 0 returns true for _PRESSED, coordinates can be extracted - * with _X, _Y for index = 0. One can then query _PRESSED, _X, _Y with + * with _X, _Y for index = 0. One can then query _PRESSED, _X, _Y with * index = 1, and so on. - * Eventually _PRESSED will return false for an index. No further presses + * Eventually _PRESSED will return false for an index. No further presses * are registered at this point. */ #define RETRO_DEVICE_POINTER 6 /* Buttons for the RetroPad (JOYPAD). - * The placement of these is equivalent to placements on the + * The placement of these is equivalent to placements on the * Super Nintendo controller. - * L2/R2/L3/R3 buttons correspond to the PS1 DualShock. */ + * L2/R2/L3/R3 buttons correspond to the PS1 DualShock. + * Also used as id values for RETRO_DEVICE_INDEX_ANALOG_BUTTON */ #define RETRO_DEVICE_ID_JOYPAD_B 0 #define RETRO_DEVICE_ID_JOYPAD_Y 1 #define RETRO_DEVICE_ID_JOYPAD_SELECT 2 @@ -193,10 +201,11 @@ extern "C" { #define RETRO_DEVICE_ID_JOYPAD_R3 15 /* Index / Id values for ANALOG device. */ -#define RETRO_DEVICE_INDEX_ANALOG_LEFT 0 -#define RETRO_DEVICE_INDEX_ANALOG_RIGHT 1 -#define RETRO_DEVICE_ID_ANALOG_X 0 -#define RETRO_DEVICE_ID_ANALOG_Y 1 +#define RETRO_DEVICE_INDEX_ANALOG_LEFT 0 +#define RETRO_DEVICE_INDEX_ANALOG_RIGHT 1 +#define RETRO_DEVICE_INDEX_ANALOG_BUTTON 2 +#define RETRO_DEVICE_ID_ANALOG_X 0 +#define RETRO_DEVICE_ID_ANALOG_Y 1 /* Id values for MOUSE. */ #define RETRO_DEVICE_ID_MOUSE_X 0 @@ -208,15 +217,30 @@ extern "C" { #define RETRO_DEVICE_ID_MOUSE_MIDDLE 6 #define RETRO_DEVICE_ID_MOUSE_HORIZ_WHEELUP 7 #define RETRO_DEVICE_ID_MOUSE_HORIZ_WHEELDOWN 8 +#define RETRO_DEVICE_ID_MOUSE_BUTTON_4 9 +#define RETRO_DEVICE_ID_MOUSE_BUTTON_5 10 -/* Id values for LIGHTGUN types. */ -#define RETRO_DEVICE_ID_LIGHTGUN_X 0 -#define RETRO_DEVICE_ID_LIGHTGUN_Y 1 -#define RETRO_DEVICE_ID_LIGHTGUN_TRIGGER 2 -#define RETRO_DEVICE_ID_LIGHTGUN_CURSOR 3 -#define RETRO_DEVICE_ID_LIGHTGUN_TURBO 4 -#define RETRO_DEVICE_ID_LIGHTGUN_PAUSE 5 -#define RETRO_DEVICE_ID_LIGHTGUN_START 6 +/* Id values for LIGHTGUN. */ +#define RETRO_DEVICE_ID_LIGHTGUN_SCREEN_X 13 /*Absolute Position*/ +#define RETRO_DEVICE_ID_LIGHTGUN_SCREEN_Y 14 /*Absolute*/ +#define RETRO_DEVICE_ID_LIGHTGUN_IS_OFFSCREEN 15 /*Status Check*/ +#define RETRO_DEVICE_ID_LIGHTGUN_TRIGGER 2 +#define RETRO_DEVICE_ID_LIGHTGUN_RELOAD 16 /*Forced off-screen shot*/ +#define RETRO_DEVICE_ID_LIGHTGUN_AUX_A 3 +#define RETRO_DEVICE_ID_LIGHTGUN_AUX_B 4 +#define RETRO_DEVICE_ID_LIGHTGUN_START 6 +#define RETRO_DEVICE_ID_LIGHTGUN_SELECT 7 +#define RETRO_DEVICE_ID_LIGHTGUN_AUX_C 8 +#define RETRO_DEVICE_ID_LIGHTGUN_DPAD_UP 9 +#define RETRO_DEVICE_ID_LIGHTGUN_DPAD_DOWN 10 +#define RETRO_DEVICE_ID_LIGHTGUN_DPAD_LEFT 11 +#define RETRO_DEVICE_ID_LIGHTGUN_DPAD_RIGHT 12 +/* deprecated */ +#define RETRO_DEVICE_ID_LIGHTGUN_X 0 /*Relative Position*/ +#define RETRO_DEVICE_ID_LIGHTGUN_Y 1 /*Relative*/ +#define RETRO_DEVICE_ID_LIGHTGUN_CURSOR 3 /*Use Aux:A*/ +#define RETRO_DEVICE_ID_LIGHTGUN_TURBO 4 /*Use Aux:B*/ +#define RETRO_DEVICE_ID_LIGHTGUN_PAUSE 5 /*Use Start*/ /* Id values for POINTER. */ #define RETRO_DEVICE_ID_POINTER_X 0 @@ -230,28 +254,30 @@ extern "C" { /* Id values for LANGUAGE */ enum retro_language { - RETRO_LANGUAGE_ENGLISH = 0, - RETRO_LANGUAGE_JAPANESE = 1, - RETRO_LANGUAGE_FRENCH = 2, - RETRO_LANGUAGE_SPANISH = 3, - RETRO_LANGUAGE_GERMAN = 4, - RETRO_LANGUAGE_ITALIAN = 5, - RETRO_LANGUAGE_DUTCH = 6, - RETRO_LANGUAGE_PORTUGUESE = 7, - RETRO_LANGUAGE_RUSSIAN = 8, - RETRO_LANGUAGE_KOREAN = 9, - RETRO_LANGUAGE_CHINESE_TRADITIONAL = 10, - RETRO_LANGUAGE_CHINESE_SIMPLIFIED = 11, - RETRO_LANGUAGE_ESPERANTO = 12, - RETRO_LANGUAGE_POLISH = 13, + RETRO_LANGUAGE_ENGLISH = 0, + RETRO_LANGUAGE_JAPANESE = 1, + RETRO_LANGUAGE_FRENCH = 2, + RETRO_LANGUAGE_SPANISH = 3, + RETRO_LANGUAGE_GERMAN = 4, + RETRO_LANGUAGE_ITALIAN = 5, + RETRO_LANGUAGE_DUTCH = 6, + RETRO_LANGUAGE_PORTUGUESE_BRAZIL = 7, + RETRO_LANGUAGE_PORTUGUESE_PORTUGAL = 8, + RETRO_LANGUAGE_RUSSIAN = 9, + RETRO_LANGUAGE_KOREAN = 10, + RETRO_LANGUAGE_CHINESE_TRADITIONAL = 11, + RETRO_LANGUAGE_CHINESE_SIMPLIFIED = 12, + RETRO_LANGUAGE_ESPERANTO = 13, + RETRO_LANGUAGE_POLISH = 14, + RETRO_LANGUAGE_VIETNAMESE = 15, RETRO_LANGUAGE_LAST, /* Ensure sizeof(enum) == sizeof(int) */ - RETRO_LANGUAGE_DUMMY = INT_MAX + RETRO_LANGUAGE_DUMMY = INT_MAX }; /* Passed to retro_get_memory_data/size(). - * If the memory type doesn't apply to the + * If the memory type doesn't apply to the * implementation NULL/0 can be returned. */ #define RETRO_MEMORY_MASK 0xff @@ -441,7 +467,7 @@ enum retro_mod RETROKMOD_DUMMY = INT_MAX /* Ensure sizeof(enum) == sizeof(int) */ }; -/* If set, this call is not part of the public libretro API yet. It can +/* If set, this call is not part of the public libretro API yet. It can * change or be removed at any time. */ #define RETRO_ENVIRONMENT_EXPERIMENTAL 0x10000 /* Environment callback to be used internally in frontend. */ @@ -451,11 +477,11 @@ enum retro_mod #define RETRO_ENVIRONMENT_SET_ROTATION 1 /* const unsigned * -- * Sets screen rotation of graphics. * Is only implemented if rotation can be accelerated by hardware. - * Valid values are 0, 1, 2, 3, which rotates screen by 0, 90, 180, + * Valid values are 0, 1, 2, 3, which rotates screen by 0, 90, 180, * 270 degrees counter-clockwise respectively. */ #define RETRO_ENVIRONMENT_GET_OVERSCAN 2 /* bool * -- - * Boolean value whether or not the implementation should use overscan, + * Boolean value whether or not the implementation should use overscan, * or crop away overscan. */ #define RETRO_ENVIRONMENT_GET_CAN_DUPE 3 /* bool * -- @@ -463,15 +489,15 @@ enum retro_mod * passing NULL to video frame callback. */ - /* Environ 4, 5 are no longer supported (GET_VARIABLE / SET_VARIABLES), + /* Environ 4, 5 are no longer supported (GET_VARIABLE / SET_VARIABLES), * and reserved to avoid possible ABI clash. */ #define RETRO_ENVIRONMENT_SET_MESSAGE 6 /* const struct retro_message * -- - * Sets a message to be displayed in implementation-specific manner + * Sets a message to be displayed in implementation-specific manner * for a certain amount of 'frames'. - * Should not be used for trivial messages, which should simply be - * logged via RETRO_ENVIRONMENT_GET_LOG_INTERFACE (or as a + * Should not be used for trivial messages, which should simply be + * logged via RETRO_ENVIRONMENT_GET_LOG_INTERFACE (or as a * fallback, stderr). */ #define RETRO_ENVIRONMENT_SHUTDOWN 7 /* N/A (NULL) -- @@ -499,15 +525,15 @@ enum retro_mod #define RETRO_ENVIRONMENT_GET_SYSTEM_DIRECTORY 9 /* const char ** -- * Returns the "system" directory of the frontend. - * This directory can be used to store system specific + * This directory can be used to store system specific * content such as BIOSes, configuration data, etc. * The returned value can be NULL. * If so, no such directory is defined, * and it's up to the implementation to find a suitable directory. * - * NOTE: Some cores used this folder also for "save" data such as + * NOTE: Some cores used this folder also for "save" data such as * memory cards, etc, for lack of a better place to put it. - * This is now discouraged, and if possible, cores should try to + * This is now discouraged, and if possible, cores should try to * use the new GET_SAVE_DIRECTORY. */ #define RETRO_ENVIRONMENT_SET_PIXEL_FORMAT 10 @@ -515,19 +541,19 @@ enum retro_mod * Sets the internal pixel format used by the implementation. * The default pixel format is RETRO_PIXEL_FORMAT_0RGB1555. * This pixel format however, is deprecated (see enum retro_pixel_format). - * If the call returns false, the frontend does not support this pixel + * If the call returns false, the frontend does not support this pixel * format. * - * This function should be called inside retro_load_game() or + * This function should be called inside retro_load_game() or * retro_get_system_av_info(). */ #define RETRO_ENVIRONMENT_SET_INPUT_DESCRIPTORS 11 /* const struct retro_input_descriptor * -- * Sets an array of retro_input_descriptors. * It is up to the frontend to present this in a usable way. - * The array is terminated by retro_input_descriptor::description + * The array is terminated by retro_input_descriptor::description * being set to NULL. - * This function can be called at any time, but it is recommended + * This function can be called at any time, but it is recommended * to call it as early as possible. */ #define RETRO_ENVIRONMENT_SET_KEYBOARD_CALLBACK 12 @@ -536,52 +562,52 @@ enum retro_mod */ #define RETRO_ENVIRONMENT_SET_DISK_CONTROL_INTERFACE 13 /* const struct retro_disk_control_callback * -- - * Sets an interface which frontend can use to eject and insert + * Sets an interface which frontend can use to eject and insert * disk images. - * This is used for games which consist of multiple images and + * This is used for games which consist of multiple images and * must be manually swapped out by the user (e.g. PSX). */ #define RETRO_ENVIRONMENT_SET_HW_RENDER 14 /* struct retro_hw_render_callback * -- - * Sets an interface to let a libretro core render with + * Sets an interface to let a libretro core render with * hardware acceleration. * Should be called in retro_load_game(). - * If successful, libretro cores will be able to render to a + * If successful, libretro cores will be able to render to a * frontend-provided framebuffer. - * The size of this framebuffer will be at least as large as + * The size of this framebuffer will be at least as large as * max_width/max_height provided in get_av_info(). - * If HW rendering is used, pass only RETRO_HW_FRAME_BUFFER_VALID or + * If HW rendering is used, pass only RETRO_HW_FRAME_BUFFER_VALID or * NULL to retro_video_refresh_t. */ #define RETRO_ENVIRONMENT_GET_VARIABLE 15 /* struct retro_variable * -- * Interface to acquire user-defined information from environment * that cannot feasibly be supported in a multi-system way. - * 'key' should be set to a key which has already been set by + * 'key' should be set to a key which has already been set by * SET_VARIABLES. * 'data' will be set to a value or NULL. */ #define RETRO_ENVIRONMENT_SET_VARIABLES 16 /* const struct retro_variable * -- * Allows an implementation to signal the environment - * which variables it might want to check for later using + * which variables it might want to check for later using * GET_VARIABLE. - * This allows the frontend to present these variables to + * This allows the frontend to present these variables to * a user dynamically. - * This should be called as early as possible (ideally in + * This should be called as early as possible (ideally in * retro_set_environment). * - * 'data' points to an array of retro_variable structs + * 'data' points to an array of retro_variable structs * terminated by a { NULL, NULL } element. - * retro_variable::key should be namespaced to not collide - * with other implementations' keys. E.g. A core called + * retro_variable::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_variable::value should contain a human readable - * description of the key as well as a '|' delimited list + * retro_variable::value should contain a human readable + * description of the key as well as a '|' delimited list * of expected values. * - * The number of possible options should be very limited, - * i.e. it should be feasible to cycle through options + * The number of possible options should be very limited, + * i.e. it should be feasible to cycle through options * without a keyboard. * * First entry should be treated as a default. @@ -589,11 +615,11 @@ enum retro_mod * Example entry: * { "foo_option", "Speed hack coprocessor X; false|true" } * - * Text before first ';' is description. This ';' must be - * followed by a space, and followed by a list of possible + * Text before first ';' is description. This ';' must be + * followed by a space, and followed by a list of possible * values split up with '|'. * - * Only strings are operated on. The possible values will + * Only strings are operated on. The possible values will * generally be displayed and stored as-is by the frontend. */ #define RETRO_ENVIRONMENT_GET_VARIABLE_UPDATE 17 @@ -604,72 +630,72 @@ enum retro_mod */ #define RETRO_ENVIRONMENT_SET_SUPPORT_NO_GAME 18 /* const bool * -- - * If true, the libretro implementation supports calls to + * If true, the libretro implementation supports calls to * retro_load_game() with NULL as argument. * Used by cores which can run without particular game data. * This should be called within retro_set_environment() only. */ #define RETRO_ENVIRONMENT_GET_LIBRETRO_PATH 19 /* const char ** -- - * Retrieves the absolute path from where this libretro + * Retrieves the absolute path from where this libretro * implementation was loaded. - * NULL is returned if the libretro was loaded statically - * (i.e. linked statically to frontend), or if the path cannot be + * NULL is returned if the libretro was loaded statically + * (i.e. linked statically to frontend), or if the path cannot be * determined. - * Mostly useful in cooperation with SET_SUPPORT_NO_GAME as assets can + * Mostly useful in cooperation with SET_SUPPORT_NO_GAME as assets can * be loaded without ugly hacks. */ - - /* Environment 20 was an obsolete version of SET_AUDIO_CALLBACK. + + /* Environment 20 was an obsolete version of SET_AUDIO_CALLBACK. * It was not used by any known core at the time, * and was removed from the API. */ #define RETRO_ENVIRONMENT_SET_AUDIO_CALLBACK 22 /* const struct retro_audio_callback * -- - * Sets an interface which is used to notify a libretro core about audio + * Sets an interface which is used to notify a libretro core about audio * being available for writing. - * The callback can be called from any thread, so a core using this must + * The callback can be called from any thread, so a core using this must * have a thread safe audio implementation. - * It is intended for games where audio and video are completely + * It is intended for games where audio and video are completely * asynchronous and audio can be generated on the fly. - * This interface is not recommended for use with emulators which have + * This interface is not recommended for use with emulators which have * highly synchronous audio. * - * The callback only notifies about writability; the libretro core still + * The callback only notifies about writability; the libretro core still * has to call the normal audio callbacks - * to write audio. The audio callbacks must be called from within the + * to write audio. The audio callbacks must be called from within the * notification callback. * The amount of audio data to write is up to the implementation. * Generally, the audio callback will be called continously in a loop. * - * Due to thread safety guarantees and lack of sync between audio and - * video, a frontend can selectively disallow this interface based on - * internal configuration. A core using this interface must also + * Due to thread safety guarantees and lack of sync between audio and + * video, a frontend can selectively disallow this interface based on + * internal configuration. A core using this interface must also * implement the "normal" audio interface. * - * A libretro core using SET_AUDIO_CALLBACK should also make use of + * A libretro core using SET_AUDIO_CALLBACK should also make use of * SET_FRAME_TIME_CALLBACK. */ #define RETRO_ENVIRONMENT_SET_FRAME_TIME_CALLBACK 21 /* const struct retro_frame_time_callback * -- - * Lets the core know how much time has passed since last + * Lets the core know how much time has passed since last * invocation of retro_run(). - * The frontend can tamper with the timing to fake fast-forward, + * The frontend can tamper with the timing to fake fast-forward, * slow-motion, frame stepping, etc. - * In this case the delta time will use the reference value + * In this case the delta time will use the reference value * in frame_time_callback.. */ #define RETRO_ENVIRONMENT_GET_RUMBLE_INTERFACE 23 /* struct retro_rumble_interface * -- - * Gets an interface which is used by a libretro core to set + * Gets an interface which is used by a libretro core to set * state of rumble motors in controllers. - * A strong and weak motor is supported, and they can be + * A strong and weak motor is supported, and they can be * controlled indepedently. */ #define RETRO_ENVIRONMENT_GET_INPUT_DEVICE_CAPABILITIES 24 /* uint64_t * -- - * Gets a bitmask telling which device type are expected to be + * Gets a bitmask telling which device type are expected to be * handled properly in a call to retro_input_state_t. - * Devices which are not handled or recognized always return + * Devices which are not handled or recognized always return * 0 in retro_input_state_t. * Example bitmask: caps = (1 << RETRO_DEVICE_JOYPAD) | (1 << RETRO_DEVICE_ANALOG). * Should only be called in retro_run(). @@ -678,56 +704,56 @@ enum retro_mod /* struct retro_sensor_interface * -- * Gets access to the sensor interface. * The purpose of this interface is to allow - * setting state related to sensors such as polling rate, + * setting state related to sensors such as polling rate, * enabling/disable it entirely, etc. - * Reading sensor state is done via the normal + * Reading sensor state is done via the normal * input_state_callback API. */ #define RETRO_ENVIRONMENT_GET_CAMERA_INTERFACE (26 | RETRO_ENVIRONMENT_EXPERIMENTAL) /* struct retro_camera_callback * -- * Gets an interface to a video camera driver. - * A libretro core can use this interface to get access to a + * A libretro core can use this interface to get access to a * video camera. - * New video frames are delivered in a callback in same + * New video frames are delivered in a callback in same * thread as retro_run(). * * GET_CAMERA_INTERFACE should be called in retro_load_game(). * - * Depending on the camera implementation used, camera frames + * Depending on the camera implementation used, camera frames * will be delivered as a raw framebuffer, * or as an OpenGL texture directly. * - * The core has to tell the frontend here which types of + * The core has to tell the frontend here which types of * buffers can be handled properly. - * An OpenGL texture can only be handled when using a + * An OpenGL texture can only be handled when using a * libretro GL core (SET_HW_RENDER). - * It is recommended to use a libretro GL core when + * It is recommended to use a libretro GL core when * using camera interface. * - * The camera is not started automatically. The retrieved start/stop + * The camera is not started automatically. The retrieved start/stop * functions must be used to explicitly * start and stop the camera driver. */ #define RETRO_ENVIRONMENT_GET_LOG_INTERFACE 27 /* struct retro_log_callback * -- - * Gets an interface for logging. This is useful for + * Gets an interface for logging. This is useful for * logging in a cross-platform way - * as certain platforms cannot use use stderr for logging. + * as certain platforms cannot use stderr for logging. * It also allows the frontend to * show logging information in a more suitable way. - * If this interface is not used, libretro cores should + * If this interface is not used, libretro cores should * log to stderr as desired. */ #define RETRO_ENVIRONMENT_GET_PERF_INTERFACE 28 /* struct retro_perf_callback * -- - * Gets an interface for performance counters. This is useful - * for performance logging in a cross-platform way and for detecting + * Gets an interface for performance counters. This is useful + * for performance logging in a cross-platform way and for detecting * architecture-specific features, such as SIMD support. */ #define RETRO_ENVIRONMENT_GET_LOCATION_INTERFACE 29 /* struct retro_location_callback * -- * Gets access to the location interface. - * The purpose of this interface is to be able to retrieve + * The purpose of this interface is to be able to retrieve * location-based information from the host device, * such as current latitude / longitude. */ @@ -735,7 +761,7 @@ enum retro_mod #define RETRO_ENVIRONMENT_GET_CORE_ASSETS_DIRECTORY 30 /* const char ** -- * Returns the "core assets" directory of the frontend. - * This directory can be used to store specific assets that the + * This directory can be used to store specific assets that the * core relies upon, such as art assets, * input data, etc etc. * The returned value can be NULL. @@ -745,75 +771,75 @@ enum retro_mod #define RETRO_ENVIRONMENT_GET_SAVE_DIRECTORY 31 /* const char ** -- * Returns the "save" directory of the frontend. - * This directory can be used to store SRAM, memory cards, + * This directory can be used to store SRAM, memory cards, * high scores, etc, if the libretro core * cannot use the regular memory interface (retro_get_memory_data()). * - * NOTE: libretro cores used to check GET_SYSTEM_DIRECTORY for + * NOTE: libretro cores used to check GET_SYSTEM_DIRECTORY for * similar things before. - * They should still check GET_SYSTEM_DIRECTORY if they want to + * They should still check GET_SYSTEM_DIRECTORY if they want to * be backwards compatible. - * The path here can be NULL. It should only be non-NULL if the + * The path here can be NULL. It should only be non-NULL if the * frontend user has set a specific save path. */ #define RETRO_ENVIRONMENT_SET_SYSTEM_AV_INFO 32 /* const struct retro_system_av_info * -- - * Sets a new av_info structure. This can only be called from + * Sets a new av_info structure. This can only be called from * within retro_run(). - * This should *only* be used if the core is completely altering the + * This should *only* be used if the core is completely altering the * internal resolutions, aspect ratios, timings, sampling rate, etc. - * Calling this can require a full reinitialization of video/audio + * Calling this can require a full reinitialization of video/audio * drivers in the frontend, * - * so it is important to call it very sparingly, and usually only with + * so it is important to call it very sparingly, and usually only with * the users explicit consent. - * An eventual driver reinitialize will happen so that video and + * An eventual driver reinitialize will happen so that video and * audio callbacks - * happening after this call within the same retro_run() call will + * happening after this call within the same retro_run() call will * target the newly initialized driver. * - * This callback makes it possible to support configurable resolutions + * This callback makes it possible to support configurable resolutions * in games, which can be useful to * avoid setting the "worst case" in max_width/max_height. * - * ***HIGHLY RECOMMENDED*** Do not call this callback every time + * ***HIGHLY RECOMMENDED*** Do not call this callback every time * resolution changes in an emulator core if it's - * expected to be a temporary change, for the reasons of possible + * expected to be a temporary change, for the reasons of possible * driver reinitialization. - * This call is not a free pass for not trying to provide - * correct values in retro_get_system_av_info(). If you need to change - * things like aspect ratio or nominal width/height, - * use RETRO_ENVIRONMENT_SET_GEOMETRY, which is a softer variant + * This call is not a free pass for not trying to provide + * correct values in retro_get_system_av_info(). If you need to change + * things like aspect ratio or nominal width/height, + * use RETRO_ENVIRONMENT_SET_GEOMETRY, which is a softer variant * of SET_SYSTEM_AV_INFO. * - * If this returns false, the frontend does not acknowledge a + * If this returns false, the frontend does not acknowledge a * changed av_info struct. */ #define RETRO_ENVIRONMENT_SET_PROC_ADDRESS_CALLBACK 33 /* const struct retro_get_proc_address_interface * -- - * Allows a libretro core to announce support for the + * Allows a libretro core to announce support for the * get_proc_address() interface. - * This interface allows for a standard way to extend libretro where + * This interface allows for a standard way to extend libretro where * use of environment calls are too indirect, * e.g. for cases where the frontend wants to call directly into the core. * - * If a core wants to expose this interface, SET_PROC_ADDRESS_CALLBACK + * If a core wants to expose this interface, SET_PROC_ADDRESS_CALLBACK * **MUST** be called from within retro_set_environment(). */ #define RETRO_ENVIRONMENT_SET_SUBSYSTEM_INFO 34 /* const struct retro_subsystem_info * -- * This environment call introduces the concept of libretro "subsystems". - * A subsystem is a variant of a libretro core which supports + * A subsystem is a variant of a libretro core which supports * different kinds of games. - * The purpose of this is to support e.g. emulators which might + * The purpose of this is to support e.g. emulators which might * have special needs, e.g. Super Nintendo's Super GameBoy, Sufami Turbo. - * It can also be used to pick among subsystems in an explicit way + * It can also be used to pick among subsystems in an explicit way * if the libretro implementation is a multi-system emulator itself. * * Loading a game via a subsystem is done with retro_load_game_special(), - * and this environment call allows a libretro core to expose which + * and this environment call allows a libretro core to expose which * subsystems are supported for use with retro_load_game_special(). - * A core passes an array of retro_game_special_info which is terminated + * A core passes an array of retro_game_special_info which is terminated * with a zeroed out retro_game_special_info struct. * * If a core wants to use this functionality, SET_SUBSYSTEM_INFO @@ -821,15 +847,15 @@ enum retro_mod */ #define RETRO_ENVIRONMENT_SET_CONTROLLER_INFO 35 /* const struct retro_controller_info * -- - * This environment call lets a libretro core tell the frontend - * which controller types are recognized in calls to + * This environment call lets a libretro core tell the frontend + * which controller types are recognized in calls to * retro_set_controller_port_device(). * * Some emulators such as Super Nintendo - * support multiple lightgun types which must be specifically + * support multiple lightgun types which must be specifically * selected from. - * It is therefore sometimes necessary for a frontend to be able - * to tell the core about a special kind of input device which is + * It is therefore sometimes necessary for a frontend to be able + * to tell the core about a special kind of input device which is * not covered by the libretro input API. * * In order for a frontend to understand the workings of an input device, @@ -837,52 +863,52 @@ enum retro_mod * of the generic device types already defined in the libretro API. * * Which devices are supported can vary per input port. - * The core must pass an array of const struct retro_controller_info which - * is terminated with a blanked out struct. Each element of the struct - * corresponds to an ascending port index to + * The core must pass an array of const struct retro_controller_info which + * is terminated with a blanked out struct. Each element of the struct + * corresponds to an ascending port index to * retro_set_controller_port_device(). - * Even if special device types are set in the libretro core, + * Even if special device types are set in the libretro core, * libretro should only poll input based on the base input device types. */ #define RETRO_ENVIRONMENT_SET_MEMORY_MAPS (36 | RETRO_ENVIRONMENT_EXPERIMENTAL) /* const struct retro_memory_map * -- - * This environment call lets a libretro core tell the frontend + * This environment call lets a libretro core tell the frontend * about the memory maps this core emulates. * This can be used to implement, for example, cheats in a core-agnostic way. * - * Should only be used by emulators; it doesn't make much sense for + * Should only be used by emulators; it doesn't make much sense for * anything else. - * It is recommended to expose all relevant pointers through + * It is recommended to expose all relevant pointers through * retro_get_memory_* as well. * * Can be called from retro_init and retro_load_game. */ #define RETRO_ENVIRONMENT_SET_GEOMETRY 37 /* const struct retro_game_geometry * -- - * This environment call is similar to SET_SYSTEM_AV_INFO for changing - * video parameters, but provides a guarantee that drivers will not be + * This environment call is similar to SET_SYSTEM_AV_INFO for changing + * video parameters, but provides a guarantee that drivers will not be * reinitialized. * This can only be called from within retro_run(). * - * The purpose of this call is to allow a core to alter nominal - * width/heights as well as aspect ratios on-the-fly, which can be + * The purpose of this call is to allow a core to alter nominal + * width/heights as well as aspect ratios on-the-fly, which can be * useful for some emulators to change in run-time. * * max_width/max_height arguments are ignored and cannot be changed - * with this call as this could potentially require a reinitialization or a + * with this call as this could potentially require a reinitialization or a * non-constant time operation. * If max_width/max_height are to be changed, SET_SYSTEM_AV_INFO is required. * - * A frontend must guarantee that this environment call completes in + * A frontend must guarantee that this environment call completes in * constant time. */ -#define RETRO_ENVIRONMENT_GET_USERNAME 38 +#define RETRO_ENVIRONMENT_GET_USERNAME 38 /* const char ** * Returns the specified username of the frontend, if specified by the user. - * This username can be used as a nickname for a core that has online facilities + * This username can be used as a nickname for a core that has online facilities * or any other mode where personalization of the user is desirable. * The returned value can be NULL. - * If this environ callback is used by a core that requires a valid username, + * If this environ callback is used by a core that requires a valid username, * a default username should be specified by the core. */ #define RETRO_ENVIRONMENT_GET_LANGUAGE 39 @@ -921,6 +947,182 @@ enum retro_mod * writeable (and readable). */ +#define RETRO_ENVIRONMENT_SET_HW_SHARED_CONTEXT (44 | RETRO_ENVIRONMENT_EXPERIMENTAL) + /* N/A (null) * -- + * The frontend will try to use a 'shared' hardware context (mostly applicable + * to OpenGL) when a hardware context is being set up. + * + * Returns true if the frontend supports shared hardware contexts and false + * if the frontend does not support shared hardware contexts. + * + * This will do nothing on its own until SET_HW_RENDER env callbacks are + * being used. + */ + +#define RETRO_ENVIRONMENT_GET_VFS_INTERFACE (45 | RETRO_ENVIRONMENT_EXPERIMENTAL) + /* struct retro_vfs_interface_info * -- + * Gets access to the VFS interface. + * VFS presence needs to be queried prior to load_game or any + * get_system/save/other_directory being called to let front end know + * core supports VFS before it starts handing out paths. + * It is recomended to do so in retro_set_environment */ + +#define RETRO_ENVIRONMENT_GET_AUDIO_VIDEO_ENABLE (47 | RETRO_ENVIRONMENT_EXPERIMENTAL) + /* int * -- + * Tells the core if the frontend wants audio or video. + * If disabled, the frontend will discard the audio or video, + * so the core may decide to skip generating a frame or generating audio. + * This is mainly used for increasing performance. + * Bit 0 (value 1): Enable Video + * Bit 1 (value 2): Enable Audio + * Bit 2 (value 4): Use Fast Savestates. + * Bit 3 (value 8): Hard Disable Audio + * Other bits are reserved for future use and will default to zero. + * If video is disabled: + * * The frontend wants the core to not generate any video, + * including presenting frames via hardware acceleration. + * * The frontend's video frame callback will do nothing. + * * After running the frame, the video output of the next frame should be + * no different than if video was enabled, and saving and loading state + * should have no issues. + * If audio is disabled: + * * The frontend wants the core to not generate any audio. + * * The frontend's audio callbacks will do nothing. + * * After running the frame, the audio output of the next frame should be + * no different than if audio was enabled, and saving and loading state + * should have no issues. + * Fast Savestates: + * * Guaranteed to be created by the same binary that will load them. + * * Will not be written to or read from the disk. + * * Suggest that the core assumes loading state will succeed. + * * Suggest that the core updates its memory buffers in-place if possible. + * * Suggest that the core skips clearing memory. + * * Suggest that the core skips resetting the system. + * * Suggest that the core may skip validation steps. + * Hard Disable Audio: + * * Used for a secondary core when running ahead. + * * Indicates that the frontend will never need audio from the core. + * * Suggests that the core may stop synthesizing audio, but this should not + * compromise emulation accuracy. + * * Audio output for the next frame does not matter, and the frontend will + * never need an accurate audio state in the future. + * * State will never be saved when using Hard Disable Audio. + */ + +/* VFS functionality */ + +/* File paths: + * File paths passed as parameters when using this api shall be well formed unix-style, + * using "/" (unquoted forward slash) as directory separator regardless of the platform's native separator. + * Paths shall also include at least one forward slash ("game.bin" is an invalid path, use "./game.bin" instead). + * Other than the directory separator, cores shall not make assumptions about path format: + * "C:/path/game.bin", "http://example.com/game.bin", "#game/game.bin", "./game.bin" (without quotes) are all valid paths. + * Cores may replace the basename or remove path components from the end, and/or add new components; + * however, cores shall not append "./", "../" or multiple consecutive forward slashes ("//") to paths they request to front end. + * The frontend is encouraged to make such paths work as well as it can, but is allowed to give up if the core alters paths too much. + * Frontends are encouraged, but not required, to support native file system paths (modulo replacing the directory separator, if applicable). + * Cores are allowed to try using them, but must remain functional if the front rejects such requests. + * Cores are encouraged to use the libretro-common filestream functions for file I/O, + * as they seamlessly integrate with VFS, deal with directory separator replacement as appropriate + * and provide platform-specific fallbacks in cases where front ends do not support VFS. */ + +/* Opaque file handle + * Introduced in VFS API v1 */ +struct retro_vfs_file_handle; + +/* File open flags + * Introduced in VFS API v1 */ +#define RETRO_VFS_FILE_ACCESS_READ (1 << 0) /* Read only mode */ +#define RETRO_VFS_FILE_ACCESS_WRITE (1 << 1) /* Write only mode, discard contents and overwrites existing file unless RETRO_VFS_FILE_ACCESS_UPDATE is also specified */ +#define RETRO_VFS_FILE_ACCESS_READ_WRITE (RETRO_VFS_FILE_ACCESS_READ | RETRO_VFS_FILE_ACCESS_WRITE) /* Read-write mode, discard contents and overwrites existing file unless RETRO_VFS_FILE_ACCESS_UPDATE is also specified*/ +#define RETRO_VFS_FILE_ACCESS_UPDATE_EXISTING (1 << 2) /* Prevents discarding content of existing files opened for writing */ + +/* These are only hints. The frontend may choose to ignore them. Other than RAM/CPU/etc use, + and how they react to unlikely external interference (for example someone else writing to that file, + or the file's server going down), behavior will not change. */ +#define RETRO_VFS_FILE_ACCESS_HINT_NONE (0) +/* Indicate that the file will be accessed many times. The frontend should aggressively cache everything. */ +#define RETRO_VFS_FILE_ACCESS_HINT_FREQUENT_ACCESS (1 << 0) + +/* Seek positions */ +#define RETRO_VFS_SEEK_POSITION_START 0 +#define RETRO_VFS_SEEK_POSITION_CURRENT 1 +#define RETRO_VFS_SEEK_POSITION_END 2 + +/* Get path from opaque handle. Returns the exact same path passed to file_open when getting the handle + * Introduced in VFS API v1 */ +typedef const char *(RETRO_CALLCONV *retro_vfs_get_path_t)(struct retro_vfs_file_handle *stream); + +/* Open a file for reading or writing. If path points to a directory, this will + * fail. Returns the opaque file handle, or NULL for error. + * Introduced in VFS API v1 */ +typedef struct retro_vfs_file_handle *(RETRO_CALLCONV *retro_vfs_open_t)(const char *path, unsigned mode, unsigned hints); + +/* Close the file and release its resources. Must be called if open_file returns non-NULL. Returns 0 on succes, -1 on failure. + * Whether the call succeeds ot not, the handle passed as parameter becomes invalid and should no longer be used. + * Introduced in VFS API v1 */ +typedef int (RETRO_CALLCONV *retro_vfs_close_t)(struct retro_vfs_file_handle *stream); + +/* Return the size of the file in bytes, or -1 for error. + * Introduced in VFS API v1 */ +typedef int64_t (RETRO_CALLCONV *retro_vfs_size_t)(struct retro_vfs_file_handle *stream); + +/* Get the current read / write position for the file. Returns - 1 for error. + * Introduced in VFS API v1 */ +typedef int64_t (RETRO_CALLCONV *retro_vfs_tell_t)(struct retro_vfs_file_handle *stream); + +/* Set the current read/write position for the file. Returns the new position, -1 for error. + * Introduced in VFS API v1 */ +typedef int64_t (RETRO_CALLCONV *retro_vfs_seek_t)(struct retro_vfs_file_handle *stream, int64_t offset, int seek_position); + +/* Read data from a file. Returns the number of bytes read, or -1 for error. + * Introduced in VFS API v1 */ +typedef int64_t (RETRO_CALLCONV *retro_vfs_read_t)(struct retro_vfs_file_handle *stream, void *s, uint64_t len); + +/* Write data to a file. Returns the number of bytes written, or -1 for error. + * Introduced in VFS API v1 */ +typedef int64_t (RETRO_CALLCONV *retro_vfs_write_t)(struct retro_vfs_file_handle *stream, const void *s, uint64_t len); + +/* Flush pending writes to file, if using buffered IO. Returns 0 on sucess, or -1 on failure. + * Introduced in VFS API v1 */ +typedef int (RETRO_CALLCONV *retro_vfs_flush_t)(struct retro_vfs_file_handle *stream); + +/* Delete the specified file. Returns 0 on success, -1 on failure + * Introduced in VFS API v1 */ +typedef int (RETRO_CALLCONV *retro_vfs_remove_t)(const char *path); + +/* Rename the specified file. Returns 0 on success, -1 on failure + * Introduced in VFS API v1 */ +typedef int (RETRO_CALLCONV *retro_vfs_rename_t)(const char *old_path, const char *new_path); + +struct retro_vfs_interface +{ + retro_vfs_get_path_t get_path; + retro_vfs_open_t open; + retro_vfs_close_t close; + retro_vfs_size_t size; + retro_vfs_tell_t tell; + retro_vfs_seek_t seek; + retro_vfs_read_t read; + retro_vfs_write_t write; + retro_vfs_flush_t flush; + retro_vfs_remove_t remove; + retro_vfs_rename_t rename; +}; + +struct retro_vfs_interface_info +{ + /* Set by core: should this be higher than the version the front end supports, + * front end will return false in the RETRO_ENVIRONMENT_GET_VFS_INTERFACE call + * Introduced in VFS API v1 */ + uint32_t required_interface_version; + + /* Frontend writes interface pointer here. The frontend also sets the actual + * version, must be at least required_interface_version. + * Introduced in VFS API v1 */ + struct retro_vfs_interface *iface; +}; + enum retro_hw_render_interface_type { RETRO_HW_RENDER_INTERFACE_VULKAN = 0, @@ -976,6 +1178,36 @@ struct retro_hw_render_context_negotiation_interface * so it will be used after SET_HW_RENDER, but before the context_reset callback. */ +/* Serialized state is incomplete in some way. Set if serialization is + * usable in typical end-user cases but should not be relied upon to + * implement frame-sensitive frontend features such as netplay or + * rerecording. */ +#define RETRO_SERIALIZATION_QUIRK_INCOMPLETE (1 << 0) +/* The core must spend some time initializing before serialization is + * supported. retro_serialize() will initially fail; retro_unserialize() + * and retro_serialize_size() may or may not work correctly either. */ +#define RETRO_SERIALIZATION_QUIRK_MUST_INITIALIZE (1 << 1) +/* Serialization size may change within a session. */ +#define RETRO_SERIALIZATION_QUIRK_CORE_VARIABLE_SIZE (1 << 2) +/* Set by the frontend to acknowledge that it supports variable-sized + * states. */ +#define RETRO_SERIALIZATION_QUIRK_FRONT_VARIABLE_SIZE (1 << 3) +/* Serialized state can only be loaded during the same session. */ +#define RETRO_SERIALIZATION_QUIRK_SINGLE_SESSION (1 << 4) +/* Serialized state cannot be loaded on an architecture with a different + * endianness from the one it was saved on. */ +#define RETRO_SERIALIZATION_QUIRK_ENDIAN_DEPENDENT (1 << 5) +/* Serialized state cannot be loaded on a different platform from the one it + * was saved on for reasons other than endianness, such as word size + * dependence */ +#define RETRO_SERIALIZATION_QUIRK_PLATFORM_DEPENDENT (1 << 6) + +#define RETRO_ENVIRONMENT_SET_SERIALIZATION_QUIRKS 44 + /* uint64_t * -- + * Sets quirk flags associated with serialization. The frontend will zero any flags it doesn't + * recognize or support. Should be set in either retro_init or retro_load_game, but not both. + */ + #define RETRO_MEMDESC_CONST (1 << 0) /* The frontend will never change this memory area once retro_load_game has returned. */ #define RETRO_MEMDESC_BIGENDIAN (1 << 1) /* The memory area contains big endian data. Default is little endian. */ #define RETRO_MEMDESC_ALIGN_2 (1 << 16) /* All memory access in this area is aligned to their own size, or 2, whichever is smaller. */ @@ -989,56 +1221,56 @@ struct retro_memory_descriptor uint64_t flags; /* Pointer to the start of the relevant ROM or RAM chip. - * It's strongly recommended to use 'offset' if possible, rather than + * It's strongly recommended to use 'offset' if possible, rather than * doing math on the pointer. * - * If the same byte is mapped my multiple descriptors, their descriptors + * If the same byte is mapped my multiple descriptors, their descriptors * must have the same pointer. - * If 'start' does not point to the first byte in the pointer, put the + * If 'start' does not point to the first byte in the pointer, put the * difference in 'offset' instead. * - * May be NULL if there's nothing usable here (e.g. hardware registers and + * May be NULL if there's nothing usable here (e.g. hardware registers and * open bus). No flags should be set if the pointer is NULL. * It's recommended to minimize the number of descriptors if possible, * but not mandatory. */ void *ptr; size_t offset; - /* This is the location in the emulated address space + /* This is the location in the emulated address space * where the mapping starts. */ size_t start; /* Which bits must be same as in 'start' for this mapping to apply. - * The first memory descriptor to claim a certain byte is the one + * The first memory descriptor to claim a certain byte is the one * that applies. * A bit which is set in 'start' must also be set in this. - * Can be zero, in which case each byte is assumed mapped exactly once. + * Can be zero, in which case each byte is assumed mapped exactly once. * In this case, 'len' must be a power of two. */ size_t select; - /* If this is nonzero, the set bits are assumed not connected to the + /* If this is nonzero, the set bits are assumed not connected to the * memory chip's address pins. */ size_t disconnect; /* This one tells the size of the current memory area. - * If, after start+disconnect are applied, the address is higher than + * If, after start+disconnect are applied, the address is higher than * this, the highest bit of the address is cleared. * * If the address is still too high, the next highest bit is cleared. - * Can be zero, in which case it's assumed to be infinite (as limited + * Can be zero, in which case it's assumed to be infinite (as limited * by 'select' and 'disconnect'). */ size_t len; - /* To go from emulated address to physical address, the following + /* To go from emulated address to physical address, the following * order applies: * Subtract 'start', pick off 'disconnect', apply 'len', add 'offset'. */ - /* The address space name must consist of only a-zA-Z0-9_-, + /* The address space name must consist of only a-zA-Z0-9_-, * should be as short as feasible (maximum length is 8 plus the NUL), - * and may not be any other address space plus one or more 0-9A-F + * and may not be any other address space plus one or more 0-9A-F * at the end. - * However, multiple memory descriptors for the same address space is - * allowed, and the address space name can be empty. NULL is treated + * However, multiple memory descriptors for the same address space is + * allowed, and the address space name can be empty. NULL is treated * as empty. * * Address space names are case sensitive, but avoid lowercase if possible. @@ -1052,11 +1284,11 @@ struct retro_memory_descriptor * 'a'+blank - valid ('a' is not in 0-9A-F) * 'a'+'A' - valid (neither is a prefix of each other) * 'AR'+blank - valid ('R' is not in 0-9A-F) - * 'ARB'+blank - valid (the B can't be part of the address either, because + * 'ARB'+blank - valid (the B can't be part of the address either, because * there is no namespace 'AR') - * blank+'B' - not valid, because it's ambigous which address space B1234 + * blank+'B' - not valid, because it's ambigous which address space B1234 * would refer to. - * The length can't be used for that purpose; the frontend may want + * The length can't be used for that purpose; the frontend may want * to append arbitrary data to an address, without a separator. */ const char *addrspace; @@ -1078,32 +1310,32 @@ struct retro_memory_descriptor * the most recent addition and continue on the next bit. * TODO: Can the above be optimized? Is "remove the lowest bit set in both * pointer and 'len'" equivalent? */ - + /* TODO: Some emulators (MAME?) emulate big endian systems by only accessing * the emulated memory in 32-bit chunks, native endian. But that's nothing * compared to Darek Mihocka * (section Emulation 103 - Nearly Free Byte Reversal) - he flips the ENTIRE * RAM backwards! I'll want to represent both of those, via some flags. - * + * * I suspect MAME either didn't think of that idea, or don't want the #ifdef. * Not sure which, nor do I really care. */ - + /* TODO: Some of those flags are unused and/or don't really make sense. Clean * them up. */ }; -/* The frontend may use the largest value of 'start'+'select' in a +/* The frontend may use the largest value of 'start'+'select' in a * certain namespace to infer the size of the address space. * - * If the address space is larger than that, a mapping with .ptr=NULL - * should be at the end of the array, with .select set to all ones for + * If the address space is larger than that, a mapping with .ptr=NULL + * should be at the end of the array, with .select set to all ones for * as long as the address space is big. * * Sample descriptors (minus .ptr, and RETRO_MEMFLAG_ on the flags): * SNES WRAM: * .start=0x7E0000, .len=0x20000 - * (Note that this must be mapped before the ROM in most cases; some of the - * ROM mappers + * (Note that this must be mapped before the ROM in most cases; some of the + * ROM mappers * try to claim $7E0000, or at least $7E8000.) * SNES SPC700 RAM: * .addrspace="S", .len=0x10000 @@ -1112,7 +1344,7 @@ struct retro_memory_descriptor * .flags=MIRROR, .start=0x800000, .select=0xC0E000, .len=0x2000 * SNES WRAM mirrors, alternate equivalent descriptor: * .flags=MIRROR, .select=0x40E000, .disconnect=~0x1FFF - * (Various similar constructions can be created by combining parts of + * (Various similar constructions can be created by combining parts of * the above two.) * SNES LoROM (512KB, mirrored a couple of times): * .flags=CONST, .start=0x008000, .select=0x408000, .disconnect=0x8000, .len=512*1024 @@ -1138,13 +1370,13 @@ struct retro_memory_map struct retro_controller_description { - /* Human-readable description of the controller. Even if using a generic - * input device type, this can be set to the particular device type the + /* Human-readable description of the controller. Even if using a generic + * input device type, this can be set to the particular device type the * core uses. */ const char *desc; - /* Device type passed to retro_set_controller_port_device(). If the device - * type is a sub-class of a generic input device type, use the + /* Device type passed to retro_set_controller_port_device(). If the device + * type is a sub-class of a generic input device type, use the * RETRO_DEVICE_SUBCLASS macro to create an ID. * * E.g. RETRO_DEVICE_SUBCLASS(RETRO_DEVICE_JOYPAD, 1). */ @@ -1162,8 +1394,8 @@ struct retro_subsystem_memory_info /* The extension associated with a memory type, e.g. "psram". */ const char *extension; - /* The memory type for retro_get_memory(). This should be at - * least 0x100 to avoid conflict with standardized + /* The memory type for retro_get_memory(). This should be at + * least 0x100 to avoid conflict with standardized * libretro memory types. */ unsigned type; }; @@ -1182,11 +1414,11 @@ struct retro_subsystem_rom_info /* Same definition as retro_get_system_info(). */ bool block_extract; - /* This is set if the content is required to load a game. + /* This is set if the content is required to load a game. * If this is set to false, a zeroed-out retro_game_info can be passed. */ bool required; - /* Content can have multiple associated persistent + /* Content can have multiple associated persistent * memory types (retro_get_memory()). */ const struct retro_subsystem_memory_info *memory; unsigned num_memory; @@ -1204,17 +1436,17 @@ struct retro_subsystem_info */ const char *ident; - /* Infos for each content file. The first entry is assumed to be the + /* Infos for each content file. The first entry is assumed to be the * "most significant" content for frontend purposes. - * E.g. with Super GameBoy, the first content should be the GameBoy ROM, + * E.g. with Super GameBoy, the first content should be the GameBoy ROM, * as it is the most "significant" content to a user. - * If a frontend creates new file paths based on the content used + * If a frontend creates new file paths based on the content used * (e.g. savestates), it should use the path for the first ROM to do so. */ const struct retro_subsystem_rom_info *roms; /* Number of content files associated with a subsystem. */ unsigned num_roms; - + /* The type passed to retro_load_game_special(). */ unsigned id; }; @@ -1225,13 +1457,13 @@ typedef void (RETRO_CALLCONV *retro_proc_address_t)(void); * (None here so far). * * Get a symbol from a libretro core. - * Cores should only return symbols which are actual + * Cores should only return symbols which are actual * extensions to the libretro API. * - * Frontends should not use this to obtain symbols to standard + * Frontends should not use this to obtain symbols to standard * libretro entry points (static linking or dlsym). * - * The symbol name must be equal to the function name, + * The symbol name must be equal to the function name, * e.g. if void retro_foo(void); exists, the symbol must be called "retro_foo". * The returned function pointer must be cast to the corresponding type. */ @@ -1284,6 +1516,8 @@ struct retro_log_callback #define RETRO_SIMD_VFPV4 (1 << 17) #define RETRO_SIMD_POPCNT (1 << 18) #define RETRO_SIMD_MOVBE (1 << 19) +#define RETRO_SIMD_CMOV (1 << 20) +#define RETRO_SIMD_ASIMD (1 << 21) typedef uint64_t retro_perf_tick_t; typedef int64_t retro_time_t; @@ -1304,7 +1538,7 @@ struct retro_perf_counter typedef retro_time_t (RETRO_CALLCONV *retro_perf_get_time_usec_t)(void); /* A simple counter. Usually nanoseconds, but can also be CPU cycles. - * Can be used directly if desired (when creating a more sophisticated + * Can be used directly if desired (when creating a more sophisticated * performance counter system). * */ typedef retro_perf_tick_t (RETRO_CALLCONV *retro_perf_get_counter_t)(void); @@ -1318,9 +1552,9 @@ typedef uint64_t (RETRO_CALLCONV *retro_get_cpu_features_t)(void); typedef void (RETRO_CALLCONV *retro_perf_log_t)(void); /* Register a performance counter. - * ident field must be set with a discrete value and other values in + * ident field must be set with a discrete value and other values in * retro_perf_counter must be 0. - * Registering can be called multiple times. To avoid calling to + * Registering can be called multiple times. To avoid calling to * frontend redundantly, you can check registered field first. */ typedef void (RETRO_CALLCONV *retro_perf_register_t)(struct retro_perf_counter *counter); @@ -1391,7 +1625,7 @@ enum retro_sensor_action #define RETRO_SENSOR_ACCELEROMETER_Y 1 #define RETRO_SENSOR_ACCELEROMETER_Z 2 -typedef bool (RETRO_CALLCONV *retro_set_sensor_state_t)(unsigned port, +typedef bool (RETRO_CALLCONV *retro_set_sensor_state_t)(unsigned port, enum retro_sensor_action action, unsigned rate); typedef float (RETRO_CALLCONV *retro_sensor_get_input_t)(unsigned port, unsigned id); @@ -1416,7 +1650,7 @@ typedef bool (RETRO_CALLCONV *retro_camera_start_t)(void); /* Stops the camera driver. Can only be called in retro_run(). */ typedef void (RETRO_CALLCONV *retro_camera_stop_t)(void); -/* Callback which signals when the camera driver is initialized +/* Callback which signals when the camera driver is initialized * and/or deinitialized. * retro_camera_start_t can be called in initialized callback. */ @@ -1426,36 +1660,36 @@ typedef void (RETRO_CALLCONV *retro_camera_lifetime_status_t)(void); * Width, height and pitch are similar to retro_video_refresh_t. * First pixel is top-left origin. */ -typedef void (RETRO_CALLCONV *retro_camera_frame_raw_framebuffer_t)(const uint32_t *buffer, +typedef void (RETRO_CALLCONV *retro_camera_frame_raw_framebuffer_t)(const uint32_t *buffer, unsigned width, unsigned height, size_t pitch); /* A callback for when OpenGL textures are used. * * texture_id is a texture owned by camera driver. - * Its state or content should be considered immutable, except for things like + * Its state or content should be considered immutable, except for things like * texture filtering and clamping. * * texture_target is the texture target for the GL texture. - * These can include e.g. GL_TEXTURE_2D, GL_TEXTURE_RECTANGLE, and possibly + * These can include e.g. GL_TEXTURE_2D, GL_TEXTURE_RECTANGLE, and possibly * more depending on extensions. * - * affine points to a packed 3x3 column-major matrix used to apply an affine + * affine points to a packed 3x3 column-major matrix used to apply an affine * transform to texture coordinates. (affine_matrix * vec3(coord_x, coord_y, 1.0)) - * After transform, normalized texture coord (0, 0) should be bottom-left + * After transform, normalized texture coord (0, 0) should be bottom-left * and (1, 1) should be top-right (or (width, height) for RECTANGLE). * - * GL-specific typedefs are avoided here to avoid relying on gl.h in + * GL-specific typedefs are avoided here to avoid relying on gl.h in * the API definition. */ -typedef void (RETRO_CALLCONV *retro_camera_frame_opengl_texture_t)(unsigned texture_id, +typedef void (RETRO_CALLCONV *retro_camera_frame_opengl_texture_t)(unsigned texture_id, unsigned texture_target, const float *affine); struct retro_camera_callback { - /* Set by libretro core. + /* Set by libretro core. * Example bitmask: caps = (1 << RETRO_CAMERA_BUFFER_OPENGL_TEXTURE) | (1 << RETRO_CAMERA_BUFFER_RAW_FRAMEBUFFER). */ - uint64_t caps; + uint64_t caps; /* Desired resolution for camera. Is only used as a hint. */ unsigned width; @@ -1469,22 +1703,22 @@ struct retro_camera_callback retro_camera_frame_raw_framebuffer_t frame_raw_framebuffer; /* Set by libretro core if OpenGL texture callbacks will be used. */ - retro_camera_frame_opengl_texture_t frame_opengl_texture; + retro_camera_frame_opengl_texture_t frame_opengl_texture; - /* Set by libretro core. Called after camera driver is initialized and + /* Set by libretro core. Called after camera driver is initialized and * ready to be started. * Can be NULL, in which this callback is not called. */ retro_camera_lifetime_status_t initialized; - /* Set by libretro core. Called right before camera driver is + /* Set by libretro core. Called right before camera driver is * deinitialized. * Can be NULL, in which this callback is not called. */ retro_camera_lifetime_status_t deinitialized; }; -/* Sets the interval of time and/or distance at which to update/poll +/* Sets the interval of time and/or distance at which to update/poll * location-based data. * * To ensure compatibility with all location-based implementations, @@ -1497,20 +1731,20 @@ typedef void (RETRO_CALLCONV *retro_location_set_interval_t)(unsigned interval_m unsigned interval_distance); /* Start location services. The device will start listening for changes to the - * current location at regular intervals (which are defined with + * current location at regular intervals (which are defined with * retro_location_set_interval_t). */ typedef bool (RETRO_CALLCONV *retro_location_start_t)(void); -/* Stop location services. The device will stop listening for changes +/* Stop location services. The device will stop listening for changes * to the current location. */ typedef void (RETRO_CALLCONV *retro_location_stop_t)(void); -/* Get the position of the current location. Will set parameters to +/* Get the position of the current location. Will set parameters to * 0 if no new location update has happened since the last time. */ typedef bool (RETRO_CALLCONV *retro_location_get_position_t)(double *lat, double *lon, double *horiz_accuracy, double *vert_accuracy); -/* Callback which signals when the location driver is initialized +/* Callback which signals when the location driver is initialized * and/or deinitialized. * retro_location_start_t can be called in initialized callback. */ @@ -1535,14 +1769,14 @@ enum retro_rumble_effect RETRO_RUMBLE_DUMMY = INT_MAX }; -/* Sets rumble state for joypad plugged in port 'port'. +/* Sets rumble state for joypad plugged in port 'port'. * Rumble effects are controlled independently, * and setting e.g. strong rumble does not override weak rumble. * Strength has a range of [0, 0xffff]. * - * Returns true if rumble state request was honored. + * Returns true if rumble state request was honored. * Calling this before first retro_run() is likely to return false. */ -typedef bool (RETRO_CALLCONV *retro_set_rumble_state_t)(unsigned port, +typedef bool (RETRO_CALLCONV *retro_set_rumble_state_t)(unsigned port, enum retro_rumble_effect effect, uint16_t strength); struct retro_rumble_interface @@ -1553,10 +1787,10 @@ struct retro_rumble_interface /* Notifies libretro that audio data should be written. */ typedef void (RETRO_CALLCONV *retro_audio_callback_t)(void); -/* True: Audio driver in frontend is active, and callback is +/* True: Audio driver in frontend is active, and callback is * expected to be called regularily. - * False: Audio driver in frontend is paused or inactive. - * Audio callback will not be called until set_state has been + * False: Audio driver in frontend is paused or inactive. + * Audio callback will not be called until set_state has been * called with true. * Initial state is false (inactive). */ @@ -1568,11 +1802,11 @@ struct retro_audio_callback retro_audio_set_state_callback_t set_state; }; -/* Notifies a libretro core of time spent since last invocation +/* Notifies a libretro core of time spent since last invocation * of retro_run() in microseconds. * * It will be called right before retro_run() every frame. - * The frontend can tamper with timing to support cases like + * The frontend can tamper with timing to support cases like * fast-forward, slow-motion and framestepping. * * In those scenarios the reference frame time value will be used. */ @@ -1581,8 +1815,8 @@ typedef void (RETRO_CALLCONV *retro_frame_time_callback_t)(retro_usec_t usec); struct retro_frame_time_callback { retro_frame_time_callback_t callback; - /* Represents the time of one frame. It is computed as - * 1000000 / fps, but the implementation will resolve the + /* Represents the time of one frame. It is computed as + * 1000000 / fps, but the implementation will resolve the * rounding to ensure that framestepping, etc is exact. */ retro_usec_t reference; }; @@ -1598,7 +1832,7 @@ struct retro_frame_time_callback * it should implement context_destroy callback. * If called, all GPU resources must be reinitialized. * Usually called when frontend reinits video driver. - * Also called first time video driver is initialized, + * Also called first time video driver is initialized, * allowing libretro core to initialize resources. */ typedef void (RETRO_CALLCONV *retro_hw_context_reset_t)(void); @@ -1615,7 +1849,7 @@ enum retro_hw_context_type { RETRO_HW_CONTEXT_NONE = 0, /* OpenGL 2.x. Driver can choose to use latest compatibility context. */ - RETRO_HW_CONTEXT_OPENGL = 1, + RETRO_HW_CONTEXT_OPENGL = 1, /* OpenGL ES 2.0. */ RETRO_HW_CONTEXT_OPENGLES2 = 2, /* Modern desktop core GL context. Use version_major/ @@ -1641,10 +1875,10 @@ struct retro_hw_render_callback /* Called when a context has been created or when it has been reset. * An OpenGL context is only valid after context_reset() has been called. * - * When context_reset is called, OpenGL resources in the libretro + * When context_reset is called, OpenGL resources in the libretro * implementation are guaranteed to be invalid. * - * It is possible that context_reset is called multiple times during an + * It is possible that context_reset is called multiple times during an * application lifecycle. * If context_reset is called without any notification (context_destroy), * the OpenGL context was lost and resources should just be recreated @@ -1657,7 +1891,8 @@ struct retro_hw_render_callback * be providing preallocated framebuffers. */ retro_hw_get_current_framebuffer_t get_current_framebuffer; - /* Set by frontend. */ + /* Set by frontend. + * Can return all relevant functions, including glClear on Windows. */ retro_hw_get_proc_address_t get_proc_address; /* Set if render buffers should have depth component attached. @@ -1668,48 +1903,48 @@ struct retro_hw_render_callback * TODO: Obsolete. */ bool stencil; - /* If depth and stencil are true, a packed 24/8 buffer will be added. + /* If depth and stencil are true, a packed 24/8 buffer will be added. * Only attaching stencil is invalid and will be ignored. */ - /* Use conventional bottom-left origin convention. If false, + /* Use conventional bottom-left origin convention. If false, * standard libretro top-left origin semantics are used. * TODO: Move to GL specific interface. */ bool bottom_left_origin; - + /* Major version number for core GL context or GLES 3.1+. */ unsigned version_major; /* Minor version number for core GL context or GLES 3.1+. */ unsigned version_minor; - /* If this is true, the frontend will go very far to avoid + /* If this is true, the frontend will go very far to avoid * resetting context in scenarios like toggling fullscreen, etc. * TODO: Obsolete? Maybe frontend should just always assume this ... */ bool cache_context; - /* The reset callback might still be called in extreme situations + /* The reset callback might still be called in extreme situations * such as if the context is lost beyond recovery. * - * For optimal stability, set this to false, and allow context to be + * For optimal stability, set this to false, and allow context to be * reset at any time. */ - - /* A callback to be called before the context is destroyed in a + + /* A callback to be called before the context is destroyed in a * controlled way by the frontend. */ retro_hw_context_reset_t context_destroy; /* OpenGL resources can be deinitialized cleanly at this step. - * context_destroy can be set to NULL, in which resources will + * context_destroy can be set to NULL, in which resources will * just be destroyed without any notification. * - * Even when context_destroy is non-NULL, it is possible that + * Even when context_destroy is non-NULL, it is possible that * context_reset is called without any destroy notification. - * This happens if context is lost by external factors (such as + * This happens if context is lost by external factors (such as * notified by GL_ARB_robustness). * * In this case, the context is assumed to be already dead, - * and the libretro implementation must not try to free any OpenGL + * and the libretro implementation must not try to free any OpenGL * resources in the subsequent context_reset. */ @@ -1717,7 +1952,7 @@ struct retro_hw_render_callback bool debug_context; }; -/* Callback type passed in RETRO_ENVIRONMENT_SET_KEYBOARD_CALLBACK. +/* Callback type passed in RETRO_ENVIRONMENT_SET_KEYBOARD_CALLBACK. * Called by the frontend in response to keyboard events. * down is set if the key is being pressed, or false if it is being released. * keycode is the RETROK value of the char. @@ -1725,16 +1960,16 @@ struct retro_hw_render_callback * key_modifiers is a set of RETROKMOD values or'ed together. * * The pressed/keycode state can be indepedent of the character. - * It is also possible that multiple characters are generated from a + * It is also possible that multiple characters are generated from a * single keypress. * Keycode events should be treated separately from character events. * However, when possible, the frontend should try to synchronize these. * If only a character is posted, keycode should be RETROK_UNKNOWN. * - * Similarily if only a keycode event is generated with no corresponding + * Similarily if only a keycode event is generated with no corresponding * character, character should be 0. */ -typedef void (RETRO_CALLCONV *retro_keyboard_event_t)(bool down, unsigned keycode, +typedef void (RETRO_CALLCONV *retro_keyboard_event_t)(bool down, unsigned keycode, uint32_t character, uint16_t key_modifiers); struct retro_keyboard_callback @@ -1743,15 +1978,15 @@ struct retro_keyboard_callback }; /* Callbacks for RETRO_ENVIRONMENT_SET_DISK_CONTROL_INTERFACE. - * Should be set for implementations which can swap out multiple disk + * Should be set for implementations which can swap out multiple disk * images in runtime. * * If the implementation can do this automatically, it should strive to do so. * However, there are cases where the user must manually do so. * - * Overview: To swap a disk image, eject the disk image with + * Overview: To swap a disk image, eject the disk image with * set_eject_state(true). - * Set the disk index with set_image_index(index). Insert the disk again + * Set the disk index with set_image_index(index). Insert the disk again * with set_eject_state(false). */ @@ -1769,7 +2004,7 @@ typedef bool (RETRO_CALLCONV *retro_get_eject_state_t)(void); typedef unsigned (RETRO_CALLCONV *retro_get_image_index_t)(void); /* Sets image index. Can only be called when disk is ejected. - * The implementation supports setting "no disk" by using an + * The implementation supports setting "no disk" by using an * index >= get_num_images(). */ typedef bool (RETRO_CALLCONV *retro_set_image_index_t)(unsigned index); @@ -1783,11 +2018,11 @@ struct retro_game_info; * Arguments to pass in info have same requirements as retro_load_game(). * Virtual disk tray must be ejected when calling this. * - * Replacing a disk image with info = NULL will remove the disk image + * Replacing a disk image with info = NULL will remove the disk image * from the internal list. * As a result, calls to get_image_index() can change. * - * E.g. replace_image_index(1, NULL), and previous get_image_index() + * E.g. replace_image_index(1, NULL), and previous get_image_index() * returned 4 before. * Index 1 will be removed, and the new index is 3. */ @@ -1796,7 +2031,7 @@ typedef bool (RETRO_CALLCONV *retro_replace_image_index_t)(unsigned index, /* Adds a new valid index (get_num_images()) to the internal disk list. * This will increment subsequent return values from get_num_images() by 1. - * This image index cannot be used until a disk image has been set + * This image index cannot be used until a disk image has been set * with replace_image_index. */ typedef bool (RETRO_CALLCONV *retro_add_image_index_t)(void); @@ -1827,7 +2062,7 @@ enum retro_pixel_format /* RGB565, native endian. * This pixel format is the recommended format to use if a 15/16-bit - * format is desired as it is the pixel format that is typically + * format is desired as it is the pixel format that is typically * available on a wide range of low-power devices. * * It is also natively supported in APIs like OpenGL ES. */ @@ -1857,43 +2092,43 @@ struct retro_input_descriptor /* Human readable description for parameters. * The pointer must remain valid until * retro_unload_game() is called. */ - const char *description; + const char *description; }; struct retro_system_info { - /* All pointers are owned by libretro implementation, and pointers must + /* All pointers are owned by libretro implementation, and pointers must * remain valid until retro_deinit() is called. */ - const char *library_name; /* Descriptive name of library. Should not + const char *library_name; /* Descriptive name of library. Should not * contain any version numbers, etc. */ const char *library_version; /* Descriptive version of core. */ - const char *valid_extensions; /* A string listing probably content - * extensions the core will be able to + const char *valid_extensions; /* A string listing probably content + * extensions the core will be able to * load, separated with pipe. * I.e. "bin|rom|iso". - * Typically used for a GUI to filter + * Typically used for a GUI to filter * out extensions. */ - /* If true, retro_load_game() is guaranteed to provide a valid pathname + /* If true, retro_load_game() is guaranteed to provide a valid pathname * in retro_game_info::path. * ::data and ::size are both invalid. * - * If false, ::data and ::size are guaranteed to be valid, but ::path + * If false, ::data and ::size are guaranteed to be valid, but ::path * might not be valid. * - * This is typically set to true for libretro implementations that must + * This is typically set to true for libretro implementations that must * load from file. - * Implementations should strive for setting this to false, as it allows + * Implementations should strive for setting this to false, as it allows * the frontend to perform patching, etc. */ - bool need_fullpath; + bool need_fullpath; - /* If true, the frontend is not allowed to extract any archives before + /* If true, the frontend is not allowed to extract any archives before * loading the real content. - * Necessary for certain libretro implementations that load games + * Necessary for certain libretro implementations that load games * from zipped archives. */ - bool block_extract; + bool block_extract; }; struct retro_game_geometry @@ -1925,14 +2160,14 @@ struct retro_system_av_info struct retro_variable { /* Variable to query in RETRO_ENVIRONMENT_GET_VARIABLE. - * If NULL, obtains the complete environment string if more + * If NULL, obtains the complete environment string if more * complex parsing is necessary. - * The environment string is formatted as key-value pairs + * The environment string is formatted as key-value pairs * delimited by semicolons as so: * "key1=value1;key2=value2;..." */ const char *key; - + /* Value to be obtained. If key does not exist, it is set to NULL. */ const char *value; }; @@ -1940,12 +2175,14 @@ struct retro_variable struct retro_game_info { const char *path; /* Path to game, UTF-8 encoded. - * Usually used as a reference. - * May be NULL if rom was loaded from stdin - * or similar. - * retro_system_info::need_fullpath guaranteed + * Sometimes used as a reference for building other paths. + * May be NULL if game was loaded from stdin or similar, + * but in this case some cores will be unable to load `data`. + * So, it is preferable to fabricate something here instead + * of passing NULL, which will help more cores to succeed. + * retro_system_info::need_fullpath requires * that this path is valid. */ - const void *data; /* Memory buffer of loaded game. Will be NULL + const void *data; /* Memory buffer of loaded game. Will be NULL * if need_fullpath was set. */ size_t size; /* Size of memory buffer. */ const char *meta; /* String of implementation specific meta-data. */ @@ -1983,25 +2220,25 @@ struct retro_framebuffer /* Callbacks */ -/* Environment callback. Gives implementations a way of performing +/* Environment callback. Gives implementations a way of performing * uncommon tasks. Extensible. */ typedef bool (RETRO_CALLCONV *retro_environment_t)(unsigned cmd, void *data); -/* Render a frame. Pixel format is 15-bit 0RGB1555 native endian +/* Render a frame. Pixel format is 15-bit 0RGB1555 native endian * unless changed (see RETRO_ENVIRONMENT_SET_PIXEL_FORMAT). * * Width and height specify dimensions of buffer. * Pitch specifices length in bytes between two lines in buffer. * - * For performance reasons, it is highly recommended to have a frame + * For performance reasons, it is highly recommended to have a frame * that is packed in memory, i.e. pitch == width * byte_per_pixel. - * Certain graphic APIs, such as OpenGL ES, do not like textures + * Certain graphic APIs, such as OpenGL ES, do not like textures * that are not packed in memory. */ typedef void (RETRO_CALLCONV *retro_video_refresh_t)(const void *data, unsigned width, unsigned height, size_t pitch); -/* Renders a single audio frame. Should only be used if implementation +/* Renders a single audio frame. Should only be used if implementation * generates a single sample at a time. * Format is signed 16-bit native endian. */ @@ -2019,20 +2256,20 @@ typedef size_t (RETRO_CALLCONV *retro_audio_sample_batch_t)(const int16_t *data, /* Polls input. */ typedef void (RETRO_CALLCONV *retro_input_poll_t)(void); -/* Queries for input for player 'port'. device will be masked with +/* Queries for input for player 'port'. device will be masked with * RETRO_DEVICE_MASK. * - * Specialization of devices such as RETRO_DEVICE_JOYPAD_MULTITAP that + * Specialization of devices such as RETRO_DEVICE_JOYPAD_MULTITAP that * have been set with retro_set_controller_port_device() * will still use the higher level RETRO_DEVICE_JOYPAD to request input. */ -typedef int16_t (RETRO_CALLCONV *retro_input_state_t)(unsigned port, unsigned device, +typedef int16_t (RETRO_CALLCONV *retro_input_state_t)(unsigned port, unsigned device, unsigned index, unsigned id); -/* Sets callbacks. retro_set_environment() is guaranteed to be called +/* Sets callbacks. retro_set_environment() is guaranteed to be called * before retro_init(). * - * The rest of the set_* functions are guaranteed to have been called + * The rest of the set_* functions are guaranteed to have been called * before the first call to retro_run() is made. */ RETRO_API void retro_set_environment(retro_environment_t); RETRO_API void retro_set_video_refresh(retro_video_refresh_t); @@ -2049,26 +2286,26 @@ RETRO_API void retro_deinit(void); * when the API is revised. */ RETRO_API unsigned retro_api_version(void); -/* Gets statically known system info. Pointers provided in *info +/* Gets statically known system info. Pointers provided in *info * must be statically allocated. * Can be called at any time, even before retro_init(). */ RETRO_API void retro_get_system_info(struct retro_system_info *info); /* Gets information about system audio/video timings and geometry. * Can be called only after retro_load_game() has successfully completed. - * NOTE: The implementation of this function might not initialize every + * NOTE: The implementation of this function might not initialize every * variable if needed. - * E.g. geom.aspect_ratio might not be initialized if core doesn't + * E.g. geom.aspect_ratio might not be initialized if core doesn't * desire a particular aspect ratio. */ RETRO_API void retro_get_system_av_info(struct retro_system_av_info *info); /* Sets device to be used for player 'port'. - * By default, RETRO_DEVICE_JOYPAD is assumed to be plugged into all + * By default, RETRO_DEVICE_JOYPAD is assumed to be plugged into all * available ports. - * Setting a particular device type is not a guarantee that libretro cores - * will only poll input based on that particular device type. It is only a - * hint to the libretro core when a core cannot automatically detect the - * appropriate input device type on its own. It is also relevant when a + * Setting a particular device type is not a guarantee that libretro cores + * will only poll input based on that particular device type. It is only a + * hint to the libretro core when a core cannot automatically detect the + * appropriate input device type on its own. It is also relevant when a * core can change its behavior depending on device type. */ RETRO_API void retro_set_controller_port_device(unsigned port, unsigned device); @@ -2077,18 +2314,18 @@ RETRO_API void retro_reset(void); /* Runs the game for one video frame. * During retro_run(), input_poll callback must be called at least once. - * + * * If a frame is not rendered for reasons where a game "dropped" a frame, - * this still counts as a frame, and retro_run() should explicitly dupe + * this still counts as a frame, and retro_run() should explicitly dupe * a frame if GET_CAN_DUPE returns true. * In this case, the video callback can take a NULL argument for data. */ RETRO_API void retro_run(void); -/* Returns the amount of data the implementation requires to serialize +/* Returns the amount of data the implementation requires to serialize * internal state (save states). - * Between calls to retro_load_game() and retro_unload_game(), the - * returned size is never allowed to be larger than a previous returned + * Between calls to retro_load_game() and retro_unload_game(), the + * returned size is never allowed to be larger than a previous returned * value, to ensure that the frontend can allocate a save state buffer once. */ RETRO_API size_t retro_serialize_size(void); @@ -2125,4 +2362,4 @@ RETRO_API size_t retro_get_memory_size(unsigned id); } #endif -#endif \ No newline at end of file +#endif diff --git a/libretro/msvc/msvc-2010.bat b/libretro/msvc/msvc-2010.bat new file mode 100644 index 00000000..a4b08228 --- /dev/null +++ b/libretro/msvc/msvc-2010.bat @@ -0,0 +1,124 @@ +@echo off + +@echo Setting environment for using Microsoft Visual Studio 2010 x86 tools. + +@call :GetVSCommonToolsDir +@if "%VS100COMNTOOLS%"=="" goto error_no_VS100COMNTOOLSDIR + +@call "%VS100COMNTOOLS%VCVarsQueryRegistry.bat" 32bit No64bit + +@if "%VSINSTALLDIR%"=="" goto error_no_VSINSTALLDIR +@if "%FrameworkDir32%"=="" goto error_no_FrameworkDIR32 +@if "%FrameworkVersion32%"=="" goto error_no_FrameworkVer32 +@if "%Framework35Version%"=="" goto error_no_Framework35Version + +@set FrameworkDir=%FrameworkDir32% +@set FrameworkVersion=%FrameworkVersion32% + +@if not "%WindowsSdkDir%" == "" ( + @set "PATH=%WindowsSdkDir%bin\NETFX 4.0 Tools;%WindowsSdkDir%bin;%PATH%" + @set "INCLUDE=%WindowsSdkDir%include;%INCLUDE%" + @set "LIB=%WindowsSdkDir%lib;%LIB%" +) + +@rem +@rem Root of Visual Studio IDE installed files. +@rem +@set DevEnvDir=%VSINSTALLDIR%Common7\IDE\ + +@rem PATH +@rem ---- +@if exist "%VSINSTALLDIR%Team Tools\Performance Tools" ( + @set "PATH=%VSINSTALLDIR%Team Tools\Performance Tools;%PATH%" +) +@if exist "%ProgramFiles%\HTML Help Workshop" set PATH=%ProgramFiles%\HTML Help Workshop;%PATH% +@if exist "%ProgramFiles(x86)%\HTML Help Workshop" set PATH=%ProgramFiles(x86)%\HTML Help Workshop;%PATH% +@if exist "%VCINSTALLDIR%VCPackages" set PATH=%VCINSTALLDIR%VCPackages;%PATH% +@set PATH=%FrameworkDir%%Framework35Version%;%PATH% +@set PATH=%FrameworkDir%%FrameworkVersion%;%PATH% +@set PATH=%VSINSTALLDIR%Common7\Tools;%PATH% +@if exist "%VCINSTALLDIR%BIN" set PATH=%VCINSTALLDIR%BIN;%PATH% +@set PATH=%DevEnvDir%;%PATH% + +@if exist "%VSINSTALLDIR%VSTSDB\Deploy" ( + @set "PATH=%VSINSTALLDIR%VSTSDB\Deploy;%PATH%" +) + +@if not "%FSHARPINSTALLDIR%" == "" ( + @set "PATH=%FSHARPINSTALLDIR%;%PATH%" +) + +@rem INCLUDE +@rem ------- +@if exist "%VCINSTALLDIR%ATLMFC\INCLUDE" set INCLUDE=%VCINSTALLDIR%ATLMFC\INCLUDE;%INCLUDE% +@if exist "%VCINSTALLDIR%INCLUDE" set INCLUDE=%VCINSTALLDIR%INCLUDE;%INCLUDE% + +@rem LIB +@rem --- +@if exist "%VCINSTALLDIR%ATLMFC\LIB" set LIB=%VCINSTALLDIR%ATLMFC\LIB;%LIB% +@if exist "%VCINSTALLDIR%LIB" set LIB=%VCINSTALLDIR%LIB;%LIB% + +@rem LIBPATH +@rem ------- +@if exist "%VCINSTALLDIR%ATLMFC\LIB" set LIBPATH=%VCINSTALLDIR%ATLMFC\LIB;%LIBPATH% +@if exist "%VCINSTALLDIR%LIB" set LIBPATH=%VCINSTALLDIR%LIB;%LIBPATH% +@set LIBPATH=%FrameworkDir%%Framework35Version%;%LIBPATH% +@set LIBPATH=%FrameworkDir%%FrameworkVersion%;%LIBPATH% + +@goto end + +@REM ----------------------------------------------------------------------- +:GetVSCommonToolsDir +@set VS100COMNTOOLS= +@call :GetVSCommonToolsDirHelper32 HKLM > nul 2>&1 +@if errorlevel 1 call :GetVSCommonToolsDirHelper32 HKCU > nul 2>&1 +@if errorlevel 1 call :GetVSCommonToolsDirHelper64 HKLM > nul 2>&1 +@if errorlevel 1 call :GetVSCommonToolsDirHelper64 HKCU > nul 2>&1 +@exit /B 0 + +:GetVSCommonToolsDirHelper32 +@for /F "tokens=1,2*" %%i in ('reg query "%1\SOFTWARE\Microsoft\VisualStudio\SxS\VS7" /v "10.0"') DO ( + @if "%%i"=="10.0" ( + @SET "VS100COMNTOOLS=%%k" + ) +) +@if "%VS100COMNTOOLS%"=="" exit /B 1 +@SET "VS100COMNTOOLS=%VS100COMNTOOLS%Common7\Tools\" +@exit /B 0 + +:GetVSCommonToolsDirHelper64 +@for /F "tokens=1,2*" %%i in ('reg query "%1\SOFTWARE\Wow6432Node\Microsoft\VisualStudio\SxS\VS7" /v "10.0"') DO ( + @if "%%i"=="10.0" ( + @SET "VS100COMNTOOLS=%%k" + ) +) +@if "%VS100COMNTOOLS%"=="" exit /B 1 +@SET "VS100COMNTOOLS=%VS100COMNTOOLS%Common7\Tools\" +@exit /B 0 + +@REM ----------------------------------------------------------------------- +:error_no_VS100COMNTOOLSDIR +@echo ERROR: Cannot determine the location of the VS Common Tools folder. +@goto end + +:error_no_VSINSTALLDIR +@echo ERROR: Cannot determine the location of the VS installation. +@goto end + +:error_no_FrameworkDIR32 +@echo ERROR: Cannot determine the location of the .NET Framework 32bit installation. +@goto end + +:error_no_FrameworkVer32 +@echo ERROR: Cannot determine the version of the .NET Framework 32bit installation. +@goto end + +:error_no_Framework35Version +@echo ERROR: Cannot determine the .NET Framework 3.5 version. +@goto end + +:end + +msbuild msvc-2010.sln /p:Configuration=Release /target:clean +msbuild msvc-2010.sln /p:Configuration=Release +exit diff --git a/libretro/msvc/msvc-2010.sln b/libretro/msvc/msvc-2010.sln new file mode 100644 index 00000000..a876749d --- /dev/null +++ b/libretro/msvc/msvc-2010.sln @@ -0,0 +1,20 @@ + +Microsoft Visual Studio Solution File, Format Version 11.00 +# Visual Studio 2010 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "msvc-2010", "msvc-2010\msvc-2010.vcxproj", "{5BDB0E63-AD88-4547-BF48-169312DDD188}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Win32 = Debug|Win32 + Release|Win32 = Release|Win32 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {5BDB0E63-AD88-4547-BF48-169312DDD188}.Debug|Win32.ActiveCfg = Debug|Win32 + {5BDB0E63-AD88-4547-BF48-169312DDD188}.Debug|Win32.Build.0 = Debug|Win32 + {5BDB0E63-AD88-4547-BF48-169312DDD188}.Release|Win32.ActiveCfg = Release|Win32 + {5BDB0E63-AD88-4547-BF48-169312DDD188}.Release|Win32.Build.0 = Release|Win32 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection +EndGlobal diff --git a/libretro/msvc/msvc-2010/libretro.def b/libretro/msvc/msvc-2010/libretro.def new file mode 100644 index 00000000..70f6699a --- /dev/null +++ b/libretro/msvc/msvc-2010/libretro.def @@ -0,0 +1,27 @@ +LIBRARY "msvc-2010" +EXPORTS +retro_set_environment +retro_set_video_refresh +retro_set_audio_sample +retro_set_audio_sample_batch +retro_set_input_poll +retro_set_input_state +retro_init +retro_deinit +retro_api_version +retro_get_system_info +retro_get_system_av_info +retro_set_controller_port_device +retro_reset +retro_run +retro_serialize_size +retro_serialize +retro_unserialize +retro_cheat_reset +retro_cheat_set +retro_load_game +retro_load_game_special +retro_unload_game +retro_get_region +retro_get_memory_data +retro_get_memory_size diff --git a/libretro/msvc/msvc-2010/msvc-2010.vcxproj b/libretro/msvc/msvc-2010/msvc-2010.vcxproj new file mode 100644 index 00000000..30c2a465 --- /dev/null +++ b/libretro/msvc/msvc-2010/msvc-2010.vcxproj @@ -0,0 +1,140 @@ + + + + + Debug + Win32 + + + Release + Win32 + + + + {5BDB0E63-AD88-4547-BF48-169312DDD188} + Win32Proj + msvc2010 + + + + DynamicLibrary + true + Unicode + + + DynamicLibrary + false + true + Unicode + + + + + + + + + + + + + true + $(SolutionDir)msvc-2010\$(Configuration)\ + + + false + $(SolutionDir)msvc-2010\$(Configuration)\ + + + + + + Level3 + Disabled + WIN32;_DEBUG;_WINDOWS;_USRDLL;MSVC2010_EXPORTS;%(PreprocessorDefinitions);RIGHTSHIFT_IS_SAR;__LIBRETRO__;__WIN32__;_CRT_SECURE_NO_WARNINGS + $(SolutionDir)\..\..\;$(SolutionDir)\..\..\..\;$(SolutionDir)\..\..\apu\bapu\;%(AdditionalIncludeDirectories) + + + Windows + true + libretro.def + + + + + Level3 + + + MaxSpeed + true + true + WIN32;NDEBUG;_WINDOWS;_USRDLL;MSVC2010_EXPORTS;%(PreprocessorDefinitions);RIGHTSHIFT_IS_SAR;__LIBRETRO__;__WIN32__;_CRT_SECURE_NO_WARNINGS + $(SolutionDir)\..\..\;$(SolutionDir)\..\..\..\;$(SolutionDir)\..\..\apu\bapu\;%(AdditionalIncludeDirectories) + + + Windows + true + true + true + libretro.def + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/libretro/msvc/msvc-2010/msvc-2010.vcxproj.filters b/libretro/msvc/msvc-2010/msvc-2010.vcxproj.filters new file mode 100644 index 00000000..53555160 --- /dev/null +++ b/libretro/msvc/msvc-2010/msvc-2010.vcxproj.filters @@ -0,0 +1,193 @@ + + + + + {4FC737F1-C7A5-4376-A066-2A32D752A2FF} + cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx + + + {93995380-89BD-4b04-88EB-625FBE52EBFB} + h;hpp;hxx;hm;inl;inc;xsd + + + {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} + rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms + + + {7722f8be-0c98-4fd5-a919-d642e2bae1ce} + + + {effa9675-f3f1-4f4e-a39c-171182a225b8} + + + {e6d15138-760b-4651-ac48-7eaab1f67fec} + + + {57cbef14-a9d6-45dd-9d6b-338d7b63a520} + + + {161f54ee-3443-4972-afe1-b1931c65570b} + + + + + Source Files\libretro + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + diff --git a/port.h b/port.h index 729f7e15..f884d031 100644 --- a/port.h +++ b/port.h @@ -216,10 +216,14 @@ #define RIGHTSHIFT_int8_IS_SAR #define RIGHTSHIFT_int16_IS_SAR #define RIGHTSHIFT_int32_IS_SAR -#ifndef __WIN32_LIBSNES__ +#ifndef __LIBRETRO__ #define SNES_JOY_READ_CALLBACKS #define GFX_MULTI_FORMAT -#endif //__WIN32_LIBSNES__ +#endif //__LIBRETRO__ +#endif + +#ifdef __LIBRETRO__ +#define GFX_MULTI_FORMAT #endif #ifdef __MACOSX__ @@ -279,9 +283,9 @@ __extension__ typedef long long int64; typedef unsigned long long uint64; #ifdef PTR_NOT_INT -typedef long pint; +typedef size_t pint; #else // __PTR_NOT_INT -typedef int pint; +typedef size_t pint; #endif // __PTR_NOT_INT #endif // __WIN32__ #endif // HAVE_STDINT_H @@ -320,14 +324,14 @@ void _makepath (char *, const char *, const char *, const char *, const char *); #define snprintf _snprintf #define strcasecmp stricmp #define strncasecmp strnicmp -#ifndef __WIN32_LIBSNES__ +#ifndef __LIBRETRO__ void WinDisplayStringFromBottom(const char *string, int linesFromBottom, int pixelsFromLeft, bool allowWrap); #define S9xDisplayString WinDisplayStringFromBottom void SetInfoDlgColor(unsigned char, unsigned char, unsigned char); #define SET_UI_COLOR(r,g,b) SetInfoDlgColor(r,g,b) -#else // __WIN32_LIBSNES__ +#else // __LIBRETRO__ #define S9xDisplayString DisplayStringFromBottom -#endif // __WIN32_LIBSNES__ +#endif // __LIBRETRO__ #endif // __WIN32__ #if defined(__DJGPP) || defined(__WIN32__)