6959965: jstat: Add new -classload option to print class loading statistics
Summary: Add a new jstat -classload option
Reviewed-by: alanb
--- a/jdk/make/sun/tools/Makefile Tue Jun 08 18:52:17 2010 -0700
+++ b/jdk/make/sun/tools/Makefile Thu Jun 10 14:14:17 2010 -0700
@@ -49,7 +49,8 @@
# Extra jstat files
FILES_copy += \
- $(CLASSDESTDIR)/sun/tools/jstat/resources/jstat_options
+ $(CLASSDESTDIR)/sun/tools/jstat/resources/jstat_options \
+ $(CLASSDESTDIR)/sun/tools/jstat/resources/jstat_unsupported_options
# Extra jhat files
JHAT_RESOURCEDIR = $(CLASSDESTDIR)/com/sun/tools/hat/resources
--- a/jdk/src/share/classes/sun/tools/jstat/Arguments.java Tue Jun 08 18:52:17 2010 -0700
+++ b/jdk/src/share/classes/sun/tools/jstat/Arguments.java Thu Jun 10 14:14:17 2010 -0700
@@ -47,6 +47,7 @@
private static final String JVMSTAT_USERDIR = ".jvmstat";
private static final String OPTIONS_FILENAME = "jstat_options";
+ private static final String UNSUPPORTED_OPTIONS_FILENAME = "jstat_unsupported_options";
private static final String ALL_NAMES = "\\w*";
private Comparator<Monitor> comparator;
@@ -411,8 +412,8 @@
return optionFormat;
}
- public URL[] optionsSources() {
- URL[] sources = new URL[2];
+ public List<URL> optionsSources() {
+ List<URL> sources = new ArrayList<URL>();
int i = 0;
String filename = OPTIONS_FILENAME;
@@ -421,7 +422,7 @@
String userHome = System.getProperty("user.home");
String userDir = userHome + "/" + JVMSTAT_USERDIR;
File home = new File(userDir + "/" + filename);
- sources[i++] = home.toURL();
+ sources.add(home.toURI().toURL());
} catch (Exception e) {
if (debug) {
System.err.println(e.getMessage());
@@ -430,8 +431,15 @@
throw new IllegalArgumentException("Internal Error: Bad URL: "
+ e.getMessage());
}
- sources[i] = this.getClass().getResource("resources/" + filename);
- assert sources[i] != null;
+ URL u = this.getClass().getResource("resources/" + filename);
+ assert u != null;
+ sources.add(u);
+
+ if (showUnsupported) {
+ u = this.getClass().getResource("resources/" + UNSUPPORTED_OPTIONS_FILENAME);
+ assert u != null;
+ sources.add(u);
+ }
return sources;
}
}
--- a/jdk/src/share/classes/sun/tools/jstat/OptionFinder.java Tue Jun 08 18:52:17 2010 -0700
+++ b/jdk/src/share/classes/sun/tools/jstat/OptionFinder.java Thu Jun 10 14:14:17 2010 -0700
@@ -39,9 +39,9 @@
private static final boolean debug = false;
- URL[] optionsSources;
+ List<URL> optionsSources;
- public OptionFinder(URL[] optionsSources) {
+ public OptionFinder(List<URL> optionsSources) {
this.optionsSources = optionsSources;
}
@@ -59,24 +59,25 @@
return of;
}
- protected OptionFormat getOptionFormat(String option, URL[] sources) {
+ protected OptionFormat getOptionFormat(String option, List<URL> sources) {
OptionFormat of = null;
- for (int i = 0; (i < sources.length) && (of == null); i++) {
+ for (URL u : sources) {
try {
- URL u = sources[i];
Reader r = new BufferedReader(
new InputStreamReader(u.openStream()));
of = new Parser(r).parse(option);
+ if (of != null)
+ break;
} catch (IOException e) {
if (debug) {
- System.err.println("Error processing " + sources[i]
+ System.err.println("Error processing " + u
+ " : " + e.getMessage());
e.printStackTrace();
}
} catch (ParserException e) {
// Exception in parsing the options file.
- System.err.println(sources[i] + ": " + e.getMessage());
- System.err.println("Parsing of " + sources[i] + " aborted");
+ System.err.println(u + ": " + e.getMessage());
+ System.err.println("Parsing of " + u + " aborted");
}
}
return of;
--- a/jdk/src/share/classes/sun/tools/jstat/OptionLister.java Tue Jun 08 18:52:17 2010 -0700
+++ b/jdk/src/share/classes/sun/tools/jstat/OptionLister.java Thu Jun 10 14:14:17 2010 -0700
@@ -37,9 +37,9 @@
*/
public class OptionLister {
private static final boolean debug = false;
- private URL[] sources;
+ private List<URL> sources;
- public OptionLister(URL[] sources) {
+ public OptionLister(List<URL> sources) {
this.sources = sources;
}
@@ -54,9 +54,8 @@
Set<OptionFormat> options = new TreeSet<OptionFormat>(c);
- for (int i = 0; i < sources.length; i++) {
+ for (URL u : sources) {
try {
- URL u = sources[i];
Reader r = new BufferedReader(
new InputStreamReader(u.openStream()));
Set<OptionFormat> s = new Parser(r).parseOptions();
@@ -68,8 +67,8 @@
}
} catch (ParserException e) {
// Exception in parsing the options file.
- System.err.println(sources[i] + ": " + e.getMessage());
- System.err.println("Parsing of " + sources[i] + " aborted");
+ System.err.println(u + ": " + e.getMessage());
+ System.err.println("Parsing of " + u + " aborted");
}
}
--- a/jdk/src/share/classes/sun/tools/jstat/resources/jstat_options Tue Jun 08 18:52:17 2010 -0700
+++ b/jdk/src/share/classes/sun/tools/jstat/resources/jstat_options Thu Jun 10 14:14:17 2010 -0700
@@ -37,7 +37,7 @@
option class {
column {
header "^Loaded^" /* Number of classes loaded */
- data java.cls.loadedClasses
+ data (java.cls.loadedClasses + java.cls.sharedLoadedClasses)
align right
scale raw
width 5
@@ -45,7 +45,7 @@
}
column {
header "^Bytes^" /* Accumulated Size of classes loaded */
- data sun.cls.loadedBytes
+ data (sun.cls.loadedBytes + sun.cls.sharedLoadedBytes)
align right
scale K
width 7
@@ -53,7 +53,7 @@
}
column {
header "^Unloaded^" /* Number of classes unloaded */
- data java.cls.unloadedClasses
+ data (java.cls.unloadedClasses + java.cls.sharedUnloadedClasses)
align right
width 5
scale raw
@@ -61,7 +61,7 @@
}
column {
header "^Bytes^" /* Accumulated size of classes unloaded */
- data sun.cls.unloadedBytes
+ data (sun.cls.unloadedBytes + sun.cls.sharedUnloadedBytes)
align right
scale K
width 7
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/share/classes/sun/tools/jstat/resources/jstat_unsupported_options Thu Jun 10 14:14:17 2010 -0700
@@ -0,0 +1,228 @@
+/*
+ * Copyright (c) 2010, 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation. Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+option classload {
+ column {
+ header "^Loaded^" /* Number of classes loaded */
+ data (java.cls.loadedClasses + java.cls.sharedLoadedClasses)
+ align right
+ scale raw
+ width 5
+ format "0"
+ }
+ column {
+ header "Time^" /* Accumulated time for class loading */
+ data sun.cls.time/sun.os.hrt.frequency
+ scale sec
+ align right
+ width 10
+ format "0.000"
+ }
+ column {
+ header "^Inited^" /* Number of initialized classes */
+ data sun.cls.initializedClasses
+ align right
+ scale raw
+ width 5
+ format "0"
+ }
+ column {
+ header "Time^" /* Accumulated time for class initialization */
+ data sun.cls.classInitTime.self/sun.os.hrt.frequency
+ scale raw
+ align right
+ width 10
+ format "0.000"
+ }
+ column {
+ header "Shared^" /* Number of system classes loaded from shared archive */
+ data java.cls.sharedLoadedClasses
+ align right
+ scale raw
+ width 5
+ format "0"
+ }
+ column {
+ header "Kbytes^" /* Accumulated Size of classes loaded */
+ data sun.cls.sharedLoadedBytes
+ align right
+ scale K
+ width 7
+ format "0.0"
+ }
+ column {
+ header "LoadTime^" /* Accumulated time for loading classes from shared archive */
+ data sun.cls.sharedClassLoadTime/sun.os.hrt.frequency
+ scale raw
+ align right
+ width 10
+ format "0.000"
+ }
+ column {
+ header "^SysClass^" /* Number of system classes loaded */
+ data java.cls.loadedClasses
+ align right
+ scale raw
+ width 5
+ format "0"
+ }
+ column {
+ header "Kbytes^" /* Bytes read from system class files */
+ data sun.cls.sysClassBytes
+ align right
+ scale K
+ width 7
+ format "0.0"
+ }
+ column {
+ header "LoadTime^" /* Accumulated time for loading non-shared system classes */
+ data sun.cls.sysClassLoadTime/sun.os.hrt.frequency
+ scale raw
+ align right
+ width 10
+ format "0.000"
+ }
+ column {
+ header "Lookup^" /* Time spent in looking up/reading of system classes */
+ data sun.cls.lookupSysClassTime/sun.os.hrt.frequency
+ scale raw
+ align right
+ width 10
+ format "0.000"
+ }
+ column {
+ header "Parse^" /* Time spent in parsing system classes */
+ data sun.cls.parseClassTime.self/sun.os.hrt.frequency
+ scale raw
+ align right
+ width 10
+ format "0.000"
+ }
+ column {
+ header "^Linked^" /* Number of linked classes */
+ data sun.cls.linkedClasses
+ align right
+ scale raw
+ width 5
+ format "0"
+ }
+ column {
+ header "Time^" /* Accumulated time for class linking */
+ data sun.cls.classInitTime.self/sun.os.hrt.frequency
+ scale raw
+ align right
+ width 10
+ format "0.000"
+ }
+ column {
+ header "^Verified^" /* Number of verified classes */
+ data sun.cls.verifiedClasses
+ align right
+ scale raw
+ width 5
+ format "0"
+ }
+ column {
+ header "Time^" /* Accumulated time for class verification */
+ data sun.cls.classVerifyTime.self/sun.os.hrt.frequency
+ scale raw
+ align right
+ width 10
+ format "0.000"
+ }
+ column {
+ header "AppClass^" /* Number of loaded application classes */
+ data sun.cls.appClassLoadCount
+ align right
+ scale raw
+ width 5
+ format "0"
+ }
+ column {
+ header "Kbytes^" /* Bytes read from app class files */
+ data sun.cls.appClassBytes
+ align right
+ scale K
+ width 7
+ format "0.0"
+ }
+ column {
+ header "AppCL^" /* Accumulated time for loading app classes */
+ data sun.cls.appClassLoadTime/sun.os.hrt.frequency
+ scale raw
+ align right
+ width 10
+ format "0.000"
+ }
+ column {
+ header "^DefineClass^" /* Number of defineClass calls */
+ data sun.cls.defineAppClasses
+ align right
+ scale raw
+ width 5
+ format "0"
+ }
+ column {
+ header "Time^" /* Accumulated time for defineClass */
+ data sun.cls.defineAppClassTime.self/sun.os.hrt.frequency
+ scale raw
+ align right
+ width 10
+ format "0.000"
+ }
+ column {
+ header "^FindClass^" /* Number of findClass calls */
+ data sun.classloader.findClasses
+ align right
+ scale raw
+ width 5
+ format "0"
+ }
+ column {
+ header "Time^" /* Accumulated time for findClass */
+ data sun.classloader.findClassTime/1000000000
+ scale raw
+ align right
+ width 10
+ format "0.000"
+ }
+ column {
+ header "Delegation^" /* Parent class loader delegation time */
+ data sun.classloader.parentDelegationTime/1000000000
+ scale raw
+ align right
+ width 10
+ format "0.000"
+ }
+ column {
+ header "URLCL Read^" /* Accumulated time for URLClassLoader reading bytes */
+ data sun.urlClassLoader.readClassBytesTime/1000000000
+ scale raw
+ align right
+ width 10
+ format "0.000"
+ }
+}
+
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/sun/tools/jstat/classloadOutput1.awk Thu Jun 10 14:14:17 2010 -0700
@@ -0,0 +1,31 @@
+#
+# matching the following output specified as a pattern that verifies
+# that the numerical values conform to a specific pattern, rather than
+# specific values.
+#
+# Loaded Time Inited Time Shared Kbytes LoadTime SysClass Kbytes LoadTime Lookup Parse Linked Time Verified Time AppClass Kbytes AppCL DefineClass Time FindClass Time Delegation URLCL Read
+# 956 0.115 777 0.032 0 0.0 0.000 956 3437.5 0.085 0.013 0.045 918 0.032 917 0.011 13 1.0 0.003 1 0.000 1 0.004 0.005 0.000
+#
+
+BEGIN {
+ headerlines=0; datalines=0; totallines=0
+ }
+
+/^Loaded Time Inited Time Shared Kbytes LoadTime SysClass Kbytes LoadTime Lookup Parse Linked Time Verified Time AppClass Kbytes AppCL DefineClass Time FindClass Time Delegation URLCL Read$/ {
+ headerlines++;
+ }
+
+/^[ ]*[0-9]+[ ]*[0-9]+\.[0-9]+[ ]*[0-9]+[ ]*[0-9]+\.[0-9]+[ ]*[0-9]+[ ]*[0-9]+\.[0-9][ ]*[0-9]+\.[0-9]+[ ]*[0-9]+[ ]*[0-9]+\.[0-9][ ]*[0-9]+\.[0-9]+[ ]*[0-9]+\.[0-9]+[ ]*[0-9]+\.[0-9]+[ ]*[0-9]+[ ]*[0-9]+\.[0-9]+[ ]*[0-9]+[ ]*[0-9]+\.[0-9]+[ ]*[0-9]+[ ]*[0-9]+\.[0-9][ ]*[0-9]+\.[0-9]+[ ]*[0-9]+[ ]*[0-9]+\.[0-9]+[ ]*[0-9]+[ ]*[0-9]+\.[0-9]+[ ]*[0-9]+\.[0-9]+[ ]*[0-9]+\.[0-9]+$/ {
+ datalines++;
+ }
+
+ { totallines++; print $0 }
+
+END {
+ if ((headerlines == 1) && (datalines == 1) && (totallines == 2)) {
+ exit 0
+ }
+ else {
+ exit 1
+ }
+ }
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/sun/tools/jstat/jstatClassloadOutput1.sh Thu Jun 10 14:14:17 2010 -0700
@@ -0,0 +1,36 @@
+#
+# Copyright (c) 2010, 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
+# under the terms of the GNU General Public License version 2 only, as
+# published by the Free Software Foundation.
+#
+# This code is distributed in the hope that it will be useful, but WITHOUT
+# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+# version 2 for more details (a copy is included in the LICENSE file that
+# accompanied this code).
+#
+# You should have received a copy of the GNU General Public License version
+# 2 along with this work; if not, write to the Free Software Foundation,
+# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+#
+# Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+# or visit www.oracle.com if you need additional information or have any
+# questions.
+#
+
+# @test
+# @bug 6959965
+# @run shell jstatClassloadOutput1.sh
+# @summary Test that output of 'jstat -classload 0' has expected line counts
+
+. ${TESTSRC-.}/../../jvmstat/testlibrary/utils.sh
+
+setup
+verify_os
+
+JSTAT="${TESTJAVA}/bin/jstat"
+
+${JSTAT} -classload -J-Djstat.showUnsupported=true 0 2>&1 | awk -f ${TESTSRC}/classloadOutput1.awk
--- a/jdk/test/sun/tools/jstat/jstatOptions1.sh Tue Jun 08 18:52:17 2010 -0700
+++ b/jdk/test/sun/tools/jstat/jstatOptions1.sh Thu Jun 10 14:14:17 2010 -0700
@@ -32,7 +32,9 @@
JSTAT="${TESTJAVA}/bin/jstat"
-rm -f jstat.out 2>/dev/null
-${JSTAT} -options > jstat.out 2>&1
+rm -f jstat.out1 jstat.out2 2>/dev/null
+${JSTAT} -options > jstat.out1 2>&1
+${JSTAT} -options -J-Djstat.showUnsupported=true > jstat.out2 2>&1
-diff -w jstat.out ${TESTSRC}/options1.out
+diff -w jstat.out1 ${TESTSRC}/options1.out
+diff -w jstat.out2 ${TESTSRC}/options2.out
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/sun/tools/jstat/options2.out Thu Jun 10 14:14:17 2010 -0700
@@ -0,0 +1,13 @@
+-class
+-classload
+-compiler
+-gc
+-gccapacity
+-gccause
+-gcnew
+-gcnewcapacity
+-gcold
+-gcoldcapacity
+-gcpermcapacity
+-gcutil
+-printcompilation