<html>
  <head>

    <meta http-equiv="content-type" content="text/html; charset=ISO-8859-1">
  </head>
  <body text="#000000" bgcolor="#FFFFFF">
    Hi all,<br>
    <br>
    could I have reviews for this patch? Please note<br>
    that I do not yet feel very confident with the sweeper,<br>
    so please take a close look.<br>
    <br>
    jbs:
    <meta http-equiv="content-type" content="text/html;
      charset=ISO-8859-1">
    <a href="https://jbs.oracle.com/bugs/browse/JDK-8020151">https://jbs.oracle.com/bugs/browse/JDK-8020151</a><br>
    webrev:
    <meta http-equiv="content-type" content="text/html;
      charset=ISO-8859-1">
    <a href="http://cr.openjdk.java.net/%7Eanoll/8020151/webrev.00/">http://cr.openjdk.java.net/~anoll/8020151/webrev.00/</a><br>
    <br>
    <br>
    Many thanks in advance,<br>
    Albert<br>
    <br>
    <br>
    Problem: There can be large performance regressions when the code
    cache fills up. There are <br>
    several reasons for the performance regression: First (1), when the
    code cache is full and methods <br>
    are speculatively disconnected, the oldest methods (based on
    compilation ID) are scheduled for<br>
    flushing. This can result in flushing hot methods. Second (2), when
    compilation is disabled due to a full<br>
    code cache, the number of sweeps can go down. A lower number of
    sweep operations results <br>
    in slower method flushing.<br>
    <br>
    Solution:<br>
    Introduce a hotness counter that is set to a particular value (e.g.,
    100) when there is an activation<br>
    of the method during stack scanning. The counter is decremented by 1
    every time the sweeper <br>
    is invoked.<br>
    <br>
    ad (1):<br>
    &nbsp; A VM operation that speculatively disconnects nmethods, selects
    the methods that should be<br>
    &nbsp; flushed based on the hotness. For example, if 50% of the code
    cache shall be flushed, we flush <br>
    &nbsp; those methods that have not been active while stack scanning for
    the longest time. Note that <br>
    &nbsp; while this strategy is more likely to flush cold methods, it is
    not clear to what extent the new <br>
    &nbsp; strategy fragments the code cache.<br>
    <br>
    &nbsp; Changes in NMethodSweeper::speculative_disconnect_nmethods(bool
    is_full)<br>
    <br>
    ad (2)<br>
    &nbsp; Currently, methods are removed from the code cache if:<br>
    &nbsp;&nbsp;&nbsp; a) code cache is full
<br>
    &nbsp;&nbsp;&nbsp; b) class is unloaded
<br>
    &nbsp;&nbsp;&nbsp; c) method is replaced by another version (i.e., compiled with a
    different tier)
<br>
    &nbsp;&nbsp;&nbsp; d) deopt<br>
    <br>
    &nbsp;&nbsp; The current patch adds a 5-th possibility to remove a method from
    the code cache. <br>
    &nbsp;&nbsp; In particular, if a method has not been active during stack
    scanning for a long-enough <br>
    &nbsp;&nbsp; amount of time, the method is removed from the code cache. The
    amount of time<br>
    &nbsp;&nbsp; required to flush the method depends on the available space in
    the code cache. <br>
    &nbsp;&nbsp; <br>
    &nbsp;&nbsp; Here is one example: If a method was seen on a stack the hotness
    counter <br>
    &nbsp;&nbsp; is set to 100. A sweep operation takes roughly place every 100ms.
    I.e., it takes <br>
    &nbsp;&nbsp; 100ms * 100 = 10s until the hotness counter reaches 0. The
    threshold that determines<br>
    &nbsp;&nbsp; if a method should be removed from the code cache is calculated
    as follows:<br>
    &nbsp;<br>
    &nbsp;&nbsp; threshold = -100 + (CodeCache::reverse_free_ratio() *
    NMethodSweepActivity)<br>
    <br>
    &nbsp;&nbsp;&nbsp; For example, if 25% of the code cache is free,
    reverse_free_ratio returns 4.<br>
    &nbsp;&nbsp;&nbsp; The default value of NMethodSweepActivity is 10. As a result,
    threshold = -60.<br>
    &nbsp;&nbsp;&nbsp; Consequently, all methods that have a hotness value smaller than
    -60 (which <br>
    &nbsp;&nbsp;&nbsp; means they have not been seen on the stack for 16s) are
    scheduled to be flushed<br>
    &nbsp;&nbsp;&nbsp; from the code cache. See an illustration of the threshold as a
    function of the available<br>
    &nbsp;&nbsp;&nbsp; code cache in threshold.pdf<br>
    <br>
    &nbsp;&nbsp;&nbsp; Note that NMethodSweepActivity is a parameter that can be
    specified via a -XX<br>
    &nbsp;&nbsp;&nbsp; flag.<br>
    <br>
    Changes in NMethodSweeper::sweep_code_cache()<br>
    <br>
    <br>
    A very preliminary performance evaluation looks promising. I used
    the DaCapo <br>
    benchmarks where a series of benchmarks is executed in the same VM
    instance.<br>
    See performance.pdf . The x-axis shows the benchmarks. Assume we
    have 2 benchmarks <br>
    (BM). The execution sequence is as follows:<br>
    <br>
    BM1 (Run 1-1)<br>
    BM1 (Run 2-1)<br>
    BM2 (Run 1-1)<br>
    BM2 (Run 2-1)<br>
    <br>
    BM1 (Run 1-2)<br>
    BM1 (Run 2-2)<br>
    BM2 (Run 1-2)<br>
    BM2 (Run 2-2)<br>
    <br>
    <br>
    A value larger than 0 on the x-axis indicates that the version
    including the proposed patch is faster.<br>
    I.e., the values are calculated as follows: (T_original /
    T_with_patch) - 1. T is the execution time <br>
    (wall clock time) of the benchmark. ReservedCodeCacheSize is set to
    50m.&nbsp; I used three runs and <br>
    the arithmetic average to compare the numbers. I know, we need much
    more data, however, <br>
    I think we can see a trend.<br>
    <br>
    The current patch does not trigger a warning that the code cache is
    full and compilation has been<br>
    disabled.<br>
    <br>
    Please let me know that you think.<br>
  </body>
</html>