1
7
这里的答案并不简单。究竟发生了什么,意味着什么取决于许多事情。对于缓存一致性/内存的基本理解,我最近的博客条目可能会有所帮助: 但除此之外,让我试着回答几个问题。首先,下面的说明对所支持的内容非常有希望。
体系结构不能完全按照您的要求实现这一点。当您指定内存顺序时,您将指定重新排序的工作方式。要使用Intel的术语,您将指定您想要的围栏类型,其中有三种:全围栏、装载围栏和存储围栏。仅仅因为你想在这个操作上设置一个特定的围栏并不意味着它得到了支持,我希望它总是回到一个完整的围栏中。
编译器可能会使用
在内存同步方面,您需要了解缓存一致性是如何工作的(我的博客可能会有所帮助)。新的CPU使用ccnuma体系结构(以前是smp)。基本上,内存上的“视图”永远不会失去同步。代码中使用的围栏本身并不强制进行任何冲洗。如果两个内核在一个缓存行中都具有相同的内存位置,那么其中一个将被标记为脏的,另一个将根据需要重新加载。 对一个非常复杂的过程的一个非常简单的解释 要回答最后一个问题,您应该始终使用逻辑上需要正确的内存语义。大多数体系结构不支持您在程序中使用的所有组合。但是,在许多情况下,您会得到很好的优化,特别是在您请求的订单没有围栏的情况下(这很常见)。 --对一些评论的回答: 您必须区分执行写指令和写入内存位置意味着什么。这就是我在博客中试图解释的。当“0”被提交到0x100时,所有核心都会看到这个零。写整数也是原子的,也就是说,即使没有锁,当你写到一个位置时,如果所有核心想要使用它,它们都会立即拥有这个值。 问题是,要使用您可能首先将其加载到寄存器中的值,之后对位置的任何更改显然都不会触及寄存器。这就是为什么一个人需要互斥锁,尽管有一个缓存一致的内存。 至于相互矛盾的主张,一般你会看到各种各样的主张。不管它们是否矛盾,归根结底就是“see”“load”“execute”在上下文中的确切含义。如果您将“1”写入0x100,这是否意味着您执行了写入指令,或者CPU实际提交了该值。差异来自于重新排序。CPU可以延迟写入“1”,但您可以确定,当它最终提交“1”时,所有核心都会看到它。围栏控制着这一秩序。 |
a a · 为什么在这个可重入锁示例中需要引用计数? 2 年前 |
Grant · goroutines有高空闲唤醒电话 2 年前 |
hoaz · 如何安全地清理并发映射 6 年前 |
Alanpatchi · int基元类型的volatile声明 6 年前 |