1.0.41.21: runtime: Current stack and frame pointers are per-thread data.
authorAlastair Bridgewater <lisphacker@users.sourceforge.net>
Sat, 7 Aug 2010 13:46:26 +0000 (13:46 +0000)
committerAlastair Bridgewater <lisphacker@users.sourceforge.net>
Sat, 7 Aug 2010 13:46:26 +0000 (13:46 +0000)
  * Add slots to the thread structure on threaded targets to hold
the control stack and frame pointers.

  * Add some macros to thread.h to grab the correct variable or
slot on all builds, and use them everywhere required.

  * Conditional-compile out the old global variables for this on
threaded targets (I probably messed this up).

16 files changed:
src/compiler/generic/objdef.lisp
src/runtime/alloc.c
src/runtime/backtrace.c
src/runtime/funcall.c
src/runtime/gc-common.c
src/runtime/gencgc.c
src/runtime/globals.c
src/runtime/globals.h
src/runtime/interrupt.c
src/runtime/monitor.c
src/runtime/purify.c
src/runtime/thread.c
src/runtime/thread.h
src/runtime/x86-64-arch.c
src/runtime/x86-arch.c
version.lisp-expr

index 0d23165..ccad11b 100644 (file)
   ;; the runtime, but it's clearly a per-thread value.
   #!+sb-thread
   (foreign-function-call-active :c-type "boolean")
+  ;; Same as above for the location of the current control stack frame.
+  #!+(and sb-thread (not (or x86 x86-64)))
+  (control-frame-pointer :c-type "lispobj *")
+  ;; Same as above for the location of the current control stack
+  ;; pointer.  This is also used on threaded x86oids to allow LDB to
+  ;; print an approximation of the CSP as needed.
+  #!+(and sb-thread)
+  (control-stack-pointer :c-type "lispobj *")
   ;; KLUDGE: On alpha, until STEPPING we have been lucky and the 32
   ;; bit slots came in pairs. However the C compiler will align
   ;; interrupt_contexts on a double word boundary. This logic should
index eeb827f..58c1798 100644 (file)
@@ -73,13 +73,13 @@ pa_alloc(int bytes, int page_type_flag)
 #ifdef LISP_FEATURE_STACK_GROWS_DOWNWARD_NOT_UPWARD
 #error "!C_STACK_IS_CONTROL_STACK and STACK_GROWS_DOWNWARD_NOT_UPWARD is not supported"
 #endif
-        *current_control_stack_pointer = (lispobj) result;
-        current_control_stack_pointer += 1;
+        *access_control_stack_pointer(th) = (lispobj) result;
+        access_control_stack_pointer(th) += 1;
 #endif
         do_pending_interrupt();
 #ifndef LISP_FEATURE_C_STACK_IS_CONTROL_STACK
-        current_control_stack_pointer -= 1;
-        result = (lispobj *) *current_control_stack_pointer;
+        access_control_stack_pointer(th) -= 1;
+        result = (lispobj *) *access_control_stack_pointer(th);
 #endif
     }
     return result;
