[kaffe] CVS kaffe (guilhem): Fix for bug #35
Kaffe CVS
cvs-commits at kaffe.org
Sun Apr 16 00:28:43 PDT 2006
PatchSet 7225
Date: 2006/04/16 07:19:56
Author: guilhem
Branch: HEAD
Tag: (none)
Log:
Fix for bug #35
* FAQ/FAQ.kaffemd
* configure.ac: Check for pthread_getattr_np
* configure, config/config.h.in: Regenerated.
* kaffe/jvmpi/jvmpi_kaffe.c
(jvmpiFillThreadStart): Filling the JVMPI event structure the same
way the JDK does (according to JMP).
* kaffe/kaffevm/thread.c
(KaffeVM_attachFakedThreadInstance): Build the JNI local reference
table at that position to catch all newly attached thread.
* kaffe/kaffevm/jni/jni-base.c
(detectAllActiveThreads): Send a THREAD_START event for each
running threads.
(JNI_CreateJavaVM): Likewise.
(KaffeJNI_DestroyJavaVM): Send a "shut down" JVMPI event
* kaffe/kaffevm/jni/jni.c
(Kaffe_DefineClass): Imported some code from
ClassLoader.defineClass.
* kaffe/kaffevm/systems/unix-pthreads/signal.c
(detectStackBoundaries): Renamed to
KaffePThread_detectStackBoundaries. Simplified the ifdef as
onstack is not needed anymore for quite a while.
(KaffePThread_detectThreadStackBoundaries): New function to detect
stack boundaries for unknown pthreads.
* kaffe/kaffevm/systems/unix-pthreads/thread-impl.c:
(jthread_attach_current_thread): If the thread is already attached
then return immediately. Detect stack boundaries. Setup signal
handlers again.
* libraries/javalib/vmspecific/gnu/classpath/VMSystemProperties.java:
Updated VM version.
Members:
ChangeLog:1.4731->1.4732
configure:1.540->1.541
configure.ac:1.218->1.219
config/config.h.in:1.161->1.162
kaffe/jvmpi/jvmpi_kaffe.c:1.18->1.19
kaffe/kaffevm/thread.c:1.108->1.109
kaffe/kaffevm/jni/jni-base.c:1.24->1.25
kaffe/kaffevm/jni/jni.c:1.42->1.43
kaffe/kaffevm/systems/unix-pthreads/signal.c:1.23->1.24
kaffe/kaffevm/systems/unix-pthreads/thread-impl.c:1.89->1.90
kaffe/kaffevm/systems/unix-pthreads/thread-internal.h:1.42->1.43
libraries/javalib/vmspecific/gnu/classpath/VMSystemProperties.java:1.4->1.5
Index: kaffe/ChangeLog
diff -u kaffe/ChangeLog:1.4731 kaffe/ChangeLog:1.4732
--- kaffe/ChangeLog:1.4731 Sat Apr 15 00:58:06 2006
+++ kaffe/ChangeLog Sun Apr 16 07:19:56 2006
@@ -1,3 +1,46 @@
+2006-04-16 Guilhem Lavaux <guilhem at kaffe.org>
+
+ Fix for bug #35
+
+ * FAQ/FAQ.kaffemd
+
+ * configure.ac: Check for pthread_getattr_np
+
+ * configure, config/config.h.in: Regenerated.
+
+ * kaffe/jvmpi/jvmpi_kaffe.c
+ (jvmpiFillThreadStart): Filling the JVMPI event structure the same
+ way the JDK does (according to JMP).
+
+ * kaffe/kaffevm/thread.c
+ (KaffeVM_attachFakedThreadInstance): Build the JNI local reference
+ table at that position to catch all newly attached thread.
+
+ * kaffe/kaffevm/jni/jni-base.c
+ (detectAllActiveThreads): Send a THREAD_START event for each
+ running threads.
+ (JNI_CreateJavaVM): Likewise.
+ (KaffeJNI_DestroyJavaVM): Send a "shut down" JVMPI event
+
+ * kaffe/kaffevm/jni/jni.c
+ (Kaffe_DefineClass): Imported some code from
+ ClassLoader.defineClass.
+
+ * kaffe/kaffevm/systems/unix-pthreads/signal.c
+ (detectStackBoundaries): Renamed to
+ KaffePThread_detectStackBoundaries. Simplified the ifdef as
+ onstack is not needed anymore for quite a while.
+ (KaffePThread_detectThreadStackBoundaries): New function to detect
+ stack boundaries for unknown pthreads.
+
+ * kaffe/kaffevm/systems/unix-pthreads/thread-impl.c:
+ (jthread_attach_current_thread): If the thread is already attached
+ then return immediately. Detect stack boundaries. Setup signal
+ handlers again.
+
+ * libraries/javalib/vmspecific/gnu/classpath/VMSystemProperties.java:
+ Updated VM version.
+
2006-04-15 Dalibor Topic <robilad at kaffe.org>
* libraries/javalib/external/classpath/configure.ac:
Index: kaffe/configure
diff -u kaffe/configure:1.540 kaffe/configure:1.541
--- kaffe/configure:1.540 Sun Apr 2 00:55:33 2006
+++ kaffe/configure Sun Apr 16 07:19:59 2006
@@ -24113,6 +24113,111 @@
ac_compiler_gnu=$ac_cv_c_compiler_gnu
+ OLD_LIBS="$LIBS"
+ LIBS="$LIBS $THREADLIBS"
+
+for ac_func in pthread_getattr_np
+do
+as_ac_var=`echo "ac_cv_func_$ac_func" | $as_tr_sh`
+echo "$as_me:$LINENO: checking for $ac_func" >&5
+echo $ECHO_N "checking for $ac_func... $ECHO_C" >&6
+if eval "test \"\${$as_ac_var+set}\" = set"; then
+ echo $ECHO_N "(cached) $ECHO_C" >&6
+else
+ cat >conftest.$ac_ext <<_ACEOF
+/* confdefs.h. */
+_ACEOF
+cat confdefs.h >>conftest.$ac_ext
+cat >>conftest.$ac_ext <<_ACEOF
+/* end confdefs.h. */
+/* Define $ac_func to an innocuous variant, in case <limits.h> declares $ac_func.
+ For example, HP-UX 11i <limits.h> declares gettimeofday. */
+#define $ac_func innocuous_$ac_func
+
+/* System header to define __stub macros and hopefully few prototypes,
+ which can conflict with char $ac_func (); below.
+ Prefer <limits.h> to <assert.h> if __STDC__ is defined, since
+ <limits.h> exists even on freestanding compilers. */
+
+#ifdef __STDC__
+# include <limits.h>
+#else
+# include <assert.h>
+#endif
+
+#undef $ac_func
+
+/* Override any gcc2 internal prototype to avoid an error. */
+#ifdef __cplusplus
+extern "C"
+{
+#endif
+/* We use char because int might match the return type of a gcc2
+ builtin and then its argument prototype would still apply. */
+char $ac_func ();
+/* The GNU C library defines this for functions which it implements
+ to always fail with ENOSYS. Some functions are actually named
+ something starting with __ and the normal name is an alias. */
+#if defined (__stub_$ac_func) || defined (__stub___$ac_func)
+choke me
+#else
+char (*f) () = $ac_func;
+#endif
+#ifdef __cplusplus
+}
+#endif
+
+int
+main ()
+{
+return f != $ac_func;
+ ;
+ return 0;
+}
+_ACEOF
+rm -f conftest.$ac_objext conftest$ac_exeext
+if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5
+ (eval $ac_link) 2>conftest.er1
+ ac_status=$?
+ grep -v '^ *+' conftest.er1 >conftest.err
+ rm -f conftest.er1
+ cat conftest.err >&5
+ echo "$as_me:$LINENO: \$? = $ac_status" >&5
+ (exit $ac_status); } &&
+ { ac_try='test -z "$ac_c_werror_flag"
+ || test ! -s conftest.err'
+ { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
+ (eval $ac_try) 2>&5
+ ac_status=$?
+ echo "$as_me:$LINENO: \$? = $ac_status" >&5
+ (exit $ac_status); }; } &&
+ { ac_try='test -s conftest$ac_exeext'
+ { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
+ (eval $ac_try) 2>&5
+ ac_status=$?
+ echo "$as_me:$LINENO: \$? = $ac_status" >&5
+ (exit $ac_status); }; }; then
+ eval "$as_ac_var=yes"
+else
+ echo "$as_me: failed program was:" >&5
+sed 's/^/| /' conftest.$ac_ext >&5
+
+eval "$as_ac_var=no"
+fi
+rm -f conftest.err conftest.$ac_objext \
+ conftest$ac_exeext conftest.$ac_ext
+fi
+echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_var'}'`" >&5
+echo "${ECHO_T}`eval echo '${'$as_ac_var'}'`" >&6
+if test `eval echo '${'$as_ac_var'}'` = yes; then
+ cat >>confdefs.h <<_ACEOF
+#define `echo "HAVE_$ac_func" | $as_tr_cpp` 1
+_ACEOF
+
+fi
+done
+
+ LIBS="$OLD_LIBS"
echo "$as_me:$LINENO: checking for sem_init in -lsemaphore" >&5
echo $ECHO_N "checking for sem_init in -lsemaphore... $ECHO_C" >&6
if test "${ac_cv_lib_semaphore_sem_init+set}" = set; then
Index: kaffe/configure.ac
diff -u kaffe/configure.ac:1.218 kaffe/configure.ac:1.219
--- kaffe/configure.ac:1.218 Sun Apr 2 00:55:41 2006
+++ kaffe/configure.ac Sun Apr 16 07:20:12 2006
@@ -696,6 +696,10 @@
ACX_PTHREAD([THREADLIBS="$PTHREAD_LIBS "
CFLAGS="$CFLAGS $PTHREAD_CFLAGS"
CC="$PTHREAD_CC"])
+ OLD_LIBS="$LIBS"
+ LIBS="$LIBS $THREADLIBS"
+ AC_CHECK_FUNCS([pthread_getattr_np])
+ LIBS="$OLD_LIBS"
AC_CHECK_LIB(semaphore,sem_init,SEMAPHORE_LIB="-lsemaphore")
AC_SUBST(SEMAPHORE_LIB)
KAFFE_LIB_SOLARIS_PTHREAD
Index: kaffe/config/config.h.in
diff -u kaffe/config/config.h.in:1.161 kaffe/config/config.h.in:1.162
--- kaffe/config/config.h.in:1.161 Fri Mar 24 22:32:48 2006
+++ kaffe/config/config.h.in Sun Apr 16 07:20:13 2006
@@ -443,6 +443,9 @@
/* Define to 1 if you have the `pthread_attr_setschedpolicy' function. */
#undef HAVE_PTHREAD_ATTR_SETSCHEDPOLICY
+/* Define to 1 if you have the `pthread_getattr_np' function. */
+#undef HAVE_PTHREAD_GETATTR_NP
+
/* Define to 1 if you have the <pthread.h> header file. */
#undef HAVE_PTHREAD_H
Index: kaffe/kaffe/jvmpi/jvmpi_kaffe.c
diff -u kaffe/kaffe/jvmpi/jvmpi_kaffe.c:1.18 kaffe/kaffe/jvmpi/jvmpi_kaffe.c:1.19
--- kaffe/kaffe/jvmpi/jvmpi_kaffe.c:1.18 Mon Mar 20 22:10:14 2006
+++ kaffe/kaffe/jvmpi/jvmpi_kaffe.c Sun Apr 16 07:20:14 2006
@@ -188,34 +188,49 @@
void jvmpiFillThreadStart(JVMPI_Event *ev, struct Hjava_lang_VMThread *vmtid)
{
- struct Hjava_lang_String *name;
- struct Hjava_lang_Thread *tid = unhand(vmtid)->thread;
-
- assert(ev != NULL);
- assert(tid != NULL);
-
- ev->event_type = JVMPI_EVENT_THREAD_START;
- if( (name = stringCharArray2Java(unhand_char_array(tid->name->value),
- tid->name->count)) != NULL )
- {
- ev->u.thread_start.thread_name = stringJava2C(name);
- }
- else
+ struct Hjava_lang_String *name;
+ struct Hjava_lang_Thread *tid = unhand(vmtid)->thread;
+
+ assert(ev != NULL);
+ assert(tid != NULL);
+
+ ev->event_type = JVMPI_EVENT_THREAD_START;
+ if( (name = stringCharArray2Java(unhand_char_array(tid->name->value),
+ tid->name->count)) != NULL )
+ ev->u.thread_start.thread_name = stringJava2C(name);
+ else
+ ev->u.thread_start.thread_name = NULL;
+
+ if (tid->group != NULL)
+ {
+ ev->u.thread_start.group_name = stringJava2C(tid->group->name);
+ if (tid->group->parent != NULL)
+ ev->u.thread_start.parent_name = stringJava2C(tid->group->parent->name);
+ else
{
- ev->u.thread_start.thread_name = NULL;
+ ev->u.thread_start.parent_name = (char *)KMALLOC(7);
+ strcpy(ev->u.thread_start.parent_name, "system");
}
- ev->u.thread_start.group_name = stringJava2C(tid->group->name);
- ev->u.thread_start.parent_name = NULL;
- ev->u.thread_start.thread_id = tid;
- ev->u.thread_start.thread_env_id =
- &KTHREAD(get_data)((jthread_t)tid->vmThread->vmdata)->jniEnv;
+ }
+ else
+ {
+ ev->u.thread_start.group_name = (char *)KMALLOC(7);
+ strcpy(ev->u.thread_start.group_name, "system");
+ ev->u.thread_start.parent_name = NULL;
+ }
+ ev->u.thread_start.thread_id = tid;
+ ev->u.thread_start.thread_env_id =
+ &KTHREAD(get_data)((jthread_t)tid->vmThread->vmdata)->jniEnv;
}
void jvmpiCleanupThreadStart(JVMPI_Event *ev)
{
- KFREE(ev->u.thread_start.parent_name);
- KFREE(ev->u.thread_start.group_name);
- KFREE(ev->u.thread_start.thread_name);
+ if (ev->u.thread_start.parent_name != NULL)
+ KFREE(ev->u.thread_start.parent_name);
+ if (ev->u.thread_start.group_name != NULL)
+ KFREE(ev->u.thread_start.group_name);
+ if (ev->u.thread_start.thread_name != NULL)
+ KFREE(ev->u.thread_start.thread_name);
}
void jvmpiFillClassLoad(JVMPI_Event *ev, struct Hjava_lang_Class *cl)
Index: kaffe/kaffe/kaffevm/thread.c
diff -u kaffe/kaffe/kaffevm/thread.c:1.108 kaffe/kaffe/kaffevm/thread.c:1.109
--- kaffe/kaffe/kaffevm/thread.c:1.108 Sat Mar 11 11:09:51 2006
+++ kaffe/kaffe/kaffevm/thread.c Sun Apr 16 07:20:14 2006
@@ -253,6 +253,7 @@
Hjava_lang_Thread* tid;
jvalue retval;
int i;
+ jnirefs *reftable;
DBG(VMTHREAD, dprintf("attachFakedThreadInstance(%s)\n", nm); );
@@ -312,6 +313,13 @@
do_execute_java_method(NULL, unhand(tid)->group, "addThread", "(Ljava/lang/Thread;)V", NULL, 0, tid);
DBG(VMTHREAD, dprintf("attachFakedThreadInstance(%s)=%p done\n", nm, tid); );
+
+ /* Setup JNI for this newly attached thread */
+ reftable = (jnirefs *)gc_malloc(sizeof(jnirefs) + sizeof(jref) * DEFAULT_JNIREFS_NUMBER,
+ KGC_ALLOC_STATIC_THREADDATA);
+ reftable->frameSize = DEFAULT_JNIREFS_NUMBER;
+ reftable->localFrames = 1;
+ THREAD_DATA()->jnireferences = reftable;
}
/*
@@ -390,10 +398,10 @@
unhand(vmtid)->thread = tid;
unhand(vmtid)->running = true;
- do_execute_java_class_method (&retval, "java/lang/ClassLoader",
- NULL,
- "getSystemClassLoader",
- "()Ljava/lang/ClassLoader;");
+ do_execute_java_class_method (&retval, "java/lang/ClassLoader",
+ NULL,
+ "getSystemClassLoader",
+ "()Ljava/lang/ClassLoader;");
unhand(tid)->contextClassLoader = (struct Hjava_lang_ClassLoader *) retval.l;
specialArgument[0] = func;
Index: kaffe/kaffe/kaffevm/jni/jni-base.c
diff -u kaffe/kaffe/kaffevm/jni/jni-base.c:1.24 kaffe/kaffe/kaffevm/jni/jni-base.c:1.25
--- kaffe/kaffe/kaffevm/jni/jni-base.c:1.24 Wed Sep 14 20:47:59 2005
+++ kaffe/kaffe/kaffevm/jni/jni-base.c Sun Apr 16 07:20:15 2006
@@ -267,12 +267,24 @@
return 1;
}
+static void
+detectAllActiveThreads(jthread_t jtid, void *param UNUSED)
+{
+ JVMPI_Event ev;
+ Hjava_lang_VMThread *tid;
+
+ tid = (Hjava_lang_VMThread *)(KTHREAD(get_data)(jtid)->jlThread);
+
+ jvmpiFillThreadStart(&ev, tid);
+ jvmpiPostEvent(&ev);
+ jvmpiCleanupThreadStart(&ev);
+}
+
jint
JNI_CreateJavaVM(JavaVM** vm, void** penv, void* args)
{
JavaVMInitArgs *vm_args = (JavaVMInitArgs *)args;
JNIEnv **env = (JNIEnv **)penv;
- jnirefs *reftable;
switch (vm_args->version)
{
@@ -297,14 +309,6 @@
/* Setup the machine */
initialiseKaffe();
- /* Setup JNI for main thread */
- reftable =
- (jnirefs *)gc_malloc(sizeof(jnirefs) + sizeof(jref) * DEFAULT_JNIREFS_NUMBER,
- KGC_ALLOC_STATIC_THREADDATA);
- reftable->frameSize = DEFAULT_JNIREFS_NUMBER;
- reftable->localFrames = 1;
- THREAD_DATA()->jnireferences = reftable;
-
/* Return the VM and JNI we're using */
*vm = KaffeJNI_GetKaffeVM();
*env = THREAD_JNIENV();
@@ -338,6 +342,16 @@
ev.event_type = JVMPI_EVENT_JVM_INIT_DONE;
jvmpiPostEvent(&ev);
}
+
+
+ if ( JVMPI_EVENT_ISENABLED(JVMPI_EVENT_THREAD_START) )
+ {
+ KTHREAD(suspendall)();
+
+ KTHREAD(walkLiveThreads) (detectAllActiveThreads, NULL);
+
+ KTHREAD(unsuspendall)();
+ }
#endif
return 0;
@@ -349,6 +363,16 @@
/* The destroy function must be called by the same thread that has
* built the VM object
*/
+#if defined(ENABLE_JVMPI)
+ if ( JVMPI_EVENT_ISENABLED(JVMPI_EVENT_JVM_SHUT_DOWN) )
+ {
+ JVMPI_Event ev;
+
+ ev.event_type = JVMPI_EVENT_JVM_SHUT_DOWN;
+ jvmpiPostEvent(&ev);
+ }
+#endif
+
if (KTHREAD(current)() != startingThread)
return -1;
Index: kaffe/kaffe/kaffevm/jni/jni.c
diff -u kaffe/kaffe/kaffevm/jni/jni.c:1.42 kaffe/kaffe/kaffevm/jni/jni.c:1.43
--- kaffe/kaffe/kaffevm/jni/jni.c:1.42 Thu Mar 30 17:39:18 2006
+++ kaffe/kaffe/kaffevm/jni/jni.c Sun Apr 16 07:20:15 2006
@@ -92,30 +92,74 @@
Kaffe_DefineClass(JNIEnv* env, const char *name UNUSED, jobject loader,
const jbyte* buf, jsize len)
{
- Hjava_lang_Class* cls;
- classFile hand;
- errorInfo info;
- jobject loader_local;
-
- BEGIN_EXCEPTION_HANDLING(NULL);
-
- loader_local = unveil(loader); /* save clobbered reg. */
-
- classFileInit(&hand, NULL, (unsigned char*)buf, (size_t)len,
- CP_BYTEARRAY);
-
- cls = newClass();
- if (cls == 0) {
- postOutOfMemory(&info);
- } else {
- cls = readClass(cls, &hand, loader_local, &info);
- }
- if (cls == 0) {
- postError(env, &info);
+ Hjava_lang_Class* cls, *dup_cls;
+ classFile hand;
+ errorInfo info;
+ jobject loader_local;
+ classEntry *centry;
+
+ BEGIN_EXCEPTION_HANDLING(NULL);
+
+ loader_local = unveil(loader); /* save clobbered reg. */
+
+ classFileInit(&hand, NULL, (unsigned char*)buf, (size_t)len,
+ CP_BYTEARRAY);
+
+ cls = newClass();
+ if (cls == NULL) {
+ postOutOfMemory(&info);
+ } else {
+ cls = readClass(cls, &hand, loader_local, &info);
+ }
+ if (cls == NULL) {
+ postError(env, &info);
+ }
+
+ /*
+ * See if an entry for that name and class loader already exists
+ * create one if not.
+ */
+ centry = lookupClassEntry(cls->name, loader_local, &info);
+ if (centry == 0) {
+ throwError(&info);
+ }
+
+ if( classMappingLoad(centry, &dup_cls, &info) )
+ {
+ if(dup_cls != NULL)
+ {
+ postExceptionMessage(&info,
+ JAVA_LANG(ClassFormatError),
+ "Duplicate name: %s",
+ centry->name->data);
+ throwError(&info);
+ }
+ /*
+ * While it is not necessary that one be able to actually *use*
+ * the returned class object at this point, it is mandatory
+ * that the returned clazz object is a functional Class object.
+ *
+ * The following call will make sure that the returned class
+ * object has its dispatch table set. The transition
+ * PRELOADED->PREPARED in processClass sets class->head.dtable.
+ *
+ * Presumably, it shouldn't be necessary here, but is at the
+ * moment - XXX
+ */
+ else if( processClass(cls,
+ CSTATE_PREPARED,
+ &info) == false )
+ {
+ throwError(&info);
}
+ }
+ else
+ {
+ throwError(&info);
+ }
+ END_EXCEPTION_HANDLING();
- END_EXCEPTION_HANDLING();
- return (cls);
+ return cls;
}
static jclass
@@ -728,8 +772,8 @@
{
if (KTHREAD(attach_current_thread) (false)) {
KSEM(init)(&THREAD_DATA()->sem);
- KaffeVM_attachFakedThreadInstance ("test attach", false);
- *penv = THREAD_JNIENV();
+ KaffeVM_attachFakedThreadInstance ("thread attach", false);
+ *penv = THREAD_JNIENV();
return 0;
}
return -1;
@@ -750,7 +794,7 @@
static jint
Kaffe_DetachCurrentThread(JavaVM* vm UNUSED)
{
- if (jthread_detach_current_thread ()) {
+ if (KTHREAD(detach_current_thread) ()) {
return 0;
} else {
return -1;
Index: kaffe/kaffe/kaffevm/systems/unix-pthreads/signal.c
diff -u kaffe/kaffe/kaffevm/systems/unix-pthreads/signal.c:1.23 kaffe/kaffe/kaffevm/systems/unix-pthreads/signal.c:1.24
--- kaffe/kaffe/kaffevm/systems/unix-pthreads/signal.c:1.23 Tue Jun 21 16:11:56 2005
+++ kaffe/kaffe/kaffevm/systems/unix-pthreads/signal.c Sun Apr 16 07:20:16 2006
@@ -9,6 +9,7 @@
* of this file.
*/
+#define _GNU_SOURCE
#include "config.h"
#include "debug.h"
#include "config-std.h"
@@ -368,7 +369,7 @@
* value it has detected.
*/
void
-detectStackBoundaries(jthread_t jtid, size_t mainThreadStackSize)
+KaffePThread_detectStackBoundaries(jthread_t jtid, size_t mainThreadStackSize)
{
void *stackPointer;
@@ -386,7 +387,7 @@
*/
void
-detectStackBoundaries(jthread_t jtid, size_t mainThreadStackSize)
+KaffePThread_detectStackBoundaries(jthread_t jtid, size_t mainThreadStackSize)
{
void *stackPointer;
@@ -405,7 +406,7 @@
*/
void
-detectStackBoundaries(jthread_t jtid, size_t mainThreadStackSize)
+KaffePThread_detectStackBoundaries(jthread_t jtid, size_t mainThreadStackSize)
{
void *stackPointer;
@@ -416,14 +417,14 @@
jtid->stackCur = jtid->stackMax;
}
-#elif defined(SA_ONSTACK) && defined(HAVE_SIGALTSTACK) && !defined(KAFFEMD_BUGGY_STACK_OVERFLOW)
+#elif !defined(KAFFEMD_BUGGY_STACK_OVERFLOW)
static JTHREAD_JMPBUF outOfLoop;
/*
* This function is called by the system when we go beyond stack boundaries
* in infiniteLoop. We get the stack address using the stack pointer register
- * and then go back in detectStackBoundaries() using the old stack.
+ * and then go back in KaffePThread_detectStackBoundaries() using the old stack.
*/
static void NONRETURNING
stackOverflowDetector(SIGNAL_ARGS(sig UNUSED, sc))
@@ -442,7 +443,7 @@
* the faulty adress directly.
*/
void
-detectStackBoundaries(jthread_t jtid, size_t mainThreadStackSize)
+KaffePThread_detectStackBoundaries(jthread_t jtid, size_t mainThreadStackSize)
{
static volatile char *guessPointer;
void *handler_segv, *handler_bus;
@@ -504,7 +505,7 @@
*/
void
-detectStackBoundaries(jthread_t jtid, size_t mainThreadStackSize)
+KaffePThread_detectStackBoundaries(jthread_t jtid, size_t mainThreadStackSize)
{
#if defined(STACK_GROWS_UP)
jtid->stackMin = (void*)(uintp)(&jtid - 0x100);
@@ -518,3 +519,32 @@
}
#endif
+
+
+void
+KaffePThread_detectThreadStackBoundaries(jthread_t jtid)
+{
+#if defined(HAVE_PTHREAD_GETATTR_NP)
+ pthread_attr_t attr;
+ size_t stackSize;
+
+ pthread_getattr_np (jtid->tid, &attr);
+
+ pthread_attr_getstack (&attr, &jtid->stackMin, &stackSize);
+
+ jtid->stackMax = (void*)(((char*)jtid->stackMin) + stackSize);
+
+ pthread_attr_destroy(&attr);
+#elif !defined(KAFFEMD_BUGGY_STACK_OVERFLOW)
+#warning KaffePThread_detectStackBoundaries is not implemented for KAFFEMD_BUGGY_STACK_OVERFLOW
+ fprintf(stderr, "Kaffe does not yet support detection of stack boundaries within unknown threads\n"
+ "Aborting.\n");
+ KAFFEVM_ABORT();
+#else
+#warning This code is totally unsafe if you plug some random application to the JVM.
+#warning This port should implement KAFFEMD_THREAD_STACK
+ fprintf(stderr, "Kaffe is not able to detect stack boundaries within unknown threads on this platform.\n"
+ "Aborting.\n");
+ KAFFEVM_ABORT();
+#endif
+}
Index: kaffe/kaffe/kaffevm/systems/unix-pthreads/thread-impl.c
diff -u kaffe/kaffe/kaffevm/systems/unix-pthreads/thread-impl.c:1.89 kaffe/kaffe/kaffevm/systems/unix-pthreads/thread-impl.c:1.90
--- kaffe/kaffe/kaffevm/systems/unix-pthreads/thread-impl.c:1.89 Fri Nov 4 20:23:48 2005
+++ kaffe/kaffe/kaffevm/systems/unix-pthreads/thread-impl.c Sun Apr 16 07:20:16 2006
@@ -617,7 +617,7 @@
/* Get stack boundaries. Note that this is just an approximation
* which should cover all gc-relevant stack locations
*/
- detectStackBoundaries(nt, mainThreadStackSize);
+ KaffePThread_detectStackBoundaries(nt, mainThreadStackSize);
DBG( JTHREAD, TMSG_SHORT( "create first ", nt));
@@ -694,6 +694,9 @@
jthread_t nt;
rlim_t stackSize;
+ if (jthread_current() != NULL)
+ return false;
+
/* create the jthread* thingy */
nt = thread_malloc( sizeof(struct _jthread) );
@@ -716,13 +719,15 @@
#else
stackSize = MAINSTACKSIZE;
#endif
- detectStackBoundaries(nt, stackSize);
- nt->stackCur = NULL;
- nt->daemon = isDaemon;
-
/* link everything together */
nt->tid = pthread_self();
pthread_setspecific( ntKey, nt);
+
+ KaffePThread_detectThreadStackBoundaries(nt);
+ tInitSignalHandlers();
+
+ nt->stackCur = NULL;
+ nt->daemon = isDaemon;
/* and done */
return true;
Index: kaffe/kaffe/kaffevm/systems/unix-pthreads/thread-internal.h
diff -u kaffe/kaffe/kaffevm/systems/unix-pthreads/thread-internal.h:1.42 kaffe/kaffe/kaffevm/systems/unix-pthreads/thread-internal.h:1.43
--- kaffe/kaffe/kaffevm/systems/unix-pthreads/thread-internal.h:1.42 Fri Dec 30 18:38:52 2005
+++ kaffe/kaffe/kaffevm/systems/unix-pthreads/thread-internal.h Sun Apr 16 07:20:16 2006
@@ -389,6 +389,7 @@
void KaffePThread_AckAndWaitForResume(jthread_t cur, unsigned int newState);
int KaffePThread_getSuspendSignal(void);
-void detectStackBoundaries(jthread_t jtid, size_t mainThreadStackSize);
+void KaffePThread_detectStackBoundaries(jthread_t jtid, size_t mainThreadStackSize);
+void KaffePThread_detectThreadStackBoundaries(jthread_t jtid);
#endif /* __thread_impl_h */
Index: kaffe/libraries/javalib/vmspecific/gnu/classpath/VMSystemProperties.java
diff -u kaffe/libraries/javalib/vmspecific/gnu/classpath/VMSystemProperties.java:1.4 kaffe/libraries/javalib/vmspecific/gnu/classpath/VMSystemProperties.java:1.5
--- kaffe/libraries/javalib/vmspecific/gnu/classpath/VMSystemProperties.java:1.4 Sun Feb 12 21:34:25 2006
+++ kaffe/libraries/javalib/vmspecific/gnu/classpath/VMSystemProperties.java Sun Apr 16 07:20:17 2006
@@ -96,7 +96,7 @@
properties.setProperty("java.vm.specification.version", "1.0");
properties.setProperty("java.vm.specification.vendor", "Sun Microsystems Inc.");
properties.setProperty("java.vm.specification.name", "Java Virtual Machine Specification");
- properties.setProperty("java.vm.version", "1.1.6");
+ properties.setProperty("java.vm.version", "1.1.8");
properties.setProperty("java.vm.vendor", "Kaffe.org project");
properties.setProperty("java.vm.name", "Kaffe");
properties.setProperty("java.specification.version", "1.4");
More information about the kaffe
mailing list