]> granicus.if.org Git - gc/commitdiff
Code refactoring of 'alt-stack registration support'
authorIvan Maidanski <ivmai@mail.ru>
Mon, 27 Jul 2015 07:34:35 +0000 (10:34 +0300)
committerIvan Maidanski <ivmai@mail.ru>
Mon, 27 Jul 2015 07:34:35 +0000 (10:34 +0300)
* darwin_stop_world.c (GC_stack_range_for, GC_push_all_stacks):
Reformat code dealing with alt-stack.
* pthread_stop_world.c (GC_push_all_stacks): Likewise.
* darwin_stop_world.c (GC_stack_range_for): Cast pointers to word when
compared.
* GC_push_all_stacks (GC_push_all_stacks): Likewise.
* include/gc.h (GC_register_altstack): Reformat comment; decorate with
GC_CALL; comment out argument names; change type of altstack_size and
stack_size to word.
* include/private/pthread_support.h (altstack, altstack_size, stack,
stack_size): Refine and reformat comment.
* include/private/pthread_support.h (altstack_size, stack_size): Change
type from int to word.
* pthread_support.c (main_stack_size, main_altstack_size): Likewise.
* pthread_support.c (main_pthread_self): Rename to main_pthread_id.
* pthread_support.c (GC_register_altstack): Decorate with GC_API and
GC_CALL.
* win32_threads.c (GC_register_altstack): Likewise.
* pthread_support.c (GC_register_altstack): Rename "thread" local
variable to "me"; new local variable "self"; use DCL_LOCK_STATE;
reformat code.
* pthread_support.c (GC_thr_init): New local variable "self"; compare
thread id using THREAD_EQUAL; reformat code.
* win32_threads.c (GC_register_altstack): Add GC_ATTR_UNUSED to all
arguments to avoid compiler warning (while the function is
unimplemented); add TODO.

darwin_stop_world.c
include/gc.h
include/private/pthread_support.h
pthread_stop_world.c
pthread_support.c
win32_threads.c

