blob: 190cb4078296a3e919ffa8fbd6c9f73b5791aa54 [file] [log] [blame]
Ben Murdoch4a90d5f2016-03-22 12:00:34 +00001// Copyright 2015 the V8 project authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4#include <stdlib.h>
5#include <string.h>
6
7#include "src/v8.h"
8
9#include "src/list.h"
10#include "src/list-inl.h"
11#include "test/cctest/cctest.h"
12
13using v8::IdleTask;
14using v8::Task;
15using v8::Isolate;
16
17#include "src/tracing/trace-event.h"
18
19#define GET_TRACE_OBJECTS_LIST platform.GetMockTraceObjects()
20
21#define GET_TRACE_OBJECT(Index) GET_TRACE_OBJECTS_LIST->at(Index)
22
23
24struct MockTraceObject {
25 char phase;
26 std::string name;
27 uint64_t id;
28 uint64_t bind_id;
29 int num_args;
30 unsigned int flags;
31 MockTraceObject(char phase, std::string name, uint64_t id, uint64_t bind_id,
32 int num_args, int flags)
33 : phase(phase),
34 name(name),
35 id(id),
36 bind_id(bind_id),
37 num_args(num_args),
38 flags(flags) {}
39};
40
41typedef v8::internal::List<MockTraceObject*> MockTraceObjectList;
42
43class MockTracingPlatform : public v8::Platform {
44 public:
45 explicit MockTracingPlatform(v8::Platform* platform) {}
46 virtual ~MockTracingPlatform() {
47 for (int i = 0; i < trace_object_list_.length(); ++i) {
48 delete trace_object_list_[i];
49 }
50 trace_object_list_.Clear();
51 }
52 void CallOnBackgroundThread(Task* task,
53 ExpectedRuntime expected_runtime) override {}
54
55 void CallOnForegroundThread(Isolate* isolate, Task* task) override {}
56
57 void CallDelayedOnForegroundThread(Isolate* isolate, Task* task,
58 double delay_in_seconds) override {}
59
60 double MonotonicallyIncreasingTime() override { return 0.0; }
61
62 void CallIdleOnForegroundThread(Isolate* isolate, IdleTask* task) override {}
63
64 bool IdleTasksEnabled(Isolate* isolate) override { return false; }
65
66 bool PendingIdleTask() { return false; }
67
68 void PerformIdleTask(double idle_time_in_seconds) {}
69
70 bool PendingDelayedTask() { return false; }
71
72 void PerformDelayedTask() {}
73
74 uint64_t AddTraceEvent(char phase, const uint8_t* category_enabled_flag,
Ben Murdochda12d292016-06-02 14:46:10 +010075 const char* name, const char* scope, uint64_t id,
76 uint64_t bind_id, int num_args, const char** arg_names,
Ben Murdoch4a90d5f2016-03-22 12:00:34 +000077 const uint8_t* arg_types, const uint64_t* arg_values,
78 unsigned int flags) override {
79 MockTraceObject* to = new MockTraceObject(phase, std::string(name), id,
80 bind_id, num_args, flags);
81 trace_object_list_.Add(to);
82 return 0;
83 }
84
85 void UpdateTraceEventDuration(const uint8_t* category_enabled_flag,
86 const char* name, uint64_t handle) override {}
87
88 const uint8_t* GetCategoryGroupEnabled(const char* name) override {
89 if (strcmp(name, "v8-cat")) {
90 static uint8_t no = 0;
91 return &no;
92 } else {
93 static uint8_t yes = 0x7;
94 return &yes;
95 }
96 }
97
98 const char* GetCategoryGroupName(
99 const uint8_t* category_enabled_flag) override {
100 static const char dummy[] = "dummy";
101 return dummy;
102 }
103
104 MockTraceObjectList* GetMockTraceObjects() { return &trace_object_list_; }
105
106 private:
107 MockTraceObjectList trace_object_list_;
108};
109
110
111TEST(TraceEventDisabledCategory) {
112 v8::Platform* old_platform = i::V8::GetCurrentPlatform();
113 MockTracingPlatform platform(old_platform);
114 i::V8::SetPlatformForTesting(&platform);
115
116 // Disabled category, will not add events.
117 TRACE_EVENT_BEGIN0("cat", "e1");
118 TRACE_EVENT_END0("cat", "e1");
119 CHECK_EQ(0, GET_TRACE_OBJECTS_LIST->length());
120
121 i::V8::SetPlatformForTesting(old_platform);
122}
123
124
125TEST(TraceEventNoArgs) {
126 v8::Platform* old_platform = i::V8::GetCurrentPlatform();
127 MockTracingPlatform platform(old_platform);
128 i::V8::SetPlatformForTesting(&platform);
129
130 // Enabled category will add 2 events.
131 TRACE_EVENT_BEGIN0("v8-cat", "e1");
132 TRACE_EVENT_END0("v8-cat", "e1");
133
134 CHECK_EQ(2, GET_TRACE_OBJECTS_LIST->length());
135 CHECK_EQ('B', GET_TRACE_OBJECT(0)->phase);
136 CHECK_EQ("e1", GET_TRACE_OBJECT(0)->name);
137 CHECK_EQ(0, GET_TRACE_OBJECT(0)->num_args);
138
139 CHECK_EQ('E', GET_TRACE_OBJECT(1)->phase);
140 CHECK_EQ("e1", GET_TRACE_OBJECT(1)->name);
141 CHECK_EQ(0, GET_TRACE_OBJECT(1)->num_args);
142
143 i::V8::SetPlatformForTesting(old_platform);
144}
145
146
147TEST(TraceEventWithOneArg) {
148 v8::Platform* old_platform = i::V8::GetCurrentPlatform();
149 MockTracingPlatform platform(old_platform);
150 i::V8::SetPlatformForTesting(&platform);
151
152 TRACE_EVENT_BEGIN1("v8-cat", "e1", "arg1", 42);
153 TRACE_EVENT_END1("v8-cat", "e1", "arg1", 42);
154 TRACE_EVENT_BEGIN1("v8-cat", "e2", "arg1", "abc");
155 TRACE_EVENT_END1("v8-cat", "e2", "arg1", "abc");
156
157 CHECK_EQ(4, GET_TRACE_OBJECTS_LIST->length());
158
159 CHECK_EQ(1, GET_TRACE_OBJECT(0)->num_args);
160 CHECK_EQ(1, GET_TRACE_OBJECT(1)->num_args);
161 CHECK_EQ(1, GET_TRACE_OBJECT(2)->num_args);
162 CHECK_EQ(1, GET_TRACE_OBJECT(3)->num_args);
163
164 i::V8::SetPlatformForTesting(old_platform);
165}
166
167
168TEST(TraceEventWithTwoArgs) {
169 v8::Platform* old_platform = i::V8::GetCurrentPlatform();
170 MockTracingPlatform platform(old_platform);
171 i::V8::SetPlatformForTesting(&platform);
172
173 TRACE_EVENT_BEGIN2("v8-cat", "e1", "arg1", 42, "arg2", "abc");
174 TRACE_EVENT_END2("v8-cat", "e1", "arg1", 42, "arg2", "abc");
175 TRACE_EVENT_BEGIN2("v8-cat", "e2", "arg1", "abc", "arg2", 43);
176 TRACE_EVENT_END2("v8-cat", "e2", "arg1", "abc", "arg2", 43);
177
178 CHECK_EQ(4, GET_TRACE_OBJECTS_LIST->length());
179
180 CHECK_EQ(2, GET_TRACE_OBJECT(0)->num_args);
181 CHECK_EQ(2, GET_TRACE_OBJECT(1)->num_args);
182 CHECK_EQ(2, GET_TRACE_OBJECT(2)->num_args);
183 CHECK_EQ(2, GET_TRACE_OBJECT(3)->num_args);
184
185 i::V8::SetPlatformForTesting(old_platform);
186}
187
188
189TEST(ScopedTraceEvent) {
190 v8::Platform* old_platform = i::V8::GetCurrentPlatform();
191 MockTracingPlatform platform(old_platform);
192 i::V8::SetPlatformForTesting(&platform);
193
194 { TRACE_EVENT0("v8-cat", "e"); }
195
196 CHECK_EQ(1, GET_TRACE_OBJECTS_LIST->length());
197 CHECK_EQ(0, GET_TRACE_OBJECT(0)->num_args);
198
199 { TRACE_EVENT1("v8-cat", "e1", "arg1", "abc"); }
200
201 CHECK_EQ(2, GET_TRACE_OBJECTS_LIST->length());
202 CHECK_EQ(1, GET_TRACE_OBJECT(1)->num_args);
203
204 { TRACE_EVENT2("v8-cat", "e1", "arg1", "abc", "arg2", 42); }
205
206 CHECK_EQ(3, GET_TRACE_OBJECTS_LIST->length());
207 CHECK_EQ(2, GET_TRACE_OBJECT(2)->num_args);
208
209 i::V8::SetPlatformForTesting(old_platform);
210}
211
212
213TEST(TestEventWithFlow) {
214 v8::Platform* old_platform = i::V8::GetCurrentPlatform();
215 MockTracingPlatform platform(old_platform);
216 i::V8::SetPlatformForTesting(&platform);
217
218 static uint64_t bind_id = 21;
219 {
220 TRACE_EVENT_WITH_FLOW0("v8-cat", "f1", bind_id, TRACE_EVENT_FLAG_FLOW_OUT);
221 }
222 {
223 TRACE_EVENT_WITH_FLOW0(
224 "v8-cat", "f2", bind_id,
225 TRACE_EVENT_FLAG_FLOW_IN | TRACE_EVENT_FLAG_FLOW_OUT);
226 }
227 { TRACE_EVENT_WITH_FLOW0("v8-cat", "f3", bind_id, TRACE_EVENT_FLAG_FLOW_IN); }
228
229 CHECK_EQ(3, GET_TRACE_OBJECTS_LIST->length());
230 CHECK_EQ(bind_id, GET_TRACE_OBJECT(0)->bind_id);
231 CHECK_EQ(TRACE_EVENT_FLAG_FLOW_OUT, GET_TRACE_OBJECT(0)->flags);
232 CHECK_EQ(bind_id, GET_TRACE_OBJECT(1)->bind_id);
233 CHECK_EQ(TRACE_EVENT_FLAG_FLOW_IN | TRACE_EVENT_FLAG_FLOW_OUT,
234 GET_TRACE_OBJECT(1)->flags);
235 CHECK_EQ(bind_id, GET_TRACE_OBJECT(2)->bind_id);
236 CHECK_EQ(TRACE_EVENT_FLAG_FLOW_IN, GET_TRACE_OBJECT(2)->flags);
237
238 i::V8::SetPlatformForTesting(old_platform);
239}
240
241
242TEST(TestEventWithId) {
243 v8::Platform* old_platform = i::V8::GetCurrentPlatform();
244 MockTracingPlatform platform(old_platform);
245 i::V8::SetPlatformForTesting(&platform);
246
247 static uint64_t event_id = 21;
248 TRACE_EVENT_ASYNC_BEGIN0("v8-cat", "a1", event_id);
249 TRACE_EVENT_ASYNC_END0("v8-cat", "a1", event_id);
250
251 CHECK_EQ(2, GET_TRACE_OBJECTS_LIST->length());
252 CHECK_EQ(TRACE_EVENT_PHASE_ASYNC_BEGIN, GET_TRACE_OBJECT(0)->phase);
253 CHECK_EQ(event_id, GET_TRACE_OBJECT(0)->id);
254 CHECK_EQ(TRACE_EVENT_PHASE_ASYNC_END, GET_TRACE_OBJECT(1)->phase);
255 CHECK_EQ(event_id, GET_TRACE_OBJECT(1)->id);
256
257 i::V8::SetPlatformForTesting(old_platform);
258}
Ben Murdochda12d292016-06-02 14:46:10 +0100259
260TEST(TestEventInContext) {
261 v8::Platform* old_platform = i::V8::GetCurrentPlatform();
262 MockTracingPlatform platform(old_platform);
263 i::V8::SetPlatformForTesting(&platform);
264
265 static uint64_t isolate_id = 0x20151021;
266 {
267 TRACE_EVENT_SCOPED_CONTEXT("v8-cat", "Isolate", isolate_id);
268 TRACE_EVENT0("v8-cat", "e");
269 }
270
271 CHECK_EQ(3, GET_TRACE_OBJECTS_LIST->length());
272 CHECK_EQ(TRACE_EVENT_PHASE_ENTER_CONTEXT, GET_TRACE_OBJECT(0)->phase);
273 CHECK_EQ("Isolate", GET_TRACE_OBJECT(0)->name);
274 CHECK_EQ(isolate_id, GET_TRACE_OBJECT(0)->id);
275 CHECK_EQ(TRACE_EVENT_PHASE_COMPLETE, GET_TRACE_OBJECT(1)->phase);
276 CHECK_EQ("e", GET_TRACE_OBJECT(1)->name);
277 CHECK_EQ(TRACE_EVENT_PHASE_LEAVE_CONTEXT, GET_TRACE_OBJECT(2)->phase);
278 CHECK_EQ("Isolate", GET_TRACE_OBJECT(2)->name);
279 CHECK_EQ(isolate_id, GET_TRACE_OBJECT(2)->id);
280
281 i::V8::SetPlatformForTesting(old_platform);
282}