Fix some libretro compilation errors on Android, Darwin, Nintendo and Windows

This commit is contained in:
刘皓 2025-01-27 11:48:53 -05:00
parent c42949713d
commit b1133b78f7
No known key found for this signature in database
GPG key ID: 7901753DB465B711
7 changed files with 320 additions and 49 deletions

View file

@ -727,7 +727,6 @@ jobs:
echo "[binaries]" | tee -a ${{ runner.temp }}/cross.ini echo "[binaries]" | tee -a ${{ runner.temp }}/cross.ini
echo "c = '${{ runner.temp }}/cc'" | tee -a ${{ runner.temp }}/cross.ini echo "c = '${{ runner.temp }}/cc'" | tee -a ${{ runner.temp }}/cross.ini
echo "cpp = '${{ runner.temp }}/c++'" | tee -a ${{ runner.temp }}/cross.ini echo "cpp = '${{ runner.temp }}/c++'" | tee -a ${{ runner.temp }}/cross.ini
echo "objc = '${{ runner.temp }}/cc'" | tee -a ${{ runner.temp }}/cross.ini
echo "ar = 'ar'" | tee -a ${{ runner.temp }}/cross.ini echo "ar = 'ar'" | tee -a ${{ runner.temp }}/cross.ini
echo "strip = 'strip'" | tee -a ${{ runner.temp }}/cross.ini echo "strip = 'strip'" | tee -a ${{ runner.temp }}/cross.ini
echo "[host_machine]" | tee -a ${{ runner.temp }}/cross.ini echo "[host_machine]" | tee -a ${{ runner.temp }}/cross.ini

View file

