1.0.25.24: x86/x86-64 runtime pseudo atomic fixes
authorGabor Melis <mega@hotpop.com>
Mon, 16 Feb 2009 21:38:43 +0000 (21:38 +0000)
committerGabor Melis <mega@hotpop.com>
Mon, 16 Feb 2009 21:38:43 +0000 (21:38 +0000)
Make sure that {clear,set}_pseudo_atomic_{atomic,interrupted} boil
down to a single assembly intruction. And that the compiler does not
reorder them.

I think the ppc bits in pseudo-atomic.h are still broken on both
accounts.

src/runtime/alloc.c
src/runtime/gc.h
src/runtime/gencgc.c
src/runtime/interrupt.c
src/runtime/parse.c
src/runtime/pseudo-atomic.h
src/runtime/thread.h
src/runtime/x86-64-arch.c
src/runtime/x86-arch.c
version.lisp-expr

index 4f3be56..19518e4 100644 (file)
@@ -24,6 +24,7 @@
 #include "globals.h"
 #include "gc.h"
 #include "thread.h"
+#include "pseudo-atomic.h"
 #include "genesis/vector.h"
 #include "genesis/cons.h"
 #include "genesis/bignum.h"
index 35f9d12..ce1b925 100644 (file)
@@ -40,8 +40,6 @@ extern void clear_auto_gc_trigger(void);
 
 #include "fixnump.h"
 
-#include "pseudo-atomic.h"
-
 extern boolean maybe_gc(os_context_t *context);
 
 extern unsigned long bytes_consed_between_gcs;
index 5d687f4..895ced2 100644 (file)
@@ -41,6 +41,7 @@
 #include "gc.h"
 #include "gc-internal.h"
 #include "thread.h"
+#include "pseudo-atomic.h"
 #include "alloc.h"
 #include "genesis/vector.h"
 #include "genesis/weak-pointer.h"
index 74fd67b..4860be2 100644 (file)
@@ -63,6 +63,7 @@
 #include "alloc.h"
 #include "dynbind.h"
 #include "interr.h"
+#include "pseudo-atomic.h"
 #include "genesis/fdefn.h"
 #include "genesis/simple-fun.h"
 #include "genesis/cons.h"
index b4218e5..beedc29 100644 (file)
@@ -32,6 +32,7 @@
 #include "arch.h"
 #include "search.h"
 #include "thread.h"
+#include "pseudo-atomic.h"
 
 #include "genesis/simple-fun.h"
 #include "genesis/fdefn.h"
index df5e900..9636e5b 100644 (file)
     SymbolValue(ALLOCATION_POINTER, 0)
 #define get_binding_stack_pointer(thread)       \
     SymbolValue(BINDING_STACK_POINTER, thread)
-#define get_pseudo_atomic_atomic(thread)        \
-    (fixnum_value(SymbolValue(PSEUDO_ATOMIC_BITS, thread) & make_fixnum(1)))
-#define set_pseudo_atomic_atomic(thread)                                \
-    { \
-        lispobj bits = SymbolValue(PSEUDO_ATOMIC_BITS, thread); \
-        SetSymbolValue(PSEUDO_ATOMIC_BITS, bits | make_fixnum(1), thread); \
-    }
-#define clear_pseudo_atomic_atomic(thread)                      \
-    { \
-        lispobj bits = SymbolValue(PSEUDO_ATOMIC_BITS, thread);       \
-        SetSymbolValue(PSEUDO_ATOMIC_BITS, bits & ~make_fixnum(1), thread); \
-    }
-#define get_pseudo_atomic_interrupted(thread)                   \
-    (fixnum_value(SymbolValue(PSEUDO_ATOMIC_BITS, thread) & make_fixnum(2)))
-#define clear_pseudo_atomic_interrupted(thread)                         \
-    { \
-        lispobj bits = SymbolValue(PSEUDO_ATOMIC_BITS, thread);       \
-        SetSymbolValue(PSEUDO_ATOMIC_BITS, bits & ~make_fixnum(2), thread); \
-    }
 
