diff options
author | bryce <bryce@138bc75d-0d04-0410-961f-82ee72b054a4> | 2004-07-11 21:19:47 +0000 |
---|---|---|
committer | bryce <bryce@138bc75d-0d04-0410-961f-82ee72b054a4> | 2004-07-11 21:19:47 +0000 |
commit | e6026a782a4bdda2a65a2121e41e9a3e13a89c49 (patch) | |
tree | 1eb123e8167930c24b33e77b72e82925706270d5 /libjava/gnu | |
parent | 93c149df04baceb7006fd44481e180ffb6824b16 (diff) | |
download | gcc-e6026a782a4bdda2a65a2121e41e9a3e13a89c49.tar.gz |
2004-07-11 Bryce McKinlay <mckinlay@redhat.com>
PR libgcj/16748
* prims.cc (_Jv_CreateJavaVM): Fix comment.
* gnu/gcj/runtime/FinalizerThread.java (init): New. Native.
(finalizerReady): Now native.
(run): Likewise.
(runFinalizers): Removed.
* gnu/gcj/runtime/natFinalizerThread.cc (run): Implement here. Use
a primitive lock, and don't hold it while running the finalizers.
(runFinalizers): Implement. Don't aquire any Java lock.
(finalizerReady): Use lock primitives to signal finalizer thread.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@84531 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'libjava/gnu')
-rw-r--r-- | libjava/gnu/gcj/runtime/FinalizerThread.java | 55 | ||||
-rw-r--r-- | libjava/gnu/gcj/runtime/natFinalizerThread.cc | 44 |
2 files changed, 49 insertions, 50 deletions
diff --git a/libjava/gnu/gcj/runtime/FinalizerThread.java b/libjava/gnu/gcj/runtime/FinalizerThread.java index e333d7a41c7..c9a917cd264 100644 --- a/libjava/gnu/gcj/runtime/FinalizerThread.java +++ b/libjava/gnu/gcj/runtime/FinalizerThread.java @@ -1,6 +1,6 @@ // FinalizerThread.java -- Thread in which finalizers are run. -/* Copyright (C) 2001 Free Software Foundation +/* Copyright (C) 2001, 2004 Free Software Foundation This file is part of libgcj. @@ -16,58 +16,17 @@ package gnu.gcj.runtime; */ public final class FinalizerThread extends Thread { - // Finalizers must be run in a thread with no Java-visible locks - // held. This qualifies because we don't make the lock visible. - private static final Object lock = new Object (); - - // This is true if the finalizer thread started successfully. It - // might be false if, for instance, there are no threads on the - // current platform. In this situation we run finalizers in the - // caller's thread. - private static boolean thread_started = false; + private static boolean finalizer_ready; public FinalizerThread () { super ("LibgcjInternalFinalizerThread"); setDaemon (true); + finalizer_ready = false; + init(); } - // This is called by the runtime when a finalizer is ready to be - // run. It simply wakes up the finalizer thread. - public static void finalizerReady () - { - synchronized (lock) - { - if (! thread_started) - runFinalizers (); - else - lock.notify (); - } - } - - // Actually run the finalizers. - private static native void runFinalizers (); - - public void run () - { - // Wait on a lock. Whenever we wake up, try to invoke the - // finalizers. - synchronized (lock) - { - thread_started = true; - while (true) - { - try - { - lock.wait (); - } - catch (InterruptedException _) - { - // Just ignore it. It doesn't hurt to run finalizers - // when none are pending. - } - runFinalizers (); - } - } - } + private native void init(); + static native void finalizerReady(); + public native void run(); } diff --git a/libjava/gnu/gcj/runtime/natFinalizerThread.cc b/libjava/gnu/gcj/runtime/natFinalizerThread.cc index d296bc40551..ec1846baf6a 100644 --- a/libjava/gnu/gcj/runtime/natFinalizerThread.cc +++ b/libjava/gnu/gcj/runtime/natFinalizerThread.cc @@ -1,6 +1,6 @@ // natFinalizerThread.cc - Implementation of FinalizerThread native methods. -/* Copyright (C) 2001 Free Software Foundation +/* Copyright (C) 2001, 2004 Free Software Foundation This file is part of libgcj. @@ -15,8 +15,48 @@ details. */ #include <gnu/gcj/runtime/FinalizerThread.h> +#include <java-threads.h> + +static _Jv_Mutex_t mutex; +static _Jv_ConditionVariable_t condition; + +// Initialize lock & condition variable. +void +gnu::gcj::runtime::FinalizerThread::init () +{ + _Jv_MutexInit (&mutex); + _Jv_CondInit (&condition); +} + +// This is called by the GC when a finalizer is ready to be +// run. It sets a flag and wakes up the finalizer thread. Note +// that this MUST NOT aquire any Java lock, as this could result in +// the hash synchronization code being re-entered: the synchronization +// code itself might need to allocate. See PR 16478. void -gnu::gcj::runtime::FinalizerThread::runFinalizers () +gnu::gcj::runtime::FinalizerThread::finalizerReady () { +#ifdef __JV_NO_THREADS__ _Jv_RunFinalizers (); +#else + _Jv_MutexLock (&mutex); + finalizer_ready = true; + _Jv_CondNotify (&condition, &mutex); + _Jv_MutexUnlock (&mutex); +#endif +} + +// Main loop for the finalizer thread. +void +gnu::gcj::runtime::FinalizerThread::run () +{ + while (true) + { + _Jv_MutexLock (&mutex); + if (! finalizer_ready) + _Jv_CondWait (&condition, &mutex, 0, 0); + finalizer_ready = false; + _Jv_MutexUnlock (&mutex); + _Jv_RunFinalizers (); + } } |