@ -7,7 +7,7 @@ if get_option('retro') == false and host_system == 'darwin'
error('\nThis Meson project no longer supports macOS. Please use the Xcode project instead.') error('\nThis Meson project no longer supports macOS. Please use the Xcode project instead.')
endif endif
git_hash = run_command('git', 'rev-parse', '--short', 'HEAD', check: true).stdout().strip() git_hash = run_command('git', 'rev-parse', '--short', 'HEAD', check: false).stdout().strip()
compilers = {'cpp': meson.get_compiler('cpp')} compilers = {'cpp': meson.get_compiler('cpp')}
@ -171,9 +171,7 @@ if get_option('retro') == true
retro_link_args += '-Wl,--version-script,' + join_paths(meson.current_source_dir(), 'retro/link.T') retro_link_args += '-Wl,--version-script,' + join_paths(meson.current_source_dir(), 'retro/link.T')
endif endif
library( retro_deps = [
'retro-' + meson.project_name(),
dependencies: [
cmake.subproject('boost_asio', options: boost_options).dependency('boost_asio'), cmake.subproject('boost_asio', options: boost_options).dependency('boost_asio'),
cmake.subproject('boost_mp11', options: boost_options).dependency('boost_mp11'), cmake.subproject('boost_mp11', options: boost_options).dependency('boost_mp11'),
cmake.subproject('boost_describe', options: boost_options).dependency('boost_describe'), cmake.subproject('boost_describe', options: boost_options).dependency('boost_describe'),
@ -194,7 +192,14 @@ if get_option('retro') == true
cmake.subproject('physfs', options: physfs_options).dependency('physfs-static'), cmake.subproject('physfs', options: physfs_options).dependency('physfs-static'),
cmake.subproject('openal-soft', options: openal_options).dependency('OpenAL'), cmake.subproject('openal-soft', options: openal_options).dependency('OpenAL'),
cmake.subproject('fluidlite', options: fluidlite_options).dependency('fluidlite-static'), cmake.subproject('fluidlite', options: fluidlite_options).dependency('fluidlite-static'),
], ]
if host_system == 'darwin'
retro_deps += compilers['cpp'].find_library('iconv')
endif
library(
'retro-' + meson.project_name(),
dependencies: retro_deps,
c_args: [ c_args: [
'-fno-optimize-sibling-calls', '-fno-optimize-sibling-calls',
'-frounding-math', '-frounding-math',

View file

@ -6,16 +6,16 @@
#include "debugwriter.h" #include "debugwriter.h"
#if __LINUX__ || __ANDROID__ #if defined(__LINUX__) || defined(__ANDROID__)
#define FLUID_LIB "libfluidsynth.so.3" # define FLUID_LIB "libfluidsynth.so.3"
#elif MKXPZ_BUILD_XCODE #elif MKXPZ_BUILD_XCODE
#define FLUID_LIB "@rpath/libfluidsynth.dylib" # define FLUID_LIB "@rpath/libfluidsynth.dylib"
#elif __APPLE__ #elif __APPLE__
#define FLUID_LIB "libfluidsynth.3.dylib" # define FLUID_LIB "libfluidsynth.3.dylib"
#elif __WIN32__ #elif __WIN32__
#define FLUID_LIB "fluidsynth.dll" # define FLUID_LIB "fluidsynth.dll"
#else #elif !defined(SHARED_FLUID)
#error "platform not recognized" # error "platform not recognized"
#endif #endif
struct FluidFunctions fluid; struct FluidFunctions fluid;

View file

@ -20,7 +20,6 @@
*/ */
#include <cstdio> #include <cstdio>
#include <stdlib.h>
#include <cstdlib> #include <cstdlib>
#include <cstdarg> #include <cstdarg>
#include <cstring> #include <cstring>
@ -35,6 +34,21 @@
using namespace mkxp_retro; using namespace mkxp_retro;
using namespace mkxp_sandbox; using namespace mkxp_sandbox;
#if defined(__unix__) || defined(__APPLE__)
static inline void *malloc_align(size_t alignment, size_t size) {
void *mem;
return posix_memalign(&mem, alignment, size) ? NULL : mem;
}
#elif defined(_WIN32) || defined(__CYGWIN__) || defined(__MINGW32__)
static inline void *malloc_align(size_t alignment, size_t size) {
return _aligned_malloc(size, alignment);
}
#else
static inline void *malloc_align(size_t alignment, size_t size) {
return aligned_alloc(alignment, size);
}
#endif
static size_t frame_number = 0; static size_t frame_number = 0;
static ALCdevice *al_device = NULL; static ALCdevice *al_device = NULL;
static ALCcontext *al_context = NULL; static ALCcontext *al_context = NULL;
@ -211,7 +225,7 @@ extern "C" RETRO_API void retro_set_input_state(retro_input_state_t cb) {
extern "C" RETRO_API void retro_init() { extern "C" RETRO_API void retro_init() {
frame_buf = (uint32_t *)std::calloc(640 * 480, sizeof *frame_buf); frame_buf = (uint32_t *)std::calloc(640 * 480, sizeof *frame_buf);
sound_buf = (int16_t *)aligned_alloc(16, 735 * 2 * sizeof *sound_buf); sound_buf = (int16_t *)malloc_align(16, 735 * 2 * sizeof *sound_buf);
} }
extern "C" RETRO_API void retro_deinit() { extern "C" RETRO_API void retro_deinit() {

View file

@ -5,15 +5,14 @@
diff --git a/CMakeLists.txt b/CMakeLists.txt diff --git a/CMakeLists.txt b/CMakeLists.txt
--- a/CMakeLists.txt --- a/CMakeLists.txt
+++ b/CMakeLists.txt +++ b/CMakeLists.txt
@@ -134,6 +134,12 @@ if("${CMAKE_C_PLATFORM_ID}" STREQUAL "QNX") @@ -134,6 +134,11 @@ if("${CMAKE_C_PLATFORM_ID}" STREQUAL "QNX")
set(INC_PATHS ${INC_PATHS} /usr/include) set(INC_PATHS ${INC_PATHS} /usr/include)
set(LINKER_FLAGS ${LINKER_FLAGS} -L/usr/lib) set(LINKER_FLAGS ${LINKER_FLAGS} -L/usr/lib)
endif() endif()
+CHECK_INCLUDE_FILE("semaphore.h" HAVE_SEMAPHORE_H) +check_symbol_exists(__DEVKITPPC__ "sys/config.h" DEVKITPPC)
+if(NOT HAVE_SEMAPHORE_H) +if(DEVKITPPC)
+ message("semaphore.h not found; using libogc semaphores instead") + set(CPP_DEFS ${CPP_DEFS} MKXPZ_DEVKITPPC)
+ set(INC_PATHS ${INC_PATHS} "$ENV{DEVKITPRO}/libogc/include") + set(INC_PATHS ${INC_PATHS} "$ENV{DEVKITPRO}/libogc/include")
+ set(INC_PATHS ${INC_PATHS} "$ENV{DEVKITPRO}/libogc/include/ogc")
+endif() +endif()
# When the library is built for static linking, apps should define # When the library is built for static linking, apps should define
@ -43,7 +42,7 @@ diff --git a/common/threads.cpp b/common/threads.cpp
semaphore::semaphore(unsigned int initial) semaphore::semaphore(unsigned int initial)
{ {
+#ifdef LWP_SEM_NULL +#ifdef MKXPZ_DEVKITPPC
+ if(LWP_SemInit(&mSem, initial, 0xffffffff) != 0) + if(LWP_SemInit(&mSem, initial, 0xffffffff) != 0)
+#else +#else
if(sem_init(&mSem, 0, initial) != 0) if(sem_init(&mSem, 0, initial) != 0)
@ -52,7 +51,7 @@ diff --git a/common/threads.cpp b/common/threads.cpp
} }
semaphore::~semaphore() semaphore::~semaphore()
+#ifdef LWP_SEM_NULL +#ifdef MKXPZ_DEVKITPPC
+{ LWP_SemDestroy(mSem); } +{ LWP_SemDestroy(mSem); }
+#else +#else
{ sem_destroy(&mSem); } { sem_destroy(&mSem); }
@ -60,7 +59,7 @@ diff --git a/common/threads.cpp b/common/threads.cpp
void semaphore::post() void semaphore::post()
{ {
+#ifdef LWP_SEM_NULL +#ifdef MKXPZ_DEVKITPPC
+ if(LWP_SemPost(mSem) != 0) + if(LWP_SemPost(mSem) != 0)
+#else +#else
if(sem_post(&mSem) != 0) if(sem_post(&mSem) != 0)
@ -70,7 +69,7 @@ diff --git a/common/threads.cpp b/common/threads.cpp
void semaphore::wait() noexcept void semaphore::wait() noexcept
{ {
+#ifdef LWP_SEM_NULL +#ifdef MKXPZ_DEVKITPPC
+ LWP_SemWait(mSem); + LWP_SemWait(mSem);
+#else +#else
while(sem_wait(&mSem) == -1 && errno == EINTR) { while(sem_wait(&mSem) == -1 && errno == EINTR) {
@ -86,7 +85,20 @@ diff --git a/common/threads.cpp b/common/threads.cpp
diff --git a/common/threads.h b/common/threads.h diff --git a/common/threads.h b/common/threads.h
--- a/common/threads.h --- a/common/threads.h
+++ b/common/threads.h +++ b/common/threads.h
@@ -40,7 +40,6 @@ public: @@ -14,7 +14,11 @@
#if defined(__APPLE__)
#include <dispatch/dispatch.h>
#elif !defined(_WIN32)
-#include <semaphore.h>
+# ifdef MKXPZ_DEVKITPPC
+# include <ogc/semaphore.h>
+# else
+# include <semaphore.h>
+# endif
#endif
void althrd_setname(const char *name);
@@ -40,7 +44,6 @@ public:
void post(); void post();
void wait() noexcept; void wait() noexcept;

View file

@ -1,14 +1,78 @@
# Fixes a compilation error when building with C++ standards older than C++17. # Fixes a compilation error when building with C++ standards older than C++17.
# Also removes the call to `__android_log_printf()` on Android.
# Also removes the Apple-specific code from alconfig.cpp.
diff --git a/alc/alconfig.cpp b/alc/alconfig.cpp
--- a/alc/alconfig.cpp
+++ b/alc/alconfig.cpp
@@ -362,22 +362,6 @@ void ReadALConfig()
fname.clear();
}
-#ifdef __APPLE__
- CFBundleRef mainBundle = CFBundleGetMainBundle();
- if(mainBundle)
- {
- unsigned char fileName[PATH_MAX];
- CFURLRef configURL;
-
- if((configURL=CFBundleCopyResourceURL(mainBundle, CFSTR(".alsoftrc"), CFSTR(""), nullptr)) &&
- CFURLGetFileSystemRepresentation(configURL, true, fileName, sizeof(fileName)))
- {
- f = al::ifstream{reinterpret_cast<char*>(fileName)};
- if(f.is_open())
- LoadConfigFromFile(f);
- }
- }
-#endif
if(auto homedir = al::getenv("HOME"))
{
diff --git a/alc/helpers.cpp b/alc/helpers.cpp
--- a/alc/helpers.cpp
+++ b/alc/helpers.cpp
@@ -348,22 +348,6 @@ void al_print(LogLevel level, FILE *logfile, const char *fmt, ...)
fputs(str, logfile);
fflush(logfile);
}
-#ifdef __ANDROID__
- auto android_severity = [](LogLevel l) noexcept
- {
- switch(l)
- {
- case LogLevel::Trace: return ANDROID_LOG_DEBUG;
- case LogLevel::Warning: return ANDROID_LOG_WARN;
- case LogLevel::Error: return ANDROID_LOG_ERROR;
- /* Should not happen. */
- case LogLevel::Disable:
- break;
- }
- return ANDROID_LOG_ERROR;
- };
- __android_log_print(android_severity(level), "openal", "%s", str);
-#endif
}
diff --git a/common/almalloc.cpp b/common/almalloc.cpp diff --git a/common/almalloc.cpp b/common/almalloc.cpp
--- a/common/almalloc.cpp --- a/common/almalloc.cpp
+++ b/common/almalloc.cpp +++ b/common/almalloc.cpp
@@ -20,7 +20,7 @@ void *al_malloc(size_t alignment, size_t size) @@ -18,14 +18,14 @@ void *al_malloc(size_t alignment, size_t size)
assert((alignment & (alignment-1)) == 0);
alignment = std::max(alignment, alignof(std::max_align_t));
#if defined(HAVE_STD_ALIGNED_ALLOC) -#if defined(HAVE_STD_ALIGNED_ALLOC)
size = (size+(alignment-1))&~(alignment-1); - size = (size+(alignment-1))&~(alignment-1);
- return std::aligned_alloc(alignment, size); - return std::aligned_alloc(alignment, size);
+ return aligned_alloc(alignment, size); -#elif defined(HAVE_POSIX_MEMALIGN)
#elif defined(HAVE_POSIX_MEMALIGN) +#if defined(HAVE_POSIX_MEMALIGN)
void *ret{}; void *ret{};
if(posix_memalign(&ret, alignment, size) == 0) if(posix_memalign(&ret, alignment, size) == 0)
return ret;
return nullptr;
+#elif defined(HAVE_STD_ALIGNED_ALLOC)
+ size = (size+(alignment-1))&~(alignment-1);
+ return aligned_alloc(alignment, size);
#elif defined(HAVE__ALIGNED_MALLOC)
return _aligned_malloc(size, alignment);
#else

View file

@ -1,7 +1,184 @@
diff --git a/CMakeLists.txt b/CMakeLists.txt
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -25,10 +25,6 @@ set(PHYSFS_CPP_SRCS)
# I hate that they define "WIN32" ... we're about to move to Win64...I hope!
-if(APPLE)
- set(OTHER_LDFLAGS ${OTHER_LDFLAGS} "-framework IOKit -framework Foundation")
- list(APPEND PHYSFS_M_SRCS src/physfs_platform_apple.m)
-endif()
if(CMAKE_COMPILER_IS_GNUCC OR CMAKE_C_COMPILER_ID MATCHES "Clang")
add_compile_options(-Wall)
@@ -58,7 +54,7 @@ if(WINRT)
list(APPEND PHYSFS_CPP_SRCS src/physfs_platform_winrt.cpp)
endif()
-if(UNIX AND NOT WIN32 AND NOT APPLE) # (MingW and such might be UNIX _and_ WINDOWS!)
+if(UNIX AND NOT WIN32) # (MingW and such might be UNIX _and_ WINDOWS!)
find_library(PTHREAD_LIBRARY pthread)
if(PTHREAD_LIBRARY)
set(OPTIONAL_LIBRARY_LIBS ${OPTIONAL_LIBRARY_LIBS} ${PTHREAD_LIBRARY})
@@ -172,11 +168,20 @@ if(PHYSFS_BUILD_STATIC)
set_target_properties(physfs-static PROPERTIES VS_WINRT_COMPONENT True)
set_target_properties(physfs-static PROPERTIES STATIC_LIBRARY_FLAGS "/ignore:4264")
endif()
+ set(CPP_DEFS)
+ set(INC_PATHS)
+ include(CheckSymbolExists)
+ check_symbol_exists(__DEVKITPPC__ "sys/config.h" DEVKITPPC)
+ if(DEVKITPPC)
+ set(CPP_DEFS ${CPP_DEFS} MKXPZ_DEVKITPPC)
+ set(INC_PATHS ${INC_PATHS} "$ENV{DEVKITPRO}/libogc/include")
+ endif()
if(WIN32 OR WINRT OR OS2)
# no dll exports from the static library
- target_compile_definitions(physfs-static PRIVATE "PHYSFS_STATIC")
+ set(CPP_DEFS ${CPP_DEFS} "PHYSFS_STATIC")
endif()
- target_include_directories(physfs-static PUBLIC "$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/src>")
+ target_compile_definitions(physfs-static PRIVATE ${CPP_DEFS})
+ target_include_directories(physfs-static PUBLIC "$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/src>" ${INC_PATHS})
target_link_libraries(physfs-static PRIVATE ${OPTIONAL_LIBRARY_LIBS} ${OTHER_LDFLAGS})
set(PHYSFS_LIB_TARGET physfs-static)
list(APPEND PHYSFS_INSTALL_TARGETS "physfs-static")
diff --git a/src/physfs_platform_posix.c b/src/physfs_platform_posix.c
--- a/src/physfs_platform_posix.c
+++ b/src/physfs_platform_posix.c
@@ -19,7 +19,11 @@
#include <dirent.h>
#include <errno.h>
#include <fcntl.h>
-#include <pthread.h>
+#ifdef MKXPZ_DEVKITPPC
+# include <ogc/mutex.h>
+#else
+# include <pthread.h>
+#endif
#include "physfs_internal.h"
@@ -369,15 +373,23 @@ int __PHYSFS_platformStat(const char *fname, PHYSFS_Stat *st, const int follow)
typedef struct
{
+#ifdef MKXPZ_DEVKITPPC
+ mutex_t mutex;
+#else
pthread_mutex_t mutex;
pthread_t owner;
+#endif
PHYSFS_uint32 count;
} PthreadMutex;
void *__PHYSFS_platformGetThreadID(void)
{
+#ifdef MKXPZ_DEVKITPPC
+ return (void *)42;
+#else
return ( (void *) ((size_t) pthread_self()) );
+#endif
} /* __PHYSFS_platformGetThreadID */
@@ -386,7 +398,11 @@ void *__PHYSFS_platformCreateMutex(void)
int rc;
PthreadMutex *m = (PthreadMutex *) allocator.Malloc(sizeof (PthreadMutex));
BAIL_IF(!m, PHYSFS_ERR_OUT_OF_MEMORY, NULL);
+#ifdef MKXPZ_DEVKITPPC
+ rc = LWP_MutexInit(&m->mutex, false);
+#else
rc = pthread_mutex_init(&m->mutex, NULL);
+#endif
if (rc != 0)
{
allocator.Free(m);
@@ -394,7 +410,9 @@ void *__PHYSFS_platformCreateMutex(void)
} /* if */
m->count = 0;
+#ifndef MKXPZ_DEVKITPPC
m->owner = (pthread_t) 0xDEADBEEF;
+#endif
return ((void *) m);
} /* __PHYSFS_platformCreateMutex */
@@ -403,11 +421,15 @@ void __PHYSFS_platformDestroyMutex(void *mutex)
{
PthreadMutex *m = (PthreadMutex *) mutex;
+#ifdef MKXPZ_DEVKITPPC
+ LWP_MutexDestroy(m->mutex);
+#else
/* Destroying a locked mutex is a bug, but we'll try to be helpful. */
if ((m->owner == pthread_self()) && (m->count > 0))
pthread_mutex_unlock(&m->mutex);
pthread_mutex_destroy(&m->mutex);
+#endif
allocator.Free(m);
} /* __PHYSFS_platformDestroyMutex */
@@ -415,6 +437,10 @@ void __PHYSFS_platformDestroyMutex(void *mutex)
int __PHYSFS_platformGrabMutex(void *mutex)
{
PthreadMutex *m = (PthreadMutex *) mutex;
+#ifdef MKXPZ_DEVKITPPC
+ if (LWP_MutexLock(m->mutex) != 0)
+ return 0;
+#else
pthread_t tid = pthread_self();
if (m->owner != tid)
{
@@ -422,6 +448,7 @@ int __PHYSFS_platformGrabMutex(void *mutex)
return 0;
m->owner = tid;
} /* if */
+#endif
m->count++;
return 1;
@@ -431,6 +458,9 @@ int __PHYSFS_platformGrabMutex(void *mutex)
void __PHYSFS_platformReleaseMutex(void *mutex)
{
PthreadMutex *m = (PthreadMutex *) mutex;
+#ifdef MKXPZ_DEVKITPPC
+ LWP_MutexUnlock(m->mutex);
+#else
assert(m->owner == pthread_self()); /* catch programming errors. */
assert(m->count > 0); /* catch programming errors. */
if (m->owner == pthread_self())
@@ -441,6 +471,7 @@ void __PHYSFS_platformReleaseMutex(void *mutex)
pthread_mutex_unlock(&m->mutex);
} /* if */
} /* if */
+#endif
} /* __PHYSFS_platformReleaseMutex */
#endif /* PHYSFS_PLATFORM_POSIX */
diff --git a/src/physfs_platforms.h b/src/physfs_platforms.h diff --git a/src/physfs_platforms.h b/src/physfs_platforms.h
--- a/src/physfs_platforms.h --- a/src/physfs_platforms.h
+++ b/src/physfs_platforms.h +++ b/src/physfs_platforms.h
@@ -73,7 +73,10 @@ @@ -31,13 +31,9 @@
#elif defined(__OS2__) || defined(OS2)
# define PHYSFS_PLATFORM_OS2 1
#elif ((defined __MACH__) && (defined __APPLE__))
-/* To check if iOS or not, we need to include this file */
-# include <TargetConditionals.h>
-# if ((TARGET_IPHONE_SIMULATOR) || (TARGET_OS_IPHONE))
-# define PHYSFS_NO_CDROM_SUPPORT 1
-# endif
-# define PHYSFS_PLATFORM_APPLE 1
+# define PHYSFS_PLATFORM_UNIX 1
# define PHYSFS_PLATFORM_POSIX 1
+# define PHYSFS_NO_CDROM_SUPPORT 1
#elif defined(macintosh)
# error Classic Mac OS support was dropped from PhysicsFS 2.0. Move to OS X.
#elif defined(__ANDROID__)
@@ -73,7 +69,10 @@
# define PHYSFS_PLATFORM_UNIX 1 # define PHYSFS_PLATFORM_UNIX 1
# define PHYSFS_PLATFORM_POSIX 1 # define PHYSFS_PLATFORM_POSIX 1
#else #else