0.8.21.41
authorDaniel Barlow <dan@telent.net>
Thu, 14 Apr 2005 22:34:33 +0000 (22:34 +0000)
committerDaniel Barlow <dan@telent.net>
Thu, 14 Apr 2005 22:34:33 +0000 (22:34 +0000)
Various cleanup to remove (a) code used only in the pre-futex
queue system, (b) some threading code copied blindly from
the x86 backend to x86-64 but is unlikely ever to actually
work there

src/code/target-unithread.lisp
src/runtime/gencgc.c
src/runtime/globals.c
src/runtime/globals.h
src/runtime/interrupt.c
src/runtime/thread.c
src/runtime/x86-64-arch.h
src/runtime/x86-64-assem.S
src/runtime/x86-64-linux-os.c
src/runtime/x86-64-linux-os.h
version.lisp-expr

index 5d2505e..e161937 100644 (file)
 (defstruct (mutex (:include waitqueue))
   (value nil))
 
-#+nil
-(defun wait-on-queue (queue &optional lock)
-  (let ((pid (current-thread-id)))
-    ;; FIXME what should happen if we get interrupted when we've blocked
-    ;; the sigcont?  For that matter, can we get interrupted?
-    (block-sigcont)
-    (when lock (release-mutex lock))
-    (get-spinlock queue 2 pid)
-    (pushnew pid (waitqueue-data queue))
-    (setf (waitqueue-lock queue) 0)
-    (unblock-sigcont-and-sleep)))
-
-#+nil
-(defun dequeue (queue)
-  (let ((pid (current-thread-id)))
-    (get-spinlock queue 2 pid)
-    (setf (waitqueue-data queue)
-         (delete pid (waitqueue-data queue)))
-    (setf (waitqueue-lock queue) 0)))
-
-#+nil
-(defun signal-queue-head (queue)
-  (let ((pid (current-thread-id)))
-    (get-spinlock queue 2 pid)
-    (let ((h (car (waitqueue-data queue))))
-      (setf (waitqueue-lock queue) 0)
-      (when h
-       (sb!unix:unix-kill h sb!unix:sigcont)))))
-
 ;;;; mutex
 
