summaryrefslogtreecommitdiffstats
path: root/llvm/atomic/coremu-template.h
diff options
context:
space:
mode:
authorTimothy Pearson <tpearson@raptorengineering.com>2019-11-29 19:00:14 -0600
committerTimothy Pearson <tpearson@raptorengineering.com>2019-11-29 19:02:28 -0600
commit4b3250c5073149c59c5c11e06c2c0d93b6a9f5ff (patch)
treedce73321255f834f7b2d4c16fa49760edb534f27 /llvm/atomic/coremu-template.h
parenta58047f7fbb055677e45c9a7d65ba40fbfad4b92 (diff)
downloadhqemu-4b3250c5073149c59c5c11e06c2c0d93b6a9f5ff.zip
hqemu-4b3250c5073149c59c5c11e06c2c0d93b6a9f5ff.tar.gz
Initial overlay of HQEMU 2.5.2 changes onto underlying 2.5.1 QEMU GIT tree2.5.1_overlay
Diffstat (limited to 'llvm/atomic/coremu-template.h')
-rw-r--r--llvm/atomic/coremu-template.h101
1 files changed, 101 insertions, 0 deletions
diff --git a/llvm/atomic/coremu-template.h b/llvm/atomic/coremu-template.h
new file mode 100644
index 0000000..66b185c
--- /dev/null
+++ b/llvm/atomic/coremu-template.h
@@ -0,0 +1,101 @@
+/* The following code may be included multiple times in a single file. */
+
+#if DATA_BITS == 64
+# define DATA_TYPE uint64_t
+# define SUFFIX q
+#elif DATA_BITS == 32
+# define DATA_TYPE uint32_t
+# define SUFFIX l
+#elif DATA_BITS == 16
+# define DATA_TYPE uint16_t
+# define SUFFIX w
+#elif DATA_BITS == 8
+# define DATA_TYPE uint8_t
+# define SUFFIX b
+#else
+#error unsupported data size
+#endif
+
+static __inline__ void coremu_glue(atomic_inc, SUFFIX)(DATA_TYPE *p) {
+ asm volatile(
+ LOCK_PREFIX "inc"coremu_str(SUFFIX)" %0"
+ : "+m"(*p)
+ :
+ : "cc");
+}
+
+static __inline__ void coremu_glue(atomic_dec, SUFFIX)(DATA_TYPE *p) {
+ asm volatile(
+ LOCK_PREFIX "dec"coremu_str(SUFFIX)" %0"
+ : "+m"(*p)
+ :
+ : "cc");
+}
+
+static __inline__ void coremu_glue(atomic_add, SUFFIX)(DATA_TYPE* addr,
+ DATA_TYPE val) {
+ asm volatile(
+ LOCK_PREFIX "add"coremu_str(SUFFIX)" %1, %0"
+ : "+m"(*addr)
+ : "a"(val)
+ : "cc");
+}
+
+/* swap the value VAL and *p.
+ * Return the value swapped out from memory. */
+static inline DATA_TYPE coremu_glue(atomic_exchange, SUFFIX)(
+ DATA_TYPE *p, DATA_TYPE val)
+{
+ DATA_TYPE out;
+ __asm __volatile(
+ "lock; xchg"coremu_str(SUFFIX)" %1,%2 \n\t"
+ : "=a" (out), "+m" (*p)
+ : "a" (val)
+ );
+ return out;
+}
+/* Return previous value in addr. So if the return value is the same as oldval,
+ * swap occured. */
+static __inline__ DATA_TYPE coremu_glue(atomic_compare_exchange, SUFFIX)(DATA_TYPE *addr,
+ DATA_TYPE oldval, DATA_TYPE newval) {
+ asm volatile(
+ LOCK_PREFIX "cmpxchg"coremu_str(SUFFIX)" %2, %1"
+ : "+a"(oldval), "+m"(*addr)
+ : "q"(newval)
+ : "cc");
+
+ return oldval;
+}
+
+static __inline__ void coremu_glue(atomic_and, SUFFIX)(DATA_TYPE *addr,
+ DATA_TYPE mask) {
+ asm volatile(
+ LOCK_PREFIX "and"coremu_str(SUFFIX)" %1, %0"
+ : "+m"(*addr)
+ : "r"(mask)
+ : "cc");
+}
+
+static __inline__ void coremu_glue(atomic_or, SUFFIX)(DATA_TYPE *addr,
+ DATA_TYPE mask) {
+ asm volatile(
+ LOCK_PREFIX "or"coremu_str(SUFFIX)" %1, %0"
+ : "+m"(*addr)
+ : "r"(mask)
+ : "cc");
+}
+
+static __inline__ DATA_TYPE coremu_glue(atomic_xadd, SUFFIX)(
+ DATA_TYPE* addr, DATA_TYPE val) {
+ asm volatile(
+ LOCK_PREFIX "xadd"coremu_str(SUFFIX)" %0, %1"
+ : "+a"(val), "+m"(*addr)
+ :
+ : "cc");
+
+ return val;
+}
+
+#undef DATA_BITS
+#undef DATA_TYPE
+#undef SUFFIX
OpenPOWER on IntegriCloud