index 23979035176dd43242d22bd2b5f1b5557431e081..21e7e1ce4273b97aa8a9b45e0c00a9ad5893db6e 100644 (file)
@@ -303,16 +303,15 @@ STATIC ptr_t GC_stack_range_for(ptr_t *phi, thread_act_t thread, GC_thread p,
     /* p is guaranteed to be non-NULL regardless of GC_query_task_threads. */
     *phi = (p->flags & MAIN_THREAD) != 0 ? GC_stackbottom : p->stack_end;
 # endif
-
-      if (p->altstack && lo >= p->altstack && lo <= p->altstack + p->altstack_size) {
-          *paltstack_lo = lo;
-          *paltstack_hi = p->altstack + p->altstack_size;
-          lo = (char*)p->stack;
-          *phi = (char*)p->stack + p->stack_size;
-      } else {
-          *paltstack_lo = NULL;
-      }
-
+  if (p->altstack != NULL && (word)p->altstack <= (word)lo
+      && (word)lo <= (word)p->altstack + p->altstack_size) {
+    *paltstack_lo = lo;
+    *paltstack_hi = p->altstack + p->altstack_size;
+    lo = p->stack;
+    *phi = p->stack + p->stack_size;
+  } else {
+    *paltstack_lo = NULL;
+  }
 # ifdef DEBUG_THREADS
     GC_log_printf("Darwin: Stack for thread %p = [%p,%p)\n",
                   (void *)thread, lo, *phi);
@@ -350,11 +349,11 @@ GC_INNER void GC_push_all_stacks(void)
         if (lo) {
           GC_ASSERT((word)lo <= (word)hi);
           total_size += hi - lo;
-            GC_push_all_stack(lo,hi);
+          GC_push_all_stack(lo, hi);
         }
         if (altstack_lo) {
           total_size += altstack_hi - altstack_lo;
-            GC_push_all_stack(altstack_lo,altstack_hi);
+          GC_push_all_stack(altstack_lo, altstack_hi);
         }
         nthreads++;
         if (thread == my_thread)
index d33049ec87e3cbe9f7bd88c8b553f0a3b11d9879..d1423818664cf726829847922dc1a0b094095ab3 100644 (file)
@@ -1367,11 +1367,13 @@ GC_API void * GC_CALL GC_call_with_stack_base(GC_stack_base_func /* fn */,
   /* registered with the garbage collector.                             */
   GC_API int GC_CALL GC_thread_is_registered(void);
 
-/* Notify the collector about the stack and the altstack of the current thread */
-/* STACK/STACK_SIZE is used to determine the stack dimensions when a thread is
- * suspended while it is on an altstack.
- */
-GC_API void GC_register_altstack(void *stack, int stack_size, void *altstack, int altstack_size);
+  /* Notify the collector about the stack and the alt-stack of the      */
+  /* current thread.  stack_start/size is used to determine the stack   */
+  /* boundaries when a thread is suspended while it is on an alt-stack. */
+  GC_API void GC_CALL GC_register_altstack(void * /* stack_start */,
+                                           GC_word /* stack_size */,
+                                           void * /* altstack_base */,
+                                           GC_word /* altstack_size */);
 
   /* Unregister the current thread.  Only an explicitly registered      */
   /* thread (i.e. for which GC_register_my_thread() returns GC_SUCCESS) */
index c45817d428797bea1f197ce28a18c8307bcf3de8..7b4814ceaa47cbc309d0901e7d15866165cb751c 100644 (file)
@@ -86,10 +86,12 @@ typedef struct GC_Thread_Rep {
 
     ptr_t stack_end;            /* Cold end of the stack (except for    */
                                 /* main thread).                        */
-    ptr_t altstack; /* The start of the altstack if there is one, NULL otherwise */
-    int altstack_size; /* The size of the altstack if there is one */
-    ptr_t stack; /* The start of the normal stack */
-    int stack_size; /* The size of the normal stack */
+    ptr_t altstack;             /* The start of the alt-stack if there  */
+                                /* is one, NULL otherwise.              */
+    word altstack_size;         /* The size of the alt-stack if exists. */
+    ptr_t stack;                /* The start and size of the normal     */
+                                /* stack (set by GC_register_altstack). */
+    word stack_size;
 #   if defined(GC_DARWIN_THREADS) && !defined(DARWIN_DONT_PARSE_STACK)
       ptr_t topOfStack;         /* Result of GC_FindTopOfStack(0);      */
                                 /* valid only if the thread is blocked; */
index 600dbdb20bed52e7eb67f2a334220b3476bf210f..c6d4915bd24b2a03f3fdfcd4ed6e665878ce85ad 100644 (file)
@@ -402,10 +402,12 @@ GC_INNER void GC_push_all_stacks(void)
                         (void *)p->id, lo, hi);
 #       endif
         if (0 == lo) ABORT("GC_push_all_stacks: sp not set!");
-    if (p->altstack && lo >= p->altstack && lo <= p->altstack + p->altstack_size)
-        hi = p->altstack + p->altstack_size;
-       /* FIXME: Need to scan the normal stack too, but how ? */
-
+        if (p->altstack != NULL && (word)p->altstack <= (word)lo
+            && (word)lo <= (word)p->altstack + p->altstack_size) {
+          hi = p->altstack + p->altstack_size;
+          /* FIXME: Need to scan the normal stack too, but how ? */
+          /* FIXME: Assume stack grows down */
+        }
         GC_push_all_stack_sections(lo, hi, traced_stack_sect);
 #       ifdef STACK_GROWS_UP
           total_size += lo - hi;
index b74a3131230e5133ef24ed6347f87e03507c97ef..bb56f4bf79716883b56f02461890657972b46ea1 100644 (file)
@@ -658,32 +658,34 @@ GC_API int GC_CALL GC_thread_is_registered(void)
     return me != NULL;
 }
 
-static pthread_t main_pthread_self;
+static pthread_t main_pthread_id;
 static void *main_stack, *main_altstack;
-static int main_stack_size, main_altstack_size;
+static word main_stack_size, main_altstack_size;
 
-void GC_register_altstack (void *stack, int stack_size, void *altstack, int altstack_size)
+GC_API void GC_CALL GC_register_altstack(void *stack, GC_word stack_size,
+                                         void *altstack,
+                                         GC_word altstack_size)
 {
-    GC_thread thread;
-
-    LOCK();
-    thread = (void *)GC_lookup_thread(pthread_self());
-    if (thread) {
-        thread->stack = stack;
-        thread->stack_size = stack_size;
-        thread->altstack = altstack;
-        thread->altstack_size = altstack_size;
-    } else {
-        /*
-         * This happens if we are called before GC_thr_init ().
-         */
-        main_pthread_self = pthread_self ();
-        main_stack = stack;
-        main_stack_size = stack_size;
-        main_altstack = altstack;
-        main_altstack_size = altstack_size;
-    }
-    UNLOCK();
+  GC_thread me;
+  pthread_t self = pthread_self();
+  DCL_LOCK_STATE;
+
+  LOCK();
+  me = GC_lookup_thread(self);
+  if (me != NULL) {
+    me->stack = stack;
+    me->stack_size = stack_size;
+    me->altstack = altstack;
+    me->altstack_size = altstack_size;
+  } else {
+    /* This happens if we are called before GC_thr_init.    */
+    main_pthread_id = self;
+    main_stack = stack;
+    main_stack_size = stack_size;
+    main_altstack = altstack;
+    main_altstack_size = altstack_size;
+  }
+  UNLOCK();
 }
 
 #ifdef CAN_HANDLE_FORK
@@ -1103,7 +1105,9 @@ GC_INNER void GC_thr_init(void)
 # endif
   /* Add the initial thread, so we can stop it. */
   {
-    GC_thread t = GC_new_thread(pthread_self());
+    pthread_t self = pthread_self();
+    GC_thread t = GC_new_thread(self);
+
     if (t == NULL)
       ABORT("Failed to allocate memory for the initial thread");
 #   ifdef GC_DARWIN_THREADS
@@ -1112,12 +1116,12 @@ GC_INNER void GC_thr_init(void)
       t -> stop_info.stack_ptr = GC_approx_sp();
 #   endif
     t -> flags = DETACHED | MAIN_THREAD;
-         if (pthread_self () == main_pthread_self) {
-             t->stack = main_stack;
-             t->stack_size = main_stack_size;
-             t->altstack = main_altstack;
-             t->altstack_size = main_altstack_size;
-         }
+    if (THREAD_EQUAL(self, main_pthread_id)) {
+      t -> stack = main_stack;
+      t -> stack_size = main_stack_size;
+      t -> altstack = main_altstack;
+      t -> altstack_size = main_altstack_size;
+    }
   }
 
 # ifndef GC_DARWIN_THREADS
index 4b3a7d8125688bf2077e92f5dc5ef6790d92a938..7032a26fb2e827560f78af581be8505221a255e9 100644 (file)
@@ -601,8 +601,12 @@ GC_API int GC_CALL GC_thread_is_registered(void)
     return me != NULL;
 }
 
-void GC_register_altstack (void *stack, int stack_size, void *altstack, int altstack_size)
+GC_API void GC_CALL GC_register_altstack(void *stack GC_ATTR_UNUSED,
+                                         GC_word stack_size GC_ATTR_UNUSED,
+                                         void *altstack GC_ATTR_UNUSED,
+                                         GC_word altstack_size GC_ATTR_UNUSED)
 {
+  /* TODO: Implement */
 }
 
 /* Make sure thread descriptor t is not protected by the VDB            */