Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(381)

Side by Side Diff: sky/engine/v8_inspector/AsyncCallStackTracker.cpp

Issue 922053002: Remove unused V8 integration code in Sky (Closed) Base URL: git@github.com:domokit/mojo.git@master
Patch Set: Created 5 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « sky/engine/v8_inspector/AsyncCallStackTracker.h ('k') | sky/engine/v8_inspector/BUILD.gn » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 /*
2 * Copyright (C) 2013 Google Inc. All rights reserved.
3 *
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions are
6 * met:
7 *
8 * * Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.
10 * * Redistributions in binary form must reproduce the above
11 * copyright notice, this list of conditions and the following disclaimer
12 * in the documentation and/or other materials provided with the
13 * distribution.
14 * * Neither the name of Google Inc. nor the names of its
15 * contributors may be used to endorse or promote products derived from
16 * this software without specific prior written permission.
17 *
18 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
19 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
20 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
21 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
22 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
23 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
24 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
28 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29 */
30
31 #include "sky/engine/config.h"
32 #include "sky/engine/v8_inspector/AsyncCallStackTracker.h"
33
34 #include "sky/engine/bindings/core/v8/V8Binding.h"
35 #include "sky/engine/bindings/core/v8/V8RecursionScope.h"
36 #include "sky/engine/core/dom/ExecutionContext.h"
37 #include "sky/engine/core/events/Event.h"
38 #include "sky/engine/core/events/EventTarget.h"
39 #include "sky/engine/wtf/text/StringBuilder.h"
40 #include "sky/engine/wtf/text/StringHash.h"
41 #include "v8/include/v8.h"
42
43 namespace {
44
45 static const char setTimeoutName[] = "setTimeout";
46 static const char setIntervalName[] = "setInterval";
47 static const char requestAnimationFrameName[] = "requestAnimationFrame";
48 static const char enqueueMutationRecordName[] = "Mutation";
49
50 }
51
52 namespace blink {
53
54 void AsyncCallStackTracker::ExecutionContextData::contextDestroyed()
55 {
56 ASSERT(executionContext());
57 OwnPtr<ExecutionContextData> self = m_tracker->m_executionContextDataMap.tak e(executionContext());
58 ASSERT_UNUSED(self, self == this);
59 ContextLifecycleObserver::contextDestroyed();
60 }
61
62 int AsyncCallStackTracker::ExecutionContextData::circularSequentialID()
63 {
64 ++m_circularSequentialID;
65 if (m_circularSequentialID <= 0)
66 m_circularSequentialID = 1;
67 return m_circularSequentialID;
68 }
69
70 AsyncCallStackTracker::AsyncCallStack::AsyncCallStack(const String& description, const ScriptValue& callFrames)
71 : m_description(description)
72 , m_callFrames(callFrames)
73 {
74 }
75
76 AsyncCallStackTracker::AsyncCallStack::~AsyncCallStack()
77 {
78 }
79
80 AsyncCallStackTracker::AsyncCallStackTracker()
81 : m_maxAsyncCallStackDepth(0)
82 , m_nestedAsyncCallCount(0)
83 {
84 }
85
86 void AsyncCallStackTracker::setAsyncCallStackDepth(int depth)
87 {
88 if (depth <= 0) {
89 m_maxAsyncCallStackDepth = 0;
90 clear();
91 } else {
92 m_maxAsyncCallStackDepth = depth;
93 }
94 }
95
96 const AsyncCallStackTracker::AsyncCallChain* AsyncCallStackTracker::currentAsync CallChain() const
97 {
98 if (m_currentAsyncCallChain)
99 ensureMaxAsyncCallChainDepth(m_currentAsyncCallChain.get(), m_maxAsyncCa llStackDepth);
100 return m_currentAsyncCallChain.get();
101 }
102
103 void AsyncCallStackTracker::didInstallTimer(ExecutionContext* context, int timer Id, bool singleShot, const ScriptValue& callFrames)
104 {
105 ASSERT(context);
106 ASSERT(isEnabled());
107 if (!validateCallFrames(callFrames))
108 return;
109 ASSERT(timerId > 0);
110 ExecutionContextData* data = createContextDataIfNeeded(context);
111 data->m_timerCallChains.set(timerId, createAsyncCallChain(singleShot ? setTi meoutName : setIntervalName, callFrames));
112 if (!singleShot)
113 data->m_intervalTimerIds.add(timerId);
114 }
115
116 void AsyncCallStackTracker::didRemoveTimer(ExecutionContext* context, int timerI d)
117 {
118 ASSERT(context);
119 ASSERT(isEnabled());
120 if (timerId <= 0)
121 return;
122 ExecutionContextData* data = m_executionContextDataMap.get(context);
123 if (!data)
124 return;
125 data->m_intervalTimerIds.remove(timerId);
126 data->m_timerCallChains.remove(timerId);
127 }
128
129 void AsyncCallStackTracker::willFireTimer(ExecutionContext* context, int timerId )
130 {
131 ASSERT(context);
132 ASSERT(isEnabled());
133 ASSERT(timerId > 0);
134 ASSERT(!m_currentAsyncCallChain);
135 if (ExecutionContextData* data = m_executionContextDataMap.get(context)) {
136 if (data->m_intervalTimerIds.contains(timerId))
137 setCurrentAsyncCallChain(context, data->m_timerCallChains.get(timerI d));
138 else
139 setCurrentAsyncCallChain(context, data->m_timerCallChains.take(timer Id));
140 } else {
141 setCurrentAsyncCallChain(context, nullptr);
142 }
143 }
144
145 void AsyncCallStackTracker::didRequestAnimationFrame(ExecutionContext* context, int callbackId, const ScriptValue& callFrames)
146 {
147 ASSERT(context);
148 ASSERT(isEnabled());
149 if (!validateCallFrames(callFrames))
150 return;
151 ASSERT(callbackId > 0);
152 ExecutionContextData* data = createContextDataIfNeeded(context);
153 data->m_animationFrameCallChains.set(callbackId, createAsyncCallChain(reques tAnimationFrameName, callFrames));
154 }
155
156 void AsyncCallStackTracker::didCancelAnimationFrame(ExecutionContext* context, i nt callbackId)
157 {
158 ASSERT(context);
159 ASSERT(isEnabled());
160 if (callbackId <= 0)
161 return;
162 if (ExecutionContextData* data = m_executionContextDataMap.get(context))
163 data->m_animationFrameCallChains.remove(callbackId);
164 }
165
166 void AsyncCallStackTracker::willFireAnimationFrame(ExecutionContext* context, in t callbackId)
167 {
168 ASSERT(context);
169 ASSERT(isEnabled());
170 ASSERT(callbackId > 0);
171 ASSERT(!m_currentAsyncCallChain);
172 if (ExecutionContextData* data = m_executionContextDataMap.get(context))
173 setCurrentAsyncCallChain(context, data->m_animationFrameCallChains.take( callbackId));
174 else
175 setCurrentAsyncCallChain(context, nullptr);
176 }
177
178 void AsyncCallStackTracker::didEnqueueEvent(EventTarget* eventTarget, Event* eve nt, const ScriptValue& callFrames)
179 {
180 ASSERT(eventTarget->executionContext());
181 ASSERT(isEnabled());
182 if (!validateCallFrames(callFrames))
183 return;
184 ExecutionContextData* data = createContextDataIfNeeded(eventTarget->executio nContext());
185 data->m_eventCallChains.set(event, createAsyncCallChain(event->type(), callF rames));
186 }
187
188 void AsyncCallStackTracker::didRemoveEvent(EventTarget* eventTarget, Event* even t)
189 {
190 ASSERT(eventTarget->executionContext());
191 ASSERT(isEnabled());
192 if (ExecutionContextData* data = m_executionContextDataMap.get(eventTarget-> executionContext()))
193 data->m_eventCallChains.remove(event);
194 }
195
196 void AsyncCallStackTracker::willHandleEvent(EventTarget* eventTarget, Event* eve nt, EventListener* listener, bool useCapture)
197 {
198 ASSERT(eventTarget->executionContext());
199 ASSERT(isEnabled());
200 ExecutionContext* context = eventTarget->executionContext();
201 if (ExecutionContextData* data = m_executionContextDataMap.get(context))
202 setCurrentAsyncCallChain(context, data->m_eventCallChains.get(event));
203 else
204 setCurrentAsyncCallChain(context, nullptr);
205 }
206
207 void AsyncCallStackTracker::didEnqueueMutationRecord(ExecutionContext* context, MutationObserver* observer, const ScriptValue& callFrames)
208 {
209 ASSERT(context);
210 ASSERT(isEnabled());
211 if (!validateCallFrames(callFrames))
212 return;
213 ExecutionContextData* data = createContextDataIfNeeded(context);
214 data->m_mutationObserverCallChains.set(observer, createAsyncCallChain(enqueu eMutationRecordName, callFrames));
215 }
216
217 bool AsyncCallStackTracker::hasEnqueuedMutationRecord(ExecutionContext* context, MutationObserver* observer)
218 {
219 ASSERT(context);
220 ASSERT(isEnabled());
221 if (ExecutionContextData* data = m_executionContextDataMap.get(context))
222 return data->m_mutationObserverCallChains.contains(observer);
223 return false;
224 }
225
226 void AsyncCallStackTracker::didClearAllMutationRecords(ExecutionContext* context , MutationObserver* observer)
227 {
228 ASSERT(context);
229 ASSERT(isEnabled());
230 if (ExecutionContextData* data = m_executionContextDataMap.get(context))
231 data->m_mutationObserverCallChains.remove(observer);
232 }
233
234 void AsyncCallStackTracker::willDeliverMutationRecords(ExecutionContext* context , MutationObserver* observer)
235 {
236 ASSERT(context);
237 ASSERT(isEnabled());
238 if (ExecutionContextData* data = m_executionContextDataMap.get(context))
239 setCurrentAsyncCallChain(context, data->m_mutationObserverCallChains.tak e(observer));
240 else
241 setCurrentAsyncCallChain(context, nullptr);
242 }
243
244 // void AsyncCallStackTracker::didPostExecutionContextTask(ExecutionContext* con text, ExecutionContextTask* task, const ScriptValue& callFrames)
245 // {
246 // ASSERT(context);
247 // ASSERT(isEnabled());
248 // if (!validateCallFrames(callFrames))
249 // return;
250 // ExecutionContextData* data = createContextDataIfNeeded(context);
251 // data->m_executionContextTaskCallChains.set(task, createAsyncCallChain(tas k->taskNameForInstrumentation(), callFrames));
252 // }
253
254 // void AsyncCallStackTracker::didKillAllExecutionContextTasks(ExecutionContext* context)
255 // {
256 // ASSERT(context);
257 // ASSERT(isEnabled());
258 // if (ExecutionContextData* data = m_executionContextDataMap.get(context))
259 // data->m_executionContextTaskCallChains.clear();
260 // }
261
262 // void AsyncCallStackTracker::willPerformExecutionContextTask(ExecutionContext* context, ExecutionContextTask* task)
263 // {
264 // ASSERT(context);
265 // ASSERT(isEnabled());
266 // if (ExecutionContextData* data = m_executionContextDataMap.get(context))
267 // setCurrentAsyncCallChain(context, data->m_executionContextTaskCallCha ins.take(task));
268 // else
269 // setCurrentAsyncCallChain(context, nullptr);
270 // }
271
272 static String makeV8AsyncTaskUniqueId(const String& eventName, int id)
273 {
274 StringBuilder builder;
275 builder.append(eventName);
276 builder.appendNumber(id);
277 return builder.toString();
278 }
279
280 void AsyncCallStackTracker::didEnqueueV8AsyncTask(ExecutionContext* context, con st String& eventName, int id, const ScriptValue& callFrames)
281 {
282 ASSERT(context);
283 ASSERT(isEnabled());
284 if (!validateCallFrames(callFrames))
285 return;
286 ExecutionContextData* data = createContextDataIfNeeded(context);
287 data->m_v8AsyncTaskCallChains.set(makeV8AsyncTaskUniqueId(eventName, id), cr eateAsyncCallChain(eventName, callFrames));
288 }
289
290 void AsyncCallStackTracker::willHandleV8AsyncTask(ExecutionContext* context, con st String& eventName, int id)
291 {
292 ASSERT(context);
293 ASSERT(isEnabled());
294 if (ExecutionContextData* data = m_executionContextDataMap.get(context))
295 setCurrentAsyncCallChain(context, data->m_v8AsyncTaskCallChains.take(mak eV8AsyncTaskUniqueId(eventName, id)));
296 else
297 setCurrentAsyncCallChain(context, nullptr);
298 }
299
300 int AsyncCallStackTracker::traceAsyncOperationStarting(ExecutionContext* context , const String& operationName, const ScriptValue& callFrames)
301 {
302 ASSERT(context);
303 ASSERT(isEnabled());
304 if (!validateCallFrames(callFrames))
305 return 0;
306 ExecutionContextData* data = createContextDataIfNeeded(context);
307 int id = data->circularSequentialID();
308 while (data->m_asyncOperationCallChains.contains(id))
309 id = data->circularSequentialID();
310 data->m_asyncOperationCallChains.set(id, createAsyncCallChain(operationName, callFrames));
311 return id;
312 }
313
314 void AsyncCallStackTracker::traceAsyncOperationCompleted(ExecutionContext* conte xt, int operationId)
315 {
316 ASSERT(context);
317 ASSERT(isEnabled());
318 if (operationId <= 0)
319 return;
320 if (ExecutionContextData* data = m_executionContextDataMap.get(context))
321 data->m_asyncOperationCallChains.remove(operationId);
322 }
323
324 void AsyncCallStackTracker::traceAsyncCallbackStarting(ExecutionContext* context , int operationId)
325 {
326 ASSERT(context);
327 ASSERT(isEnabled());
328 if (ExecutionContextData* data = m_executionContextDataMap.get(context))
329 setCurrentAsyncCallChain(context, operationId > 0 ? data->m_asyncOperati onCallChains.get(operationId) : nullptr);
330 else
331 setCurrentAsyncCallChain(context, nullptr);
332 }
333
334 void AsyncCallStackTracker::didFireAsyncCall()
335 {
336 clearCurrentAsyncCallChain();
337 }
338
339 PassRefPtr<AsyncCallStackTracker::AsyncCallChain> AsyncCallStackTracker::createA syncCallChain(const String& description, const ScriptValue& callFrames)
340 {
341 if (callFrames.isEmpty()) {
342 ASSERT(m_currentAsyncCallChain);
343 return m_currentAsyncCallChain; // Propogate async call stack chain.
344 }
345 RefPtr<AsyncCallChain> chain = adoptRef(m_currentAsyncCallChain ? new AsyncC allStackTracker::AsyncCallChain(*m_currentAsyncCallChain) : new AsyncCallStackTr acker::AsyncCallChain());
346 ensureMaxAsyncCallChainDepth(chain.get(), m_maxAsyncCallStackDepth - 1);
347 chain->m_callStacks.prepend(adoptRef(new AsyncCallStackTracker::AsyncCallSta ck(description, callFrames)));
348 return chain.release();
349 }
350
351 void AsyncCallStackTracker::setCurrentAsyncCallChain(ExecutionContext* context, PassRefPtr<AsyncCallChain> chain)
352 {
353 if (chain && !V8RecursionScope::recursionLevel(toIsolate(context))) {
354 // Current AsyncCallChain corresponds to the bottommost JS call frame.
355 m_currentAsyncCallChain = chain;
356 m_nestedAsyncCallCount = 1;
357 } else {
358 if (m_currentAsyncCallChain)
359 ++m_nestedAsyncCallCount;
360 }
361 }
362
363 void AsyncCallStackTracker::clearCurrentAsyncCallChain()
364 {
365 if (!m_nestedAsyncCallCount)
366 return;
367 --m_nestedAsyncCallCount;
368 if (!m_nestedAsyncCallCount)
369 m_currentAsyncCallChain.clear();
370 }
371
372 void AsyncCallStackTracker::ensureMaxAsyncCallChainDepth(AsyncCallChain* chain, unsigned maxDepth)
373 {
374 while (chain->m_callStacks.size() > maxDepth)
375 chain->m_callStacks.removeLast();
376 }
377
378 bool AsyncCallStackTracker::validateCallFrames(const ScriptValue& callFrames)
379 {
380 return !callFrames.isEmpty() || m_currentAsyncCallChain;
381 }
382
383 AsyncCallStackTracker::ExecutionContextData* AsyncCallStackTracker::createContex tDataIfNeeded(ExecutionContext* context)
384 {
385 ExecutionContextData* data = m_executionContextDataMap.get(context);
386 if (!data) {
387 data = m_executionContextDataMap.set(context, adoptPtr(new AsyncCallStac kTracker::ExecutionContextData(this, context)))
388 .storedValue->value.get();
389 }
390 return data;
391 }
392
393 void AsyncCallStackTracker::clear()
394 {
395 m_currentAsyncCallChain.clear();
396 m_nestedAsyncCallCount = 0;
397 m_executionContextDataMap.clear();
398 }
399
400 } // namespace blink
OLDNEW
« no previous file with comments | « sky/engine/v8_inspector/AsyncCallStackTracker.h ('k') | sky/engine/v8_inspector/BUILD.gn » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698