]> git.ipfire.org Git - thirdparty/open-vm-tools.git/commitdiff
Replace Atomic_MFence with architecture-independent barrier primitives
authorOliver Kurth <okurth@vmware.com>
Fri, 15 Sep 2017 18:23:31 +0000 (11:23 -0700)
committerOliver Kurth <okurth@vmware.com>
Fri, 15 Sep 2017 18:23:31 +0000 (11:23 -0700)
Atomic_MFence was used to implement a full memory barrier on x86
architectures. In an effort to clean up duplicate code, this change
removes Atomic_MFence and replaces all previous uses with the most
conservative architecture-independent barrier primitive
(LDST_LDST_MEM_BARRIER). Since LDST_LDST_MEM_BARRIER is also a full
memory barrier, this change does not affect any existing ordering
semantics.

open-vm-tools/lib/include/vm_atomic.h
open-vm-tools/modules/linux/vsock/linux/notifyQState.c

index e909e7fd4f5c9a68de99e6b241fa461794e509c7..0b3db45f1709065bdc72b9f1888012a069f6c1ba 100644 (file)
@@ -1,5 +1,5 @@
 /*********************************************************
- * Copyright (C) 1998-2016 VMware, Inc. All rights reserved.
+ * Copyright (C) 1998-2017 VMware, Inc. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify it
  * under the terms of the GNU Lesser General Public License as published
@@ -139,10 +139,9 @@ long  _InterlockedCompareExchange(long volatile*, long, long);
 long  _InterlockedExchangeAdd(long volatile*, long);
 long  _InterlockedDecrement(long volatile*);
 long  _InterlockedIncrement(long volatile*);
-void  _ReadWriteBarrier(void);
 #pragma intrinsic(_InterlockedExchange, _InterlockedCompareExchange)
 #pragma intrinsic(_InterlockedExchangeAdd, _InterlockedDecrement)
-#pragma intrinsic(_InterlockedIncrement, _ReadWriteBarrier)
+#pragma intrinsic(_InterlockedIncrement)
 
 # if _MSC_VER >= 1600
 char     _InterlockedExchange8(char volatile *, char);
@@ -3934,69 +3933,6 @@ MAKE_ATOMIC_TYPE(Ptr, 32, void const *, void *, uintptr_t)
 MAKE_ATOMIC_TYPE(Int, 32, int, int, int)
 MAKE_ATOMIC_TYPE(Bool, 8, Bool, Bool, Bool)
 
-
-#if    defined VM_ARM_64 && defined VMKERNEL \
-    && !defined ATOMIC_MFENCE_SHOULD_NOT_BE_IN_CROSS_PLATFORM_CODE
-/*
- * Atomic_MFence() is an x86-ism, so in an ideal world it should never be
- * defined on ARM.
- *
- * There is ongoing work to remove all legacy Atomic_MFence() calls in
- * cross-platform code. The vmkernel code has mostly been cleaned up, but a few
- * calls remain in vmkernel module files which are granted an exception (by
- * defining ATOMIC_MFENCE_SHOULD_NOT_BE_IN_CROSS_PLATFORM_CODE) for now.
- *
- * Do not add more Atomic_MFence() calls to cross-platform code. Do not grant
- * any new exception. Instead, either move existing calls to an x86-specific
- * location, or replace them with cross-platform memory barriers such as
- * LDST_LDST_MEM_BARRIER().
- */
-#else // Should we define Atomic_MFence?
-/* Prevent the compiler from re-ordering memory references. */
-#ifdef __GNUC__
-#define ATOMIC_COMPILER_BARRIER()   __asm__ __volatile__ ("": : :"memory")
-#elif defined _MSC_VER
-#define ATOMIC_COMPILER_BARRIER()   _ReadWriteBarrier()
-#else
-#error No compiler defined for ATOMIC_COMPILER_BARRIER
-#endif
-
-
-/*
- *-----------------------------------------------------------------------------
- *
- * Atomic_MFence --
- *
- *      Implements mfence in terms of a lock xor. The reason for implementing
- *      our own mfence is that not all of our supported cpus have an assembly
- *      mfence (P3, Athlon). We put it here to avoid duplicating code which is
- *      also why it is prefixed with "Atomic_". Moreover, this implementation
- *      performs slightly better than 'mfence' on modern CPUs (See PR 817059).
- *
- * Results:
- *      None.
- *
- * Side effects:
- *      Cause loads and stores prior to this to be globally
- *      visible.
- *
- *-----------------------------------------------------------------------------
- */
-
-static INLINE void
-Atomic_MFence(void)
-{
-   Atomic_uint32 fence;
-   ATOMIC_COMPILER_BARRIER();
-   Atomic_Xor32(&fence, 0x1);
-   ATOMIC_COMPILER_BARRIER();
-}
-
-#ifdef ATOMIC_COMPILER_BARRIER
-#undef ATOMIC_COMPILER_BARRIER
-#endif /* ATOMIC_COMPILER_BARRIER */
-#endif // Should we define Atomic_MFence?
-
 #ifdef VM_ARM_64
 #   include "vm_atomic_arm64_end.h"
 #endif
index 464454b35a3f9be384ac7e028c173eb2dc5c3157..3e7f2aef4031497bbe0ab0499d525e1dc2009ae7 100644 (file)
@@ -1,5 +1,5 @@
 /*********************************************************
- * Copyright (C) 2009-2014 VMware, Inc. All rights reserved.
+ * Copyright (C) 2009-2014,2017 VMware, Inc. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify it
  * under the terms of the GNU General Public License as published by the
@@ -551,7 +551,7 @@ VSockVmciNotifyPktRecvPostDequeue(struct sock *sk,               // IN
    err = 0;
 
    if (dataRead) {
-      Atomic_MFence();
+      LDST_LDST_MEM_BARRIER();
 
       freeSpace = vmci_qpair_consume_free_space(vsk->qpair);
       wasFull = freeSpace == copied;
@@ -635,7 +635,7 @@ VSockVmciNotifyPktSendPostEnqueue(struct sock *sk,               // IN
 
    vsk = vsock_sk(sk);
 
-   Atomic_MFence();
+   LDST_LDST_MEM_BARRIER();
 
    wasEmpty = (vmci_qpair_produce_buf_ready(vsk->qpair) == written);
    if (wasEmpty) {