test/hotspot/jtreg/gc/g1/TestGCLogMessages.java
changeset 47216 71c04702a3d5
parent 47106 bed18a111b90
child 48791 6e079ff6c83c
equal deleted inserted replaced
47215:4ebc2e2fb97c 47216:71c04702a3d5
       
     1 /*
       
     2  * Copyright (c) 2014, 2017, Oracle and/or its affiliates. All rights reserved.
       
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
       
     4  *
       
     5  * This code is free software; you can redistribute it and/or modify it
       
     6  * under the terms of the GNU General Public License version 2 only, as
       
     7  * published by the Free Software Foundation.
       
     8  *
       
     9  * This code is distributed in the hope that it will be useful, but WITHOUT
       
    10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
       
    11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
       
    12  * version 2 for more details (a copy is included in the LICENSE file that
       
    13  * accompanied this code).
       
    14  *
       
    15  * You should have received a copy of the GNU General Public License version
       
    16  * 2 along with this work; if not, write to the Free Software Foundation,
       
    17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
       
    18  *
       
    19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
       
    20  * or visit www.oracle.com if you need additional information or have any
       
    21  * questions.
       
    22  */
       
    23 
       
    24 /*
       
    25  * @test TestGCLogMessages
       
    26  * @bug 8035406 8027295 8035398 8019342 8027959 8048179 8027962 8069330 8076463 8150630 8160055 8177059 8166191
       
    27  * @summary Ensure the output for a minor GC with G1
       
    28  * includes the expected necessary messages.
       
    29  * @key gc
       
    30  * @requires vm.gc.G1
       
    31  * @library /test/lib
       
    32  * @modules java.base/jdk.internal.misc
       
    33  *          java.management
       
    34  * @build sun.hotspot.WhiteBox
       
    35  * @run main ClassFileInstaller sun.hotspot.WhiteBox
       
    36  * @run main TestGCLogMessages
       
    37  */
       
    38 
       
    39 import jdk.test.lib.process.OutputAnalyzer;
       
    40 import jdk.test.lib.process.ProcessTools;
       
    41 import jdk.test.lib.Platform;
       
    42 
       
    43 public class TestGCLogMessages {
       
    44 
       
    45     private enum Level {
       
    46         OFF(""),
       
    47         INFO("info"),
       
    48         DEBUG("debug"),
       
    49         TRACE("trace");
       
    50 
       
    51         private String logName;
       
    52 
       
    53         Level(String logName) {
       
    54             this.logName = logName;
       
    55         }
       
    56 
       
    57         public boolean lessThan(Level other) {
       
    58             return this.compareTo(other) < 0;
       
    59         }
       
    60 
       
    61         public String toString() {
       
    62             return logName;
       
    63         }
       
    64     }
       
    65 
       
    66     private class LogMessageWithLevel {
       
    67         String message;
       
    68         Level level;
       
    69 
       
    70         public LogMessageWithLevel(String message, Level level) {
       
    71             this.message = message;
       
    72             this.level = level;
       
    73         }
       
    74 
       
    75         public boolean isAvailable() {
       
    76             return true;
       
    77         }
       
    78     };
       
    79 
       
    80     private class LogMessageWithLevelC2OrJVMCIOnly extends LogMessageWithLevel {
       
    81         public LogMessageWithLevelC2OrJVMCIOnly(String message, Level level) {
       
    82             super(message, level);
       
    83         }
       
    84 
       
    85         public boolean isAvailable() {
       
    86             return Platform.isGraal() || Platform.isServer();
       
    87         }
       
    88     }
       
    89 
       
    90     private LogMessageWithLevel allLogMessages[] = new LogMessageWithLevel[] {
       
    91         new LogMessageWithLevel("Pre Evacuate Collection Set", Level.INFO),
       
    92         new LogMessageWithLevel("Evacuate Collection Set", Level.INFO),
       
    93         new LogMessageWithLevel("Post Evacuate Collection Set", Level.INFO),
       
    94         new LogMessageWithLevel("Other", Level.INFO),
       
    95 
       
    96         // Update RS
       
    97         new LogMessageWithLevel("Update RS", Level.DEBUG),
       
    98         new LogMessageWithLevel("Processed Buffers", Level.DEBUG),
       
    99         new LogMessageWithLevel("Scanned Cards", Level.DEBUG),
       
   100         new LogMessageWithLevel("Skipped Cards", Level.DEBUG),
       
   101         new LogMessageWithLevel("Scan HCC", Level.TRACE),
       
   102         // Scan RS
       
   103         new LogMessageWithLevel("Scan RS", Level.DEBUG),
       
   104         new LogMessageWithLevel("Scanned Cards", Level.DEBUG),
       
   105         new LogMessageWithLevel("Claimed Cards", Level.DEBUG),
       
   106         new LogMessageWithLevel("Skipped Cards", Level.DEBUG),
       
   107         // Ext Root Scan
       
   108         new LogMessageWithLevel("Thread Roots", Level.TRACE),
       
   109         new LogMessageWithLevel("StringTable Roots", Level.TRACE),
       
   110         new LogMessageWithLevel("Universe Roots", Level.TRACE),
       
   111         new LogMessageWithLevel("JNI Handles Roots", Level.TRACE),
       
   112         new LogMessageWithLevel("ObjectSynchronizer Roots", Level.TRACE),
       
   113         new LogMessageWithLevel("Management Roots", Level.TRACE),
       
   114         new LogMessageWithLevel("SystemDictionary Roots", Level.TRACE),
       
   115         new LogMessageWithLevel("CLDG Roots", Level.TRACE),
       
   116         new LogMessageWithLevel("JVMTI Roots", Level.TRACE),
       
   117         new LogMessageWithLevel("SATB Filtering", Level.TRACE),
       
   118         new LogMessageWithLevel("CM RefProcessor Roots", Level.TRACE),
       
   119         new LogMessageWithLevel("Wait For Strong CLD", Level.TRACE),
       
   120         new LogMessageWithLevel("Weak CLD Roots", Level.TRACE),
       
   121         // Redirty Cards
       
   122         new LogMessageWithLevel("Redirty Cards", Level.DEBUG),
       
   123         new LogMessageWithLevel("Parallel Redirty", Level.TRACE),
       
   124         new LogMessageWithLevel("Redirtied Cards", Level.TRACE),
       
   125         // Misc Top-level
       
   126         new LogMessageWithLevel("Code Roots Purge", Level.DEBUG),
       
   127         new LogMessageWithLevel("String Dedup Fixup", Level.DEBUG),
       
   128         new LogMessageWithLevel("Expand Heap After Collection", Level.DEBUG),
       
   129         // Free CSet
       
   130         new LogMessageWithLevel("Free Collection Set", Level.DEBUG),
       
   131         new LogMessageWithLevel("Free Collection Set Serial", Level.TRACE),
       
   132         new LogMessageWithLevel("Young Free Collection Set", Level.TRACE),
       
   133         new LogMessageWithLevel("Non-Young Free Collection Set", Level.TRACE),
       
   134         // Humongous Eager Reclaim
       
   135         new LogMessageWithLevel("Humongous Reclaim", Level.DEBUG),
       
   136         new LogMessageWithLevel("Humongous Register", Level.DEBUG),
       
   137         // Preserve CM Referents
       
   138         new LogMessageWithLevel("Preserve CM Refs", Level.DEBUG),
       
   139         // Merge PSS
       
   140         new LogMessageWithLevel("Merge Per-Thread State", Level.DEBUG),
       
   141         // TLAB handling
       
   142         new LogMessageWithLevel("Prepare TLABs", Level.DEBUG),
       
   143         new LogMessageWithLevel("Resize TLABs", Level.DEBUG),
       
   144         // Reference Processing
       
   145         new LogMessageWithLevel("Reference Processing", Level.DEBUG),
       
   146         new LogMessageWithLevel("Reference Enqueuing", Level.DEBUG),
       
   147 
       
   148         new LogMessageWithLevelC2OrJVMCIOnly("DerivedPointerTable Update", Level.DEBUG),
       
   149         new LogMessageWithLevel("Start New Collection Set", Level.DEBUG),
       
   150     };
       
   151 
       
   152     void checkMessagesAtLevel(OutputAnalyzer output, LogMessageWithLevel messages[], Level level) throws Exception {
       
   153         for (LogMessageWithLevel l : messages) {
       
   154             if (level.lessThan(l.level) || !l.isAvailable()) {
       
   155                 output.shouldNotContain(l.message);
       
   156             } else {
       
   157                 output.shouldMatch("\\[" + l.level + ".*" + l.message);
       
   158             }
       
   159         }
       
   160     }
       
   161 
       
   162     public static void main(String[] args) throws Exception {
       
   163         new TestGCLogMessages().testNormalLogs();
       
   164         new TestGCLogMessages().testWithToSpaceExhaustionLogs();
       
   165         new TestGCLogMessages().testWithInitialMark();
       
   166         new TestGCLogMessages().testExpandHeap();
       
   167     }
       
   168 
       
   169     private void testNormalLogs() throws Exception {
       
   170 
       
   171         ProcessBuilder pb = ProcessTools.createJavaProcessBuilder("-XX:+UseG1GC",
       
   172                                                                   "-Xmx10M",
       
   173                                                                   GCTest.class.getName());
       
   174 
       
   175         OutputAnalyzer output = new OutputAnalyzer(pb.start());
       
   176         checkMessagesAtLevel(output, allLogMessages, Level.OFF);
       
   177         output.shouldHaveExitValue(0);
       
   178 
       
   179         pb = ProcessTools.createJavaProcessBuilder("-XX:+UseG1GC",
       
   180                                                    "-XX:+UseStringDeduplication",
       
   181                                                    "-Xmx10M",
       
   182                                                    "-Xlog:gc+phases=debug",
       
   183                                                    GCTest.class.getName());
       
   184 
       
   185         output = new OutputAnalyzer(pb.start());
       
   186         checkMessagesAtLevel(output, allLogMessages, Level.DEBUG);
       
   187 
       
   188         pb = ProcessTools.createJavaProcessBuilder("-XX:+UseG1GC",
       
   189                                                    "-XX:+UseStringDeduplication",
       
   190                                                    "-Xmx10M",
       
   191                                                    "-Xlog:gc+phases=trace",
       
   192                                                    GCTest.class.getName());
       
   193 
       
   194         output = new OutputAnalyzer(pb.start());
       
   195         checkMessagesAtLevel(output, allLogMessages, Level.TRACE);
       
   196         output.shouldHaveExitValue(0);
       
   197     }
       
   198 
       
   199     LogMessageWithLevel exhFailureMessages[] = new LogMessageWithLevel[] {
       
   200         new LogMessageWithLevel("Evacuation Failure", Level.DEBUG),
       
   201         new LogMessageWithLevel("Recalculate Used", Level.TRACE),
       
   202         new LogMessageWithLevel("Remove Self Forwards", Level.TRACE),
       
   203     };
       
   204 
       
   205     private void testWithToSpaceExhaustionLogs() throws Exception {
       
   206         ProcessBuilder pb = ProcessTools.createJavaProcessBuilder("-XX:+UseG1GC",
       
   207                                                                   "-Xmx32M",
       
   208                                                                   "-Xmn16M",
       
   209                                                                   "-Xlog:gc+phases=debug",
       
   210                                                                   GCTestWithToSpaceExhaustion.class.getName());
       
   211 
       
   212         OutputAnalyzer output = new OutputAnalyzer(pb.start());
       
   213         checkMessagesAtLevel(output, exhFailureMessages, Level.DEBUG);
       
   214         output.shouldHaveExitValue(0);
       
   215 
       
   216         pb = ProcessTools.createJavaProcessBuilder("-XX:+UseG1GC",
       
   217                                                    "-Xmx32M",
       
   218                                                    "-Xmn16M",
       
   219                                                    "-Xlog:gc+phases=trace",
       
   220                                                    GCTestWithToSpaceExhaustion.class.getName());
       
   221 
       
   222         output = new OutputAnalyzer(pb.start());
       
   223         checkMessagesAtLevel(output, exhFailureMessages, Level.TRACE);
       
   224         output.shouldHaveExitValue(0);
       
   225     }
       
   226 
       
   227     private void testWithInitialMark() throws Exception {
       
   228         ProcessBuilder pb = ProcessTools.createJavaProcessBuilder("-XX:+UseG1GC",
       
   229                                                                   "-Xmx10M",
       
   230                                                                   "-Xbootclasspath/a:.",
       
   231                                                                   "-Xlog:gc*=debug",
       
   232                                                                   "-XX:+UnlockDiagnosticVMOptions",
       
   233                                                                   "-XX:+WhiteBoxAPI",
       
   234                                                                   GCTestWithInitialMark.class.getName());
       
   235 
       
   236         OutputAnalyzer output = new OutputAnalyzer(pb.start());
       
   237         output.shouldContain("Clear Claimed Marks");
       
   238         output.shouldHaveExitValue(0);
       
   239     }
       
   240 
       
   241     private void testExpandHeap() throws Exception {
       
   242         ProcessBuilder pb = ProcessTools.createJavaProcessBuilder("-XX:+UseG1GC",
       
   243                                                                   "-Xmx10M",
       
   244                                                                   "-Xbootclasspath/a:.",
       
   245                                                                   "-Xlog:gc+ergo+heap=debug",
       
   246                                                                   "-XX:+UnlockDiagnosticVMOptions",
       
   247                                                                   "-XX:+WhiteBoxAPI",
       
   248                                                                   GCTest.class.getName());
       
   249 
       
   250         OutputAnalyzer output = new OutputAnalyzer(pb.start());
       
   251         output.shouldContain("Expand the heap. requested expansion amount: ");
       
   252         output.shouldContain("B expansion amount: ");
       
   253         output.shouldHaveExitValue(0);
       
   254     }
       
   255 
       
   256 
       
   257     static class GCTest {
       
   258         private static byte[] garbage;
       
   259         public static void main(String [] args) {
       
   260             System.out.println("Creating garbage");
       
   261             // create 128MB of garbage. This should result in at least one GC
       
   262             for (int i = 0; i < 1024; i++) {
       
   263                 garbage = new byte[128 * 1024];
       
   264             }
       
   265             System.out.println("Done");
       
   266         }
       
   267     }
       
   268 
       
   269     static class GCTestWithToSpaceExhaustion {
       
   270         private static byte[] garbage;
       
   271         private static byte[] largeObject;
       
   272         public static void main(String [] args) {
       
   273             largeObject = new byte[16*1024*1024];
       
   274             System.out.println("Creating garbage");
       
   275             // create 128MB of garbage. This should result in at least one GC,
       
   276             // some of them with to-space exhaustion.
       
   277             for (int i = 0; i < 1024; i++) {
       
   278                 garbage = new byte[128 * 1024];
       
   279             }
       
   280             System.out.println("Done");
       
   281         }
       
   282     }
       
   283 
       
   284     static class GCTestWithInitialMark {
       
   285         public static void main(String [] args) {
       
   286             sun.hotspot.WhiteBox WB = sun.hotspot.WhiteBox.getWhiteBox();
       
   287             WB.g1StartConcMarkCycle();
       
   288         }
       
   289     }
       
   290 
       
   291 }
       
   292