Skip to content

Commit

Permalink
Add cflamegraph schema
Browse files Browse the repository at this point in the history
  • Loading branch information
kornilova203 committed Jul 21, 2018
1 parent 6a714c8 commit f537cbd
Show file tree
Hide file tree
Showing 4 changed files with 73 additions and 44 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -8,3 +8,4 @@ visualization/node_modules/
/protobuf/src/main/gen/*
/visualization/static/js/generated/*
protobuf/generated/main/
/src/gen/
22 changes: 22 additions & 0 deletions build.gradle
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
import io.netifi.flatbuffers.plugin.tasks.FlatBuffers

buildscript {
ext.kotlin_version = '1.2.51'
repositories {
Expand Down Expand Up @@ -28,6 +30,8 @@ plugins {
id 'com.google.protobuf' version '0.8.6' apply false
id 'com.moowork.node' version '1.2.0'
id 'com.liferay.soy' version '3.1.6'
id "io.netifi.flatbuffers" version "1.0.4"
id 'idea'
}

allprojects {
Expand Down Expand Up @@ -56,6 +60,7 @@ configurations {

dependencies {
compile group: 'com.google.code.gson', name: 'gson', version: '2.8.1'
compile group: 'com.github.davidmoten', name: 'flatbuffers-java', version: '1.9.0.1'
compile fileTree(dir: 'lib', include: ['com.jrockit.mc.flightrecorder_5.5.1.172852.jar'])
compile fileTree(dir: 'lib', include: ['com.jrockit.mc.common_5.5.1.172852.jar'])
compile fileTree(dir: 'lib', include: ['flight-recorder-parser-for-java-9.jar'])
Expand Down Expand Up @@ -126,6 +131,23 @@ compileTestKotlin {
}
}

flatbuffers {
flatcPath = '/usr/local/bin/flatc'
language = 'java'
}

task compileFlatBuffers(type: FlatBuffers) {
inputDir = file("src/main/flatbuffers")
outputDir = file("src/gen/java")
}

sourceSets.main.java.srcDir file('src/gen/java')
idea {
module {
generatedSourceDirs += file('src/gen/java')
}
}

/* if have some problems with jmh - execute clean first */
jmh {
/* jmh Jar warns about duplicate dependencies
Expand Down
22 changes: 22 additions & 0 deletions src/main/flatbuffers/cflamegraph_schema.fbs
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
namespace com.github.kornilova_l.flamegraph.cflamegraph;

table Names {
class_names:[string];
method_names:[string];
descriptions:[string];
}

struct Node {
class_name_id:int; // -1 if class name is not set
method_name_id:int;
description_id:int; // -1 if description is not set
width:int;
depth:int;
}

table Tree {
names:Names;
nodes:[Node];
}

root_type Tree;
Original file line number Diff line number Diff line change
Expand Up @@ -7,64 +7,48 @@ import java.io.File


/**
* Original flamegraph format consumes a lot of memory on disk and it takes more time to parse
* because it has lots of duplicate parts of call traces.
* Original flamegraph format consumes a lot of memory on disk and it takes more
* time to parse because it has lots of duplicate parts of call traces.
* cflamegraph (compressed flamegraph) solves this problem.
* It uses FlatBuffers for data serialization and does not duplicate
* class names, method names and descriptions.
*
* Header of file contains ids of class names, method names and descriptions.
* For example:
* C
* ClassName1 0
* ClassName2 1
* M
* method1 0
* method2 1
* D
* () 0
* (int)int 1
*
* Each line of cflamegraph contains information in following format:
* C=<class name id> M=<method name id> D=<description id> w=<width> d=<depth>
*
* C and D are optional.
* See scheme in /src/main/flatbuffers/cflamegraph_schema.fbs
*
* Example:
* ._ _
* |c|d|___ _
* |b()____|e|_______ _
* |Class.a__________|f|
*
* --C-- 1
* Class 0
* --M-- 6
* a 0
* b 1
* c 2
* d 3
* e 4
* f 5
* --D-- 1
* () 0
* C0M0w100d1
* M1w40d2
* M2w5d3
* M3w5d3
* M4w5d2
* M5w5d1
*
* As you can see order of lines matters
* because if a call has bigger depth than previous it means that
* the call is a child of previous call.
*
* In original flamegraph format this example would look like this:
* a;b;c 5
* a;b;d 5
* a;b 10
* a;b();c 5
* a;b();d 5
* a;b() 10
* a;e 5
* a 50
* f 5
*
* In cflamegraph files strings are not duplicated and equal parts of stacktraces are also not duplicated.
* Serialized with flatbuffers tree will have following structure:
* Names: {
* classNames: ["Class"],
* methodNames: ["a", "b", "c", "d", "e", "f"],
* descriptions: ["()"]
* }
* Tree: {
* nodes: [
* { class_name_id: 0, method_name_id: 0, width: 100, depth: 1 },
* { method_name_id: 1, description_id: 0, width: 40, depth: 2 },
* { method_name_id: 2, width: 5, depth: 3 },
* { method_name_id: 3, width: 5, depth: 3 },
* { method_name_id: 4, width: 5, depth: 2 },
* { method_name_id: 5, width: 5, depth: 1 }
* ]
* }
*
* Order of nodes matters.
* If a call has bigger depth than previous it means that the call is a child
* of previous call.
*
* Converter merges unmerged stacktraces.
*/
Expand Down

0 comments on commit f537cbd

Please sign in to comment.