6

我最近了解到编译器会通过重新排列指令来优化你的代码,这可以通过使用屏障来控制。

IIRC,锁定互斥锁会造成障碍,解锁互斥锁也会造成障碍,以防止关键部分内的代码流出。

所以 pthread_mutex_lock 和 pthread_mutex_unlock 必须隐含地成为这些“障碍”。如果我有这样一个包含互斥锁的类怎么办?

class IMutex {
public:
    virtual void lock() = 0;
    virtual void unlock() = 0;
};

在我看来,编译器不会知道我在 lock() 中调用 pthread_mutex_lock(),在 unlock() 中调用 pthread_mutex_unlock(),因为它们都是虚拟的。

这会导致错误吗?我是否需要以某种方式手动指定障碍?

4

1 回答 1

6

重新排序指令在各个级别上完成。最明显的是编译器,不太明显的是 CPU(运行中)。然而,同步函数几乎总是一个栅栏,它可以防止栅栏前后的指令重新排序。

因此,如果您的虚拟lock调用pthread_mutex_*(),那么您的虚拟功能包含一个栅栏。

所以简短的回答是:不,它不会导致错误。

还有 volatile 关键字,根据平台也可以生成栅栏。然而,使用 volatile 关键字会使检测这些栅栏变得更加困难,因为每次使用易失的函数或变量时,都会引入栅栏。所以建议你使用平台的同步功能。

The only time you need to be aware of fences is when you are not using concurrency objects to perform synchronization (like using a bool instead of a mutex).

于 2013-04-08T10:53:57.420 回答