changeset 12779:f6c511451e4a

made Graal report its compilation info under -XX:+CITime in the same format as c1 and c2
author Doug Simon <doug.simon@oracle.com>
date Tue, 19 Nov 2013 01:31:19 +0100
parents c125485642e2
children 430a95455271
files graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/CompilationTask.java graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMConfig.java graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/bridge/VMToCompiler.java graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/bridge/VMToCompilerImpl.java src/share/vm/classfile/vmSymbols.hpp src/share/vm/compiler/abstractCompiler.hpp src/share/vm/compiler/compileBroker.cpp src/share/vm/graal/graalCompiler.cpp src/share/vm/graal/graalCompilerToVM.cpp src/share/vm/graal/graalVMToCompiler.cpp src/share/vm/graal/graalVMToCompiler.hpp src/share/vm/runtime/vmStructs.cpp
diffstat 12 files changed, 251 insertions(+), 60 deletions(-) [+]
line wrap: on
line diff
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/CompilationTask.java	Tue Nov 19 01:12:27 2013 +0100
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/CompilationTask.java	Tue Nov 19 01:31:19 2013 +0100
@@ -25,6 +25,7 @@
 import static com.oracle.graal.api.code.CodeUtil.*;
 import static com.oracle.graal.nodes.StructuredGraph.*;
 import static com.oracle.graal.phases.GraalOptions.*;
+import static com.oracle.graal.phases.common.InliningUtil.*;
 
 import java.lang.reflect.*;
 import java.util.concurrent.*;
@@ -33,15 +34,15 @@
 import com.oracle.graal.api.code.*;
 import com.oracle.graal.api.code.CallingConvention.Type;
 import com.oracle.graal.api.meta.*;
+import com.oracle.graal.compiler.CompilerThreadFactory.CompilerThread;
 import com.oracle.graal.compiler.*;
-import com.oracle.graal.compiler.CompilerThreadFactory.CompilerThread;
 import com.oracle.graal.debug.*;
 import com.oracle.graal.debug.internal.*;
+import com.oracle.graal.hotspot.bridge.*;
 import com.oracle.graal.hotspot.meta.*;
 import com.oracle.graal.nodes.*;
 import com.oracle.graal.nodes.spi.*;
 import com.oracle.graal.phases.*;
-import com.oracle.graal.phases.common.*;
 import com.oracle.graal.phases.tiers.*;
 
 public final class CompilationTask implements Runnable {
@@ -119,6 +120,11 @@
          * no code must be outside this try/finally because it could happen otherwise that
          * clearQueuedForCompilation() is not executed
          */
+
+        HotSpotVMConfig config = backend.getRuntime().getConfig();
+        long previousInlinedBytecodes = InlinedBytecodes.getCurrentValue();
+        long previousCompilationTime = CompilationTime.getCurrentValue();
+        HotSpotInstalledCode installedCode = null;
         try (TimerCloseable a = CompilationTime.start()) {
             if (!tryToChangeStatus(CompilationStatus.Queued, CompilationStatus.Running) || method.hasCompiledCode()) {
                 return;
@@ -155,7 +161,7 @@
                             // Compiling method substitution - must clone the graph
                             graph = graph.copy();
                         }
-                        InliningUtil.InlinedBytecodes.add(method.getCodeSize());
+                        InlinedBytecodes.add(method.getCodeSize());
                         CallingConvention cc = getCallingConvention(providers.getCodeCache(), Type.JavaCallee, graph.method(), false);
                         Suites suites = providers.getSuites().getDefaultSuites();
                         return GraalCompiler.compileGraph(graph, cc, method, providers, backend, backend.getTarget(), graphCache, plan, optimisticOpts, method.getSpeculationLog(), suites,
@@ -173,7 +179,7 @@
             }
 
             try (TimerCloseable b = CodeInstallationTime.start()) {
-                installMethod(result);
+                installedCode = installMethod(result);
             }
             stats.finish(method);
         } catch (BailoutException bailout) {
@@ -194,6 +200,14 @@
                 System.exit(-1);
             }
         } finally {
+            if (config.ciTime && installedCode != null) {
+                long processedBytes = InlinedBytecodes.getCurrentValue() - previousInlinedBytecodes;
+                long time = CompilationTime.getCurrentValue() - previousCompilationTime;
+                TimeUnit timeUnit = CompilationTime.getTimeUnit();
+                VMToCompiler vm2c = backend.getRuntime().getVMToCompiler();
+                vm2c.notifyCompilationDone(id, method, entryBCI != INVOCATION_ENTRY_BCI, (int) processedBytes, time, timeUnit, installedCode);
+            }
+
             assert method.isQueuedForCompilation();
             method.clearQueuedForCompilation();
         }
