<AWT Dev> OpenJdk11-28-EA JDialog hanging

Krishna Addepalli krishna.addepalli at oracle.com
Wed Oct 17 13:51:09 UTC 2018

Hi Martin,


Excellent assessment of the problem and great explanation of it. Appreciate your efforts in debugging and proposing a solution to this problem.


I have couple questions:

1.       This problem (including the one described in JDK-8152974) is not reproducible at all in Mac. I would like to understand why this happens only on Windows/Linux because the proposed fix is in generic code.

2.       I’m not sure if I agree to your proposal of dispatching non-SequencedEvents, from the queue. The events arriving after a particular SequencedEvent could be dependent on this event – for example, the current SequencedEvent could be a focus change event, and the subsequent events could be Key events. So, as per your solution, if we dispatch them, there is a possibility that the intended component may not receive those events.




From: Martin Balao <mbalao at redhat.com> 
Sent: Tuesday, October 16, 2018 5:18 PM
To: Laurent Bourgès <bourges.laurent at gmail.com>
Cc: awt-dev at openjdk.java.net
Subject: Re: <AWT Dev> OpenJdk11-28-EA JDialog hanging


Hi Laurent,


Thanks for your test! Great job :-)


I applied some minor changes for integration:


 * Renamed to TestSeqEventsMultipleContexts

  * A bit longer but should describe what this is about

  * Placed in jdk/java/awt/event/SequencedEvent


 * Encapsulated the window in TestWindow class


 * Instead of waiting 1s for windows to show, loop until windows are shown -or the test hard stops-. When I ran in my environment, 1s was not enough. This should make the test more resilent. We still depend on a timer but that is inevitably.


 * Incremented the time we wait for the TGs to finish. 2s was not enough in my runs. However, we now do frequent checks to finish earlier in the success path.


 * Calculated expected value in initilization time


 * Changed a bit how the test finishes

  * System.exit(0) is a failure for jtreg

  * We need status -1 for jtreg to detect failures, and will do a hard stop when time expires

  * Stack traces for the main thread are not much relevant 

  * dispose window to exit gracefully on the success path


 * Removed unused code (button click action)


 * Added jtreg tags & copyright


Webrev.02 with test integrated:


 * http://cr.openjdk.java.net/~mbalao/webrevs/8204142/8204142.webrev.02

 * http://cr.openjdk.java.net/~mbalao/webrevs/8204142/8204142.webrev.02.zip


Kind regards,



On Mon, Oct 15, 2018 at 3:38 PM, Laurent Bourgès <HYPERLINK "mailto:bourges.laurent at gmail.com"bourges.laurent at gmail.com> wrote:

Hi Martin,

Thanks for your feedback and happy to hear that it worked!


In regards to pendingEvents sync, my understanding is that SequencedEvent objects will be posted to one EventQueue only and, thus, be dispatched by one EDT.





I had a quick look at "Exception in thread "AWT-EventQueue-1" java.lang.IllegalArgumentException: null source" exception and could not find any connection to the code modified in the context of this bug. Apparently, "activeWindow" variable in "WindowEvent.WINDOW_LOST_FOCUS" case is null (DefaultKeyboardFocusManager.dispatchEvent function). I thought that this was caused by the fact that the test is injecting events that modify the focus on both windows at a very high rate and, by the time DefaultKeyboardFocusManager dispatches the event, it could be too late. Just an hypothesis.


I agree, it is certainly a side-effect: other issues may be triggered by such event intensive test.


Look forward to your re-written test.


Here it is:

import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.atomic.AtomicReference;
import javax.swing.JButton;

import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.SwingUtilities;
import javax.swing.Timer;

 * Running this code causes the AWT Event Queues to be blocked on OpenJDK11
 * javac --add-exports java.desktop/sun.awt=ALL-UNNAMED TestWinEvent.java
 * @author Laurent Bourges
public final class TestWinEvent extends JFrame implements ActionListener {

    private static final long serialVersionUID = 1L;

    private static final int NUM_WINDOW = 2;
    private static final int INTERVAL = 50;
    private static final int MAX_TIME = 10000; // 10s
    private static final int MAX_COUNT = MAX_TIME / INTERVAL;
    private static final List<TestWinEvent> WINDOWS = new ArrayList<TestWinEvent>();

    private final JButton btn;
    private int counter = 0;
    private final Timer t;

    public static void main(String[] args) {
        try {
            for (int i = 0; i < NUM_WINDOW; i++) {
                createWin(i + 1);

            // Wait MAX_TIME + 2s
            Thread.sleep(MAX_TIME + 2000);

            int total = 0;
            for (TestWinEvent window : WINDOWS) {
                total += window.getCounter();

            // Failure if AWT hanging: assert
            final int expected = MAX_COUNT * NUM_WINDOW;
            if (total != expected) {
                throw new IllegalStateException("Total [" + total + "] != expected [" + expected + "] !");
        } catch (InterruptedException ie) {
        } catch (IllegalStateException iae) {
        } finally {

    private static void createWin(int tgNum) {
        new Thread(new ThreadGroup("TG " + tgNum),
                new Runnable() {
            public void run() {

                final AtomicReference<TestWinEvent> ref = new AtomicReference<TestWinEvent>();

                SwingUtilities.invokeLater(new Runnable() {
                    public void run() {
                        final TestWinEvent window = new TestWinEvent(tgNum);

                try {
                    // Wait 1s to show window
                } catch (InterruptedException ie) {

                final TestWinEvent window = ref.get();
                if (window != null) {

    TestWinEvent(final int num) {
        super("Test Window [" + num + "]");
        setMinimumSize(new Dimension(300, 200));
        setLocation(100 + 400 * (num - 1), 100);

        setLayout(new BorderLayout());
        JLabel textBlock = new JLabel("Lorem ipsum dolor sit amet...");

        btn = new JButton("TEST");
        btn.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                System.out.println("Button#" + num + " clicked: " + counter);

        add(btn, BorderLayout.SOUTH);


        t = new Timer(INTERVAL, this);

    public void actionPerformed(ActionEvent e) {
        btn.setText("TEST " + (++counter));
        if (counter < MAX_COUNT) {
        } else {

    void enableTimer(boolean enable) {
        if (enable) {
        } else {

    int getCounter() {
        return counter;


I will attach it in the JBS bug.




-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.openjdk.java.net/pipermail/awt-dev/attachments/20181017/8f236c72/attachment-0001.html>

More information about the awt-dev mailing list