jruby-async-profiler 0.1.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.gitignore +8 -0
- data/.gitmodules +3 -0
- data/Gemfile +4 -0
- data/README.md +35 -0
- data/Rakefile +2 -0
- data/bin/console +14 -0
- data/bin/setup +8 -0
- data/ext/Rakefile +6 -0
- data/ext/async-profiler/.gitattributes +1 -0
- data/ext/async-profiler/.gitignore +6 -0
- data/ext/async-profiler/.travis.yml +11 -0
- data/ext/async-profiler/CHANGELOG.md +107 -0
- data/ext/async-profiler/JavaHome.class +0 -0
- data/ext/async-profiler/LICENSE +201 -0
- data/ext/async-profiler/Makefile +66 -0
- data/ext/async-profiler/README.md +487 -0
- data/ext/async-profiler/demo/SwingSet2.svg +2247 -0
- data/ext/async-profiler/docs/cddl1.txt +358 -0
- data/ext/async-profiler/profiler.sh +240 -0
- data/ext/async-profiler/src/allocTracer.cpp +155 -0
- data/ext/async-profiler/src/allocTracer.h +74 -0
- data/ext/async-profiler/src/arch.h +69 -0
- data/ext/async-profiler/src/arguments.cpp +265 -0
- data/ext/async-profiler/src/arguments.h +152 -0
- data/ext/async-profiler/src/codeCache.cpp +128 -0
- data/ext/async-profiler/src/codeCache.h +99 -0
- data/ext/async-profiler/src/engine.cpp +50 -0
- data/ext/async-profiler/src/engine.h +38 -0
- data/ext/async-profiler/src/flameGraph.cpp +770 -0
- data/ext/async-profiler/src/flameGraph.h +118 -0
- data/ext/async-profiler/src/flightRecorder.cpp +727 -0
- data/ext/async-profiler/src/flightRecorder.h +39 -0
- data/ext/async-profiler/src/frameName.cpp +189 -0
- data/ext/async-profiler/src/frameName.h +56 -0
- data/ext/async-profiler/src/itimer.cpp +49 -0
- data/ext/async-profiler/src/itimer.h +43 -0
- data/ext/async-profiler/src/jattach/jattach.c +437 -0
- data/ext/async-profiler/src/java/one/profiler/AsyncProfiler.java +160 -0
- data/ext/async-profiler/src/java/one/profiler/AsyncProfilerMXBean.java +43 -0
- data/ext/async-profiler/src/java/one/profiler/Counter.java +25 -0
- data/ext/async-profiler/src/java/one/profiler/Events.java +28 -0
- data/ext/async-profiler/src/javaApi.cpp +124 -0
- data/ext/async-profiler/src/lockTracer.cpp +161 -0
- data/ext/async-profiler/src/lockTracer.h +55 -0
- data/ext/async-profiler/src/mutex.cpp +33 -0
- data/ext/async-profiler/src/mutex.h +49 -0
- data/ext/async-profiler/src/os.h +45 -0
- data/ext/async-profiler/src/os_linux.cpp +129 -0
- data/ext/async-profiler/src/os_macos.cpp +115 -0
- data/ext/async-profiler/src/perfEvents.h +60 -0
- data/ext/async-profiler/src/perfEvents_linux.cpp +550 -0
- data/ext/async-profiler/src/perfEvents_macos.cpp +64 -0
- data/ext/async-profiler/src/profiler.cpp +952 -0
- data/ext/async-profiler/src/profiler.h +238 -0
- data/ext/async-profiler/src/spinLock.h +66 -0
- data/ext/async-profiler/src/stackFrame.h +57 -0
- data/ext/async-profiler/src/stackFrame_aarch64.cpp +75 -0
- data/ext/async-profiler/src/stackFrame_arm.cpp +58 -0
- data/ext/async-profiler/src/stackFrame_i386.cpp +82 -0
- data/ext/async-profiler/src/stackFrame_x64.cpp +113 -0
- data/ext/async-profiler/src/symbols.h +37 -0
- data/ext/async-profiler/src/symbols_linux.cpp +354 -0
- data/ext/async-profiler/src/symbols_macos.cpp +156 -0
- data/ext/async-profiler/src/vmEntry.cpp +173 -0
- data/ext/async-profiler/src/vmEntry.h +105 -0
- data/ext/async-profiler/src/vmStructs.cpp +104 -0
- data/ext/async-profiler/src/vmStructs.h +112 -0
- data/ext/async-profiler/src/wallClock.cpp +96 -0
- data/ext/async-profiler/src/wallClock.h +56 -0
- data/ext/async-profiler/test/AllocatingTarget.java +26 -0
- data/ext/async-profiler/test/LoadLibraryTest.java +21 -0
- data/ext/async-profiler/test/Target.java +31 -0
- data/ext/async-profiler/test/ThreadsTarget.java +35 -0
- data/ext/async-profiler/test/alloc-smoke-test.sh +36 -0
- data/ext/async-profiler/test/load-library-test.sh +35 -0
- data/ext/async-profiler/test/smoke-test.sh +37 -0
- data/ext/async-profiler/test/thread-smoke-test.sh +32 -0
- data/jruby-async-profiler.gemspec +32 -0
- data/lib/jruby/async/profiler.rb +10 -0
- data/lib/jruby/async/profiler/version.rb +7 -0
- metadata +155 -0
@@ -0,0 +1,152 @@
|
|
1
|
+
/*
|
2
|
+
* Copyright 2017 Andrei Pangin
|
3
|
+
*
|
4
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
5
|
+
* you may not use this file except in compliance with the License.
|
6
|
+
* You may obtain a copy of the License at
|
7
|
+
*
|
8
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
9
|
+
*
|
10
|
+
* Unless required by applicable law or agreed to in writing, software
|
11
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
12
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
13
|
+
* See the License for the specific language governing permissions and
|
14
|
+
* limitations under the License.
|
15
|
+
*/
|
16
|
+
|
17
|
+
#ifndef _ARGUMENTS_H
|
18
|
+
#define _ARGUMENTS_H
|
19
|
+
|
20
|
+
#include <stddef.h>
|
21
|
+
|
22
|
+
|
23
|
+
const long DEFAULT_INTERVAL = 10000000; // 10 ms
|
24
|
+
const int DEFAULT_FRAMEBUF = 1000000;
|
25
|
+
const int DEFAULT_JSTACKDEPTH = 2048;
|
26
|
+
|
27
|
+
const char* const EVENT_CPU = "cpu";
|
28
|
+
const char* const EVENT_ALLOC = "alloc";
|
29
|
+
const char* const EVENT_LOCK = "lock";
|
30
|
+
const char* const EVENT_WALL = "wall";
|
31
|
+
const char* const EVENT_ITIMER = "itimer";
|
32
|
+
|
33
|
+
enum Action {
|
34
|
+
ACTION_NONE,
|
35
|
+
ACTION_START,
|
36
|
+
ACTION_RESUME,
|
37
|
+
ACTION_STOP,
|
38
|
+
ACTION_STATUS,
|
39
|
+
ACTION_LIST,
|
40
|
+
ACTION_VERSION,
|
41
|
+
ACTION_DUMP
|
42
|
+
};
|
43
|
+
|
44
|
+
enum Counter {
|
45
|
+
COUNTER_SAMPLES,
|
46
|
+
COUNTER_TOTAL
|
47
|
+
};
|
48
|
+
|
49
|
+
enum Ring {
|
50
|
+
RING_ANY,
|
51
|
+
RING_KERNEL,
|
52
|
+
RING_USER
|
53
|
+
};
|
54
|
+
|
55
|
+
enum Style {
|
56
|
+
STYLE_SIMPLE = 1,
|
57
|
+
STYLE_DOTTED = 2,
|
58
|
+
STYLE_SIGNATURES = 4,
|
59
|
+
STYLE_ANNOTATE = 8
|
60
|
+
};
|
61
|
+
|
62
|
+
enum Output {
|
63
|
+
OUTPUT_NONE,
|
64
|
+
OUTPUT_TEXT,
|
65
|
+
OUTPUT_COLLAPSED,
|
66
|
+
OUTPUT_FLAMEGRAPH,
|
67
|
+
OUTPUT_TREE,
|
68
|
+
OUTPUT_JFR
|
69
|
+
};
|
70
|
+
|
71
|
+
|
72
|
+
class Error {
|
73
|
+
private:
|
74
|
+
const char* _message;
|
75
|
+
|
76
|
+
public:
|
77
|
+
static const Error OK;
|
78
|
+
|
79
|
+
explicit Error(const char* message) : _message(message) {
|
80
|
+
}
|
81
|
+
|
82
|
+
const char* message() {
|
83
|
+
return _message;
|
84
|
+
}
|
85
|
+
|
86
|
+
operator bool() {
|
87
|
+
return _message != NULL;
|
88
|
+
}
|
89
|
+
};
|
90
|
+
|
91
|
+
|
92
|
+
class Arguments {
|
93
|
+
private:
|
94
|
+
char* _buf;
|
95
|
+
|
96
|
+
static const char* expandFilePattern(char* dest, size_t max_size, const char* pattern);
|
97
|
+
static Output detectOutputFormat(const char* file);
|
98
|
+
static long parseUnits(const char* str);
|
99
|
+
|
100
|
+
public:
|
101
|
+
Action _action;
|
102
|
+
Counter _counter;
|
103
|
+
Ring _ring;
|
104
|
+
const char* _event;
|
105
|
+
long _interval;
|
106
|
+
int _jstackdepth;
|
107
|
+
int _framebuf;
|
108
|
+
bool _threads;
|
109
|
+
bool _sync_walk;
|
110
|
+
int _style;
|
111
|
+
const char* _file;
|
112
|
+
Output _output;
|
113
|
+
int _dump_traces;
|
114
|
+
int _dump_flat;
|
115
|
+
// FlameGraph parameters
|
116
|
+
const char* _title;
|
117
|
+
int _width;
|
118
|
+
int _height;
|
119
|
+
double _minwidth;
|
120
|
+
bool _reverse;
|
121
|
+
|
122
|
+
Arguments() :
|
123
|
+
_buf(NULL),
|
124
|
+
_action(ACTION_NONE),
|
125
|
+
_counter(COUNTER_SAMPLES),
|
126
|
+
_ring(RING_ANY),
|
127
|
+
_event(EVENT_CPU),
|
128
|
+
_interval(0),
|
129
|
+
_jstackdepth(DEFAULT_JSTACKDEPTH),
|
130
|
+
_framebuf(DEFAULT_FRAMEBUF),
|
131
|
+
_threads(false),
|
132
|
+
_sync_walk(false),
|
133
|
+
_style(0),
|
134
|
+
_file(NULL),
|
135
|
+
_output(OUTPUT_NONE),
|
136
|
+
_dump_traces(0),
|
137
|
+
_dump_flat(0),
|
138
|
+
_title("Flame Graph"),
|
139
|
+
_width(1200),
|
140
|
+
_height(16),
|
141
|
+
_minwidth(0.25),
|
142
|
+
_reverse(false) {
|
143
|
+
}
|
144
|
+
|
145
|
+
~Arguments();
|
146
|
+
|
147
|
+
void save(Arguments& other);
|
148
|
+
|
149
|
+
Error parse(const char* args);
|
150
|
+
};
|
151
|
+
|
152
|
+
#endif // _ARGUMENTS_H
|
@@ -0,0 +1,128 @@
|
|
1
|
+
/*
|
2
|
+
* Copyright 2016 Andrei Pangin
|
3
|
+
*
|
4
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
5
|
+
* you may not use this file except in compliance with the License.
|
6
|
+
* You may obtain a copy of the License at
|
7
|
+
*
|
8
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
9
|
+
*
|
10
|
+
* Unless required by applicable law or agreed to in writing, software
|
11
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
12
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
13
|
+
* See the License for the specific language governing permissions and
|
14
|
+
* limitations under the License.
|
15
|
+
*/
|
16
|
+
|
17
|
+
#include <stdlib.h>
|
18
|
+
#include <string.h>
|
19
|
+
#include "codeCache.h"
|
20
|
+
|
21
|
+
|
22
|
+
void CodeCache::expand() {
|
23
|
+
CodeBlob* old_blobs = _blobs;
|
24
|
+
CodeBlob* new_blobs = new CodeBlob[_capacity * 2];
|
25
|
+
memcpy(new_blobs, old_blobs, _capacity * sizeof(CodeBlob));
|
26
|
+
_capacity *= 2;
|
27
|
+
_blobs = new_blobs;
|
28
|
+
delete[] old_blobs;
|
29
|
+
}
|
30
|
+
|
31
|
+
void CodeCache::add(const void* start, int length, jmethodID method) {
|
32
|
+
if (_count >= _capacity) {
|
33
|
+
expand();
|
34
|
+
}
|
35
|
+
|
36
|
+
_blobs[_count]._start = start;
|
37
|
+
_blobs[_count]._end = (const char*)start + length;
|
38
|
+
_blobs[_count]._method = method;
|
39
|
+
_count++;
|
40
|
+
}
|
41
|
+
|
42
|
+
void CodeCache::remove(const void* start, jmethodID method) {
|
43
|
+
for (int i = 0; i < _count; i++) {
|
44
|
+
if (_blobs[i]._start == start && _blobs[i]._method == method) {
|
45
|
+
_blobs[i]._method = NULL;
|
46
|
+
return;
|
47
|
+
}
|
48
|
+
}
|
49
|
+
}
|
50
|
+
|
51
|
+
jmethodID CodeCache::find(const void* address) {
|
52
|
+
for (int i = 0; i < _count; i++) {
|
53
|
+
if (address >= _blobs[i]._start && address < _blobs[i]._end) {
|
54
|
+
return _blobs[i]._method;
|
55
|
+
}
|
56
|
+
}
|
57
|
+
return NULL;
|
58
|
+
}
|
59
|
+
|
60
|
+
|
61
|
+
NativeCodeCache::NativeCodeCache(const char* name, const void* min_address, const void* max_address) {
|
62
|
+
_name = strdup(name);
|
63
|
+
_min_address = min_address;
|
64
|
+
_max_address = max_address;
|
65
|
+
}
|
66
|
+
|
67
|
+
NativeCodeCache::~NativeCodeCache() {
|
68
|
+
for (int i = 0; i < _count; i++) {
|
69
|
+
free(_blobs[i]._method);
|
70
|
+
}
|
71
|
+
free(_name);
|
72
|
+
}
|
73
|
+
|
74
|
+
void NativeCodeCache::add(const void* start, int length, const char* name) {
|
75
|
+
CodeCache::add(start, length, (jmethodID)strdup(name));
|
76
|
+
}
|
77
|
+
|
78
|
+
void NativeCodeCache::sort() {
|
79
|
+
if (_count == 0) return;
|
80
|
+
|
81
|
+
qsort(_blobs, _count, sizeof(CodeBlob), CodeBlob::comparator);
|
82
|
+
|
83
|
+
if (_min_address == NULL) _min_address = _blobs[0]._start;
|
84
|
+
if (_max_address == NULL) _max_address = _blobs[_count - 1]._end;
|
85
|
+
}
|
86
|
+
|
87
|
+
const char* NativeCodeCache::binarySearch(const void* address) {
|
88
|
+
int low = 0;
|
89
|
+
int high = _count - 1;
|
90
|
+
|
91
|
+
while (low <= high) {
|
92
|
+
int mid = (unsigned int)(low + high) >> 1;
|
93
|
+
if (_blobs[mid]._end <= address) {
|
94
|
+
low = mid + 1;
|
95
|
+
} else if (_blobs[mid]._start > address) {
|
96
|
+
high = mid - 1;
|
97
|
+
} else {
|
98
|
+
return (const char*)_blobs[mid]._method;
|
99
|
+
}
|
100
|
+
}
|
101
|
+
|
102
|
+
// Symbols with zero size can be valid functions: e.g. ASM entry points or kernel code
|
103
|
+
if (low > 0 && _blobs[low - 1]._start == _blobs[low - 1]._end) {
|
104
|
+
return (const char*)_blobs[low - 1]._method;
|
105
|
+
}
|
106
|
+
return _name;
|
107
|
+
}
|
108
|
+
|
109
|
+
const void* NativeCodeCache::findSymbol(const char* name) {
|
110
|
+
for (int i = 0; i < _count; i++) {
|
111
|
+
const char* blob_name = (const char*)_blobs[i]._method;
|
112
|
+
if (blob_name != NULL && strcmp(blob_name, name) == 0) {
|
113
|
+
return _blobs[i]._start;
|
114
|
+
}
|
115
|
+
}
|
116
|
+
return NULL;
|
117
|
+
}
|
118
|
+
|
119
|
+
const void* NativeCodeCache::findSymbolByPrefix(const char* prefix) {
|
120
|
+
int prefix_len = strlen(prefix);
|
121
|
+
for (int i = 0; i < _count; i++) {
|
122
|
+
const char* blob_name = (const char*)_blobs[i]._method;
|
123
|
+
if (blob_name != NULL && strncmp(blob_name, prefix, prefix_len) == 0) {
|
124
|
+
return _blobs[i]._start;
|
125
|
+
}
|
126
|
+
}
|
127
|
+
return NULL;
|
128
|
+
}
|
@@ -0,0 +1,99 @@
|
|
1
|
+
/*
|
2
|
+
* Copyright 2017 Andrei Pangin
|
3
|
+
*
|
4
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
5
|
+
* you may not use this file except in compliance with the License.
|
6
|
+
* You may obtain a copy of the License at
|
7
|
+
*
|
8
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
9
|
+
*
|
10
|
+
* Unless required by applicable law or agreed to in writing, software
|
11
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
12
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
13
|
+
* See the License for the specific language governing permissions and
|
14
|
+
* limitations under the License.
|
15
|
+
*/
|
16
|
+
|
17
|
+
#ifndef _CODECACHE_H
|
18
|
+
#define _CODECACHE_H
|
19
|
+
|
20
|
+
#include <jvmti.h>
|
21
|
+
|
22
|
+
|
23
|
+
const int INITIAL_CODE_CACHE_CAPACITY = 1000;
|
24
|
+
|
25
|
+
|
26
|
+
class CodeBlob {
|
27
|
+
public:
|
28
|
+
const void* _start;
|
29
|
+
const void* _end;
|
30
|
+
jmethodID _method;
|
31
|
+
|
32
|
+
static int comparator(const void* c1, const void* c2) {
|
33
|
+
CodeBlob* cb1 = (CodeBlob*)c1;
|
34
|
+
CodeBlob* cb2 = (CodeBlob*)c2;
|
35
|
+
if (cb1->_start < cb2->_start) {
|
36
|
+
return -1;
|
37
|
+
} else if (cb1->_start > cb2->_start) {
|
38
|
+
return 1;
|
39
|
+
} else if (cb1->_end == cb2->_end) {
|
40
|
+
return 0;
|
41
|
+
} else {
|
42
|
+
return cb1->_end > cb2->_end ? -1 : 1;
|
43
|
+
}
|
44
|
+
}
|
45
|
+
};
|
46
|
+
|
47
|
+
|
48
|
+
class CodeCache {
|
49
|
+
protected:
|
50
|
+
int _capacity;
|
51
|
+
int _count;
|
52
|
+
CodeBlob* _blobs;
|
53
|
+
|
54
|
+
void expand();
|
55
|
+
|
56
|
+
public:
|
57
|
+
CodeCache() {
|
58
|
+
_capacity = INITIAL_CODE_CACHE_CAPACITY;
|
59
|
+
_count = 0;
|
60
|
+
_blobs = new CodeBlob[_capacity];
|
61
|
+
}
|
62
|
+
|
63
|
+
~CodeCache() {
|
64
|
+
delete[] _blobs;
|
65
|
+
}
|
66
|
+
|
67
|
+
void add(const void* start, int length, jmethodID method);
|
68
|
+
void remove(const void* start, jmethodID method);
|
69
|
+
jmethodID find(const void* address);
|
70
|
+
};
|
71
|
+
|
72
|
+
|
73
|
+
class NativeCodeCache : public CodeCache {
|
74
|
+
private:
|
75
|
+
char* _name;
|
76
|
+
const void* _min_address;
|
77
|
+
const void* _max_address;
|
78
|
+
|
79
|
+
public:
|
80
|
+
NativeCodeCache(const char* name, const void* min_address = NULL, const void* max_address = NULL);
|
81
|
+
|
82
|
+
~NativeCodeCache();
|
83
|
+
|
84
|
+
const char* name() {
|
85
|
+
return _name;
|
86
|
+
}
|
87
|
+
|
88
|
+
bool contains(const void* address) {
|
89
|
+
return address >= _min_address && address < _max_address;
|
90
|
+
}
|
91
|
+
|
92
|
+
void add(const void* start, int length, const char* name);
|
93
|
+
void sort();
|
94
|
+
const char* binarySearch(const void* address);
|
95
|
+
const void* findSymbol(const char* name);
|
96
|
+
const void* findSymbolByPrefix(const char* prefix);
|
97
|
+
};
|
98
|
+
|
99
|
+
#endif // _CODECACHE_H
|
@@ -0,0 +1,50 @@
|
|
1
|
+
/*
|
2
|
+
* Copyright 2018 Andrei Pangin
|
3
|
+
*
|
4
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
5
|
+
* you may not use this file except in compliance with the License.
|
6
|
+
* You may obtain a copy of the License at
|
7
|
+
*
|
8
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
9
|
+
*
|
10
|
+
* Unless required by applicable law or agreed to in writing, software
|
11
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
12
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
13
|
+
* See the License for the specific language governing permissions and
|
14
|
+
* limitations under the License.
|
15
|
+
*/
|
16
|
+
|
17
|
+
#include "engine.h"
|
18
|
+
#include "stackFrame.h"
|
19
|
+
|
20
|
+
|
21
|
+
int Engine::getNativeTrace(void* ucontext, int tid, const void** callchain, int max_depth,
|
22
|
+
const void* jit_min_address, const void* jit_max_address) {
|
23
|
+
StackFrame frame(ucontext);
|
24
|
+
const void* pc = (const void*)frame.pc();
|
25
|
+
uintptr_t fp = frame.fp();
|
26
|
+
uintptr_t prev_fp = (uintptr_t)&fp;
|
27
|
+
|
28
|
+
int depth = 0;
|
29
|
+
const void* const valid_pc = (const void*)0x1000;
|
30
|
+
|
31
|
+
// Walk until the bottom of the stack or until the first Java frame
|
32
|
+
while (depth < max_depth && pc >= valid_pc) {
|
33
|
+
callchain[depth++] = pc;
|
34
|
+
|
35
|
+
if (pc >= jit_min_address && pc < jit_max_address) {
|
36
|
+
break;
|
37
|
+
}
|
38
|
+
|
39
|
+
// Check if the next frame is below on the current stack
|
40
|
+
if (fp <= prev_fp || fp >= prev_fp + 0x40000) {
|
41
|
+
break;
|
42
|
+
}
|
43
|
+
|
44
|
+
prev_fp = fp;
|
45
|
+
pc = ((const void**)fp)[1];
|
46
|
+
fp = ((uintptr_t*)fp)[0];
|
47
|
+
}
|
48
|
+
|
49
|
+
return depth;
|
50
|
+
}
|
@@ -0,0 +1,38 @@
|
|
1
|
+
/*
|
2
|
+
* Copyright 2017 Andrei Pangin
|
3
|
+
*
|
4
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
5
|
+
* you may not use this file except in compliance with the License.
|
6
|
+
* You may obtain a copy of the License at
|
7
|
+
*
|
8
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
9
|
+
*
|
10
|
+
* Unless required by applicable law or agreed to in writing, software
|
11
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
12
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
13
|
+
* See the License for the specific language governing permissions and
|
14
|
+
* limitations under the License.
|
15
|
+
*/
|
16
|
+
|
17
|
+
#ifndef _ENGINE_H
|
18
|
+
#define _ENGINE_H
|
19
|
+
|
20
|
+
#include "arguments.h"
|
21
|
+
|
22
|
+
|
23
|
+
class Engine {
|
24
|
+
public:
|
25
|
+
virtual const char* name() = 0;
|
26
|
+
virtual const char* units() = 0;
|
27
|
+
|
28
|
+
virtual Error start(Arguments& args) = 0;
|
29
|
+
virtual void stop() = 0;
|
30
|
+
|
31
|
+
virtual void onThreadStart() {}
|
32
|
+
virtual void onThreadEnd() {}
|
33
|
+
|
34
|
+
virtual int getNativeTrace(void* ucontext, int tid, const void** callchain, int max_depth,
|
35
|
+
const void* jit_min_address, const void* jit_max_address);
|
36
|
+
};
|
37
|
+
|
38
|
+
#endif // _ENGINE_H
|