mirror of
https://github.com/openjdk/jdk.git
synced 2025-09-18 01:54:47 +02:00
8187443: Forest Consolidation: Move files to unified layout
Reviewed-by: darcy, ihse
This commit is contained in:
parent
270fe13182
commit
3789983e89
56923 changed files with 3 additions and 15727 deletions
|
@ -0,0 +1,193 @@
|
|||
<!--
|
||||
Copyright (c) 2002, 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
|
||||
This code is free software; you can redistribute it and/or modify it
|
||||
under the terms of the GNU General Public License version 2 only, as
|
||||
published by the Free Software Foundation. Oracle designates this
|
||||
particular file as subject to the "Classpath" exception as provided
|
||||
by Oracle in the LICENSE file that accompanied this code.
|
||||
|
||||
This code 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 General Public License
|
||||
version 2 for more details (a copy is included in the LICENSE file that
|
||||
accompanied this code).
|
||||
|
||||
You should have received a copy of the GNU General Public License version
|
||||
2 along with this work; if not, write to the Free Software Foundation,
|
||||
Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
|
||||
Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
or visit www.oracle.com if you need additional information or have any
|
||||
questions.
|
||||
-->
|
||||
|
||||
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
|
||||
<html>
|
||||
<head>
|
||||
<title></title>
|
||||
</head>
|
||||
<body bgcolor=white>
|
||||
|
||||
<h1 align=center>AWT Threading Issues</h1>
|
||||
|
||||
<a name="ListenersThreads"></a>
|
||||
<h2>Listeners and threads</h2>
|
||||
|
||||
Unless otherwise noted all AWT listeners are notified on the event
|
||||
dispatch thread. It is safe to remove/add listeners from any thread
|
||||
during dispatching, but the changes only effect subsequent notification.
|
||||
<br>For example, if a key listeners is added from another key listener, the
|
||||
newly added listener is only notified on subsequent key events.
|
||||
|
||||
<a name="Autoshutdown"></a>
|
||||
<h2>Auto-shutdown</h2>
|
||||
|
||||
According to
|
||||
<cite>The Java™ Virtual Machine Specification</cite>,
|
||||
sections 2.17.9 and 2.19,
|
||||
the Java virtual machine (JVM) initially starts up with a single non-daemon
|
||||
thread, which typically calls the <code>main</code> method of some class.
|
||||
The virtual machine terminates all its activity and exits when
|
||||
one of two things happens:
|
||||
<ul>
|
||||
<li> All the threads that are not daemon threads terminate.
|
||||
<li> Some thread invokes the <code>exit</code> method of class
|
||||
<code>Runtime</code> or class <code>System</code>, and the exit
|
||||
operation is permitted by the security manager.
|
||||
</ul>
|
||||
<p>
|
||||
This implies that if an application doesn't start any threads itself,
|
||||
the JVM will exit as soon as <code>main</code> terminates.
|
||||
This is not the case, however, for a simple application
|
||||
that creates and displays a <code>java.awt.Frame</code>:
|
||||
<pre>
|
||||
public static void main(String[] args) {
|
||||
Frame frame = new Frame();
|
||||
frame.setVisible(true);
|
||||
}
|
||||
</pre>
|
||||
The reason is that AWT encapsulates asynchronous event dispatch
|
||||
machinery to process events AWT or Swing components can fire. The
|
||||
exact behavior of this machinery is implementation-dependent. In
|
||||
particular, it can start non-daemon helper threads for its internal
|
||||
purposes. In fact, these are the threads that prevent the example
|
||||
above from exiting. The only restrictions imposed on the behavior of
|
||||
this machinery are as follows:
|
||||
<ul>
|
||||
<li> <a href="../EventQueue.html#isDispatchThread()"><code>EventQueue.isDispatchThread</code></a>
|
||||
returns <code>true</code> if and only if the calling thread is the
|
||||
event dispatch thread started by the machinery;
|
||||
<li> <code>AWTEvents</code> which were actually enqueued to a
|
||||
particular <code>EventQueue</code> (note that events being
|
||||
posted to the <code>EventQueue</code> can be coalesced) are
|
||||
dispatched:
|
||||
<ul>
|
||||
<li> Sequentially.
|
||||
<dl><dd> That is, it is not permitted that several events from
|
||||
this queue are dispatched simultaneously. </dd></dl>
|
||||
<li> In the same order as they are enqueued.
|
||||
<dl><dd> That is, if <code>AWTEvent</code> A is enqueued
|
||||
to the <code>EventQueue</code> before
|
||||
<code>AWTEvent</code> B then event B will not be
|
||||
dispatched before event A.</dd></dl>
|
||||
</ul>
|
||||
<li> There is at least one alive non-daemon thread while there is at
|
||||
least one displayable AWT or Swing component within the
|
||||
application (see
|
||||
<a href="../Component.html#isDisplayable()"><code>Component.isDisplayable</code></a>).
|
||||
</ul>
|
||||
The implications of the third restriction are as follows:
|
||||
<ul>
|
||||
<li> The JVM will exit if some thread invokes the <code>exit</code>
|
||||
method of class <code>Runtime</code> or class <code>System</code>
|
||||
regardless of the presence of displayable components;
|
||||
<li> Even if the application terminates all non-daemon threads it
|
||||
started, the JVM will not exit while there is at least one
|
||||
displayable component.
|
||||
</ul>
|
||||
It depends on the implementation if and when the non-daemon helper
|
||||
threads are terminated once all components are made undisplayable.
|
||||
The implementation-specific details are given below.
|
||||
|
||||
<h3>
|
||||
Implementation-dependent behavior.
|
||||
</h3>
|
||||
|
||||
Prior to 1.4, the helper threads were never terminated.
|
||||
<p>
|
||||
Starting with 1.4, the behavior has changed as a result of the fix for
|
||||
<a href="http://bugs.sun.com/view_bug.do?bug_id=4030718">
|
||||
4030718</a>. With the current implementation, AWT terminates all its
|
||||
helper threads allowing the application to exit cleanly when the
|
||||
following three conditions are true:
|
||||
<ul>
|
||||
<li> There are no displayable AWT or Swing components.
|
||||
<li> There are no native events in the native event queue.
|
||||
<li> There are no AWT events in java EventQueues.
|
||||
</ul>
|
||||
Therefore, a stand-alone AWT application that wishes to exit
|
||||
cleanly without calling <code>System.exit</code> must:
|
||||
<ul>
|
||||
<li> Make sure that all AWT or Swing components are made
|
||||
undisplayable when the application finishes. This can be done
|
||||
by calling
|
||||
<a href="../Window.html#dispose()"><code>Window.dispose</code></a>
|
||||
on all top-level <code>Windows</code>. See
|
||||
<a href="../Frame.html#getFrames()"><code>Frame.getFrames</code></a>.
|
||||
<li> Make sure that no method of AWT event listeners registered by
|
||||
the application with any AWT or Swing component can run into an
|
||||
infinite loop or hang indefinitely. For example, an AWT listener
|
||||
method triggered by some AWT event can post a new AWT event of
|
||||
the same type to the <code>EventQueue</code>.
|
||||
The argument is that methods
|
||||
of AWT event listeners are typically executed on helper
|
||||
threads.
|
||||
</ul>
|
||||
Note, that while an application following these recommendations will
|
||||
exit cleanly under normal conditions, it is not guaranteed that it
|
||||
will exit cleanly in all cases. Two examples:
|
||||
<ul>
|
||||
<li> Other packages can create displayable components for internal
|
||||
needs and never make them undisplayable. See
|
||||
<a href="http://bugs.sun.com/view_bug.do?bug_id=4515058">
|
||||
4515058</a>,
|
||||
<a href="http://bugs.sun.com/view_bug.do?bug_id=4671025">
|
||||
4671025</a>, and
|
||||
<a href="http://bugs.sun.com/view_bug.do?bug_id=4465537">
|
||||
4465537</a>.
|
||||
<li> Both Microsoft Windows and X11 allow an application to send native
|
||||
events to windows that belong to another application. With this
|
||||
feature it is possible to write a malicious program that will
|
||||
continuously send events to all available windows preventing
|
||||
any AWT application from exiting cleanly.
|
||||
</ul>
|
||||
On the other hand, if you require the JVM to continue running even after
|
||||
the application has made all components undisplayable you should start a
|
||||
non-daemon thread that blocks forever.
|
||||
|
||||
<pre>
|
||||
<...>
|
||||
Runnable r = new Runnable() {
|
||||
public void run() {
|
||||
Object o = new Object();
|
||||
try {
|
||||
synchronized (o) {
|
||||
o.wait();
|
||||
}
|
||||
} catch (InterruptedException ie) {
|
||||
}
|
||||
}
|
||||
};
|
||||
Thread t = new Thread(r);
|
||||
t.setDaemon(false);
|
||||
t.start();
|
||||
<...>
|
||||
</pre>
|
||||
|
||||
<cite>The Java™ Virtual Machine Specification</cite>
|
||||
guarantees
|
||||
that the JVM doesn't exit until this thread terminates.
|
||||
</body>
|
||||
</html>
|
Loading…
Add table
Add a link
Reference in a new issue