/*
- * sgen-os-posix.c: Simple generational GC.
+ * sgen-os-posix.c: Posix support.
*
* Author:
* Paolo Molaro (lupus@ximian.com)
* Geoff Norton (gnorton@novell.com)
*
* Copyright 2010 Novell, Inc (http://www.novell.com)
+ * Copyright (C) 2012 Xamarin Inc
*
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License 2.0 as published by the Free Software Foundation;
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public
+ * License 2.0 along with this library; if not, write to the Free
+ * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include "config.h"
suspend_thread (SgenThreadInfo *info, void *context)
{
int stop_count;
-#ifdef USE_MONO_CTX
- MonoContext monoctx;
-#else
+#ifndef USE_MONO_CTX
gpointer regs [ARCH_NUM_REGS];
#endif
gpointer stack_start;
#ifdef USE_MONO_CTX
if (context) {
- mono_sigctx_to_monoctx (context, &monoctx);
- info->monoctx = &monoctx;
+ mono_sigctx_to_monoctx (context, &info->ctx);
} else {
- info->monoctx = NULL;
+ memset (&info->ctx, 0, sizeof (MonoContext));
}
#else
if (context) {
ARCH_COPY_SIGCTX_REGS (regs, context);
- info->stopped_regs = regs;
+ memcpy (&info->regs, regs, sizeof (info->regs));
} else {
- info->stopped_regs = NULL;
+ memset (&info->regs, 0, sizeof (info->regs));
}
#endif
} else {
/* Notify the JIT */
if (mono_gc_get_gc_callbacks ()->thread_suspend_func)
- mono_gc_get_gc_callbacks ()->thread_suspend_func (info->runtime_data, context);
+ mono_gc_get_gc_callbacks ()->thread_suspend_func (info->runtime_data, context, NULL);
- DEBUG (4, fprintf (gc_debug_file, "Posting suspend_ack_semaphore for suspend from %p %p\n", info, (gpointer)mono_native_thread_id_get ()));
+ SGEN_LOG (4, "Posting suspend_ack_semaphore for suspend from %p %p", info, (gpointer)mono_native_thread_id_get ());
/*
Block the restart signal.
/* Unblock the restart signal. */
pthread_sigmask (SIG_UNBLOCK, &suspend_ack_signal_mask, NULL);
- DEBUG (4, fprintf (gc_debug_file, "Posting suspend_ack_semaphore for resume from %p %p\n", info, (gpointer)mono_native_thread_id_get ()));
+ SGEN_LOG (4, "Posting suspend_ack_semaphore for resume from %p %p\n", info, (gpointer)mono_native_thread_id_get ());
/* notify the waiting thread */
MONO_SEM_POST (suspend_ack_semaphore_ptr);
}
rely on pthread_self () and seatch over the thread list.
*/
if (!info)
- info = mono_thread_info_lookup (pthread_self ());
+ info = (SgenThreadInfo*)mono_thread_info_lookup (pthread_self ());
/*
* If a thread is dying there might be no thread info. In
*/
if (info) {
info->signal = restart_signal_num;
- DEBUG (4, fprintf (gc_debug_file, "Restart handler in %p %p\n", info, (gpointer)mono_native_thread_id_get ()));
+ SGEN_LOG (4, "Restart handler in %p %p", info, (gpointer)mono_native_thread_id_get ());
}
errno = old_errno;
}
for (i = 0; i < count; ++i) {
while ((result = MONO_SEM_WAIT (suspend_ack_semaphore_ptr)) != 0) {
if (errno != EINTR) {
- g_error ("sem_wait ()");
+ g_error ("MONO_SEM_WAIT FAILED with %d errno %d (%s)", result, errno, strerror (errno));
}
}
}
count = 0;
FOREACH_THREAD_SAFE (info) {
+ if (info->joined_stw == suspend)
+ continue;
+ info->joined_stw = suspend;
if (mono_native_thread_id_equals (mono_thread_info_get_tid (info), me)) {
continue;
}