@@ -214,12 +228,12 @@
                         MetaUtil.format("%H::%n(%p)", method), isOSR ? "@ " + entryBCI + " " : "", method.getCodeSize()));
     }
 
-    private void installMethod(final CompilationResult compResult) {
+    private HotSpotInstalledCode installMethod(final CompilationResult compResult) {
         final HotSpotCodeCacheProvider codeCache = backend.getProviders().getCodeCache();
-        Debug.scope("CodeInstall", new Object[]{new DebugDumpScope(String.valueOf(id), true), codeCache, method}, new Runnable() {
+        return Debug.scope("CodeInstall", new Object[]{new DebugDumpScope(String.valueOf(id), true), codeCache, method}, new Callable<HotSpotInstalledCode>() {
 
             @Override
-            public void run() {
+            public HotSpotInstalledCode call() {
                 HotSpotInstalledCode installedCode = codeCache.installMethod(method, entryBCI, compResult);
                 if (Debug.isDumpEnabled()) {
                     Debug.dump(new Object[]{compResult, installedCode}, "After code installation");
@@ -227,6 +241,7 @@
                 if (Debug.isLogEnabled()) {
                     Debug.log("%s", backend.getProviders().getDisassembler().disassemble(installedCode));
                 }
+                return installedCode;
             }
 
         });
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMConfig.java	Tue Nov 19 01:12:27 2013 +0100
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMConfig.java	Tue Nov 19 01:31:19 2013 +0100
@@ -648,6 +648,7 @@
     @HotSpotVMFlag(name = "CodeEntryAlignment") @Stable public int codeEntryAlignment;
     @HotSpotVMFlag(name = "VerifyOops") @Stable public boolean verifyOops;
     @HotSpotVMFlag(name = "CITime") @Stable public boolean ciTime;
+    @HotSpotVMFlag(name = "CITimeEach", optional = true) @Stable public boolean ciTimeEach;
     @HotSpotVMFlag(name = "CompileThreshold") @Stable public long compileThreshold;
     @HotSpotVMFlag(name = "CompileTheWorld") @Stable public boolean compileTheWorld;
     @HotSpotVMFlag(name = "CompileTheWorldStartAt") @Stable public int compileTheWorldStartAt;
@@ -737,6 +738,16 @@
 
     @HotSpotVMConstant(name = "GRAAL_COUNTERS_SIZE", optional = true) @Stable public int graalCountersSize;
 
+    @HotSpotVMField(name = "CompilerStatistics::_standard", get = HotSpotVMField.Type.OFFSET) @Stable public long compilerStatisticsStandardOffset;
+    @HotSpotVMField(name = "CompilerStatistics::_osr", get = HotSpotVMField.Type.OFFSET) @Stable public long compilerStatisticsOsrOffset;
+    @HotSpotVMField(name = "CompilerStatistics::_nmethods_size", get = HotSpotVMField.Type.OFFSET) @Stable public long compilerStatisticsNmethodsSizeOffset;
+    @HotSpotVMField(name = "CompilerStatistics::_nmethods_code_size", get = HotSpotVMField.Type.OFFSET) @Stable public long compilerStatisticsNmethodsCodeSizeOffset;
+    @HotSpotVMField(name = "CompilerStatistics::Data::_bytes", get = HotSpotVMField.Type.OFFSET) @Stable public long compilerStatisticsDataBytesOffset;
+    @HotSpotVMField(name = "CompilerStatistics::Data::_time", get = HotSpotVMField.Type.OFFSET) @Stable public long compilerStatisticsDataTimeOffset;
+    @HotSpotVMField(name = "CompilerStatistics::Data::_count", get = HotSpotVMField.Type.OFFSET) @Stable public long compilerStatisticsDataCountOffset;
+    @HotSpotVMField(name = "elapsedTimer::_counter", get = HotSpotVMField.Type.OFFSET) @Stable public long elapsedTimerCounterOffset;
+    @Stable public long elapsedTimerFrequency;
+
     /**
      * This field is used to pass exception objects into and out of the runtime system during
      * exception handling for compiled code.
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/bridge/VMToCompiler.java	Tue Nov 19 01:12:27 2013 +0100
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/bridge/VMToCompiler.java	Tue Nov 19 01:31:19 2013 +0100
@@ -24,6 +24,7 @@
 package com.oracle.graal.hotspot.bridge;
 
 import java.io.*;
+import java.util.concurrent.*;
 
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.hotspot.debug.*;
@@ -45,9 +46,23 @@
      */
     void compileMethod(HotSpotResolvedJavaMethod method, int entryBCI, boolean blocking) throws Throwable;
 
+    /**
+     * Notifies this object of statistics for a completed compilation.
+     * 
+     * @param id the identifier of the compilation
+     * @param method the method compiled
+     * @param osr specifies if the compilation was for on-stack-replacement
+     * @param processedBytecodes the number of bytecodes processed during the compilation, including
+     *            the bytecodes of all inlined methods
+     * @param time the amount time spent compiling {@code method}
+     * @param timeUnit the units of {@code time}
+     * @param installedCode the nmethod installed as a result of the compilation
+     */
+    void notifyCompilationDone(int id, HotSpotResolvedJavaMethod method, boolean osr, int processedBytecodes, long time, TimeUnit timeUnit, HotSpotInstalledCode installedCode);
+
     void shutdownCompiler() throws Throwable;
 
-    void startCompiler(boolean bootstrapEnabled) throws Throwable;
+    void startCompiler(boolean bootstrapEnabled, long statsAddress) throws Throwable;
 
     void bootstrap() throws Throwable;
 
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/bridge/VMToCompilerImpl.java	Tue Nov 19 01:12:27 2013 +0100
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/bridge/VMToCompilerImpl.java	Tue Nov 19 01:31:19 2013 +0100
@@ -29,6 +29,7 @@
 import static com.oracle.graal.hotspot.HotSpotGraalRuntime.*;
 import static com.oracle.graal.java.GraphBuilderPhase.*;
 import static com.oracle.graal.phases.common.InliningUtil.*;
+import static java.util.concurrent.TimeUnit.*;
 
 import java.io.*;
 import java.lang.reflect.*;
@@ -102,6 +103,8 @@
 
     private long compilerStartTime;
 
+    private long compilerStatistics;
+
     public VMToCompilerImpl(HotSpotGraalRuntime runtime) {
         this.runtime = runtime;
 
@@ -122,7 +125,7 @@
         assert unsafe.getObject(mirror, offset) == type;
     }
 
-    public void startCompiler(boolean bootstrapEnabled) throws Throwable {
+    public void startCompiler(boolean bootstrapEnabled, long compilerStatisticsAddress) throws Throwable {
 
         FastNodeClassRegistry.initialize();
 
@@ -149,6 +152,8 @@
             }
         }
 
+        compilerStatistics = compilerStatisticsAddress;
+
         TTY.initialize(log);
 
         if (Log.getValue() == null && Meter.getValue() == null && Time.getValue() == null && Dump.getValue() == null) {
@@ -319,6 +324,7 @@
 
         if (ResetDebugValuesAfterBootstrap.getValue()) {
             printDebugValues("bootstrap", true);
+            resetCompilerStatistics();
         }
         phaseTransition("bootstrap");
 
@@ -594,6 +600,64 @@
         }
     }
 
+    private TimeUnit elapsedTimerTimeUnit;
+
+    private TimeUnit getElapsedTimerTimeUnit() {
+        if (elapsedTimerTimeUnit == null) {
+            long freq = runtime.getConfig().elapsedTimerFrequency;
+            for (TimeUnit tu : TimeUnit.values()) {
+                if (tu.toSeconds(freq) == 1) {
+                    elapsedTimerTimeUnit = tu;
+                    break;
+                }
+            }
+            assert elapsedTimerTimeUnit != null;
+        }
+        return elapsedTimerTimeUnit;
+    }
+
+    public synchronized void notifyCompilationDone(int id, HotSpotResolvedJavaMethod method, boolean osr, int processedBytecodes, long time, TimeUnit timeUnit, HotSpotInstalledCode installedCode) {
+        HotSpotVMConfig config = runtime.getConfig();
+        long dataAddress = compilerStatistics + (osr ? config.compilerStatisticsOsrOffset : config.compilerStatisticsStandardOffset);
+
+        long timeAddress = dataAddress + config.compilerStatisticsDataTimeOffset + config.elapsedTimerCounterOffset;
+        long previousElapsedTime = unsafe.getLong(timeAddress);
+        long elapsedTime = getElapsedTimerTimeUnit().convert(time, timeUnit);
+        unsafe.putLong(timeAddress, previousElapsedTime + elapsedTime);
+
+        long bytesAddress = dataAddress + config.compilerStatisticsDataBytesOffset;
+        int currentBytes = unsafe.getInt(bytesAddress);
+        unsafe.putInt(bytesAddress, currentBytes + processedBytecodes);
+
+        long countAddress = dataAddress + config.compilerStatisticsDataCountOffset;
+        int currentCount = unsafe.getInt(countAddress);
+        unsafe.putInt(countAddress, currentCount + 1);
+
+        long nmethodsSizeAddress = compilerStatistics + config.compilerStatisticsNmethodsSizeOffset;
+        int currentSize = unsafe.getInt(nmethodsSizeAddress);
+        unsafe.putInt(nmethodsSizeAddress, currentSize + installedCode.getSize());
+
+        long nmethodsCodeSizeAddress = compilerStatistics + config.compilerStatisticsNmethodsCodeSizeOffset;
+        int currentCodeSize = unsafe.getInt(nmethodsCodeSizeAddress);
+        unsafe.putInt(nmethodsCodeSizeAddress, currentCodeSize + (int) installedCode.getCodeSize());
+
+        if (config.ciTimeEach) {
+            TTY.println(String.format("%-6d {%s: %d ms, %d bytes}", id, osr ? "osr" : "standard", MILLISECONDS.convert(time, timeUnit), processedBytecodes));
+        }
+    }
+
+    private static void resetCompilerStatisticsData(HotSpotVMConfig config, long dataAddress) {
+        unsafe.putInt(dataAddress + config.compilerStatisticsDataBytesOffset, 0);
+        unsafe.putInt(dataAddress + config.compilerStatisticsDataCountOffset, 0);
+        unsafe.putLong(dataAddress + config.compilerStatisticsDataTimeOffset + config.elapsedTimerCounterOffset, 0L);
+    }
+
+    private void resetCompilerStatistics() {
+        HotSpotVMConfig config = runtime.getConfig();
+        resetCompilerStatisticsData(config, compilerStatistics + config.compilerStatisticsStandardOffset);
+        resetCompilerStatisticsData(config, compilerStatistics + config.compilerStatisticsOsrOffset);
+    }
+
     @Override
     public JavaMethod createUnresolvedJavaMethod(String name, String signature, JavaType holder) {
         return new HotSpotMethodUnresolved(name, signature, holder);
--- a/src/share/vm/classfile/vmSymbols.hpp	Tue Nov 19 01:12:27 2013 +0100
+++ b/src/share/vm/classfile/vmSymbols.hpp	Tue Nov 19 01:31:19 2013 +0100
@@ -574,6 +574,7 @@
   template(char_array_void_signature,                 "([C)V")                                                    \
   template(int_int_void_signature,                    "(II)V")                                                    \
   template(long_long_void_signature,                  "(JJ)V")                                                    \
+  template(boolean_long_void_signature,               "(ZJ)V")                                                    \
   template(void_classloader_signature,                "()Ljava/lang/ClassLoader;")                                \
   template(void_object_signature,                     "()Ljava/lang/Object;")                                     \
   template(void_class_signature,                      "()Ljava/lang/Class;")                                      \
@@ -903,7 +904,7 @@
    do_signature(copyMemory_signature,         "(Ljava/lang/Object;JLjava/lang/Object;JJ)V")                             \
   do_intrinsic(_park,                     sun_misc_Unsafe,        park_name, park_signature,                     F_RN)  \
    do_name(     park_name,                                       "park")                                                \
-   do_signature(park_signature,                                  "(ZJ)V")                                               \
+   do_alias(park_signature,                                       boolean_long_void_signature)                          \
   do_intrinsic(_unpark,                   sun_misc_Unsafe,        unpark_name, unpark_signature,                 F_RN)  \
    do_name(     unpark_name,                                     "unpark")                                              \
    do_alias(    unpark_signature,                               /*(LObject;)V*/ object_void_signature)                  \
--- a/src/share/vm/compiler/abstractCompiler.hpp	Tue Nov 19 01:12:27 2013 +0100
+++ b/src/share/vm/compiler/abstractCompiler.hpp	Tue Nov 19 01:31:19 2013 +0100
@@ -30,13 +30,38 @@
 typedef void (*initializer)(void);
 
 #ifdef GRAAL
-class CompilerStatistics {
+// Per-compiler statistics
+class CompilerStatistics VALUE_OBJ_CLASS_SPEC {
+  friend class VMStructs;
+
+  class Data VALUE_OBJ_CLASS_SPEC {
+    friend class VMStructs;
+  public:
+    elapsedTimer _time;  // time spent compiling
+    int _bytes;          // number of bytecodes compiled, including inlined bytecodes
+    int _count;          // number of compilations
+    Data() : _bytes(0), _count(0) {}
+    void update(elapsedTimer time, int bytes) {
+      _time.add(time);
+      _bytes += bytes;
+      _count++;
+    }
+  };
+
  public:
-  elapsedTimer _t_osr_compilation;
-  elapsedTimer _t_standard_compilation;
-  int _sum_osr_bytes_compiled;
-  int _sum_standard_bytes_compiled;
-  CompilerStatistics() : _sum_osr_bytes_compiled(0), _sum_standard_bytes_compiled(0) {}
+  Data _standard;  // stats for non-OSR compilations
+  Data _osr;       // stats for OSR compilations
+  int _nmethods_size; //
+  int _nmethods_code_size;
+  int bytes_per_second() {
+    int bytes = _standard._bytes + _osr._bytes;
+    if (bytes == 0) {
+      return 0;
+    }
+    double seconds = _standard._time.seconds() + _osr._time.seconds();
+    return seconds == 0.0 ? 0 : (int) (bytes / seconds);
+  }
+  CompilerStatistics() : _nmethods_size(0), _nmethods_code_size(0) {}
 };
 #endif
 
--- a/src/share/vm/compiler/compileBroker.cpp	Tue Nov 19 01:12:27 2013 +0100
+++ b/src/share/vm/compiler/compileBroker.cpp	Tue Nov 19 01:31:19 2013 +0100
@@ -2125,21 +2125,19 @@
     _peak_compilation_time = time.milliseconds() > _peak_compilation_time ? time.milliseconds() : _peak_compilation_time;
 
     if (CITime) {
+      int bytes_compiled = method->code_size() + task->num_inlined_bytecodes();
+      GRAAL_ONLY(CompilerStatistics* stats = compiler(task->comp_level())->stats();)
       if (is_osr) {
         _t_osr_compilation.add(time);
-        _sum_osr_bytes_compiled += method->code_size() + task->num_inlined_bytecodes();
-#ifdef GRAAL
-        compiler(task->comp_level())->stats()->_t_osr_compilation.add(time);
-        compiler(task->comp_level())->stats()->_sum_osr_bytes_compiled += method->code_size() + task->num_inlined_bytecodes();
-#endif
+        _sum_osr_bytes_compiled += bytes_compiled;
+        GRAAL_ONLY(stats->_osr.update(time, bytes_compiled);)
       } else {
         _t_standard_compilation.add(time);
         _sum_standard_bytes_compiled += method->code_size() + task->num_inlined_bytecodes();
-#ifdef GRAAL
-        compiler(task->comp_level())->stats()->_t_standard_compilation.add(time);
-        compiler(task->comp_level())->stats()->_sum_standard_bytes_compiled += method->code_size() + task->num_inlined_bytecodes();
-#endif
+        GRAAL_ONLY(stats->_standard.update(time, bytes_compiled);)
       }
+      GRAAL_ONLY(stats->_nmethods_size += code->total_size();)
+      GRAAL_ONLY(stats->_nmethods_code_size += code->insts_size();)
     }
 
     if (UsePerfData) {
@@ -2196,16 +2194,82 @@
 }
 
 void CompileBroker::print_times() {
+#ifdef GRAAL
+  elapsedTimer standard_compilation;
+  elapsedTimer total_compilation;
+  elapsedTimer osr_compilation;
+
+  int standard_bytes_compiled = 0;
+  int osr_bytes_compiled = 0;
+
+  int standard_compile_count = 0;
+  int osr_compile_count = 0;
+  int total_compile_count = 0;
+
+  int nmethods_size = 0;
+  int nmethods_code_size = 0;
+  bool printedHeader = false;
+
+  for (unsigned int i = 0; i < sizeof(_compilers) / sizeof(AbstractCompiler*); i++) {
+    AbstractCompiler* comp = _compilers[i];
+    if (comp != NULL) {
+      if (!printedHeader) {
+        printedHeader = true;
+        tty->cr();
+        tty->print_cr("Individual compiler times (for compiled methods only)");
+        tty->print_cr("------------------------------------------------");
+        tty->cr();
+      }
+      CompilerStatistics* stats = comp->stats();
+
+      standard_compilation.add(stats->_standard._time);
+      osr_compilation.add(stats->_osr._time);
+
+      standard_bytes_compiled += stats->_standard._bytes;
+      osr_bytes_compiled += stats->_osr._bytes;
+
+      standard_compile_count += stats->_standard._count;
+      osr_compile_count += stats->_osr._count;
+
+      nmethods_size += stats->_nmethods_size;
+      nmethods_code_size += stats->_nmethods_code_size;
+
+      tty->print_cr("  %s { speed: %d bytes/s; standard: %6.3f s, %d bytes, %d methods; osr: %6.3f s, %d bytes, %d methods; nmethods_size: %d bytes; nmethods_code_size: %d bytes}",
+          comp->name(), stats->bytes_per_second(),
+          stats->_standard._time.seconds(), stats->_standard._bytes, stats->_standard._count,
+          stats->_osr._time.seconds(), stats->_osr._bytes, stats->_osr._count,
+          stats->_nmethods_size, stats->_nmethods_code_size);
+    }
+  }
+  total_compile_count = osr_compile_count + standard_compile_count;
+  total_compilation.add(osr_compilation);
+  total_compilation.add(standard_compilation);
+#else
+  elapsedTimer standard_compilation = CompileBroker::_t_standard_compilation;
+  elapsedTimer osr_compilation = CompileBroker::_t_osr_compilation;
+  elapsedTimer total_compilation = CompileBroker::_t_total_compilation;
+
+  int standard_bytes_compiled = CompileBroker::_sum_standard_bytes_compiled;
+  int osr_bytes_compiled = CompileBroker::_sum_osr_bytes_compiled;
+
+  int standard_compile_count = CompileBroker::_total_standard_compile_count;
+  int osr_compile_count = CompileBroker::_total_osr_compile_count;
+  int total_compile_count = CompileBroker::_total_compile_count;
+
+  int nmethods_size = CompileBroker::_sum_nmethod_code_size;
+  int nmethods_code_size = CompileBroker::_sum_nmethod_size;
+#endif
+
   tty->cr();
   tty->print_cr("Accumulated compiler times (for compiled methods only)");
   tty->print_cr("------------------------------------------------");
                //0000000000111111111122222222223333333333444444444455555555556666666666
                //0123456789012345678901234567890123456789012345678901234567890123456789
-  tty->print_cr("  Total compilation time   : %6.3f s", CompileBroker::_t_total_compilation.seconds());
+  tty->print_cr("  Total compilation time   : %6.3f s", total_compilation.seconds());
   tty->print_cr("    Standard compilation   : %6.3f s, Average : %2.3f",
-                CompileBroker::_t_standard_compilation.seconds(),
-                CompileBroker::_t_standard_compilation.seconds() / CompileBroker::_total_standard_compile_count);
-  tty->print_cr("    On stack replacement   : %6.3f s, Average : %2.3f", CompileBroker::_t_osr_compilation.seconds(), CompileBroker::_t_osr_compilation.seconds() / CompileBroker::_total_osr_compile_count);
+                standard_compilation.seconds(),
+                standard_compilation.seconds() / standard_compile_count);
+  tty->print_cr("    On stack replacement   : %6.3f s, Average : %2.3f", osr_compilation.seconds(), osr_compilation.seconds() / osr_compile_count);
 
   AbstractCompiler *comp = compiler(CompLevel_simple);
   if (comp != NULL) {
@@ -2216,35 +2280,19 @@
     comp->print_timers();
   }
   tty->cr();
-  tty->print_cr("  Total compiled methods   : %6d methods", CompileBroker::_total_compile_count);
-  tty->print_cr("    Standard compilation   : %6d methods", CompileBroker::_total_standard_compile_count);
-  tty->print_cr("    On stack replacement   : %6d methods", CompileBroker::_total_osr_compile_count);
-  int tcb = CompileBroker::_sum_osr_bytes_compiled + CompileBroker::_sum_standard_bytes_compiled;
+  tty->print_cr("  Total compiled methods   : %6d methods", total_compile_count);
+  tty->print_cr("    Standard compilation   : %6d methods", standard_compile_count);
+  tty->print_cr("    On stack replacement   : %6d methods", osr_compile_count);
+  int tcb = osr_bytes_compiled + standard_bytes_compiled;
   tty->print_cr("  Total compiled bytecodes : %6d bytes", tcb);
-  tty->print_cr("    Standard compilation   : %6d bytes", CompileBroker::_sum_standard_bytes_compiled);
-  tty->print_cr("    On stack replacement   : %6d bytes", CompileBroker::_sum_osr_bytes_compiled);
-  double tcs = CompileBroker::_t_total_compilation.seconds();
+  tty->print_cr("    Standard compilation   : %6d bytes", standard_bytes_compiled);
+  tty->print_cr("    On stack replacement   : %6d bytes", osr_bytes_compiled);
+  double tcs = total_compilation.seconds();
   int bps = tcs == 0.0 ? 0 : (int)(tcb / tcs);
   tty->print_cr("  Average compilation speed: %6d bytes/s", bps);
-#ifdef GRAAL
-  for (unsigned int i = 0; i < sizeof(_compilers) / sizeof(AbstractCompiler*); i++) {
-    AbstractCompiler* comp = _compilers[i];
-    if (comp != NULL) {
-      CompilerStatistics* stats = comp->stats();
-      int bytecodes = stats->_sum_osr_bytes_compiled + stats->_sum_standard_bytes_compiled;
-      if (bytecodes != 0) {
-        double seconds = stats->_t_osr_compilation.seconds() + stats->_t_standard_compilation.seconds();
-        int bps = seconds == 0.0 ? 0 : (int) (bytecodes / seconds);
-        tty->print_cr("  %7s compilation speed: %6d bytes/s {standard: %6.3f s, %6d bytes; osr: %6.3f s, %6d bytes}",
-            comp->name(), bps, stats->_t_standard_compilation.seconds(), stats->_sum_standard_bytes_compiled,
-            stats->_t_osr_compilation.seconds(), stats->_sum_osr_bytes_compiled);
-      }
-    }
-  }
-#endif
   tty->cr();
-  tty->print_cr("  nmethod code size        : %6d bytes", CompileBroker::_sum_nmethod_code_size);
-  tty->print_cr("  nmethod total size       : %6d bytes", CompileBroker::_sum_nmethod_size);
+  tty->print_cr("  nmethod code size        : %6d bytes", nmethods_code_size);
+  tty->print_cr("  nmethod total size       : %6d bytes", nmethods_size);
 }
 
 // Debugging output for failure
--- a/src/share/vm/graal/graalCompiler.cpp	Tue Nov 19 01:12:27 2013 +0100
+++ b/src/share/vm/graal/graalCompiler.cpp	Tue Nov 19 01:31:19 2013 +0100
@@ -99,7 +99,8 @@
 
     if (UseCompiler) {
       bool bootstrap = GRAALVM_ONLY(BootstrapGraal) NOT_GRAALVM(false);
-      VMToCompiler::startCompiler(bootstrap);
+      jlong compilerStatisticsAddress = (jlong) ((address) (stats()));
+      VMToCompiler::startCompiler(bootstrap, compilerStatisticsAddress);
       _initialized = true;
       CompilationPolicy::completed_vm_startup();
       if (bootstrap) {
--- a/src/share/vm/graal/graalCompilerToVM.cpp	Tue Nov 19 01:12:27 2013 +0100
+++ b/src/share/vm/graal/graalCompilerToVM.cpp	Tue Nov 19 01:31:19 2013 +0100
@@ -732,6 +732,8 @@
 
   set_int("instanceKlassVtableStartOffset", InstanceKlass::vtable_start_offset() * HeapWordSize);
 
+  set_long("elapsedTimerFrequency", os::elapsed_frequency());
+
   //------------------------------------------------------------------------------------------------
 
   set_address("handleDeoptStub", SharedRuntime::deopt_blob()->unpack());
--- a/src/share/vm/graal/graalVMToCompiler.cpp	Tue Nov 19 01:12:27 2013 +0100
+++ b/src/share/vm/graal/graalVMToCompiler.cpp	Tue Nov 19 01:31:19 2013 +0100
@@ -146,13 +146,14 @@
   }
 }
 
-void VMToCompiler::startCompiler(jboolean bootstrap_enabled) {
+void VMToCompiler::startCompiler(jboolean bootstrap_enabled, jlong compilerStatisticsAddress) {
   JavaThread* THREAD = JavaThread::current();
   JavaValue result(T_VOID);
   JavaCallArguments args;
   args.push_oop(instance());
   args.push_int(bootstrap_enabled);
-  JavaCalls::call_interface(&result, vmToCompilerKlass(), vmSymbols::startCompiler_name(), vmSymbols::bool_void_signature(), &args, THREAD);
+  args.push_long(compilerStatisticsAddress);
+  JavaCalls::call_interface(&result, vmToCompilerKlass(), vmSymbols::startCompiler_name(), vmSymbols::boolean_long_void_signature(), &args, THREAD);
   check_pending_exception("Error while calling startCompiler");
 }
 
--- a/src/share/vm/graal/graalVMToCompiler.hpp	Tue Nov 19 01:12:27 2013 +0100
+++ b/src/share/vm/graal/graalVMToCompiler.hpp	Tue Nov 19 01:31:19 2013 +0100
@@ -67,7 +67,7 @@
   static void shutdownCompiler();
   
   // public abstract void startCompiler(boolean bootstrapEnabled);
-  static void startCompiler(jboolean bootstrap_enabled);
+  static void startCompiler(jboolean bootstrap_enabled, jlong compilerStatisticsAddress);
   
   // public abstract void bootstrap();
   static void bootstrap();
--- a/src/share/vm/runtime/vmStructs.cpp	Tue Nov 19 01:12:27 2013 +0100
+++ b/src/share/vm/runtime/vmStructs.cpp	Tue Nov 19 01:31:19 2013 +0100
@@ -1283,8 +1283,14 @@
   nonstatic_field(FreeList<Metablock>,         _size,                                        size_t)                                 \
   nonstatic_field(FreeList<FreeChunk>,         _count,                                       ssize_t)                                \
   nonstatic_field(FreeList<Metablock>,         _count,                                       ssize_t)                                \
-  nonstatic_field(MetablockTreeDictionary,     _total_size,                                  size_t)
-
+  nonstatic_field(MetablockTreeDictionary,     _total_size,                                  size_t)                                 \
+  GRAAL_ONLY(nonstatic_field(CompilerStatistics, _standard,                                  CompilerStatistics::Data))              \
+  GRAAL_ONLY(nonstatic_field(CompilerStatistics, _osr,                                       CompilerStatistics::Data))              \
+  GRAAL_ONLY(nonstatic_field(CompilerStatistics, _nmethods_size,                             int))                                   \
+  GRAAL_ONLY(nonstatic_field(CompilerStatistics, _nmethods_code_size,                        int))                                   \
+  GRAAL_ONLY(nonstatic_field(CompilerStatistics::Data, _bytes,                               int))                                   \
+  GRAAL_ONLY(nonstatic_field(CompilerStatistics::Data, _count,                               int))                                   \
+  GRAAL_ONLY(nonstatic_field(CompilerStatistics::Data, _time,                                elapsedTimer))
 
 //--------------------------------------------------------------------------------
 // VM_TYPES
@@ -2143,6 +2149,8 @@
   /* Miscellaneous types */                                               \
   /***************/                                                       \
                                                                           \
+  GRAAL_ONLY(declare_toplevel_type(CompilerStatistics))                   \
+  GRAAL_ONLY(declare_toplevel_type(CompilerStatistics::Data))             \
   declare_toplevel_type(PtrQueue)                                         \
                                                                           \
   /* freelist */                                                          \