/* ----------------------------------------------------------------------------
*
- * (c) The GHC Team, 2005-2008
+ * (c) The GHC Team, 2005-2009
*
* Macros for multi-CPU support
*
+ * Do not #include this file directly: #include "Rts.h" instead.
+ *
+ * To understand the structure of the RTS headers, see the wiki:
+ * http://hackage.haskell.org/trac/ghc/wiki/Commentary/SourceTree/Includes
+ *
* -------------------------------------------------------------------------- */
#ifndef SMP_H
*/
EXTERN_INLINE StgWord atomic_dec(StgVolatilePtr p);
+/*
+ * Busy-wait nop: this is a hint to the CPU that we are currently in a
+ * busy-wait loop waiting for another CPU to change something. On a
+ * hypertreaded CPU it should yield to another thread, for example.
+ */
+EXTERN_INLINE void busy_wait_nop(void);
+
#endif // !IN_STG_CODE
/*
#endif
}
+EXTERN_INLINE void
+busy_wait_nop(void)
+{
+#if defined(i386_HOST_ARCH) || defined(x86_64_HOST_ARCH)
+ __asm__ __volatile__ ("rep; nop");
+ //
+#else
+ // nothing
+#endif
+}
+
#endif // !IN_STG_CODE
/*
#endif
}
+// Load a pointer from a memory location that might be being modified
+// concurrently. This prevents the compiler from optimising away
+// multiple loads of the memory location, as it might otherwise do in
+// a busy wait loop for example.
+#define VOLATILE_LOAD(p) (*((StgVolatilePtr)(p)))
+
/* ---------------------------------------------------------------------- */
#else /* !THREADED_RTS */
return old;
}
-STATIC_INLINE StgWord
+EXTERN_INLINE StgWord cas(StgVolatilePtr p, StgWord o, StgWord n);
+EXTERN_INLINE StgWord
cas(StgVolatilePtr p, StgWord o, StgWord n)
{
StgWord result;
return --(*p);
}
+#define VOLATILE_LOAD(p) ((StgWord)*((StgWord*)(p)))
+
#endif /* !THREADED_RTS */
#endif /* SMP_H */