指令和屏障:在x86上,'lwsync'与PowerPC上的哪个指令等效?

4

我的代码如下所示。我发现了读和写的rmbwmb,但没有找到通用的方法。lwsync在PowerPC上可用,但在x86上有什么替代品呢?提前感谢。

#define barrier() __asm__ volatile ("lwsync")
...
    lock()
    if(!pInst);
    {
        T* temp=new T;
        barrier();
        pInst=temp;
    }
    unlock();
3个回答

2

rmb()wmb()是Linux内核函数。还有mb()

我记得x86指令是lfencesfencemfence


rmb()和wmb()是汇编代码中的宏而不是函数。我只想看看如果没有设置屏障,gcc会如何进行优化。 - schemacs
1
如果你想特别谨慎,可以使用 asm volatile ("whatever":::memory); 告诉 GCC 任意内存地址可能已被破坏。我认为仅仅发出指令并不足够,如果 GCC 将加载缓存在寄存器中。 - tc.
这个答案似乎是错误的;至少对于直接的问题而言是如此。在x86上,lwsync是一个无操作指令,因为它没有像ARM、PPC和Alpha那样弱的内存模型。请参见Herding cats..第4.6节。对于IBM文档中的lwsync确保在执行函数的处理器上执行任何后续存储指令之前,调用__lwsync之前的所有指令都已经完成。 它只针对单个核心,而不是整个SMP系统。所以,它实际上是为了使流水线与O-O执行同步。 - artless noise
但我不明白这在OP的例子中有什么作用。它通常需要与多个内存元素一起使用。我猜它可能确保在赋值之前执行了任何“new”记账,但据我所知,其他核心可能看不到它。 - artless noise

0

在 Cilk 运行时中,有一个特定的文件可能会引起您的兴趣,即 cilk-sysdep.h,其中包含与内存屏障相关的系统特定映射。我提取了一个关于 x86 的小节,与您的问题相关,即 i386。

文件:-- cilk-sysdep.h(左侧的数字实际上是行号)
*我们使用xchg指令序列化内存访问,可以根据英特尔架构软件开发人员手册第3卷:系统编程指南进行操作 *(http://www.intel.com/design/pro/manuals/243192.htm),第7-6页, *“对于P6系列处理器,锁定操作会序列化所有未完成的加载和存储操作(即等待它们完成)。” *xchg指令默认是一个锁定操作。 *请注意,推荐的内存屏障是cpuid指令,这个指令非常慢(~70个周期)。相比之下, *xchg只需要大约23个周期(加上每个写缓冲区的几个?)仍然很慢,但这是我能找到的最好的方法。 -KHR * *Bradley还计时了“mfence”,在Pentium IV xchgl上速度要快得多 *mfence似乎需要在2.5GHZ P4上花费约125纳秒 *xchgl 似乎需要在2.5GHZ P4上花费约90纳秒 *但是在opteron上,mfence和xchgl的性能都很好。 *mfence在1.5GHZ AMD64上只需要8ns(也许这是801) *sfence需要5ns *lfence需要3ns *xchgl需要14ns *查看mfence-benchmark.c */ int x = 0,y; __asm__ volatile ("xchgl %0,%1" :"=r"(x) :"m"(y),"0"(x) :"memory"); }

我喜欢的是xchgl似乎更快 :) 不过你应该真正实现它们并检查一下。


在P6上更快?在AMD64上,mfence比xchg更快。 - doug65536

0

在这段代码中,您没有明确说明锁定和解锁是什么。我假设它们是互斥操作。在PowerPC上,互斥获取函数将使用isync(如果没有该硬件,则可能在lock()之前评估if(!pInst)),并且在unlock()中将具有lwsync(或sync,如果您的互斥实现过时)。

因此,假设您对pInst的所有访问(读取和写入)都受到锁定和解锁方法的保护,则您的屏障使用是多余的。解锁将具有足够的屏障,以确保在解锁操作完成之前pInst存储可见(因此,在使用相同的锁定的情况下,它将在任何后续锁定获取之后可见)。

在x86和x64上,您的lock()将使用某种形式的LOCK前缀指令,该指令自动具有双向栅栏行为。

在x86和x64上,您的解锁只需要是一个存储指令(除非您在CS中使用一些特殊的字符串指令,在这种情况下,您将需要一个SFENCE)。

手册:

http://www.intel.com/content/dam/www/public/us/en/documents/manuals/64-ia-32-architectures-software-developer-manual-325462.pdf

这个内容包含有关所有障碍以及LOCK前缀的影响的良好信息(以及何时暗示使用该前缀)。

附注:在解锁代码中,您还必须有一些强制编译器排序的东西(因此,如果只是存储零,则还需要类似于GCC样式的asm _volatile_("" ::: "memory"))。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接