diff --git a/PROFILING.md b/PROFILING.md index 1313c493c..24f163acd 100644 --- a/PROFILING.md +++ b/PROFILING.md @@ -11,22 +11,24 @@ See: ### jvm-profiling-tools/async-profiler The first one I recommend is async-profiler. This is available for macOS and Linux, -and works fairly well. +and works fairly well. See their readme for the details, but see the following to get started. -1. Download the installer from https://github.com/jvm-profiling-tools/async-profiler/releases/tag/v1.2 -2. Make symbolic link to `build/` and `profiler.sh` to `$HOME/bin`, assuming you have PATH to `$HOME/bin`: - `ln -s ~/Applications/async-profiler/profiler.sh $HOME/bin/profiler.sh` - `ln -s ~/Applications/async-profiler/build $HOME/bin/build` +1. Download the installer from +2. Make symbolic link from `asprof` to `$HOME/bin`, assuming you have PATH to `$HOME/bin`: + +```bash +$ ln -s $HOME/Applications/async-profiler-4.2/bin/asprof $HOME/bin/asprof +``` Next, close all Java applications and anything that may affect the profiling, and run sbt in one terminal: -``` -$ sbt exit +```bash +$ sbt ``` In another terminal, run: -``` +```bash $ jps 92746 sbt-launch.jar 92780 Jps @@ -34,43 +36,42 @@ $ jps This tells you the process ID of sbt. In this case, it's 92746. While it's running, run -``` -$ profiler.sh -d 60 -Started [cpu] profiling +```bash +$ asprof -d 60 +Profiling for 60 seconds +Done --- Execution profile --- -Total samples: 31602 -Non-Java: 3239 (10.25%) -GC active: 46 (0.15%) -Unknown (native): 14667 (46.41%) -Not walkable (native): 3 (0.01%) -Unknown (Java): 433 (1.37%) -Not walkable (Java): 8 (0.03%) -Thread exit: 1 (0.00%) -Deopt: 9 (0.03%) +Total samples : 26096 -Frame buffer usage: 55.658% - -Total: 1932000000 (6.11%) samples: 1932 - [ 0] java.lang.ClassLoader$NativeLibrary.load - [ 1] java.lang.ClassLoader.loadLibrary0 - [ 2] java.lang.ClassLoader.loadLibrary - [ 3] java.lang.Runtime.loadLibrary0 - [ 4] java.lang.System.loadLibrary +--- 66180000000 ns (25.36%), 6618 samples + [ 0] java.lang.invoke.VarHandleByteArrayAsInts$ArrayHandle.index + [ 1] java.lang.invoke.VarHandleByteArrayAsInts$ArrayHandle.get + [ 2] java.lang.invoke.VarHandleGuards.guard_LI_I + [ 3] sun.security.provider.ByteArrayAccess.b2iBig64 + [ 4] sun.security.provider.SHA2.implCompress0 + [ 5] sun.security.provider.SHA2.implCompress + [ 6] sun.security.provider.DigestBase.implCompressMultiBlock0 + [ 7] sun.security.provider.DigestBase.implCompressMultiBlock + [ 8] sun.security.provider.DigestBase.engineUpdate + [ 9] java.security.MessageDigest$Delegate.engineUpdate + [10] java.security.MessageDigest.update + [11] java.security.DigestInputStream.read + [12] java.io.FilterInputStream.read + [13] sbt.internal.inc.HashUtil$.sha256Hash + [14] sbt.internal.inc.HashUtil$.sha256HashStr .... ``` This should show a bunch of stacktraces that are useful. To visualize this as a flamegraph, run: -``` -$ profiler.sh -d 60 -f /tmp/flamegraph.svg +```bash +$ asprof -d 60 -f /tmp/flamegraph.html ``` -This should produce `/tmp/flamegraph.svg` at the end. +This should produce `/tmp/flamegraph.html` at the end. -![flamegraph](project/flamegraph_svg.png) - -See https://gist.github.com/eed3si9n/82d43acc95a002876d357bd8ad5f40d5 +![flamegraph](project/flamegraph.png) ### running sbt with standby @@ -80,7 +81,7 @@ while wanting to profile the beginning of the application. For this purpose, we've added `sbt.launcher.standby` JVM flag. In the next version of sbt, you should be able to run: -``` +```bash $ sbt -J-Dsbt.launcher.standby=20s exit ``` @@ -94,7 +95,7 @@ This uses `dtrace` on macOS and `perf` on Linux. You first have to compile https://github.com/jvm-profiling-tools/perf-map-agent. For macOS, here to how to export `JAVA_HOME` before running `cmake .`: -``` +```bash $ export JAVA_HOME=$(/usr/libexec/java_home) $ cmake . -- The C compiler identification is AppleClang 9.0.0.9000039 @@ -107,13 +108,13 @@ In addition, you have to git clone https://github.com/brendangregg/FlameGraph In a fresh terminal, run sbt with `-XX:+PreserveFramePointer` flag: -``` +```bash $ sbt -J-Dsbt.launcher.standby=20s -J-XX:+PreserveFramePointer exit ``` In the terminal that you will run the perf-map: -``` +```bash $ cd quicktest/ $ export JAVA_HOME=$(/usr/libexec/java_home) $ export FLAMEGRAPH_DIR=$HOME/work/FlameGraph diff --git a/project/flamegraph.png b/project/flamegraph.png new file mode 100644 index 000000000..2799d7013 Binary files /dev/null and b/project/flamegraph.png differ diff --git a/project/flamegraph_svg.png b/project/flamegraph_svg.png deleted file mode 100644 index 2fc2638c3..000000000 Binary files a/project/flamegraph_svg.png and /dev/null differ