Skip to content

Commit 24157a0

Browse files
committed
coreaudio: shim stdatomic.h and dispatch/dispatch.h on pre-10.7 SDKs
<stdatomic.h> is C11 (GCC 4.9+, Xcode 5+) and <dispatch/dispatch.h> requires GCD (Mac OS X 10.6+). Neither exists on Xcode 3.1 / 10.4- 10.5 / PowerPC, so coreaudio.c fails to compile there with: coreaudio.c:17:23: error: stdatomic.h: No such file or directory coreaudio.c:20:31: error: dispatch/dispatch.h: No such file or directory On SDKs predating 10.7, provide local replacements: - atomic_size_t / atomic_load_explicit / atomic_fetch_add_explicit / atomic_fetch_sub_explicit / atomic_init -> OSAtomicAdd32Barrier (<libkern/OSAtomic.h>, available since 10.4). The ring-buffer fill counter fits easily in int32_t (worst case ~200k samples). - dispatch_semaphore_t / _create / _signal / _wait / dispatch_time / dispatch_release -> Mach semaphore_t (<mach/semaphore.h>), which has been on OS X since NeXTSTEP. The file's logic is unchanged; only the header block at the top is conditional. Shim macros are #undef'd at EOF so they cannot leak into later translation units in the griffin unity build. Modern SDKs take the existing code path unchanged.
1 parent 77cd5bc commit 24157a0

1 file changed

Lines changed: 105 additions & 1 deletion

File tree

audio/drivers/coreaudio.c

Lines changed: 105 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,10 +14,92 @@
1414
* If not, see <http://www.gnu.org/licenses/>.
1515
*/
1616
#include <stdlib.h>
17-
#include <stdatomic.h>
1817
#include <math.h>
1918

19+
#include <AvailabilityMacros.h>
20+
21+
/* stdatomic.h arrived with C11 (GCC 4.9+, Xcode 5+).
22+
* GCD arrived in Mac OS X 10.6 Snow Leopard.
23+
* On older Apple toolchains (e.g. Xcode 3.1 / 10.4-10.5 / PowerPC),
24+
* shim both to legacy OS X primitives:
25+
* - atomic_size_t / atomic_* -> OSAtomic (libkern/OSAtomic.h, 10.4+)
26+
* - dispatch_semaphore_* -> Mach semaphores (mach/semaphore.h) */
27+
#if !defined(MAC_OS_X_VERSION_10_7) || \
28+
(defined(MAC_OS_X_VERSION_MIN_REQUIRED) && \
29+
MAC_OS_X_VERSION_MIN_REQUIRED < MAC_OS_X_VERSION_10_7)
30+
#define RARCH_COREAUDIO_LEGACY_APPLE 1
31+
#endif
32+
33+
#ifdef RARCH_COREAUDIO_LEGACY_APPLE
34+
#include <libkern/OSAtomic.h>
35+
#include <mach/mach.h>
36+
#include <mach/semaphore.h>
37+
#include <mach/task.h>
38+
#include <mach/clock_types.h>
39+
40+
/* --- atomic shim (size_t, acquire/release subset actually used) --- */
41+
typedef volatile int32_t atomic_size_t;
42+
typedef int memory_order;
43+
#define memory_order_acquire 0
44+
#define memory_order_release 0
45+
#define atomic_init(ptr, val) \
46+
(*(ptr) = (int32_t)(val))
47+
#define atomic_load_explicit(ptr, mo) \
48+
((size_t)OSAtomicAdd32Barrier(0, (ptr)))
49+
#define atomic_fetch_add_explicit(ptr, n, mo) \
50+
((size_t)(OSAtomicAdd32Barrier((int32_t)(n), (ptr)) - (int32_t)(n)))
51+
#define atomic_fetch_sub_explicit(ptr, n, mo) \
52+
((size_t)(OSAtomicAdd32Barrier(-(int32_t)(n), (ptr)) + (int32_t)(n)))
53+
54+
/* --- GCD semaphore shim (thin wrapper over Mach semaphore_t) --- */
55+
#ifndef NSEC_PER_MSEC
56+
#define NSEC_PER_MSEC 1000000ULL
57+
#endif
58+
#ifndef NSEC_PER_SEC
59+
#define NSEC_PER_SEC 1000000000ULL
60+
#endif
61+
#define DISPATCH_TIME_NOW 0
62+
63+
typedef semaphore_t dispatch_semaphore_t;
64+
typedef uint64_t dispatch_time_t;
65+
66+
static INLINE dispatch_semaphore_t dispatch_semaphore_create(long value)
67+
{
68+
semaphore_t s;
69+
if (semaphore_create(mach_task_self(), &s, SYNC_POLICY_FIFO,
70+
(int)value) != KERN_SUCCESS)
71+
return 0;
72+
return s;
73+
}
74+
static INLINE void dispatch_semaphore_signal(dispatch_semaphore_t s)
75+
{
76+
if (s)
77+
semaphore_signal(s);
78+
}
79+
static INLINE dispatch_time_t dispatch_time(dispatch_time_t base, int64_t delta)
80+
{
81+
(void)base;
82+
return (dispatch_time_t)delta;
83+
}
84+
static INLINE long dispatch_semaphore_wait(dispatch_semaphore_t s,
85+
dispatch_time_t ns)
86+
{
87+
mach_timespec_t ts;
88+
if (!s)
89+
return -1;
90+
ts.tv_sec = (unsigned int)(ns / NSEC_PER_SEC);
91+
ts.tv_nsec = (clock_res_t)(ns % NSEC_PER_SEC);
92+
return (semaphore_timedwait(s, ts) == KERN_SUCCESS) ? 0 : 1;
93+
}
94+
static INLINE void dispatch_release(dispatch_semaphore_t s)
95+
{
96+
if (s)
97+
semaphore_destroy(mach_task_self(), s);
98+
}
99+
#else
100+
#include <stdatomic.h>
20101
#include <dispatch/dispatch.h>
102+
#endif
21103

22104
#if TARGET_OS_IPHONE
23105
#include <AudioToolbox/AudioToolbox.h>
@@ -787,3 +869,25 @@ audio_driver_t audio_coreaudio = {
787869
coreaudio_buffer_size,
788870
coreaudio_write_raw
789871
};
872+
873+
/* Undo the legacy-Apple shim macros so they don't leak into other
874+
* translation units when this file is #included into griffin.c.
875+
*
876+
* Shim typedefs (atomic_size_t, memory_order, dispatch_semaphore_t,
877+
* dispatch_time_t) are left in place: C89/C99 forbid redefining a
878+
* typedef even to the same type, but nothing else in the PPC griffin
879+
* bundle declares these names (task_queue.c's GCD path is gated out
880+
* by HAVE_GCD; the Obj-C users are in griffin_objc.m, a separate TU).
881+
* If a future change adds another GCD/atomic user in griffin.c after
882+
* this point, wrap its typedefs in the same RARCH_COREAUDIO_LEGACY_APPLE
883+
* gate and include the shim there too. */
884+
#ifdef RARCH_COREAUDIO_LEGACY_APPLE
885+
#undef atomic_init
886+
#undef atomic_load_explicit
887+
#undef atomic_fetch_add_explicit
888+
#undef atomic_fetch_sub_explicit
889+
#undef memory_order_acquire
890+
#undef memory_order_release
891+
#undef DISPATCH_TIME_NOW
892+
#undef RARCH_COREAUDIO_LEGACY_APPLE
893+
#endif

0 commit comments

Comments
 (0)