Java Unsafe.storeFence()文档错误了?

时间:2015-06-02 15:42:22

标签: java multithreading unsafe memory-fences

Java 8为sun.misc.Unsafe添加了三个围栏。

在阅读他们的文档后我感到困惑。

所以,我搜索了网络,发现了这个link

根据上面的页面,我相信这些方法在实践中几乎没有增加任何内容。如果我错了,请纠正我,粗略地说,loadFence(),storeFence()和fullFence()分别对应于volatile read,lazy write和volatile write,尽管技术上这些fences比volatile变量更强。所以loadFence()是一个获取栅栏,而storeFence()是一个释放栅栏,而fullFence()是一个完整的栅栏。

但是,storeFence()的文档看起来很奇怪。

它说,

/**
 * Ensures lack of reordering of stores before the fence
 * with loads or stores after the fence.
 */
void storeFence();

这看起来不像发布栏。它应该如何使用?不应该是

/**
 * Ensures lack of reordering of loads or stores before the fence
 * with stores after the fence.
 */
void storeFence();

我认为之前意味着更早,而之后意味着更晚。

修改

当我说这些“围栏在实践中没有添加任何内容”时,我并不是说“我们不会在通常的开发中使用它们。”

我的意思是,即使没有这些方法,我们也可以获得这些“围栏”。如果我是正确的,实际上,读取一个虚拟的volatile会产生loadFence()的效果,而写一个虚拟的volatile会产生fullFence()的效果,而unsafe.putOrderedXXX()(或者AtomicInteger.lazySet())会产生效果。 storeFence()。

它们可能有细微差别,但在目前的实施中,它们是可交换的。 (链接暗示似乎)

这就是我所说的“他们没有添加任何新内容”。

另一个编辑

这已经修好了。

请参阅https://bugs.openjdk.java.net/browse/JDK-8038978

谢谢@ john-vint

2 个答案:

答案 0 :(得分:6)

在JDK9中实际上存在差异。有人提出并澄清了类似的问题:

http://hg.openjdk.java.net/jdk9/jdk9/jdk/rev/84e19392365e

      /**
!      * Ensures that loads before the fence will not be reordered with loads and
!      * stores after the fence; a "LoadLoad plus LoadStore barrier".
!      *
!      * Corresponds to C11 atomic_thread_fence(memory_order_acquire)
!      * (an "acquire fence").
!      *
!      * A pure LoadLoad fence is not provided, since the addition of LoadStore
!      * is almost always desired, and most current hardware instructions that
!      * provide a LoadLoad barrier also provide a LoadStore barrier for free.
       * @since 1.8
       */
      public native void loadFence();

      /**
!      * Ensures that loads and stores before the fence will not be reordered with
!      * stores after the fence; a "StoreStore plus LoadStore barrier".
!      *
!      * Corresponds to C11 atomic_thread_fence(memory_order_release)
!      * (a "release fence").
!      *
!      * A pure StoreStore fence is not provided, since the addition of LoadStore
!      * is almost always desired, and most current hardware instructions that
!      * provide a StoreStore barrier also provide a LoadStore barrier for free.
       * @since 1.8
       */
      public native void storeFence();

      /**
!      * Ensures that loads and stores before the fence will not be reordered
!      * with loads and stores after the fence.  Implies the effects of both
!      * loadFence() and storeFence(), and in addition, the effect of a StoreLoad
!      * barrier.
!      *
!      * Corresponds to C11 atomic_thread_fence(memory_order_seq_cst).
       * @since 1.8
       */
      public native void fullFence();

答案 1 :(得分:0)

  

我相信这些方法在实践中几乎没有增加任何东西。

正确,他们不会在99.9%的应用程序中添加任何内容。只有在特定情况下才需要直接调用此方法,而不是使用更高级别的构造。

  

分别是volatile read,lazy write和volatile write,

我将其读作"易失性读取,易失性写入,易失性写入和读取"它似乎不是一个懒惰/有序的写入围栏。

  

loadFence()是一个获取栅栏,而storeFence()是一个释放栅栏,

我不相信这些转化为获取/释放语义。他们比这更基本。例如,这些方法没有状态变化。获取/释放需要原子操作,例如compareAndSet,这是另一种不安全的方法。