[prev in list] [next in list] [prev in thread] [next in thread] 

List:       openjdk-2d-dev
Subject:    [OpenJDK 2D-Dev] RFR: 8196100: javax/swing/text/JTextComponent/5074573/bug5074573.java fails
From:       Sergey Bylokhov <serb () openjdk ! java ! net>
Date:       2020-11-25 0:52:09
Message-ID: odiw68_aqTfJSmoCMm6W2c2KCfaE4H1zbdAtazkmmvc=.1b78ca1d-7820-478a-b3db-e5a72dd422cb () github ! com
[Download RAW message or body]

Here is a fix for one of the annoying bug, which causes random test failures in the \
CI.

We have a method Robot.waitForIdle(), which supposed to wait until the java and the \
native queue stabilized. The common use case is to click on the button or show the \
window, and call waitForIdle() which will wait until the native event will be \
dispatched by the X11/Windows/macOS as well as followed Java event(paint/focus/etc \
event) will be dispatched to the EDT.

Currently, it is implemented in this way:
  1. Flush the EventQueue, so all old events will be posted to EDT.
  2. Flush the native event queue, by posting the native event.
  3. Flush the EDT, by posting a java event.
  4. If some events(unrelated to waitForIdle machinery) were dispatched on steps 2. \
or 3. then repeat since step 1.

It is implemented that they because the native events caused by the OS usually \
generate the java events, and the java events may generate native events. So we have \
to wait for both queues (java/native).

But it has the next disadvantages:
 - It is implemented as a busy loop, which does not give a chance for the application \
to proceed further since it blocks 3 threads EDT/native toolkit thread like \
                appkit/main thread.
- It throws the InfiniteLoop exception if the number of attempts is bigger than 20. \
And this limitation is too small because some tests generate much more events during \
                startup.
 - Note that the timeout value for the realSync method is 10 seconds, and it was \
assumed that this method will not be executed longer, but it uses this timeout for \
all events flushing which can lead up to 600 seconds (20 iters * 3  calls * 10 \
seconds).


The fix:
 - Add a small delay to the method, so the app can do something useful when \
                waitForIdle() is called
 - The timeout=10 second is taken care of, we calculate the "end" time and exits if \
                it is exceeded
 - The maximum number of attempts is increased to 100 and InfiniteLoop is removed.

Note that I have made one additional change to the new realSync implementation. At \
the beginning of the method I call:  EventQueue.invokeAndWait(() -> {/*dummy \
implementation*/}); It is needed to be sure that we flush the first event on EDT even \
if we spend more time than 10 seconds.

-------------

Commit messages:
 - Update SunToolkit.java
 - The new tests
 - Do not use shared state
 - Update SunToolkit.java
 - realSync too slow
 - Update bug5074573.java
 - Test update
 - Initial fix

Changes: https://git.openjdk.java.net/jdk/pull/1424/files
 Webrev: https://webrevs.openjdk.java.net/?repo=jdk&pr=1424&range=00
  Issue: https://bugs.openjdk.java.net/browse/JDK-8196100
  Stats: 242 lines in 9 files changed: 192 ins; 20 del; 30 mod
  Patch: https://git.openjdk.java.net/jdk/pull/1424.diff
  Fetch: git fetch https://git.openjdk.java.net/jdk pull/1424/head:pull/1424

PR: https://git.openjdk.java.net/jdk/pull/1424


[prev in list] [next in list] [prev in thread] [next in thread] 

Configure | About | News | Add a list | Sponsored by KoreLogic