Allow FluidSynth to build for libretro targets with no threading support

This commit is contained in:
刘皓 2025-04-08 00:27:32 -04:00
parent 89ffd49acf
commit 192300dbe9
No known key found for this signature in database
GPG key ID: 7901753DB465B711
5 changed files with 233 additions and 1 deletions

View file

@ -219,6 +219,10 @@ if is_libretro
if not compilers['cpp'].has_header_symbol('mutex', 'std::mutex')
libretro_defines += '-DMKXPZ_NO_STD_MUTEX'
if not compilers['cpp'].has_header_symbol('condition_variable', 'std::condition_variable_any')
libretro_defines += '-DMKXPZ_NO_STD_CONDITION_VARIABLE_ANY'
endif
endif
if not compilers['cpp'].has_header_symbol('mutex', 'std::recursive_mutex')

View file

@ -86,6 +86,46 @@ extern "C" int mkxp_mutex_unlock(mkxp_mutex_t *mutex) {
#endif
}
extern "C" int mkxp_cond_init(mkxp_cond_t *cond) {
#ifndef MKXPZ_NO_PTHREAD_H
return pthread_cond_init(cond, NULL);
#else
return 0;
#endif
}
extern "C" int mkxp_cond_destroy(mkxp_cond_t *cond) {
#ifndef MKXPZ_NO_PTHREAD_H
return pthread_cond_destroy(cond);
#else
return 0;
#endif
}
extern "C" int mkxp_cond_signal(mkxp_cond_t *cond) {
#ifndef MKXPZ_NO_PTHREAD_H
return pthread_cond_signal(cond);
#else
return 0;
#endif
}
extern "C" int mkxp_cond_broadcast(mkxp_cond_t *cond) {
#ifndef MKXPZ_NO_PTHREAD_H
return pthread_cond_broadcast(cond);
#else
return 0;
#endif
}
extern "C" int mkxp_cond_wait(mkxp_cond_t *cond, mkxp_mutex_t *mutex) {
#ifndef MKXPZ_NO_PTHREAD_H
return pthread_cond_wait(cond, mutex);
#else
return 0;
#endif
}
extern "C" int mkxp_sem_init(mkxp_sem_t *sem, unsigned int value) {
#ifndef MKXPZ_NO_SEMAPHORE_H
return sem_init(sem, 0, value);

View file

@ -40,6 +40,7 @@
#include <cstdio>
#include <cstdlib>
#include <mutex>
#include <condition_variable>
#include <string>
extern "C" long long strtoll(const char *str, char **str_end, int base);
@ -51,9 +52,11 @@ extern "C" {
#ifndef MKXPZ_NO_PTHREAD_H
typedef pthread_t mkxp_thread_t;
typedef pthread_mutex_t mkxp_mutex_t;
typedef pthread_cond_t mkxp_cond_t;
#else
typedef size_t mkxp_thread_t;
typedef unsigned int mkxp_mutex_t;
typedef bool mkxp_cond_t;
#endif
#ifndef MKXPZ_NO_SEMAPHORE_H
@ -74,6 +77,16 @@ int mkxp_mutex_lock(mkxp_mutex_t *mutex);
int mkxp_mutex_unlock(mkxp_mutex_t *mutex);
int mkxp_cond_init(mkxp_cond_t *cond);
int mkxp_cond_destroy(mkxp_cond_t *cond);
int mkxp_cond_signal(mkxp_cond_t *cond);
int mkxp_cond_broadcast(mkxp_cond_t *cond);
int mkxp_cond_wait(mkxp_cond_t *cond, mkxp_mutex_t *mutex);
int mkxp_sem_init(mkxp_sem_t *sem, unsigned int value);
int mkxp_sem_destroy(mkxp_sem_t *sem);
@ -159,6 +172,43 @@ namespace std {
}
# endif
# ifdef MKXPZ_NO_STD_CONDITION_VARIABLE_ANY
namespace std {
class condition_variable_any {
public:
mkxp_cond_t inner;
inline condition_variable_any() noexcept {
if (mkxp_cond_init(&inner)) {
abort();
}
}
inline ~condition_variable_any() noexcept {
mkxp_cond_destroy(&inner);
}
inline void notify_one() noexcept {
if (mkxp_cond_signal(&inner)) {
abort();
}
}
inline void notify_all() noexcept {
if (mkxp_cond_broadcast(&inner)) {
abort();
}
}
inline void wait(std::mutex &mutex) noexcept {
if (mkxp_cond_wait(&inner, &mutex.inner)) {
abort();
}
}
};
}
# endif
# ifdef MKXPZ_NO_STD_ROUND
namespace std {
inline constexpr float round(float x) {

View file

@ -2,4 +2,4 @@
url = https://github.com/mkxp-z/fluidsynth-sans-glib
revision = 5c7716bda52f4f86271f32337c79f806f9402144
depth = 1
diff_files = fluidsynth-cmake-policy.patch, fluidsynth-emscripten-endian.patch, fluidsynth-linker-flags.patch, fluidsynth-pic.patch, fluidsynth-pthreads.patch, fluidsynth-test-doc.patch
diff_files = fluidsynth-cmake-policy.patch, fluidsynth-emscripten-endian.patch, fluidsynth-linker-flags.patch, fluidsynth-mkxp-polyfill.patch, fluidsynth-pic.patch, fluidsynth-pthreads.patch, fluidsynth-test-doc.patch

View file

@ -0,0 +1,138 @@
# This patch makes OpenAL Soft use mkxp-polyfill.cpp instead of POSIX threads and `std::mutex` for portability reasons.
--- a/src/utils/fluid_sys.c
+++ b/src/utils/fluid_sys.c
@@ -342,7 +342,7 @@ char *fluid_strtok(char **str, char *delim)
*/
void fluid_msleep(unsigned int msecs)
{
- _thread_sleep(msecs * 1000);
+ fputs("sleeping is not supported by this build of fluidsynth", stderr); abort();
}
/**
@@ -969,7 +969,7 @@ new_fluid_thread(const char *name, fluid_thread_func_t func, void *data, int pri
{
_thread *thread = FLUID_NEW(_thread);
fluid_thread_info_t *info = NULL;
-
+ return NULL;
fluid_return_val_if_fail(func != NULL, NULL);
if(prio_level > 0)
@@ -985,17 +985,17 @@ new_fluid_thread(const char *name, fluid_thread_func_t func, void *data, int pri
info->func = func;
info->data = data;
info->prio_level = prio_level;
- _thread_create(thread, fluid_thread_high_prio, info);
+
}
else
{
- _thread_create(thread, func, data);
+
}
if(detach)
{
- _thread_detach(thread); // Release thread reference, if caller wants to detach
+
}
return thread;
@@ -1008,7 +1008,7 @@ new_fluid_thread(const char *name, fluid_thread_func_t func, void *data, int pri
void
delete_fluid_thread(fluid_thread_t *thread)
{
- _thread_detach(thread);
+
free(thread);
}
@@ -1020,7 +1020,7 @@ delete_fluid_thread(fluid_thread_t *thread)
int
fluid_thread_join(fluid_thread_t *thread)
{
- _thread_join(thread);
+
return FLUID_OK;
}
--- a/src/utils/fluid_threading.cpp
+++ b/src/utils/fluid_threading.cpp
@@ -3,10 +3,10 @@
#include <functional>
#include <chrono>
#include <thread>
-#include <mutex>
-#include <atomic>
+#include "../../../src/mkxp-polyfill.h"
+
#include <ratio>
-#include <condition_variable>
+
thread_local void* privs[16];
bool occupied[16]={false};
void _mutex_init(_mutex *mutex)
@@ -84,33 +84,33 @@ void _private_set(_private *priv,void *val)
for(int i=0;i<16;++i)if(!occupied[i]){priv->id=i+1;break;}
if(priv->id)privs[priv->id-1]=val;
}
-unsigned _thread_get_id(void)
-{
- std::hash<std::thread::id>h;
- return h(std::this_thread::get_id());
-}
-void _thread_create(_thread *th,_thread_func_t func,void* data)
-{
- th->thrd=(void*)(new std::thread(func,data));
-}
-void _thread_detach(_thread *th)
-{
- if(!th->thrd)return;
- ((std::thread*)(th->thrd))->detach();
- delete (std::thread*)(th->thrd);
- th->thrd=nullptr;
-}
-void _thread_join(_thread *th)
-{
- if(!th->thrd)return;
- ((std::thread*)(th->thrd))->join();
- delete (std::thread*)(th->thrd);
- th->thrd=nullptr;
-}
-void _thread_sleep(unsigned long us)
-{
- std::this_thread::sleep_for(std::chrono::microseconds(us));
-}
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
double _monotonic_time()
{
return std::chrono::duration_cast<std::chrono::duration<double,std::micro>>(std::chrono::steady_clock::now().time_since_epoch()).count();