re PR awt/16748 (IAA.ImageComponentsTest: Freezes When Window Is Resized)
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. From-SVN: r84531
This commit is contained in:
parent
f44b0c8ec5
commit
31a7b75558
@ -1,3 +1,16 @@
|
||||
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.
|
||||
|
||||
2004-07-11 Mark Wielaard <mark@klomp.org>
|
||||
|
||||
Reported by Roman Kennke <roman@ontographics.com> (bug #9331)
|
||||
|
@ -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();
|
||||
}
|
||||
|
@ -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::runFinalizers ()
|
||||
gnu::gcj::runtime::FinalizerThread::init ()
|
||||
{
|
||||
_Jv_RunFinalizers ();
|
||||
_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::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 ();
|
||||
}
|
||||
}
|
||||
|
@ -1008,8 +1008,7 @@ _Jv_CreateJavaVM (void* /*vm_args*/)
|
||||
_Jv_GCInitializeFinalizers (&::gnu::gcj::runtime::FinalizerThread::finalizerReady);
|
||||
|
||||
// Start the GC finalizer thread. A VirtualMachineError can be
|
||||
// thrown by the runtime if, say, threads aren't available. In this
|
||||
// case finalizers simply won't run.
|
||||
// thrown by the runtime if, say, threads aren't available.
|
||||
try
|
||||
{
|
||||
using namespace gnu::gcj::runtime;
|
||||
|
Loading…
Reference in New Issue
Block a user