OSX 10.11.6,提升1.63.0
我有一个64位master进程,它使用一个32位slave过程来进行一些实时渲染(我没有特定32位动态库的源代码,因此无法将其重新编译为64位)。时机很关键,我发现boost::interprocess的共享内存实用程序运行得很好,但我遇到了互操作性问题。当编译32与64&因此,当从从共享内存引用它们时,会导致问题。
64 bit
Scoped Lock: 16
Condition: 48
Mutex: 64
Semaphore: 4
32 bit
Scoped Lock: 8
Condition: 28
Mutex: 44
Semaphore: 4
我深入研究了boost::interprocess::interprocess_mutex标头,发现了_pthread_types.h:中声明的大小
// pthread opaque structures
#if defined(__LP64__)
#define __PTHREAD_SIZE__ 8176
#define __PTHREAD_ATTR_SIZE__ 56
#define __PTHREAD_MUTEXATTR_SIZE__ 8
#define __PTHREAD_MUTEX_SIZE__ 56
#define __PTHREAD_CONDATTR_SIZE__ 8
#define __PTHREAD_COND_SIZE__ 40
#define __PTHREAD_ONCE_SIZE__ 8
#define __PTHREAD_RWLOCK_SIZE__ 192
#define __PTHREAD_RWLOCKATTR_SIZE__ 16
#else // !__LP64__
#define __PTHREAD_SIZE__ 4088
#define __PTHREAD_ATTR_SIZE__ 36
#define __PTHREAD_MUTEXATTR_SIZE__ 8
#define __PTHREAD_MUTEX_SIZE__ 40
#define __PTHREAD_CONDATTR_SIZE__ 4
#define __PTHREAD_COND_SIZE__ 24
#define __PTHREAD_ONCE_SIZE__ 4
#define __PTHREAD_RWLOCK_SIZE__ 124
#define __PTHREAD_RWLOCKATTR_SIZE__ 12
#endif // !__LP64__
struct _opaque_pthread_mutex_t {
long __sig;
char __opaque[__PTHREAD_MUTEX_SIZE__];
};
使用时
boost::interprocess::interprocess_mutex
boost::interprocess::interprocess_condition
两个程序都编译为64位,数据呈现效果非常好。
有什么方法可以强制尺寸一致吗?或者我忽略了另一种IPC机制?
使用条件的好处是,它们可以向被阻塞的线程发出何时唤醒的信号,并大大减少浪费的CPU周期,因为等待的线程/进程不必不断运行来检查值。有没有其他方法可以用这种方式向线程/进程发出信号?
据我所知,OSX上至少有几个程序实现了64位<->之间的快速高效数据渲染32位,所以答案一定在某个地方。。
所以我接受了MikeMB&对管道做了一些研究。我找到了这张纸http://ace.ucv.ro/sintes12/SINTES12_2005/SOFTWARE%20ENGINEERING/44.pdf其建议使用管道作为锁定机构。对管道的读/写似乎实现了与进程间条件变量相同的信号机制,因此线程阻塞/唤醒非常有效。
看起来读/写速度足够快,可以在我的机器上进行实时设置!(尽管def还不能保证它能在其他机器上运行,但我只在2011年的MBP(2.2 GHz英特尔酷睿i7)上进行了测试)
它似乎和条件一样有效,我还没有得到任何数据丢失。这是我做的。只需将其中一个放在共享内存中,master和slave进程就可以调用wait()&post()。
struct PipeSemaphore
{
PipeSemaphore()
{
// make sure semaphore will work in shared memory
// between 32 <-> 64 bit processes
static_assert (sizeof (int) == 4);
int res = pipe (p);
// pipe failed to open
if (res == -1)
assert (false);
}
~PipeSemaphore()
{
close (p[0]);
close (p[1]);
}
// if nothing is in the pipe stream,
// the curr thread will block
inline int wait() noexcept
{
char b;
return read (p[0], &b, 1);
}
// writing to the pipe stream will notify
// & wake blocked threads
inline int post() noexcept
{
return write (p[1], "1", 1);
}
private:
int p[2];
};
任何对代码的建议都将不胜感激!