index 996357e..a9fde5d 100644 (file)
@@ -110,13 +110,13 @@ cs_valid_pointer_p(struct call_frame *pointer)
 {
     struct thread *thread=arch_os_get_current_thread();
     return (((char *) thread->control_stack_start <= (char *) pointer) &&
-            ((char *) pointer < (char *) current_control_stack_pointer));
+            ((char *) pointer < (char *) access_control_stack_pointer(thread)));
 }
 
 static void
 call_info_from_lisp_state(struct call_info *info)
 {
-    info->frame = (struct call_frame *)current_control_frame_pointer;
+    info->frame = (struct call_frame *)access_control_frame_pointer(arch_os_get_current_thread());
     info->interrupted = 0;
     info->code = NULL;
     info->lra = 0;
index 91f5513..c3724eb 100644 (file)
@@ -85,7 +85,9 @@ funcall3(lispobj function, lispobj arg0, lispobj arg1, lispobj arg2)
 lispobj
 funcall0(lispobj function)
 {
-    lispobj *args = current_control_stack_pointer;
+    lispobj **stack_pointer
+        = &access_control_stack_pointer(arch_os_get_current_thread());
+    lispobj *args = *stack_pointer;
 
     return safe_call_into_lisp(function, args, 0);
 }
@@ -93,9 +95,11 @@ funcall0(lispobj function)
 lispobj
 funcall1(lispobj function, lispobj arg0)
 {
-    lispobj *args = current_control_stack_pointer;
+    lispobj **stack_pointer
+        = &access_control_stack_pointer(arch_os_get_current_thread());
+    lispobj *args = *stack_pointer;
 
-    current_control_stack_pointer += 1;
+    *stack_pointer += 1;
     args[0] = arg0;
 
     return safe_call_into_lisp(function, args, 1);
@@ -104,9 +108,11 @@ funcall1(lispobj function, lispobj arg0)
 lispobj
 funcall2(lispobj function, lispobj arg0, lispobj arg1)
 {
-    lispobj *args = current_control_stack_pointer;
+    lispobj **stack_pointer
+        = &access_control_stack_pointer(arch_os_get_current_thread());
+    lispobj *args = *stack_pointer;
 
-    current_control_stack_pointer += 2;
+    *stack_pointer += 2;
     args[0] = arg0;
     args[1] = arg1;
 
@@ -116,9 +122,11 @@ funcall2(lispobj function, lispobj arg0, lispobj arg1)
 lispobj
 funcall3(lispobj function, lispobj arg0, lispobj arg1, lispobj arg2)
 {
-    lispobj *args = current_control_stack_pointer;
+    lispobj **stack_pointer
+        = &access_control_stack_pointer(arch_os_get_current_thread());
+    lispobj *args = *stack_pointer;
 
-    current_control_stack_pointer += 3;
+    *stack_pointer += 3;
     args[0] = arg0;
     args[1] = arg1;
     args[2] = arg2;
index cc76f5c..95b5c3b 100644 (file)
@@ -2514,7 +2514,7 @@ scrub_control_stack(void)
 #ifdef LISP_FEATURE_C_STACK_IS_CONTROL_STACK
     sp = (lispobj *)&sp - 1;
 #else
-    sp = current_control_stack_pointer;
+    sp = access_control_stack_pointer(th);
 #endif
  scrub:
     if ((((os_vm_address_t)sp < (hard_guard_page_address + os_vm_page_size)) &&
index 74b818e..f3c3aab 100644 (file)
@@ -3833,14 +3833,11 @@ write_protect_generation_pages(generation_index_t generation)
 static void
 scavenge_control_stack(struct thread *th)
 {
-    unsigned long control_stack_size;
-
-    /* This is going to be a big problem when we try to port threads
-     * to PPC... CLH */
     lispobj *control_stack =
         (lispobj *)(th->control_stack_start);
+    unsigned long control_stack_size =
+        access_control_stack_pointer(th) - control_stack;
 
-    control_stack_size = current_control_stack_pointer - control_stack;
     scavenge(control_stack, control_stack_size);
 }
 #endif
index 9eec708..5c0cd1d 100644 (file)
 int foreign_function_call_active;
 #endif
 
+#if !defined(LISP_FEATURE_SB_THREAD) && !defined(LISP_FEATURE_C_STACK_IS_CONTROL_STACK)
 lispobj *current_control_stack_pointer;
+#endif
+#if defined(LISP_FEATURE_X86) || defined(LISP_FEATURE_X86_64) || !defined(LISP_FEATURE_SB_THREAD)
 lispobj *current_control_frame_pointer;
+#endif
 #if !defined(BINDING_STACK_POINTER) && !defined(LISP_FEATURE_SB_THREAD)
 lispobj *current_binding_stack_pointer;
 #endif
@@ -56,7 +60,9 @@ void globals_init(void)
 {
     /* Space, stack, and free pointer vars are initialized by
      * validate() and coreparse(). */
+#if defined(LISP_FEATURE_X86) || defined(LISP_FEATURE_X86_64) || !defined(LISP_FEATURE_SB_THREAD)
     current_control_frame_pointer = (lispobj *)0;
+#endif
 
 #ifndef LISP_FEATURE_GENCGC
     /* no GC trigger yet */
index 7d424a8..e807eee 100644 (file)
@@ -47,8 +47,12 @@ extern char **ENVIRON;
 extern pthread_key_t specials;
 #endif
 
+#if !defined(LISP_FEATURE_SB_THREAD) && !defined(LISP_FEATURE_C_STACK_IS_CONTROL_STACK)
 extern lispobj *current_control_stack_pointer;
+#endif
+#if defined(LISP_FEATURE_X86) || defined(LISP_FEATURE_X86_64) || !defined(LISP_FEATURE_SB_THREAD)
 extern lispobj *current_control_frame_pointer;
+#endif
 #if !defined(LISP_FEATURE_X86) && !defined(LISP_FEATURE_X86_64) && !defined(LISP_FEATURE_SB_THREAD)
 extern lispobj *current_binding_stack_pointer;
 #endif
@@ -118,7 +122,9 @@ extern void globals_init(void);
 EXTERN(foreign_function_call_active, 4)
 #endif
 
+#if !defined(LISP_FEATURE_SB_THREAD) && !defined(LISP_FEATURE_C_STACK_IS_CONTROL_STACK)
 EXTERN(current_control_stack_pointer, POINTERSIZE)
+#endif
 EXTERN(current_control_frame_pointer, POINTERSIZE)
 # if !defined(LISP_FEATURE_X86) && !defined(LISP_FEATURE_X86_64)
 EXTERN(current_binding_stack_pointer, POINTERSIZE)
index 5f057aa..ea0880f 100644 (file)
@@ -609,23 +609,23 @@ build_fake_control_stack_frames(struct thread *th,os_context_t *context)
 
     /* Build a fake stack frame or frames */
 
-    current_control_frame_pointer =
+    access_control_frame_pointer(th) =
         (lispobj *)(unsigned long)
             (*os_context_register_addr(context, reg_CSP));
     if ((lispobj *)(unsigned long)
             (*os_context_register_addr(context, reg_CFP))
-        == current_control_frame_pointer) {
+        == access_control_frame_pointer(th)) {
         /* There is a small window during call where the callee's
          * frame isn't built yet. */
         if (lowtag_of(*os_context_register_addr(context, reg_CODE))
             == FUN_POINTER_LOWTAG) {
             /* We have called, but not built the new frame, so
              * build it for them. */
-            current_control_frame_pointer[0] =
+            access_control_frame_pointer(th)[0] =
                 *os_context_register_addr(context, reg_OCFP);
-            current_control_frame_pointer[1] =
+            access_control_frame_pointer(th)[1] =
                 *os_context_register_addr(context, reg_LRA);
-            current_control_frame_pointer += 8;
+            access_control_frame_pointer(th) += 8;
             /* Build our frame on top of it. */
             oldcont = (lispobj)(*os_context_register_addr(context, reg_CFP));
         }
@@ -644,11 +644,11 @@ build_fake_control_stack_frames(struct thread *th,os_context_t *context)
         oldcont = (lispobj)(*os_context_register_addr(context, reg_CFP));
     }
 
-    current_control_stack_pointer = current_control_frame_pointer + 8;
+    access_control_stack_pointer(th) = access_control_frame_pointer(th) + 8;
 
-    current_control_frame_pointer[0] = oldcont;
-    current_control_frame_pointer[1] = NIL;
-    current_control_frame_pointer[2] =
+    access_control_frame_pointer(th)[0] = oldcont;
+    access_control_frame_pointer(th)[1] = NIL;
+    access_control_frame_pointer(th)[2] =
         (lispobj)(*os_context_register_addr(context, reg_CODE));
 #endif
 }
@@ -1475,7 +1475,7 @@ arrange_return_to_lisp_function(os_context_t *context, lispobj function)
     *os_context_register_addr(context,reg_LIP) =
         (os_context_register_t)(unsigned long)code;
     *os_context_register_addr(context,reg_CFP) =
-        (os_context_register_t)(unsigned long)current_control_frame_pointer;
+        (os_context_register_t)(unsigned long)access_control_frame_pointer(th);
 #endif
 #ifdef ARCH_HAS_NPC_REGISTER
     *os_context_npc_addr(context) =
index 193f4c1..1f13630 100644 (file)
@@ -190,8 +190,10 @@ regs_cmd(char **ptr)
 {
     struct thread *thread=arch_os_get_current_thread();
 
-    printf("CSP\t=\t0x%08lx   ", (unsigned long)current_control_stack_pointer);
-    printf("CFP\t=\t0x%08lx   ", (unsigned long)current_control_frame_pointer);
+    printf("CSP\t=\t0x%08lx   ", (unsigned long)access_control_stack_pointer(thread));
+#if !defined(LISP_FEATURE_X86) && !defined(LISP_FEATURE_X86_64)
+    printf("CFP\t=\t0x%08lx   ", (unsigned long)access_control_frame_pointer(thread));
+#endif
 
 #ifdef reg_BSP
     printf("BSP\t=\t0x%08lx\n", (unsigned long)get_binding_stack_pointer(thread));
index eeedda4..90c4669 100644 (file)
@@ -954,7 +954,7 @@ purify(lispobj static_roots, lispobj read_only_roots)
     fflush(stdout);
 #endif
     pscav((lispobj *)all_threads->control_stack_start,
-          current_control_stack_pointer -
+          access_control_stack_pointer(all_threads) -
           all_threads->control_stack_start,
           0);
 
@@ -1030,10 +1030,10 @@ purify(lispobj static_roots, lispobj read_only_roots)
             (os_vm_size_t) dynamic_space_size);
 
     /* Zero the stack. */
-    os_zero((os_vm_address_t) current_control_stack_pointer,
+    os_zero((os_vm_address_t) access_control_stack_pointer(all_threads),
             (os_vm_size_t)
             ((all_threads->control_stack_end -
-              current_control_stack_pointer) * sizeof(lispobj)));
+              access_control_stack_pointer(all_threads)) * sizeof(lispobj)));
 
     /* It helps to update the heap free pointers so that free_heap can
      * verify after it's done. */
index 60821ee..8e3f7fd 100644 (file)
@@ -469,8 +469,6 @@ create_thread_struct(lispobj initial_function) {
 #if defined(LISP_FEATURE_X86) || defined (LISP_FEATURE_X86_64)
     SetSymbolValue(ALIEN_STACK,(lispobj)th->alien_stack_pointer,th);
     SetSymbolValue(PSEUDO_ATOMIC_BITS,(lispobj)th->pseudo_atomic_bits,th);
-#else
-    current_control_stack_pointer=th->control_stack_start;
 #endif
 #endif
     bind_variable(CURRENT_CATCH_BLOCK,make_fixnum(0),th);
@@ -487,6 +485,9 @@ create_thread_struct(lispobj initial_function) {
 #ifdef LISP_FEATURE_SB_THREAD
     bind_variable(STOP_FOR_GC_PENDING,NIL,th);
 #endif
+#ifndef LISP_FEATURE_C_STACK_IS_CONTROL_STACK
+    access_control_stack_pointer(th)=th->control_stack_start;
+#endif
 
     th->interrupt_data = (struct interrupt_data *)
         os_validate(0,(sizeof (struct interrupt_data)));
index fa4b7bc..e1765d7 100644 (file)
@@ -177,6 +177,12 @@ StaticSymbolFunction(lispobj sym)
     ((thread)->binding_stack_pointer)
 #define set_binding_stack_pointer(thread,value) \
     ((thread)->binding_stack_pointer = (lispobj *)(value))
+#define access_control_stack_pointer(thread) \
+    ((thread)->control_stack_pointer)
+#  if !defined(LISP_FEATURE_X86) && !defined(LISP_FEATURE_X86_64)
+#define access_control_frame_pointer(thread) \
+    ((thread)->control_frame_pointer)
+#  endif
 #elif defined(LISP_FEATURE_X86) || defined(LISP_FEATURE_X86_64)
 #define get_binding_stack_pointer(thread)       \
     SymbolValue(BINDING_STACK_POINTER, thread)
@@ -187,6 +193,10 @@ StaticSymbolFunction(lispobj sym)
     (current_binding_stack_pointer)
 #define set_binding_stack_pointer(thread,value) \
     (current_binding_stack_pointer = (lispobj *)(value))
+#define access_control_stack_pointer(thread) \
+    (current_control_stack_pointer)
+#define access_control_frame_pointer(thread) \
+    (current_control_frame_pointer)
 #endif
 
 #if defined(LISP_FEATURE_SB_THREAD) && defined(LISP_FEATURE_GCC_TLS)
index 0612ce9..bc25a9e 100644 (file)
@@ -276,7 +276,7 @@ sigtrap_handler(int signal, siginfo_t *info, os_context_t *context)
 
     /* This is just for info in case the monitor wants to print an
      * approximation. */
-    current_control_stack_pointer =
+    access_control_stack_pointer(arch_os_get_current_thread()) =
         (lispobj *)*os_context_sp_addr(context);
 
     /* On entry %eip points just after the INT3 byte and aims at the
index b000e0f..cbb6fb4 100644 (file)
@@ -287,7 +287,7 @@ sigtrap_handler(int signal, siginfo_t *info, os_context_t *context)
 
     /* This is just for info in case the monitor wants to print an
      * approximation. */
-    current_control_stack_pointer =
+    access_control_stack_pointer(arch_os_get_current_thread()) =
         (lispobj *)*os_context_sp_addr(context);
 
 #ifdef LISP_FEATURE_SUNOS
index ceec0e9..6854cea 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.41.20"
+"1.0.41.21"