Skip to content

Commit 29d8069

Browse files
authored
Merge pull request #4 from CoreRC/master
Add macOS support
2 parents 59b4e45 + 65323ef commit 29d8069

File tree

4 files changed

+160
-2
lines changed

4 files changed

+160
-2
lines changed

Disruptor/BuildConfig.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,11 @@
6262
# define DISRUPTOR_OS_FAMILY_WINDOWS
6363
#else
6464
# define DISRUPTOR_OS_FAMILY_UNIX
65+
# ifdef __APPLE__
66+
# define DISRUPTOR_OS_FAMILY_MACOS
67+
# else
68+
# define DISRUPTOR_OS_FAMILY_LINUX
69+
# endif
6570
#endif
6671

6772
#ifdef _DEBUG

Disruptor/CMakeLists.txt

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
project(Disruptor)
22
cmake_minimum_required(VERSION 2.6)
33

4-
find_package(Boost COMPONENTS system)
4+
find_package(Boost COMPONENTS system thread chrono)
55
if(Boost_FOUND)
66
include_directories(${Boost_INCLUDE_DIRS})
77
link_directories(${Boost_LIBRARY_DIRS})
@@ -27,6 +27,7 @@ set(Disruptor_sources
2727
stdafx.cpp
2828
ThreadPerTaskScheduler.cpp
2929
ThreadHelper_Linux.cpp
30+
ThreadHelper_macOS.cpp
3031
ThreadHelper_Windows.cpp
3132
TimeoutBlockingWaitStrategy.cpp
3233
TypeInfo.cpp
@@ -114,6 +115,7 @@ set(Disruptor_headers
114115
)
115116

116117
add_library(DisruptorShared SHARED ${Disruptor_sources})
118+
target_link_libraries(DisruptorShared ${Boost_LIBRARIES})
117119
set_target_properties(DisruptorShared PROPERTIES OUTPUT_NAME Disruptor)
118120
set_target_properties(DisruptorShared PROPERTIES VERSION ${DISRUPTOR_VERSION})
119121
set_target_properties(DisruptorShared PROPERTIES SOVERSION ${DISRUPTOR_VERSION_MAJOR})

Disruptor/ThreadHelper_Linux.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33

44
#include "BuildConfig.h"
55

6-
#ifdef DISRUPTOR_OS_FAMILY_UNIX
6+
#ifdef DISRUPTOR_OS_FAMILY_LINUX
77

88
#include <string>
99

Disruptor/ThreadHelper_macOS.cpp

Lines changed: 151 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,151 @@
1+
#include "stdafx.h"
2+
#include "ThreadHelper.h"
3+
4+
#include "BuildConfig.h"
5+
6+
#ifdef DISRUPTOR_OS_FAMILY_MACOS
7+
8+
#include <string>
9+
10+
#include <pthread.h>
11+
#include <unistd.h>
12+
#include <sched.h>
13+
#include <cpuid.h>
14+
#include <sys/sysctl.h>
15+
#include <sys/syscall.h>
16+
#include <sys/types.h>
17+
#include <mach/mach_types.h>
18+
#include <mach/thread_act.h>
19+
20+
#define SYSCTL_CORE_COUNT "machdep.cpu.core_count"
21+
22+
#define CPUID(INFO, LEAF, SUBLEAF) __cpuid_count(LEAF, SUBLEAF, INFO[0], INFO[1], INFO[2], INFO[3])
23+
24+
#define GETCPU(CPU) { \
25+
uint32_t CPUInfo[4]; \
26+
CPUID(CPUInfo, 1, 0); \
27+
/* CPUInfo[1] is EBX, bits 24-31 are APIC ID */ \
28+
if ( (CPUInfo[3] & (1 << 9)) == 0) { \
29+
(CPU) = -1; /* no APIC on chip */ \
30+
} \
31+
else { \
32+
(CPU) = (unsigned)CPUInfo[1] >> 24; \
33+
} \
34+
if ((CPU) < 0) (CPU) = 0; \
35+
}
36+
37+
namespace Disruptor
38+
{
39+
namespace ThreadHelper
40+
{
41+
typedef struct cpu_set {
42+
uint32_t count;
43+
} cpu_set_t;
44+
45+
static inline void CPU_ZERO(cpu_set_t *cs) { cs->count = 0; }
46+
47+
static inline void CPU_SET(int num, cpu_set_t *cs) { cs->count |= (1 << num); }
48+
49+
static inline int CPU_ISSET(int num, cpu_set_t *cs) { return (cs->count & (1 << num)); }
50+
51+
int sched_getaffinity(pid_t pid, size_t cpu_size, cpu_set_t *cpu_set)
52+
{
53+
(void) pid;
54+
(void) cpu_size;
55+
56+
int32_t core_count = 0;
57+
size_t len = sizeof(core_count);
58+
int ret = sysctlbyname(SYSCTL_CORE_COUNT, &core_count, &len, 0, 0);
59+
if (ret) {
60+
return -1;
61+
}
62+
cpu_set->count = 0;
63+
for (int i = 0; i < core_count; i++) {
64+
cpu_set->count |= (1 << i);
65+
}
66+
67+
return 0;
68+
}
69+
70+
int pthread_setaffinity_np(pthread_t thread, size_t cpu_size,
71+
cpu_set_t *cpu_set)
72+
{
73+
thread_port_t mach_thread;
74+
int core = 0;
75+
76+
for (core = 0; core < 8 * (int)cpu_size; core++) {
77+
if (CPU_ISSET(core, cpu_set)) break;
78+
}
79+
80+
thread_affinity_policy_data_t policy = { core };
81+
mach_thread = pthread_mach_thread_np(thread);
82+
thread_policy_set(mach_thread, THREAD_AFFINITY_POLICY,
83+
(thread_policy_t)&policy, 1);
84+
return 0;
85+
}
86+
87+
88+
size_t getProcessorCount()
89+
{
90+
return static_cast<size_t>(sysconf(_SC_NPROCESSORS_CONF));
91+
}
92+
93+
uint32_t getCurrentProcessor()
94+
{
95+
uint32_t cpu_id;
96+
97+
GETCPU(cpu_id);
98+
99+
return cpu_id;
100+
}
101+
102+
bool setThreadAffinity(const AffinityMask& mask)
103+
{
104+
cpu_set_t cpuSet;
105+
CPU_ZERO(&cpuSet);
106+
107+
for (size_t i = 0; i < mask.size(); ++i)
108+
{
109+
if (mask.test(i))
110+
CPU_SET(i, &cpuSet);
111+
}
112+
113+
return pthread_setaffinity_np(pthread_self(), sizeof(cpuSet), &cpuSet) == 0;
114+
}
115+
116+
AffinityMask getThreadAffinity()
117+
{
118+
AffinityMask mask;
119+
120+
cpu_set_t cpuSet;
121+
CPU_ZERO(&cpuSet);
122+
if (sched_getaffinity(0, sizeof(cpuSet), &cpuSet) == 0)
123+
{
124+
int processorCount = getProcessorCount();
125+
int maskSize = (int) mask.size();
126+
for (int i = 0; i < processorCount && i < maskSize; ++i)
127+
{
128+
if (CPU_ISSET(i, &cpuSet))
129+
mask.set(i);
130+
}
131+
}
132+
133+
return mask;
134+
}
135+
136+
uint32_t getCurrentThreadId()
137+
{
138+
uint64_t result;
139+
pthread_threadid_np(NULL, &result);
140+
return (uint32_t) result;
141+
}
142+
143+
void setThreadName(const std::string& name)
144+
{
145+
pthread_setname_np(name.c_str());
146+
}
147+
148+
} // namespace ThreadHelper
149+
} // namespace Disruptor
150+
151+
#endif // DISRUPTOR_OS_FAMILY_UNIX

0 commit comments

Comments
 (0)