|
1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ |
|
2 /* This Source Code Form is subject to the terms of the Mozilla Public |
|
3 * License, v. 2.0. If a copy of the MPL was not distributed with this |
|
4 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ |
|
5 |
|
6 /* *************** SPS Sampler Information **************** |
|
7 * |
|
8 * SPS is an always on profiler that takes fast and low overheads samples |
|
9 * of the program execution using only userspace functionity for portability. |
|
10 * The goal of this module is to provide performance data in a generic |
|
11 * cross platform way without requiring custom tools or kernel support. |
|
12 * |
|
13 * Non goals: Support features that are platform specific or replace |
|
14 * platform specific profilers. |
|
15 * |
|
16 * Samples are collected to form a timeline with optional timeline event (markers) |
|
17 * used for filtering. |
|
18 * |
|
19 * SPS collects samples in a platform independant way by using a speudo stack abstraction |
|
20 * of the real program stack by using 'sample stack frames'. When a sample is collected |
|
21 * all active sample stack frames and the program counter are recorded. |
|
22 */ |
|
23 |
|
24 /* *************** SPS Sampler File Format **************** |
|
25 * |
|
26 * Simple new line seperated tag format: |
|
27 * S -> BOF tags EOF |
|
28 * tags -> tag tags |
|
29 * tag -> CHAR - STRING |
|
30 * |
|
31 * Tags: |
|
32 * 's' - Sample tag followed by the first stack frame followed by 0 or more 'c' tags. |
|
33 * 'c' - Continue Sample tag gives remaining tag element. If a 'c' tag is seen without |
|
34 * a preceding 's' tag it should be ignored. This is to support the behavior |
|
35 * of circular buffers. |
|
36 * If the 'stackwalk' feature is enabled this tag will have the format |
|
37 * 'l-<library name>@<hex address>' and will expect an external tool to translate |
|
38 * the tag into something readable through a symbolication processing step. |
|
39 * 'm' - Timeline marker. Zero or more may appear before a 's' tag. |
|
40 * 'l' - Information about the program counter library and address. Post processing |
|
41 * can include function and source line. If built with leaf data enabled |
|
42 * this tag will describe the last 'c' tag. |
|
43 * 'r' - Responsiveness tag following an 's' tag. Gives an indication on how well the |
|
44 * application is responding to the event loop. Lower is better. |
|
45 * 't' - Elapse time since recording started. |
|
46 * |
|
47 */ |
|
48 |
|
49 #ifndef SAMPLER_H |
|
50 #define SAMPLER_H |
|
51 |
|
52 #include "mozilla/NullPtr.h" |
|
53 #include "js/TypeDecls.h" |
|
54 |
|
55 namespace mozilla { |
|
56 class TimeStamp; |
|
57 } |
|
58 |
|
59 enum TracingMetadata { |
|
60 TRACING_DEFAULT, |
|
61 TRACING_INTERVAL_START, |
|
62 TRACING_INTERVAL_END |
|
63 }; |
|
64 |
|
65 #ifndef MOZ_ENABLE_PROFILER_SPS |
|
66 |
|
67 #include <stdint.h> |
|
68 |
|
69 // Insert a RAII in this scope to active a pseudo label. Any samples collected |
|
70 // in this scope will contain this annotation. For dynamic strings use |
|
71 // PROFILER_LABEL_PRINTF. Arguments must be string literals. |
|
72 #define PROFILER_LABEL(name_space, info) do {} while (0) |
|
73 |
|
74 // Format a dynamic string as a pseudo label. These labels will a considerable |
|
75 // storage size in the circular buffer compared to regular labels. This function |
|
76 // can be used to annotate custom information such as URL for the resource being |
|
77 // decoded or the size of the paint. |
|
78 #define PROFILER_LABEL_PRINTF(name_space, info, format, ...) do {} while (0) |
|
79 |
|
80 // Insert a marker in the profile timeline. This is useful to delimit something |
|
81 // important happening such as the first paint. Unlike profiler_label that are |
|
82 // only recorded if a sample is collected while it is active, marker will always |
|
83 // be collected. |
|
84 #define PROFILER_MARKER(info) do {} while (0) |
|
85 #define PROFILER_MARKER_PAYLOAD(info, payload) do {} while (0) |
|
86 |
|
87 // Main thread specilization to avoid TLS lookup for performance critical use. |
|
88 #define PROFILER_MAIN_THREAD_LABEL(name_space, info) do {} while (0) |
|
89 #define PROFILER_MAIN_THREAD_LABEL_PRINTF(name_space, info, format, ...) do {} while (0) |
|
90 |
|
91 static inline void profiler_tracing(const char* aCategory, const char* aInfo, |
|
92 TracingMetadata metaData = TRACING_DEFAULT) {} |
|
93 |
|
94 // Initilize the profiler TLS, signal handlers on linux. If MOZ_PROFILER_STARTUP |
|
95 // is set the profiler will be started. This call must happen before any other |
|
96 // sampler calls. Particularly sampler_label/sampler_marker. |
|
97 static inline void profiler_init(void* stackTop) {}; |
|
98 |
|
99 // Clean up the profiler module, stopping it if required. This function may |
|
100 // also save a shutdown profile if requested. No profiler calls should happen |
|
101 // after this point and all pseudo labels should have been popped. |
|
102 static inline void profiler_shutdown() {}; |
|
103 |
|
104 // Start the profiler with the selected options. The samples will be |
|
105 // recorded in a circular buffer. |
|
106 // "aProfileEntries" is an abstract size indication of how big |
|
107 // the profile's circular buffer should be. Multiply by 4 |
|
108 // words to get the cost. |
|
109 // "aInterval" the sampling interval. The profiler will do its |
|
110 // best to sample at this interval. The profiler visualization |
|
111 // should represent the actual sampling accuracy. |
|
112 static inline void profiler_start(int aProfileEntries, double aInterval, |
|
113 const char** aFeatures, uint32_t aFeatureCount, |
|
114 const char** aThreadNameFilters, uint32_t aFilterCount) {} |
|
115 |
|
116 // Stop the profiler and discard the profile. Call 'profiler_save' before this |
|
117 // to retrieve the profile. |
|
118 static inline void profiler_stop() {} |
|
119 |
|
120 // These functions pause and resume the profiler. While paused the profile will not |
|
121 // take any samples and will not record any data into its buffers. The profiler |
|
122 // remains fully initialized in this state. Timeline markers will still be stored. |
|
123 // This feature will keep javascript profiling enabled, thus allowing toggling the |
|
124 // profiler without invalidating the JIT. |
|
125 static inline bool profiler_is_paused() { return false; } |
|
126 static inline void profiler_pause() {} |
|
127 static inline void profiler_resume() {} |
|
128 |
|
129 class ProfilerBacktrace; |
|
130 |
|
131 // Immediately capture the current thread's call stack and return it |
|
132 static inline ProfilerBacktrace* profiler_get_backtrace() { return nullptr; } |
|
133 |
|
134 // Free a ProfilerBacktrace returned by profiler_get_backtrace() |
|
135 static inline void profiler_free_backtrace(ProfilerBacktrace* aBacktrace) {} |
|
136 |
|
137 static inline bool profiler_is_active() { return false; } |
|
138 |
|
139 // Internal-only. Used by the event tracer. |
|
140 static inline void profiler_responsiveness(const mozilla::TimeStamp& aTime) {} |
|
141 |
|
142 // Internal-only. Used by the event tracer. |
|
143 static inline double* profiler_get_responsiveness() { return nullptr; } |
|
144 |
|
145 // Internal-only. |
|
146 static inline void profiler_set_frame_number(int frameNumber) {} |
|
147 |
|
148 // Get the profile encoded as a JSON string. |
|
149 static inline char* profiler_get_profile() { return nullptr; } |
|
150 |
|
151 // Get the profile encoded as a JSON object. |
|
152 static inline JSObject* profiler_get_profile_jsobject(JSContext* aCx) { return nullptr; } |
|
153 |
|
154 // Get the profile and write it into a file |
|
155 static inline void profiler_save_profile_to_file(char* aFilename) { } |
|
156 |
|
157 // Get the features supported by the profiler that are accepted by profiler_init. |
|
158 // Returns a null terminated char* array. |
|
159 static inline char** profiler_get_features() { return nullptr; } |
|
160 |
|
161 // Print the current location to the console. This functill will do it best effort |
|
162 // to show the profiler's combined js/c++ if the profiler is running. Note that |
|
163 // printing the location require symbolicating which is very slow. |
|
164 static inline void profiler_print_location() {} |
|
165 |
|
166 // Discard the profile, throw away the profile and notify 'profiler-locked'. |
|
167 // This function is to be used when entering private browsing to prevent |
|
168 // the profiler from collecting sensitive data. |
|
169 static inline void profiler_lock() {} |
|
170 |
|
171 // Re-enable the profiler and notify 'profiler-unlocked'. |
|
172 static inline void profiler_unlock() {} |
|
173 |
|
174 static inline void profiler_register_thread(const char* name, void* stackTop) {} |
|
175 static inline void profiler_unregister_thread() {} |
|
176 |
|
177 // These functions tell the profiler that a thread went to sleep so that we can avoid |
|
178 // sampling it while it's sleeping. Calling profiler_sleep_start() twice without |
|
179 // profiler_sleep_end() is an error. |
|
180 static inline void profiler_sleep_start() {} |
|
181 static inline void profiler_sleep_end() {} |
|
182 |
|
183 // Call by the JSRuntime's operation callback. This is used to enable |
|
184 // profiling on auxilerary threads. |
|
185 static inline void profiler_js_operation_callback() {} |
|
186 |
|
187 static inline double profiler_time() { return 0; } |
|
188 static inline double profiler_time(const mozilla::TimeStamp& aTime) { return 0; } |
|
189 |
|
190 static inline bool profiler_in_privacy_mode() { return false; } |
|
191 |
|
192 #else |
|
193 |
|
194 #include "GeckoProfilerImpl.h" |
|
195 |
|
196 #endif |
|
197 |
|
198 class GeckoProfilerInitRAII { |
|
199 public: |
|
200 GeckoProfilerInitRAII(void* stackTop) { |
|
201 profiler_init(stackTop); |
|
202 } |
|
203 ~GeckoProfilerInitRAII() { |
|
204 profiler_shutdown(); |
|
205 } |
|
206 }; |
|
207 |
|
208 class GeckoProfilerSleepRAII { |
|
209 public: |
|
210 GeckoProfilerSleepRAII() { |
|
211 profiler_sleep_start(); |
|
212 } |
|
213 ~GeckoProfilerSleepRAII() { |
|
214 profiler_sleep_end(); |
|
215 } |
|
216 }; |
|
217 |
|
218 #endif // ifndef SAMPLER_H |