diff -r 2c3cc4b01880 -r c16ac7a2eba4 src/jdk.jfr/share/classes/jdk/jfr/internal/RequestEngine.java --- a/src/jdk.jfr/share/classes/jdk/jfr/internal/RequestEngine.java Wed Oct 30 16:14:56 2019 +0100 +++ b/src/jdk.jfr/share/classes/jdk/jfr/internal/RequestEngine.java Wed Oct 30 19:43:52 2019 +0100 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2016, 2018, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2016, 2019, 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 @@ -30,6 +30,7 @@ import java.security.PrivilegedAction; import java.util.ArrayList; import java.util.Collection; +import java.util.Iterator; import java.util.List; import java.util.Objects; import java.util.concurrent.CopyOnWriteArrayList; @@ -96,6 +97,8 @@ private final static List entries = new CopyOnWriteArrayList<>(); private static long lastTimeMillis; + private static long flushInterval = Long.MAX_VALUE; + private static long streamDelta; public static void addHook(AccessControlContext acc, PlatformEventType type, Runnable hook) { Objects.requireNonNull(acc); @@ -209,7 +212,9 @@ lastTimeMillis = now; return 0; } - for (RequestHook he : entries) { + Iterator hookIterator = entries.iterator(); + while(hookIterator.hasNext()) { + RequestHook he = hookIterator.next(); long left = 0; PlatformEventType es = he.type; // Not enabled, skip. @@ -228,7 +233,6 @@ // for wait > period r_delta = 0; he.execute(); - ; } // calculate time left @@ -250,7 +254,39 @@ min = left; } } + // Flush should happen after all periodic events has been emitted + // Repeat of the above algorithm, but using the stream interval. + if (flushInterval != Long.MAX_VALUE) { + long r_period = flushInterval; + long r_delta = streamDelta; + r_delta += delta; + if (r_delta >= r_period) { + r_delta = 0; + MetadataRepository.getInstance().flush(); + Utils.notifyFlush(); + } + long left = (r_period - r_delta); + if (left < 0) { + left = 0; + } + streamDelta = r_delta; + if (min == 0 || left < min) { + min = left; + } + } + lastTimeMillis = now; return min; } + + static void setFlushInterval(long millis) { + // Don't accept shorter interval than 1 s. + long interval = millis < 1000 ? 1000 : millis; + flushInterval = interval; + if (interval < flushInterval) { + synchronized (JVM.FILE_DELTA_CHANGE) { + JVM.FILE_DELTA_CHANGE.notifyAll(); + } + } + } }