-#+nil
-(defun get-mutex (lock &optional new-value (wait-p t))
-  (declare (type mutex lock))
-  (let ((pid (current-thread-id)))
-    (unless new-value (setf new-value pid))
-    (assert (not (eql new-value (mutex-value lock))))
-    (loop
-     (unless
-        ;; args are object slot-num old-value new-value
-        (sb!vm::%instance-set-conditional lock 4 nil new-value)
-       (dequeue lock)
-       (return t))
-     (unless wait-p (return nil))
-     (wait-on-queue lock nil))))
-
-#+nil
-(defun release-mutex (lock &optional (new-value nil))
-  (declare (type mutex lock))
-  (let ((old-value (mutex-value lock))
-       (t1 nil))
-    (loop
-     (unless
-        ;; args are object slot-num old-value new-value
-        (eql old-value
-             (setf t1
-                   (sb!vm::%instance-set-conditional lock 4 old-value new-value)))       
-       (signal-queue-head lock)
-       (return t))
-     (setf old-value t1))))
-
 (defun get-mutex (lock &optional new-value (wait-p t))
   (declare (type mutex lock))
   (let ((old-value (mutex-value lock)))
   (declare (type mutex lock))
   (setf (mutex-value lock) nil))
 
-;;; what's the best thing to do with these on unithread?  commented
-;;; functions are the thread versions, just to remind me what they do
-;;; there
-#+nil
-(defun condition-wait (queue lock)
-  "Atomically release LOCK and enqueue ourselves on QUEUE.  Another
-thread may subsequently notify us using CONDITION-NOTIFY, at which
-time we reacquire LOCK and return to the caller."
-  (unwind-protect
-       (wait-on-queue queue lock)
-    ;; If we are interrupted while waiting, we should do these things
-    ;; before returning.  Ideally, in the case of an unhandled signal,
-    ;; we should do them before entering the debugger, but this is
-    ;; better than nothing.
-    (dequeue queue)
-    (get-mutex lock)))
-
-#+nil
-(defun condition-notify (queue)
-  "Notify one of the processes waiting on QUEUE"
-  (signal-queue-head queue))
+
+;; FIXME need suitable stub or ERROR-signaling definitions for 
+;; condition-wait (queue lock)
+;; condition-notify (queue)
 
 ;;;; job control
 
index 1dcfd35..8f9028b 100644 (file)
@@ -3584,7 +3584,7 @@ garbage_collect_generation(int generation, int raise)
            free=fixnum_value(SymbolValue(FREE_INTERRUPT_CONTEXT_INDEX,th));
            for(i=free-1;i>=0;i--) {
                os_context_t *c=th->interrupt_contexts[i];
-               esp1 = (void **) *os_context_register_addr(c,reg_ESP);
+               esp1 = (void **) *os_context_register_addr(c,reg_SP);
                if(esp1>=th->control_stack_start&& esp1<th->control_stack_end){
                    if(esp1<esp) esp=esp1;
                    for(ptr = (void **)(c+1); ptr>=(void **)c; ptr--) {
index 916cd1f..5cd53b2 100644 (file)
@@ -42,7 +42,6 @@ lispobj *current_auto_gc_trigger;
 #endif
 
 #ifdef LISP_FEATURE_SB_THREAD
-pid_t parent_pid;
 boolean stop_the_world=0;
 #endif
 
@@ -64,7 +63,4 @@ void globals_init(void)
 
     /* Set foreign function call active. */
     foreign_function_call_active = 1;
-#ifdef LISP_FEATURE_SB_THREAD
-    parent_pid=getpid();
-#endif
 }
index e8dd9de..c94cb62 100644 (file)
@@ -35,7 +35,6 @@ extern lispobj *current_auto_gc_trigger;
 #endif
 
 extern lispobj *current_dynamic_space;
-extern pid_t parent_pid;
 extern boolean stop_the_world;
 
 extern void globals_init(void);
index 65f50bf..2377308 100644 (file)
@@ -124,32 +124,12 @@ struct interrupt_data * global_interrupt_data;
  * mask ought to be clear anyway most of the time, but may be non-zero
  * if we were interrupted e.g. while waiting for a queue.  */
 
-#if 1
 void reset_signal_mask () 
 {
     sigset_t new;
     sigemptyset(&new);
     sigprocmask(SIG_SETMASK,&new,0);
 }
-#else
-void reset_signal_mask () 
-{
-    sigset_t new,old;
-    int i;
-    int wrong=0;
-    sigemptyset(&new);
-    sigprocmask(SIG_SETMASK,&new,&old);
-    for(i=1; i<NSIG; i++) {
-       if(sigismember(&old,i)) {
-           fprintf(stderr,
-                   "Warning: signal %d is masked: this is unexpected\n",i);
-           wrong=1;
-       }
-    }
-    if(wrong) 
-       fprintf(stderr,"If this version of SBCL is less than three months old, please report this.\nOtherwise, please try a newer version first\n.  Reset signal mask.\n");
-}
-#endif
 
 
 
@@ -615,7 +595,7 @@ extern lispobj call_into_lisp(lispobj fun, lispobj *args, int nargs);
 extern void post_signal_tramp(void);
 void arrange_return_to_lisp_function(os_context_t *context, lispobj function)
 {
-#ifndef LISP_FEATURE_X86
+#if !(defined(LISP_FEATURE_X86) || defined(LISP_FEATURE_X86_64))
     void * fun=native_pointer(function);
     void *code = &(((struct simple_fun *) fun)->code);
 #endif    
index 0f28c30..05637bb 100644 (file)
@@ -239,7 +239,7 @@ pid_t create_thread(lispobj initial_function) {
     if(th==0) return 0;
     kid_pid=clone(new_thread_trampoline,
                  (((void*)th->control_stack_start)+
-                  THREAD_CONTROL_STACK_SIZE-4),
+                  THREAD_CONTROL_STACK_SIZE-16),
                  CLONE_FILES|SIG_THREAD_EXIT|CLONE_VM,th);
     
     if(kid_pid>0) {
@@ -256,32 +256,6 @@ pid_t create_thread(lispobj initial_function) {
 }
 #endif
 
-/* unused */
-void destroy_thread (struct thread *th)
-{
-    /* precondition: the unix task has already been killed and exited.
-     * This is called by the parent or some other thread */
-#ifdef LISP_FEATURE_GENCGC
-    gc_alloc_update_page_tables(0, &th->alloc_region);
-#endif
-    get_spinlock(&all_threads_lock,th->pid);
-    th->unbound_marker=0;      /* for debugging */
-    if(th==all_threads) 
-       all_threads=th->next;
-    else {
-       struct thread *th1=all_threads;
-       while(th1 && th1->next!=th) th1=th1->next;
-       if(th1) th1->next=th->next;     /* unlink */
-    }
-    release_spinlock(&all_threads_lock);
-    if(th && th->tls_cookie>=0) arch_os_thread_cleanup(th); 
-    os_invalidate((os_vm_address_t) th->control_stack_start,
-                 ((sizeof (lispobj))
-                  * (th->control_stack_end-th->control_stack_start)) +
-                 BINDING_STACK_SIZE+ALIEN_STACK_SIZE+dynamic_values_bytes+
-                 32*SIGSTKSZ);
-}
-
 struct thread *find_thread_by_pid(pid_t pid) 
 {
     struct thread *th;
index bf3306b..4e3a18d 100644 (file)
@@ -2,8 +2,8 @@
  * reserved for the system libraries? If so, it would be tidy to
  * rename flags like _X86_ARCH_H so their names are in a part of the
  * namespace that we control. */
-#ifndef _X86_ARCH_H
-#define _X86_ARCH_H
+#ifndef _X86_64_ARCH_H
+#define _X86_64_ARCH_H
 
 #define ARCH_HAS_STACK_POINTER
 
 static inline void 
 get_spinlock(lispobj *word,long value)
 {
-#if 0
-    u32 eax=0;
+#ifdef LISP_FEATURE_SB_THREAD
+    u64 rax=0;
     do {
        asm ("xor %0,%0\n\
               lock cmpxchg %1,%2" 
-            : "=a" (eax)
+            : "=a" (rax)
             : "r" (value), "m" (*word)
             : "memory", "cc");
-    } while(eax!=0);
+    } while(rax!=0);
 #else
     *word=value;
 #endif
@@ -35,4 +35,4 @@ release_spinlock(lispobj *word)
     *word=0;
 }
 
-#endif /* _X86_ARCH_H */
+#endif /* _X86_64_ARCH_H */
index cf5b970..1751d5d 100644 (file)
@@ -97,7 +97,7 @@ GNAME(call_into_lisp_first_time):
        mov    THREAD_CONTROL_STACK_START_OFFSET(%rax) ,%rsp
        /* don't think too hard about what happens if we get interrupted
        * here */
-       add     $THREAD_CONTROL_STACK_SIZE-8,%rsp
+       add     $THREAD_CONTROL_STACK_SIZE-16,%rsp
        jmp     Lstack
 \f
        .text   
@@ -174,8 +174,9 @@ Lcall:
        pop     %rbx
 
 /* FIXME Restore the NPX state. */
-       pop     %rbp            # c-sp
+
        /* return value is already in rax where lisp expects it */
+       leave
        ret
        .size   GNAME(call_into_lisp), . - GNAME(call_into_lisp)
 \f
index c996813..6633b32 100644 (file)
@@ -1,6 +1,6 @@
 /*
- * The x86 Linux incarnation of arch-dependent OS-dependent routines.
- * See also "linux-os.c".
+ * The x86-64 Linux incarnation of arch-dependent OS-dependent
+ * routines.  See also "linux-os.c".
  */
 
 /*
 #include <linux/version.h>
 #include "thread.h"            /* dynamic_values_bytes */
 
-#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,0)
-#define user_desc  modify_ldt_ldt_s 
-#endif
-
-_syscall3(int, modify_ldt, int, func, void *, ptr, unsigned long, bytecount );
-
 #include "validate.h"
 size_t os_vm_page_size;
 
-u32 local_ldt_copy[LDT_ENTRIES*LDT_ENTRY_SIZE/sizeof(u32)];
-
-/* This is never actually called, but it's great for calling from gdb when
- * users have thread-related problems that maintainers can't duplicate */
-
-void debug_get_ldt()
-{ 
-    int n=modify_ldt (0, local_ldt_copy, sizeof local_ldt_copy);
-    printf("%d bytes in ldt: print/x local_ldt_copy\n", n);
-}
-
-lispobj modify_ldt_lock;       /* protect all calls to modify_ldt */
-
 int arch_os_thread_init(struct thread *thread) {
     stack_t sigstack;
 #ifdef LISP_FEATURE_SB_THREAD
-    /* this must be called from a function that has an exclusive lock
-     * on all_threads
-     */
-    struct user_desc ldt_entry = {
-       1, 0, 0, /* index, address, length filled in later */
-       1, MODIFY_LDT_CONTENTS_DATA, 0, 0, 0, 1
-    }; 
-    int n;
-    get_spinlock(&modify_ldt_lock,thread);
-    n=modify_ldt(0,local_ldt_copy,sizeof local_ldt_copy);
-    /* get next free ldt entry */
-
-    if(n) {
-       u32 *p;
-       for(n=0,p=local_ldt_copy;*p;p+=LDT_ENTRY_SIZE/sizeof(u32))
-           n++;
-    }
-    ldt_entry.entry_number=n;
-    ldt_entry.base_addr=(unsigned long) thread;
-    ldt_entry.limit=dynamic_values_bytes;
-    ldt_entry.limit_in_pages=0;
-    if (modify_ldt (1, &ldt_entry, sizeof (ldt_entry)) != 0) {
-       modify_ldt_lock=0;
-       /* modify_ldt call failed: something magical is not happening */
-       return -1;
-    }
-    __asm__ __volatile__ ("movw %w0, %%fs" : : "q" 
-                         ((n << 3) /* selector number */
-                          + (1 << 2) /* TI set = LDT */
-                          + 3)); /* privilege level */
-    thread->tls_cookie=n;
-    modify_ldt_lock=0;
-
-    if(n<0) return 0;
+#error Threads are not supported on x86-64 in this SBCL version
 #endif
 #ifdef LISP_FEATURE_C_STACK_IS_CONTROL_STACK
     /* Signal handlers are run on the control stack, so if it is exhausted
@@ -122,30 +70,11 @@ int arch_os_thread_init(struct thread *thread) {
     return 1;
 }
 
-struct thread *debug_get_fs() {
-    register u32 fs;
-    __asm__ __volatile__ ("movl %%fs,%0" : "=r" (fs)  : );
-    return fs;
-}
-
 /* free any arch/os-specific resources used by thread, which is now
  * defunct.  Not called on live threads
  */
 
 int arch_os_thread_cleanup(struct thread *thread) {
-    struct user_desc ldt_entry = {
-       0, 0, 0, 
-       0, MODIFY_LDT_CONTENTS_DATA, 0, 0, 0, 0
-    }; 
-
-    ldt_entry.entry_number=thread->tls_cookie;
-    get_spinlock(&modify_ldt_lock,thread);
-    if (modify_ldt (1, &ldt_entry, sizeof (ldt_entry)) != 0) {
-       modify_ldt_lock=0;
-       /* modify_ldt call failed: something magical is not happening */
-       return 0;
-    }
-    modify_ldt_lock=0;
     return 1;
 }
 
index 90b34c0..ba96988 100644 (file)
@@ -1,5 +1,5 @@
-#ifndef _X86_LINUX_OS_H
-#define _X86_LINUX_OS_H
+#ifndef _X86_64_LINUX_OS_H
+#define _X86_64_LINUX_OS_H
 
 typedef struct ucontext os_context_t;
 typedef long os_context_register_t;
@@ -11,4 +11,4 @@ static inline os_context_t *arch_os_get_context(void **void_context) {
 unsigned long os_context_fp_control(os_context_t *context);
 void os_restore_fp_control(os_context_t *context);
 
-#endif /* _X86_LINUX_OS_H */
+#endif /* _X86_64_LINUX_OS_H */
index 966b235..5db653f 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".)
-"0.8.21.40"
+"0.8.21.41"