/* 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);
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)
/* 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) */
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; */
(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;
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
# 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
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
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 */