-#define set_pseudo_atomic_interrupted(thread)                           \
-    { \
-        lispobj bits = SymbolValue(PSEUDO_ATOMIC_BITS, thread); \
-        SetSymbolValue(PSEUDO_ATOMIC_BITS, bits | make_fixnum(2), thread); \
-    }
+#if defined(LISP_FEATURE_X86)
+#define LISPOBJ_ASM_SUFFIX "l"
+#elif defined(LISP_FEATURE_X86_64)
+#define LISPOBJ_ASM_SUFFIX "q"
+#endif
+
+static inline int
+get_pseudo_atomic_atomic(struct thread *thread)
+{
+    return fixnum_value(SymbolValue(PSEUDO_ATOMIC_BITS, thread) &
+                        make_fixnum(1));
+}
+
+static inline void
+set_pseudo_atomic_atomic(struct thread *thread)
+{
+    lispobj *p = SymbolValueAddress(PSEUDO_ATOMIC_BITS, thread);
+    __asm__ __volatile__
+        ("or" LISPOBJ_ASM_SUFFIX " %0,%1"
+         :
+         : "g" (make_fixnum(1)), "m" (*p)
+         : "memory");
+}
+
+static inline void
+clear_pseudo_atomic_atomic(struct thread *thread)
+{
+    lispobj *p = SymbolValueAddress(PSEUDO_ATOMIC_BITS, thread);
+    __asm__ __volatile__
+        ("and" LISPOBJ_ASM_SUFFIX " %0,%1"
+         :
+         : "g" (~make_fixnum(1)), "m" (*p)
+         : "memory");
+}
+
+static inline int
+get_pseudo_atomic_interrupted(struct thread *thread)
+{
+    return fixnum_value(SymbolValue(PSEUDO_ATOMIC_BITS, thread) &
+                        make_fixnum(2));
+}
+
+static inline void
+set_pseudo_atomic_interrupted(struct thread *thread)
+{
+    lispobj *p = SymbolValueAddress(PSEUDO_ATOMIC_BITS, thread);
+    __asm__ __volatile__
+        ("or" LISPOBJ_ASM_SUFFIX " %0,%1"
+         :
+         : "g" (make_fixnum(2)), "m" (*p)
+         : "memory");
+}
+
+static inline void
+clear_pseudo_atomic_interrupted(struct thread *thread)
+{
+    lispobj *p = SymbolValueAddress(PSEUDO_ATOMIC_BITS, thread);
+    __asm__ __volatile__
+        ("and" LISPOBJ_ASM_SUFFIX " %0,%1"
+         :
+         : "g" (~make_fixnum(2)), "m" (*p)
+         : "memory");
+}
+
+#undef LISPOBJ_SUFFIX
 
 #elif defined(LISP_FEATURE_PPC) && defined(LISP_FEATURE_GENCGC)
 
+/* FIXME: Are these async signal safe? Compiler reordering? */
+
 #define set_alloc_pointer(value) \
     (dynamic_space_free_pointer = \
      ((lispobj *) \
index cf13ac9..074edec 100644 (file)
@@ -51,6 +51,21 @@ extern int dynamic_values_bytes;
 #define for_each_thread(th) for(th=all_threads;th;th=0)
 #endif
 
+static inline lispobj *
+SymbolValueAddress(u64 tagged_symbol_pointer, void *thread)
+{
+    struct symbol *sym= (struct symbol *)
+        (pointer_sized_uint_t)(tagged_symbol_pointer-OTHER_POINTER_LOWTAG);
+#ifdef LISP_FEATURE_SB_THREAD
+    if(thread && sym->tls_index) {
+        lispobj *r = &(((union per_thread_data *)thread)
+                       ->dynamic_values[fixnum_value(sym->tls_index)]);
+        if((*r)!=NO_TLS_VALUE_MARKER_WIDETAG) return r;
+    }
+#endif
+    return &sym->value;
+}
+
 static inline lispobj
 SymbolValue(u64 tagged_symbol_pointer, void *thread)
 {
index a7f7354..d075ce6 100644 (file)
@@ -25,6 +25,7 @@
 #include "interr.h"
 #include "breakpoint.h"
 #include "thread.h"
+#include "pseudo-atomic.h"
 
 #include "genesis/static-symbols.h"
 #include "genesis/symbol.h"
index d6150dd..3ef4bec 100644 (file)
@@ -24,6 +24,7 @@
 #include "interr.h"
 #include "breakpoint.h"
 #include "thread.h"
+#include "pseudo-atomic.h"
 
 #include "genesis/static-symbols.h"
 #include "genesis/symbol.h"
index 7861267..36ac9e2 100644 (file)
@@ -17,4 +17,4 @@
 ;;; checkins which aren't released. (And occasionally for internal
 ;;; versions, especially for internal versions off the main CVS
 ;;; branch, it gets hairier, e.g. "0.pre7.14.flaky4.13".)
-"1.0.25.23"
+"1.0.25.24"