Web Inspector: Instrument active pixel memory used by canvases
[WebKit-https.git] / Source / WebCore / inspector / InspectorInstrumentation.cpp
1 /*
2 * Copyright (C) 2011 Google Inc. All rights reserved.
3 * Copyright (C) 2014-2017 Apple Inc. All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are
7 * met:
8 *
9 *     * Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 *     * Redistributions in binary form must reproduce the above
12 * copyright notice, this list of conditions and the following disclaimer
13 * in the documentation and/or other materials provided with the
14 * distribution.
15 *     * Neither the name of Google Inc. nor the names of its
16 * contributors may be used to endorse or promote products derived from
17 * this software without specific prior written permission.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
20 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
21 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
22 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
23 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
24 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
25 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
26 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
27 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
29 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30 */
31
32 #include "config.h"
33 #include "InspectorInstrumentation.h"
34
35 #include "DOMWindow.h"
36 #include "DOMWrapperWorld.h"
37 #include "Database.h"
38 #include "DocumentLoader.h"
39 #include "Event.h"
40 #include "EventDispatcher.h"
41 #include "InspectorApplicationCacheAgent.h"
42 #include "InspectorCSSAgent.h"
43 #include "InspectorCanvasAgent.h"
44 #include "InspectorDOMAgent.h"
45 #include "InspectorDOMDebuggerAgent.h"
46 #include "InspectorDOMStorageAgent.h"
47 #include "InspectorDatabaseAgent.h"
48 #include "InspectorLayerTreeAgent.h"
49 #include "InspectorMemoryAgent.h"
50 #include "InspectorNetworkAgent.h"
51 #include "InspectorPageAgent.h"
52 #include "InspectorTimelineAgent.h"
53 #include "InspectorWorkerAgent.h"
54 #include "InstrumentingAgents.h"
55 #include "LoaderStrategy.h"
56 #include "MainFrame.h"
57 #include "PageDebuggerAgent.h"
58 #include "PageHeapAgent.h"
59 #include "PageRuntimeAgent.h"
60 #include "PlatformStrategies.h"
61 #include "RenderObject.h"
62 #include "RenderView.h"
63 #include "ScriptController.h"
64 #include "WebConsoleAgent.h"
65 #include "WebGLRenderingContextBase.h"
66 #include "WebSocketFrame.h"
67 #include <inspector/ConsoleMessage.h>
68 #include <inspector/ScriptArguments.h>
69 #include <inspector/ScriptCallStack.h>
70 #include <inspector/agents/InspectorDebuggerAgent.h>
71 #include <runtime/ConsoleTypes.h>
72 #include <wtf/StdLibExtras.h>
73
74 #if ENABLE(WEB_REPLAY)
75 #include "InspectorReplayAgent.h"
76 #include "ReplayController.h"
77 #endif
78
79 using namespace Inspector;
80
81 namespace WebCore {
82
83 static const char* const requestAnimationFrameEventName = "requestAnimationFrame";
84 static const char* const cancelAnimationFrameEventName = "cancelAnimationFrame";
85 static const char* const animationFrameFiredEventName = "animationFrameFired";
86 static const char* const setTimerEventName = "setTimer";
87 static const char* const clearTimerEventName = "clearTimer";
88 static const char* const timerFiredEventName = "timerFired";
89
90 enum AsyncCallType {
91     AsyncCallTypeRequestAnimationFrame,
92     AsyncCallTypeTimer,
93 };
94
95 namespace {
96 static HashSet<InstrumentingAgents*>* s_instrumentingAgentsSet = nullptr;
97 }
98
99 int InspectorInstrumentation::s_frontendCounter = 0;
100
101 void InspectorInstrumentation::firstFrontendCreated()
102 {
103     platformStrategies()->loaderStrategy()->setCaptureExtraNetworkLoadMetricsEnabled(true);
104 }
105
106 void InspectorInstrumentation::lastFrontendDeleted()
107 {
108     platformStrategies()->loaderStrategy()->setCaptureExtraNetworkLoadMetricsEnabled(false);
109 }
110
111 static void didScheduleAsyncCall(InstrumentingAgents& instrumentingAgents, AsyncCallType type, int callbackId, ScriptExecutionContext& context, bool singleShot)
112 {
113     if (InspectorDebuggerAgent* debuggerAgent = instrumentingAgents.inspectorDebuggerAgent()) {
114         JSC::ExecState* scriptState = context.execState();
115         if (!scriptState)
116             return;
117
118         debuggerAgent->didScheduleAsyncCall(scriptState, type, callbackId, singleShot);
119     }
120 }
121
122 static Frame* frameForScriptExecutionContext(ScriptExecutionContext* context)
123 {
124     Frame* frame = nullptr;
125     if (is<Document>(*context))
126         frame = downcast<Document>(*context).frame();
127     return frame;
128 }
129
130 static Frame* frameForScriptExecutionContext(ScriptExecutionContext& context)
131 {
132     Frame* frame = nullptr;
133     if (is<Document>(context))
134         frame = downcast<Document>(context).frame();
135     return frame;
136 }
137
138 void InspectorInstrumentation::didClearWindowObjectInWorldImpl(InstrumentingAgents& instrumentingAgents, Frame& frame, DOMWrapperWorld& world)
139 {
140     InspectorPageAgent* pageAgent = instrumentingAgents.inspectorPageAgent();
141     if (pageAgent)
142         pageAgent->didClearWindowObjectInWorld(&frame, world);
143     if (PageDebuggerAgent* debuggerAgent = instrumentingAgents.pageDebuggerAgent()) {
144         if (pageAgent && &world == &mainThreadNormalWorld() && &frame == &pageAgent->mainFrame())
145             debuggerAgent->didClearMainFrameWindowObject();
146     }
147     if (PageRuntimeAgent* pageRuntimeAgent = instrumentingAgents.pageRuntimeAgent()) {
148         if (&world == &mainThreadNormalWorld())
149             pageRuntimeAgent->didCreateMainWorldContext(frame);
150     }
151 }
152
153 bool InspectorInstrumentation::isDebuggerPausedImpl(InstrumentingAgents& instrumentingAgents)
154 {
155     if (InspectorDebuggerAgent* debuggerAgent = instrumentingAgents.inspectorDebuggerAgent())
156         return debuggerAgent->isPaused();
157     return false;
158 }
159
160 void InspectorInstrumentation::willInsertDOMNodeImpl(InstrumentingAgents& instrumentingAgents, Node& parent)
161 {
162     if (InspectorDOMDebuggerAgent* domDebuggerAgent = instrumentingAgents.inspectorDOMDebuggerAgent())
163         domDebuggerAgent->willInsertDOMNode(parent);
164 }
165
166 void InspectorInstrumentation::didInsertDOMNodeImpl(InstrumentingAgents& instrumentingAgents, Node& node)
167 {
168     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
169         domAgent->didInsertDOMNode(node);
170     if (InspectorDOMDebuggerAgent* domDebuggerAgent = instrumentingAgents.inspectorDOMDebuggerAgent())
171         domDebuggerAgent->didInsertDOMNode(node);
172 }
173
174 void InspectorInstrumentation::willRemoveDOMNodeImpl(InstrumentingAgents& instrumentingAgents, Node& node)
175 {
176     if (InspectorDOMDebuggerAgent* domDebuggerAgent = instrumentingAgents.inspectorDOMDebuggerAgent())
177         domDebuggerAgent->willRemoveDOMNode(node);
178 }
179
180 void InspectorInstrumentation::didRemoveDOMNodeImpl(InstrumentingAgents& instrumentingAgents, Node& node)
181 {
182     if (InspectorDOMDebuggerAgent* domDebuggerAgent = instrumentingAgents.inspectorDOMDebuggerAgent())
183         domDebuggerAgent->didRemoveDOMNode(node);
184     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
185         domAgent->didRemoveDOMNode(node);
186 }
187
188 void InspectorInstrumentation::willModifyDOMAttrImpl(InstrumentingAgents& instrumentingAgents, Element& element, const AtomicString& oldValue, const AtomicString& newValue)
189 {
190     if (InspectorDOMDebuggerAgent* domDebuggerAgent = instrumentingAgents.inspectorDOMDebuggerAgent())
191         domDebuggerAgent->willModifyDOMAttr(element);
192     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
193         domAgent->willModifyDOMAttr(element, oldValue, newValue);
194 }
195
196 void InspectorInstrumentation::didModifyDOMAttrImpl(InstrumentingAgents& instrumentingAgents, Element& element, const AtomicString& name, const AtomicString& value)
197 {
198     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
199         domAgent->didModifyDOMAttr(element, name, value);
200 }
201
202 void InspectorInstrumentation::didRemoveDOMAttrImpl(InstrumentingAgents& instrumentingAgents, Element& element, const AtomicString& name)
203 {
204     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
205         domAgent->didRemoveDOMAttr(element, name);
206 }
207
208 void InspectorInstrumentation::didInvalidateStyleAttrImpl(InstrumentingAgents& instrumentingAgents, Node& node)
209 {
210     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
211         domAgent->didInvalidateStyleAttr(node);
212     if (InspectorDOMDebuggerAgent* domDebuggerAgent = instrumentingAgents.inspectorDOMDebuggerAgent())
213         domDebuggerAgent->didInvalidateStyleAttr(node);
214 }
215
216 void InspectorInstrumentation::documentDetachedImpl(InstrumentingAgents& instrumentingAgents, Document& document)
217 {
218     if (InspectorCSSAgent* cssAgent = instrumentingAgents.inspectorCSSAgent())
219         cssAgent->documentDetached(document);
220 }
221
222 void InspectorInstrumentation::frameWindowDiscardedImpl(InstrumentingAgents& instrumentingAgents, DOMWindow* window)
223 {
224     if (WebConsoleAgent* consoleAgent = instrumentingAgents.webConsoleAgent())
225         consoleAgent->frameWindowDiscarded(window);
226 }
227
228 void InspectorInstrumentation::mediaQueryResultChangedImpl(InstrumentingAgents& instrumentingAgents)
229 {
230     if (InspectorCSSAgent* cssAgent = instrumentingAgents.inspectorCSSAgent())
231         cssAgent->mediaQueryResultChanged();
232 }
233
234 void InspectorInstrumentation::activeStyleSheetsUpdatedImpl(InstrumentingAgents& instrumentingAgents, Document& document)
235 {
236     if (InspectorCSSAgent* cssAgent = instrumentingAgents.inspectorCSSAgent())
237         cssAgent->activeStyleSheetsUpdated(document);
238 }
239
240 void InspectorInstrumentation::didPushShadowRootImpl(InstrumentingAgents& instrumentingAgents, Element& host, ShadowRoot& root)
241 {
242     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
243         domAgent->didPushShadowRoot(host, root);
244 }
245
246 void InspectorInstrumentation::willPopShadowRootImpl(InstrumentingAgents& instrumentingAgents, Element& host, ShadowRoot& root)
247 {
248     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
249         domAgent->willPopShadowRoot(host, root);
250 }
251
252 void InspectorInstrumentation::didChangeCustomElementStateImpl(InstrumentingAgents& instrumentingAgents, Element& element)
253 {
254     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
255         domAgent->didChangeCustomElementState(element);
256 }
257
258 void InspectorInstrumentation::pseudoElementCreatedImpl(InstrumentingAgents& instrumentingAgents, PseudoElement& pseudoElement)
259 {
260     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
261         domAgent->pseudoElementCreated(pseudoElement);
262 }
263
264 void InspectorInstrumentation::pseudoElementDestroyedImpl(InstrumentingAgents& instrumentingAgents, PseudoElement& pseudoElement)
265 {
266     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
267         domAgent->pseudoElementDestroyed(pseudoElement);
268     if (InspectorLayerTreeAgent* layerTreeAgent = instrumentingAgents.inspectorLayerTreeAgent())
269         layerTreeAgent->pseudoElementDestroyed(pseudoElement);
270 }
271
272 void InspectorInstrumentation::didCreateNamedFlowImpl(InstrumentingAgents& instrumentingAgents, Document* document, WebKitNamedFlow& namedFlow)
273 {
274     if (!document)
275         return;
276
277     if (InspectorCSSAgent* cssAgent = instrumentingAgents.inspectorCSSAgent())
278         cssAgent->didCreateNamedFlow(*document, namedFlow);
279 }
280
281 void InspectorInstrumentation::willRemoveNamedFlowImpl(InstrumentingAgents& instrumentingAgents, Document* document, WebKitNamedFlow& namedFlow)
282 {
283     if (!document)
284         return;
285
286     if (InspectorCSSAgent* cssAgent = instrumentingAgents.inspectorCSSAgent())
287         cssAgent->willRemoveNamedFlow(*document, namedFlow);
288 }
289
290 void InspectorInstrumentation::didChangeRegionOversetImpl(InstrumentingAgents& instrumentingAgents, Document& document, WebKitNamedFlow& namedFlow)
291 {
292     if (InspectorCSSAgent* cssAgent = instrumentingAgents.inspectorCSSAgent())
293         cssAgent->didChangeRegionOverset(document, namedFlow);
294 }
295
296 void InspectorInstrumentation::didRegisterNamedFlowContentElementImpl(InstrumentingAgents& instrumentingAgents, Document& document, WebKitNamedFlow& namedFlow, Node& contentElement, Node* nextContentElement)
297 {
298     if (InspectorCSSAgent* cssAgent = instrumentingAgents.inspectorCSSAgent())
299         cssAgent->didRegisterNamedFlowContentElement(document, namedFlow, contentElement, nextContentElement);
300 }
301
302 void InspectorInstrumentation::didUnregisterNamedFlowContentElementImpl(InstrumentingAgents& instrumentingAgents, Document& document, WebKitNamedFlow& namedFlow, Node& contentElement)
303 {
304     if (InspectorCSSAgent* cssAgent = instrumentingAgents.inspectorCSSAgent())
305         cssAgent->didUnregisterNamedFlowContentElement(document, namedFlow, contentElement);
306 }
307
308 void InspectorInstrumentation::mouseDidMoveOverElementImpl(InstrumentingAgents& instrumentingAgents, const HitTestResult& result, unsigned modifierFlags)
309 {
310     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
311         domAgent->mouseDidMoveOverElement(result, modifierFlags);
312 }
313
314 void InspectorInstrumentation::didScrollImpl(InstrumentingAgents& instrumentingAgents)
315 {
316     if (InspectorPageAgent* pageAgent = instrumentingAgents.inspectorPageAgent())
317         pageAgent->didScroll();
318 }
319
320 bool InspectorInstrumentation::handleTouchEventImpl(InstrumentingAgents& instrumentingAgents, Node& node)
321 {
322     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
323         return domAgent->handleTouchEvent(node);
324     return false;
325 }
326
327 bool InspectorInstrumentation::handleMousePressImpl(InstrumentingAgents& instrumentingAgents)
328 {
329     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
330         return domAgent->handleMousePress();
331     return false;
332 }
333
334 bool InspectorInstrumentation::forcePseudoStateImpl(InstrumentingAgents& instrumentingAgents, const Element& element, CSSSelector::PseudoClassType pseudoState)
335 {
336     if (InspectorCSSAgent* cssAgent = instrumentingAgents.inspectorCSSAgent())
337         return cssAgent->forcePseudoState(element, pseudoState);
338     return false;
339 }
340
341 void InspectorInstrumentation::characterDataModifiedImpl(InstrumentingAgents& instrumentingAgents, CharacterData& characterData)
342 {
343     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
344         domAgent->characterDataModified(characterData);
345 }
346
347 void InspectorInstrumentation::willSendXMLHttpRequestImpl(InstrumentingAgents& instrumentingAgents, const String& url)
348 {
349     if (InspectorDOMDebuggerAgent* domDebuggerAgent = instrumentingAgents.inspectorDOMDebuggerAgent())
350         domDebuggerAgent->willSendXMLHttpRequest(url);
351 }
352
353 void InspectorInstrumentation::didInstallTimerImpl(InstrumentingAgents& instrumentingAgents, int timerId, Seconds timeout, bool singleShot, ScriptExecutionContext& context)
354 {
355     pauseOnNativeEventIfNeeded(instrumentingAgents, false, setTimerEventName, true);
356     didScheduleAsyncCall(instrumentingAgents, AsyncCallTypeTimer, timerId, context, singleShot);
357
358     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent())
359         timelineAgent->didInstallTimer(timerId, timeout, singleShot, frameForScriptExecutionContext(context));
360 }
361
362 void InspectorInstrumentation::didRemoveTimerImpl(InstrumentingAgents& instrumentingAgents, int timerId, ScriptExecutionContext& context)
363 {
364     pauseOnNativeEventIfNeeded(instrumentingAgents, false, clearTimerEventName, true);
365
366     if (InspectorDebuggerAgent* debuggerAgent = instrumentingAgents.inspectorDebuggerAgent())
367         debuggerAgent->didCancelAsyncCall(AsyncCallTypeTimer, timerId);
368     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent())
369         timelineAgent->didRemoveTimer(timerId, frameForScriptExecutionContext(context));
370 }
371
372 InspectorInstrumentationCookie InspectorInstrumentation::willCallFunctionImpl(InstrumentingAgents& instrumentingAgents, const String& scriptName, int scriptLine, ScriptExecutionContext* context)
373 {
374     int timelineAgentId = 0;
375     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent()) {
376         timelineAgent->willCallFunction(scriptName, scriptLine, frameForScriptExecutionContext(context));
377         timelineAgentId = timelineAgent->id();
378     }
379     return InspectorInstrumentationCookie(instrumentingAgents, timelineAgentId);
380 }
381
382 void InspectorInstrumentation::didCallFunctionImpl(const InspectorInstrumentationCookie& cookie, ScriptExecutionContext* context)
383 {
384     if (InspectorTimelineAgent* timelineAgent = retrieveTimelineAgent(cookie))
385         timelineAgent->didCallFunction(frameForScriptExecutionContext(context));
386 }
387
388 InspectorInstrumentationCookie InspectorInstrumentation::willDispatchEventImpl(InstrumentingAgents& instrumentingAgents, Document& document, const Event& event, bool hasEventListeners)
389 {
390     int timelineAgentId = 0;
391     InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent();
392     if (timelineAgent && hasEventListeners) {
393         timelineAgent->willDispatchEvent(event, document.frame());
394         timelineAgentId = timelineAgent->id();
395     }
396 #if ENABLE(WEB_REPLAY)
397     if (InspectorReplayAgent* replayAgent = instrumentingAgents.inspectorReplayAgent())
398         replayAgent->willDispatchEvent(event, document.frame());
399 #endif
400     return InspectorInstrumentationCookie(instrumentingAgents, timelineAgentId);
401 }
402
403 void InspectorInstrumentation::willHandleEventImpl(InstrumentingAgents& instrumentingAgents, const Event& event)
404 {
405     pauseOnNativeEventIfNeeded(instrumentingAgents, true, event.type(), false);
406 }
407
408 void InspectorInstrumentation::didDispatchEventImpl(const InspectorInstrumentationCookie& cookie)
409 {
410     if (InspectorTimelineAgent* timelineAgent = retrieveTimelineAgent(cookie))
411         timelineAgent->didDispatchEvent();
412 }
413
414 InspectorInstrumentationCookie InspectorInstrumentation::willDispatchEventOnWindowImpl(InstrumentingAgents& instrumentingAgents, const Event& event, DOMWindow& window)
415 {
416     int timelineAgentId = 0;
417     InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent();
418     if (timelineAgent && window.hasEventListeners(event.type())) {
419         timelineAgent->willDispatchEvent(event, window.frame());
420         timelineAgentId = timelineAgent->id();
421     }
422 #if ENABLE(WEB_REPLAY)
423     if (InspectorReplayAgent* replayAgent = instrumentingAgents.inspectorReplayAgent())
424         replayAgent->willDispatchEvent(event, window.frame());
425 #endif
426     return InspectorInstrumentationCookie(instrumentingAgents, timelineAgentId);
427 }
428
429 void InspectorInstrumentation::didDispatchEventOnWindowImpl(const InspectorInstrumentationCookie& cookie)
430 {
431     if (InspectorTimelineAgent* timelineAgent = retrieveTimelineAgent(cookie))
432         timelineAgent->didDispatchEvent();
433 }
434
435 InspectorInstrumentationCookie InspectorInstrumentation::willEvaluateScriptImpl(InstrumentingAgents& instrumentingAgents, Frame& frame, const String& url, int lineNumber)
436 {
437     int timelineAgentId = 0;
438     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent()) {
439         timelineAgent->willEvaluateScript(url, lineNumber, frame);
440         timelineAgentId = timelineAgent->id();
441     }
442     return InspectorInstrumentationCookie(instrumentingAgents, timelineAgentId);
443 }
444
445 void InspectorInstrumentation::didEvaluateScriptImpl(const InspectorInstrumentationCookie& cookie, Frame& frame)
446 {
447     if (InspectorTimelineAgent* timelineAgent = retrieveTimelineAgent(cookie))
448         timelineAgent->didEvaluateScript(frame);
449 }
450
451 InspectorInstrumentationCookie InspectorInstrumentation::willFireTimerImpl(InstrumentingAgents& instrumentingAgents, int timerId, ScriptExecutionContext& context)
452 {
453     pauseOnNativeEventIfNeeded(instrumentingAgents, false, timerFiredEventName, false);
454
455     if (InspectorDebuggerAgent* debuggerAgent = instrumentingAgents.inspectorDebuggerAgent())
456         debuggerAgent->willDispatchAsyncCall(AsyncCallTypeTimer, timerId);
457
458     int timelineAgentId = 0;
459     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent()) {
460         timelineAgent->willFireTimer(timerId, frameForScriptExecutionContext(context));
461         timelineAgentId = timelineAgent->id();
462     }
463     return InspectorInstrumentationCookie(instrumentingAgents, timelineAgentId);
464 }
465
466 void InspectorInstrumentation::didFireTimerImpl(const InspectorInstrumentationCookie& cookie)
467 {
468     if (InspectorDebuggerAgent* debuggerAgent = cookie.instrumentingAgents()->inspectorDebuggerAgent())
469         debuggerAgent->didDispatchAsyncCall();
470     if (InspectorTimelineAgent* timelineAgent = retrieveTimelineAgent(cookie))
471         timelineAgent->didFireTimer();
472 }
473
474 void InspectorInstrumentation::didInvalidateLayoutImpl(InstrumentingAgents& instrumentingAgents, Frame& frame)
475 {
476     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent())
477         timelineAgent->didInvalidateLayout(frame);
478 }
479
480 InspectorInstrumentationCookie InspectorInstrumentation::willLayoutImpl(InstrumentingAgents& instrumentingAgents, Frame& frame)
481 {
482     int timelineAgentId = 0;
483     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent()) {
484         timelineAgent->willLayout(frame);
485         timelineAgentId = timelineAgent->id();
486     }
487     return InspectorInstrumentationCookie(instrumentingAgents, timelineAgentId);
488 }
489
490 void InspectorInstrumentation::didLayoutImpl(const InspectorInstrumentationCookie& cookie, RenderObject& root)
491 {
492     if (InspectorTimelineAgent* timelineAgent = retrieveTimelineAgent(cookie))
493         timelineAgent->didLayout(root);
494
495     if (InspectorPageAgent* pageAgent = cookie.instrumentingAgents()->inspectorPageAgent())
496         pageAgent->didLayout();
497 }
498
499 void InspectorInstrumentation::willCompositeImpl(InstrumentingAgents& instrumentingAgents, Frame& frame)
500 {
501     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent())
502         timelineAgent->willComposite(frame);
503 }
504
505 void InspectorInstrumentation::didCompositeImpl(InstrumentingAgents& instrumentingAgents)
506 {
507     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent())
508         timelineAgent->didComposite();
509 }
510
511 void InspectorInstrumentation::willPaintImpl(InstrumentingAgents& instrumentingAgents, RenderObject& renderer)
512 {
513     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent())
514         timelineAgent->willPaint(renderer.frame());
515 }
516
517 void InspectorInstrumentation::didPaintImpl(InstrumentingAgents& instrumentingAgents, RenderObject& renderer, const LayoutRect& rect)
518 {
519     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent())
520         timelineAgent->didPaint(renderer, rect);
521
522     if (InspectorPageAgent* pageAgent = instrumentingAgents.inspectorPageAgent())
523         pageAgent->didPaint(renderer, rect);
524 }
525
526 InspectorInstrumentationCookie InspectorInstrumentation::willRecalculateStyleImpl(InstrumentingAgents& instrumentingAgents, Document& document)
527 {
528     int timelineAgentId = 0;
529     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent()) {
530         timelineAgent->willRecalculateStyle(document.frame());
531         timelineAgentId = timelineAgent->id();
532     }
533     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
534         networkAgent->willRecalculateStyle();
535     return InspectorInstrumentationCookie(instrumentingAgents, timelineAgentId);
536 }
537
538 void InspectorInstrumentation::didRecalculateStyleImpl(const InspectorInstrumentationCookie& cookie)
539 {
540     if (!cookie.isValid())
541         return;
542     
543     InstrumentingAgents& instrumentingAgents = *cookie.instrumentingAgents();
544
545     if (InspectorTimelineAgent* timelineAgent = retrieveTimelineAgent(cookie))
546         timelineAgent->didRecalculateStyle();
547     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
548         networkAgent->didRecalculateStyle();
549     if (InspectorPageAgent* pageAgent = instrumentingAgents.inspectorPageAgent())
550         pageAgent->didRecalculateStyle();
551 }
552
553 void InspectorInstrumentation::didScheduleStyleRecalculationImpl(InstrumentingAgents& instrumentingAgents, Document& document)
554 {
555     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent())
556         timelineAgent->didScheduleStyleRecalculation(document.frame());
557     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
558         networkAgent->didScheduleStyleRecalculation(document);
559 }
560
561 void InspectorInstrumentation::applyEmulatedMediaImpl(InstrumentingAgents& instrumentingAgents, String& media)
562 {
563     if (InspectorPageAgent* pageAgent = instrumentingAgents.inspectorPageAgent())
564         pageAgent->applyEmulatedMedia(media);
565 }
566
567 void InspectorInstrumentation::willSendRequestImpl(InstrumentingAgents& instrumentingAgents, unsigned long identifier, DocumentLoader* loader, ResourceRequest& request, const ResourceResponse& redirectResponse)
568 {
569     if (!loader)
570         return;
571
572     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
573         networkAgent->willSendRequest(identifier, *loader, request, redirectResponse);
574 }
575
576 void InspectorInstrumentation::continueAfterPingLoaderImpl(InstrumentingAgents& instrumentingAgents, unsigned long identifier, DocumentLoader* loader, ResourceRequest& request, const ResourceResponse& response)
577 {
578     willSendRequestImpl(instrumentingAgents, identifier, loader, request, response);
579 }
580
581 void InspectorInstrumentation::didLoadResourceFromMemoryCacheImpl(InstrumentingAgents& instrumentingAgents, DocumentLoader* loader, CachedResource* cachedResource)
582 {
583     if (!instrumentingAgents.inspectorEnvironment().developerExtrasEnabled())
584         return;
585     
586     if (!loader || !cachedResource)
587         return;
588
589     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
590         networkAgent->didLoadResourceFromMemoryCache(*loader, *cachedResource);
591 }
592
593 void InspectorInstrumentation::didReceiveResourceResponseImpl(InstrumentingAgents& instrumentingAgents, unsigned long identifier, DocumentLoader* loader, const ResourceResponse& response, ResourceLoader* resourceLoader)
594 {
595     if (!loader)
596         return;
597
598     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
599         networkAgent->didReceiveResponse(identifier, *loader, response, resourceLoader);
600     if (WebConsoleAgent* consoleAgent = instrumentingAgents.webConsoleAgent())
601         consoleAgent->didReceiveResponse(identifier, response); // This should come AFTER resource notification, front-end relies on this.
602 }
603
604 void InspectorInstrumentation::didReceiveThreadableLoaderResponseImpl(InstrumentingAgents& instrumentingAgents, DocumentThreadableLoader& documentThreadableLoader, unsigned long identifier)
605 {
606     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
607         networkAgent->didReceiveThreadableLoaderResponse(identifier, documentThreadableLoader);
608 }
609
610 void InspectorInstrumentation::didReceiveDataImpl(InstrumentingAgents& instrumentingAgents, unsigned long identifier, const char* data, int dataLength, int encodedDataLength)
611 {
612     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
613         networkAgent->didReceiveData(identifier, data, dataLength, encodedDataLength);
614 }
615
616 void InspectorInstrumentation::didFinishLoadingImpl(InstrumentingAgents& instrumentingAgents, unsigned long identifier, DocumentLoader* loader, const NetworkLoadMetrics& networkLoadMetrics, ResourceLoader* resourceLoader)
617 {
618     if (!loader)
619         return;
620
621     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
622         networkAgent->didFinishLoading(identifier, *loader, networkLoadMetrics, resourceLoader);
623 }
624
625 void InspectorInstrumentation::didFailLoadingImpl(InstrumentingAgents& instrumentingAgents, unsigned long identifier, DocumentLoader* loader, const ResourceError& error)
626 {
627     if (!loader)
628         return;
629
630     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
631         networkAgent->didFailLoading(identifier, *loader, error);
632     if (WebConsoleAgent* consoleAgent = instrumentingAgents.webConsoleAgent())
633         consoleAgent->didFailLoading(identifier, error); // This should come AFTER resource notification, front-end relies on this.
634 }
635
636 void InspectorInstrumentation::didFinishXHRLoadingImpl(InstrumentingAgents& instrumentingAgents, unsigned long identifier, std::optional<String> decodedText, const String& url, const String& sendURL, unsigned sendLineNumber, unsigned sendColumnNumber)
637 {
638     if (WebConsoleAgent* consoleAgent = instrumentingAgents.webConsoleAgent())
639         consoleAgent->didFinishXHRLoading(identifier, url, sendURL, sendLineNumber, sendColumnNumber);
640     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent()) {
641         if (decodedText)
642             networkAgent->didFinishXHRLoading(identifier, *decodedText);
643     }
644 }
645
646 void InspectorInstrumentation::willLoadXHRSynchronouslyImpl(InstrumentingAgents& instrumentingAgents)
647 {
648     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
649         networkAgent->willLoadXHRSynchronously();
650 }
651
652 void InspectorInstrumentation::didLoadXHRSynchronouslyImpl(InstrumentingAgents& instrumentingAgents)
653 {
654     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
655         networkAgent->didLoadXHRSynchronously();
656 }
657
658 void InspectorInstrumentation::scriptImportedImpl(InstrumentingAgents& instrumentingAgents, unsigned long identifier, const String& sourceString)
659 {
660     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
661         networkAgent->setInitialScriptContent(identifier, sourceString);
662 }
663
664 void InspectorInstrumentation::scriptExecutionBlockedByCSPImpl(InstrumentingAgents& instrumentingAgents, const String& directiveText)
665 {
666     if (InspectorDebuggerAgent* debuggerAgent = instrumentingAgents.inspectorDebuggerAgent())
667         debuggerAgent->scriptExecutionBlockedByCSP(directiveText);
668 }
669
670 void InspectorInstrumentation::didReceiveScriptResponseImpl(InstrumentingAgents& instrumentingAgents, unsigned long identifier)
671 {
672     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
673         networkAgent->didReceiveScriptResponse(identifier);
674 }
675
676 void InspectorInstrumentation::domContentLoadedEventFiredImpl(InstrumentingAgents& instrumentingAgents, Frame& frame)
677 {
678     if (!frame.isMainFrame())
679         return;
680
681     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
682         domAgent->mainFrameDOMContentLoaded();
683
684     if (InspectorDOMDebuggerAgent* domDebuggerAgent = instrumentingAgents.inspectorDOMDebuggerAgent())
685         domDebuggerAgent->mainFrameDOMContentLoaded();
686
687     if (InspectorPageAgent* pageAgent = instrumentingAgents.inspectorPageAgent())
688         pageAgent->domContentEventFired();
689 }
690
691 void InspectorInstrumentation::loadEventFiredImpl(InstrumentingAgents& instrumentingAgents, Frame* frame)
692 {
693     if (!frame || !frame->isMainFrame())
694         return;
695
696     if (InspectorPageAgent* pageAgent = instrumentingAgents.inspectorPageAgent())
697         pageAgent->loadEventFired();
698 }
699
700 void InspectorInstrumentation::frameDetachedFromParentImpl(InstrumentingAgents& instrumentingAgents, Frame& frame)
701 {
702     if (InspectorPageAgent* pageAgent = instrumentingAgents.inspectorPageAgent())
703         pageAgent->frameDetached(frame);
704
705 #if ENABLE(WEB_REPLAY)
706     if (!frame.isMainFrame())
707         return;
708
709     if (InspectorReplayAgent* replayAgent = instrumentingAgents.inspectorReplayAgent())
710         replayAgent->frameDetached(frame);
711 #endif
712 }
713
714 void InspectorInstrumentation::didCommitLoadImpl(InstrumentingAgents& instrumentingAgents, Frame& frame, DocumentLoader* loader)
715 {
716     if (!instrumentingAgents.inspectorEnvironment().developerExtrasEnabled())
717         return;
718
719     if (!frame.page())
720         return;
721
722     if (!loader)
723         return;
724
725     ASSERT(loader->frame() == &frame);
726
727     if (frame.isMainFrame()) {
728         if (WebConsoleAgent* consoleAgent = instrumentingAgents.webConsoleAgent())
729             consoleAgent->reset();
730
731         if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
732             networkAgent->mainFrameNavigated(*loader);
733
734         if (InspectorCSSAgent* cssAgent = instrumentingAgents.inspectorCSSAgent())
735             cssAgent->reset();
736
737         if (InspectorDatabaseAgent* databaseAgent = instrumentingAgents.inspectorDatabaseAgent())
738             databaseAgent->clearResources();
739
740         if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
741             domAgent->setDocument(frame.document());
742
743         if (InspectorLayerTreeAgent* layerTreeAgent = instrumentingAgents.inspectorLayerTreeAgent())
744             layerTreeAgent->reset();
745
746         if (PageDebuggerAgent* pageDebuggerAgent = instrumentingAgents.pageDebuggerAgent())
747             pageDebuggerAgent->mainFrameNavigated();
748
749         if (PageHeapAgent* pageHeapAgent = instrumentingAgents.pageHeapAgent())
750             pageHeapAgent->mainFrameNavigated();
751     }
752
753     if (InspectorCanvasAgent* canvasAgent = instrumentingAgents.inspectorCanvasAgent())
754         canvasAgent->frameNavigated(frame);
755
756     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
757         domAgent->didCommitLoad(frame.document());
758
759     if (InspectorPageAgent* pageAgent = instrumentingAgents.inspectorPageAgent())
760         pageAgent->frameNavigated(frame);
761
762     if (frame.isMainFrame()) {
763         if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent())
764             timelineAgent->mainFrameNavigated();
765     }
766
767 #if ENABLE(WEB_REPLAY)
768     if (InspectorReplayAgent* replayAgent = instrumentingAgents.inspectorReplayAgent())
769         replayAgent->frameNavigated(frame);
770 #endif
771 }
772
773 void InspectorInstrumentation::frameDocumentUpdatedImpl(InstrumentingAgents& instrumentingAgents, Frame& frame)
774 {
775     if (!instrumentingAgents.inspectorEnvironment().developerExtrasEnabled())
776         return;
777     if (InspectorDOMAgent* domAgent = instrumentingAgents.inspectorDOMAgent())
778         domAgent->frameDocumentUpdated(frame);
779 }
780
781 void InspectorInstrumentation::loaderDetachedFromFrameImpl(InstrumentingAgents& instrumentingAgents, DocumentLoader& loader)
782 {
783     if (InspectorPageAgent* inspectorPageAgent = instrumentingAgents.inspectorPageAgent())
784         inspectorPageAgent->loaderDetachedFromFrame(loader);
785 }
786
787 void InspectorInstrumentation::frameStartedLoadingImpl(InstrumentingAgents& instrumentingAgents, Frame& frame)
788 {
789     if (frame.isMainFrame()) {
790         if (PageDebuggerAgent* pageDebuggerAgent = instrumentingAgents.pageDebuggerAgent())
791             pageDebuggerAgent->mainFrameStartedLoading();
792         if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.persistentInspectorTimelineAgent())
793             timelineAgent->mainFrameStartedLoading();
794     }
795
796     if (InspectorPageAgent* inspectorPageAgent = instrumentingAgents.inspectorPageAgent())
797         inspectorPageAgent->frameStartedLoading(frame);
798 }
799
800 void InspectorInstrumentation::frameStoppedLoadingImpl(InstrumentingAgents& instrumentingAgents, Frame& frame)
801 {
802     if (frame.isMainFrame()) {
803         if (PageDebuggerAgent* pageDebuggerAgent = instrumentingAgents.pageDebuggerAgent())
804             pageDebuggerAgent->mainFrameStoppedLoading();
805     }
806
807     if (InspectorPageAgent* inspectorPageAgent = instrumentingAgents.inspectorPageAgent())
808         inspectorPageAgent->frameStoppedLoading(frame);
809 }
810
811 void InspectorInstrumentation::frameScheduledNavigationImpl(InstrumentingAgents& instrumentingAgents, Frame& frame, Seconds delay)
812 {
813     if (InspectorPageAgent* inspectorPageAgent = instrumentingAgents.inspectorPageAgent())
814         inspectorPageAgent->frameScheduledNavigation(frame, delay);
815 }
816
817 void InspectorInstrumentation::frameClearedScheduledNavigationImpl(InstrumentingAgents& instrumentingAgents, Frame& frame)
818 {
819     if (InspectorPageAgent* inspectorPageAgent = instrumentingAgents.inspectorPageAgent())
820         inspectorPageAgent->frameClearedScheduledNavigation(frame);
821 }
822
823 void InspectorInstrumentation::willDestroyCachedResourceImpl(CachedResource& cachedResource)
824 {
825     if (!s_instrumentingAgentsSet)
826         return;
827
828     for (auto* instrumentingAgent : *s_instrumentingAgentsSet) {
829         if (InspectorNetworkAgent* inspectorNetworkAgent = instrumentingAgent->inspectorNetworkAgent())
830             inspectorNetworkAgent->willDestroyCachedResource(cachedResource);
831     }
832 }
833
834 // JavaScriptCore InspectorDebuggerAgent should know Console MessageTypes.
835 static bool isConsoleAssertMessage(MessageSource source, MessageType type)
836 {
837     return source == MessageSource::ConsoleAPI && type == MessageType::Assert;
838 }
839
840 void InspectorInstrumentation::addMessageToConsoleImpl(InstrumentingAgents& instrumentingAgents, std::unique_ptr<ConsoleMessage> message)
841 {
842     MessageSource source = message->source();
843     MessageType type = message->type();
844     String messageText = message->message();
845
846     if (WebConsoleAgent* consoleAgent = instrumentingAgents.webConsoleAgent())
847         consoleAgent->addMessageToConsole(WTFMove(message));
848     // FIXME: This should just pass the message on to the debugger agent. JavaScriptCore InspectorDebuggerAgent should know Console MessageTypes.
849     if (InspectorDebuggerAgent* debuggerAgent = instrumentingAgents.inspectorDebuggerAgent()) {
850         if (isConsoleAssertMessage(source, type))
851             debuggerAgent->handleConsoleAssert(messageText);
852     }
853 }
854
855 void InspectorInstrumentation::consoleCountImpl(InstrumentingAgents& instrumentingAgents, JSC::ExecState* state, Ref<ScriptArguments>&& arguments)
856 {
857     if (WebConsoleAgent* consoleAgent = instrumentingAgents.webConsoleAgent())
858         consoleAgent->count(state, WTFMove(arguments));
859 }
860
861 void InspectorInstrumentation::takeHeapSnapshotImpl(InstrumentingAgents& instrumentingAgents, const String& title)
862 {
863     if (WebConsoleAgent* consoleAgent = instrumentingAgents.webConsoleAgent())
864         consoleAgent->takeHeapSnapshot(title);
865 }
866
867 void InspectorInstrumentation::startConsoleTimingImpl(InstrumentingAgents& instrumentingAgents, Frame& frame, const String& title)
868 {
869     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent())
870         timelineAgent->time(frame, title);
871     if (WebConsoleAgent* consoleAgent = instrumentingAgents.webConsoleAgent())
872         consoleAgent->startTiming(title);
873 }
874
875 void InspectorInstrumentation::startConsoleTimingImpl(InstrumentingAgents& instrumentingAgents, const String& title)
876 {
877     if (WebConsoleAgent* consoleAgent = instrumentingAgents.webConsoleAgent())
878         consoleAgent->startTiming(title);
879 }
880
881 void InspectorInstrumentation::stopConsoleTimingImpl(InstrumentingAgents& instrumentingAgents, Frame& frame, const String& title, Ref<ScriptCallStack>&& stack)
882 {
883     if (WebConsoleAgent* consoleAgent = instrumentingAgents.webConsoleAgent())
884         consoleAgent->stopTiming(title, WTFMove(stack));
885     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent())
886         timelineAgent->timeEnd(frame, title);
887 }
888
889 void InspectorInstrumentation::stopConsoleTimingImpl(InstrumentingAgents& instrumentingAgents, const String& title, Ref<ScriptCallStack>&& stack)
890 {
891     if (WebConsoleAgent* consoleAgent = instrumentingAgents.webConsoleAgent())
892         consoleAgent->stopTiming(title, WTFMove(stack));
893 }
894
895 void InspectorInstrumentation::consoleTimeStampImpl(InstrumentingAgents& instrumentingAgents, Frame& frame, Ref<ScriptArguments>&& arguments)
896 {
897     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent()) {
898         String message;
899         arguments->getFirstArgumentAsString(message);
900         timelineAgent->didTimeStamp(frame, message);
901      }
902 }
903
904 void InspectorInstrumentation::startProfilingImpl(InstrumentingAgents& instrumentingAgents, JSC::ExecState* exec, const String& title)
905 {
906     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.persistentInspectorTimelineAgent())
907         timelineAgent->startFromConsole(exec, title);
908 }
909
910 void InspectorInstrumentation::stopProfilingImpl(InstrumentingAgents& instrumentingAgents, JSC::ExecState* exec, const String& title)
911 {
912     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.persistentInspectorTimelineAgent())
913         timelineAgent->stopFromConsole(exec, title);
914 }
915
916 void InspectorInstrumentation::didOpenDatabaseImpl(InstrumentingAgents& instrumentingAgents, RefPtr<Database>&& database, const String& domain, const String& name, const String& version)
917 {
918     if (!instrumentingAgents.inspectorEnvironment().developerExtrasEnabled())
919         return;
920     if (InspectorDatabaseAgent* dbAgent = instrumentingAgents.inspectorDatabaseAgent())
921         dbAgent->didOpenDatabase(WTFMove(database), domain, name, version);
922 }
923
924 void InspectorInstrumentation::didDispatchDOMStorageEventImpl(InstrumentingAgents& instrumentingAgents, const String& key, const String& oldValue, const String& newValue, StorageType storageType, SecurityOrigin* securityOrigin)
925 {
926     if (InspectorDOMStorageAgent* domStorageAgent = instrumentingAgents.inspectorDOMStorageAgent())
927         domStorageAgent->didDispatchDOMStorageEvent(key, oldValue, newValue, storageType, securityOrigin);
928 }
929
930 bool InspectorInstrumentation::shouldWaitForDebuggerOnStartImpl(InstrumentingAgents& instrumentingAgents)
931 {
932     if (InspectorWorkerAgent* workerAgent = instrumentingAgents.inspectorWorkerAgent())
933         return workerAgent->shouldWaitForDebuggerOnStart();
934     return false;
935 }
936
937 void InspectorInstrumentation::workerStartedImpl(InstrumentingAgents& instrumentingAgents, WorkerInspectorProxy* proxy, const URL& url)
938 {
939     if (InspectorWorkerAgent* workerAgent = instrumentingAgents.inspectorWorkerAgent())
940         workerAgent->workerStarted(proxy, url);
941 }
942
943 void InspectorInstrumentation::workerTerminatedImpl(InstrumentingAgents& instrumentingAgents, WorkerInspectorProxy* proxy)
944 {
945     if (InspectorWorkerAgent* workerAgent = instrumentingAgents.inspectorWorkerAgent())
946         workerAgent->workerTerminated(proxy);
947 }
948
949 #if ENABLE(WEB_SOCKETS)
950 void InspectorInstrumentation::didCreateWebSocketImpl(InstrumentingAgents& instrumentingAgents, unsigned long identifier, const URL& requestURL)
951 {
952     if (!instrumentingAgents.inspectorEnvironment().developerExtrasEnabled())
953         return;
954
955     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
956         networkAgent->didCreateWebSocket(identifier, requestURL);
957 }
958
959 void InspectorInstrumentation::willSendWebSocketHandshakeRequestImpl(InstrumentingAgents& instrumentingAgents, unsigned long identifier, const ResourceRequest& request)
960 {
961     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
962         networkAgent->willSendWebSocketHandshakeRequest(identifier, request);
963 }
964
965 void InspectorInstrumentation::didReceiveWebSocketHandshakeResponseImpl(InstrumentingAgents& instrumentingAgents, unsigned long identifier, const ResourceResponse& response)
966 {
967     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
968         networkAgent->didReceiveWebSocketHandshakeResponse(identifier, response);
969 }
970
971 void InspectorInstrumentation::didCloseWebSocketImpl(InstrumentingAgents& instrumentingAgents, unsigned long identifier)
972 {
973     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
974         networkAgent->didCloseWebSocket(identifier);
975 }
976
977 void InspectorInstrumentation::didReceiveWebSocketFrameImpl(InstrumentingAgents& instrumentingAgents, unsigned long identifier, const WebSocketFrame& frame)
978 {
979     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
980         networkAgent->didReceiveWebSocketFrame(identifier, frame);
981 }
982
983 void InspectorInstrumentation::didReceiveWebSocketFrameErrorImpl(InstrumentingAgents& instrumentingAgents, unsigned long identifier, const String& errorMessage)
984 {
985     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
986         networkAgent->didReceiveWebSocketFrameError(identifier, errorMessage);
987 }
988
989 void InspectorInstrumentation::didSendWebSocketFrameImpl(InstrumentingAgents& instrumentingAgents, unsigned long identifier, const WebSocketFrame& frame)
990 {
991     if (InspectorNetworkAgent* networkAgent = instrumentingAgents.inspectorNetworkAgent())
992         networkAgent->didSendWebSocketFrame(identifier, frame);
993 }
994 #endif
995
996 void InspectorInstrumentation::didCreateCSSCanvasImpl(InstrumentingAgents* instrumentingAgents, HTMLCanvasElement& canvasElement, const String& name)
997 {
998     if (InspectorCanvasAgent* canvasAgent = instrumentingAgents->inspectorCanvasAgent())
999         canvasAgent->didCreateCSSCanvas(canvasElement, name);
1000 }
1001
1002 void InspectorInstrumentation::didCreateCanvasRenderingContextImpl(InstrumentingAgents* instrumentingAgents, HTMLCanvasElement& canvasElement)
1003 {
1004     if (InspectorCanvasAgent* canvasAgent = instrumentingAgents->inspectorCanvasAgent())
1005         canvasAgent->didCreateCanvasRenderingContext(canvasElement);
1006 }
1007
1008 void InspectorInstrumentation::didChangeCanvasMemoryImpl(InstrumentingAgents* instrumentingAgents, HTMLCanvasElement& canvasElement)
1009 {
1010     if (InspectorCanvasAgent* canvasAgent = instrumentingAgents->inspectorCanvasAgent())
1011         canvasAgent->didChangeCanvasMemory(canvasElement);
1012 }
1013
1014 #if ENABLE(WEB_REPLAY)
1015 void InspectorInstrumentation::sessionCreatedImpl(InstrumentingAgents& instrumentingAgents, RefPtr<ReplaySession>&& session)
1016 {
1017     if (InspectorReplayAgent* replayAgent = instrumentingAgents.inspectorReplayAgent())
1018         replayAgent->sessionCreated(WTFMove(session));
1019 }
1020
1021 void InspectorInstrumentation::sessionLoadedImpl(InstrumentingAgents& instrumentingAgents, RefPtr<ReplaySession>&& session)
1022 {
1023     if (InspectorReplayAgent* replayAgent = instrumentingAgents.inspectorReplayAgent())
1024         replayAgent->sessionLoaded(WTFMove(session));
1025 }
1026
1027 void InspectorInstrumentation::sessionModifiedImpl(InstrumentingAgents& instrumentingAgents, RefPtr<ReplaySession>&& session)
1028 {
1029     if (InspectorReplayAgent* replayAgent = instrumentingAgents.inspectorReplayAgent())
1030         replayAgent->sessionModified(WTFMove(session));
1031 }
1032
1033 void InspectorInstrumentation::segmentCreatedImpl(InstrumentingAgents& instrumentingAgents, RefPtr<ReplaySessionSegment>&& segment)
1034 {
1035     if (InspectorReplayAgent* replayAgent = instrumentingAgents.inspectorReplayAgent())
1036         replayAgent->segmentCreated(WTFMove(segment));
1037 }
1038
1039 void InspectorInstrumentation::segmentCompletedImpl(InstrumentingAgents& instrumentingAgents, RefPtr<ReplaySessionSegment>&& segment)
1040 {
1041     if (InspectorReplayAgent* replayAgent = instrumentingAgents.inspectorReplayAgent())
1042         replayAgent->segmentCompleted(WTFMove(segment));
1043 }
1044
1045 void InspectorInstrumentation::segmentLoadedImpl(InstrumentingAgents& instrumentingAgents, RefPtr<ReplaySessionSegment>&& segment)
1046 {
1047     if (InspectorReplayAgent* replayAgent = instrumentingAgents.inspectorReplayAgent())
1048         replayAgent->segmentLoaded(WTFMove(segment));
1049 }
1050
1051 void InspectorInstrumentation::segmentUnloadedImpl(InstrumentingAgents& instrumentingAgents)
1052 {
1053     if (InspectorReplayAgent* replayAgent = instrumentingAgents.inspectorReplayAgent())
1054         replayAgent->segmentUnloaded();
1055 }
1056
1057 void InspectorInstrumentation::captureStartedImpl(InstrumentingAgents& instrumentingAgents)
1058 {
1059     if (InspectorReplayAgent* replayAgent = instrumentingAgents.inspectorReplayAgent())
1060         replayAgent->captureStarted();
1061 }
1062
1063 void InspectorInstrumentation::captureStoppedImpl(InstrumentingAgents& instrumentingAgents)
1064 {
1065     if (InspectorReplayAgent* replayAgent = instrumentingAgents.inspectorReplayAgent())
1066         replayAgent->captureStopped();
1067 }
1068
1069 void InspectorInstrumentation::playbackStartedImpl(InstrumentingAgents& instrumentingAgents)
1070 {
1071     if (InspectorReplayAgent* replayAgent = instrumentingAgents.inspectorReplayAgent())
1072         replayAgent->playbackStarted();
1073 }
1074
1075 void InspectorInstrumentation::playbackPausedImpl(InstrumentingAgents& instrumentingAgents, const ReplayPosition& position)
1076 {
1077     if (InspectorReplayAgent* replayAgent = instrumentingAgents.inspectorReplayAgent())
1078         replayAgent->playbackPaused(position);
1079 }
1080
1081 void InspectorInstrumentation::playbackHitPositionImpl(InstrumentingAgents& instrumentingAgents, const ReplayPosition& position)
1082 {
1083     if (InspectorReplayAgent* replayAgent = instrumentingAgents.inspectorReplayAgent())
1084         replayAgent->playbackHitPosition(position);
1085 }
1086
1087 void InspectorInstrumentation::playbackFinishedImpl(InstrumentingAgents& instrumentingAgents)
1088 {
1089     if (InspectorReplayAgent* replayAgent = instrumentingAgents.inspectorReplayAgent())
1090         replayAgent->playbackFinished();
1091 }
1092 #endif
1093
1094 #if ENABLE(RESOURCE_USAGE)
1095 void InspectorInstrumentation::didHandleMemoryPressureImpl(InstrumentingAgents& instrumentingAgents, Critical critical)
1096 {
1097     if (InspectorMemoryAgent* memoryAgent = instrumentingAgents.inspectorMemoryAgent())
1098         memoryAgent->didHandleMemoryPressure(critical);
1099 }
1100 #endif
1101
1102 void InspectorInstrumentation::networkStateChangedImpl(InstrumentingAgents& instrumentingAgents)
1103 {
1104     if (InspectorApplicationCacheAgent* applicationCacheAgent = instrumentingAgents.inspectorApplicationCacheAgent())
1105         applicationCacheAgent->networkStateChanged();
1106 }
1107
1108 void InspectorInstrumentation::updateApplicationCacheStatusImpl(InstrumentingAgents& instrumentingAgents, Frame& frame)
1109 {
1110     if (auto* applicationCacheAgent = instrumentingAgents.inspectorApplicationCacheAgent())
1111         applicationCacheAgent->updateApplicationCacheStatus(&frame);
1112 }
1113
1114 bool InspectorInstrumentation::consoleAgentEnabled(ScriptExecutionContext* scriptExecutionContext)
1115 {
1116     InstrumentingAgents* instrumentingAgents = instrumentingAgentsForContext(scriptExecutionContext);
1117     InspectorConsoleAgent* consoleAgent = instrumentingAgents ? instrumentingAgents->webConsoleAgent() : nullptr;
1118     return consoleAgent && consoleAgent->enabled();
1119 }
1120
1121 bool InspectorInstrumentation::timelineAgentEnabled(ScriptExecutionContext* scriptExecutionContext)
1122 {
1123     InstrumentingAgents* instrumentingAgents = instrumentingAgentsForContext(scriptExecutionContext);
1124     return instrumentingAgents && instrumentingAgents->inspectorTimelineAgent();
1125 }
1126
1127 bool InspectorInstrumentation::replayAgentEnabled(ScriptExecutionContext* scriptExecutionContext)
1128 {
1129 #if ENABLE(WEB_REPLAY)
1130     InstrumentingAgents* instrumentingAgents = instrumentingAgentsForContext(scriptExecutionContext);
1131     return instrumentingAgents && instrumentingAgents->inspectorReplayAgent();
1132 #else
1133     UNUSED_PARAM(scriptExecutionContext);
1134     return false;
1135 #endif
1136 }
1137
1138 void InspectorInstrumentation::pauseOnNativeEventIfNeeded(InstrumentingAgents& instrumentingAgents, bool isDOMEvent, const String& eventName, bool synchronous)
1139 {
1140     if (InspectorDOMDebuggerAgent* domDebuggerAgent = instrumentingAgents.inspectorDOMDebuggerAgent())
1141         domDebuggerAgent->pauseOnNativeEventIfNeeded(isDOMEvent, eventName, synchronous);
1142 }
1143
1144 void InspectorInstrumentation::didRequestAnimationFrameImpl(InstrumentingAgents& instrumentingAgents, int callbackId, Frame* frame)
1145 {
1146     pauseOnNativeEventIfNeeded(instrumentingAgents, false, requestAnimationFrameEventName, true);
1147     didScheduleAsyncCall(instrumentingAgents, AsyncCallTypeRequestAnimationFrame, callbackId, *frame->document(), true);
1148
1149     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent())
1150         timelineAgent->didRequestAnimationFrame(callbackId, frame);
1151 }
1152
1153 void InspectorInstrumentation::didCancelAnimationFrameImpl(InstrumentingAgents& instrumentingAgents, int callbackId, Frame* frame)
1154 {
1155     pauseOnNativeEventIfNeeded(instrumentingAgents, false, cancelAnimationFrameEventName, true);
1156
1157     if (InspectorDebuggerAgent* debuggerAgent = instrumentingAgents.inspectorDebuggerAgent())
1158         debuggerAgent->didCancelAsyncCall(AsyncCallTypeRequestAnimationFrame, callbackId);
1159     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent())
1160         timelineAgent->didCancelAnimationFrame(callbackId, frame);
1161 }
1162
1163 InspectorInstrumentationCookie InspectorInstrumentation::willFireAnimationFrameImpl(InstrumentingAgents& instrumentingAgents, int callbackId, Frame* frame)
1164 {
1165     pauseOnNativeEventIfNeeded(instrumentingAgents, false, animationFrameFiredEventName, false);
1166
1167     if (InspectorDebuggerAgent* debuggerAgent = instrumentingAgents.inspectorDebuggerAgent())
1168         debuggerAgent->willDispatchAsyncCall(AsyncCallTypeRequestAnimationFrame, callbackId);
1169
1170     int timelineAgentId = 0;
1171     if (InspectorTimelineAgent* timelineAgent = instrumentingAgents.inspectorTimelineAgent()) {
1172         timelineAgent->willFireAnimationFrame(callbackId, frame);
1173         timelineAgentId = timelineAgent->id();
1174     }
1175     return InspectorInstrumentationCookie(instrumentingAgents, timelineAgentId);
1176 }
1177
1178 void InspectorInstrumentation::didFireAnimationFrameImpl(const InspectorInstrumentationCookie& cookie)
1179 {
1180     if (InspectorDebuggerAgent* debuggerAgent = cookie.instrumentingAgents()->inspectorDebuggerAgent())
1181         debuggerAgent->didDispatchAsyncCall();
1182     if (InspectorTimelineAgent* timelineAgent = retrieveTimelineAgent(cookie))
1183         timelineAgent->didFireAnimationFrame();
1184 }
1185
1186 void InspectorInstrumentation::registerInstrumentingAgents(InstrumentingAgents& instrumentingAgents)
1187 {
1188     if (!s_instrumentingAgentsSet)
1189         s_instrumentingAgentsSet = new HashSet<InstrumentingAgents*>();
1190
1191     s_instrumentingAgentsSet->add(&instrumentingAgents);
1192 }
1193
1194 void InspectorInstrumentation::unregisterInstrumentingAgents(InstrumentingAgents& instrumentingAgents)
1195 {
1196     if (!s_instrumentingAgentsSet)
1197         return;
1198
1199     s_instrumentingAgentsSet->remove(&instrumentingAgents);
1200     if (s_instrumentingAgentsSet->isEmpty()) {
1201         delete s_instrumentingAgentsSet;
1202         s_instrumentingAgentsSet = nullptr;
1203     }
1204 }
1205
1206 InspectorTimelineAgent* InspectorInstrumentation::retrieveTimelineAgent(const InspectorInstrumentationCookie& cookie)
1207 {
1208     if (!cookie.isValid())
1209         return nullptr;
1210
1211     InspectorTimelineAgent* timelineAgent = cookie.instrumentingAgents()->inspectorTimelineAgent();
1212     if (timelineAgent && cookie.hasMatchingTimelineAgentId(timelineAgent->id()))
1213         return timelineAgent;
1214     return nullptr;
1215 }
1216
1217 InstrumentingAgents* InspectorInstrumentation::instrumentingAgentsForRenderer(RenderObject& renderer)
1218 {
1219     return instrumentingAgentsForFrame(renderer.frame());
1220 }
1221
1222 void InspectorInstrumentation::layerTreeDidChangeImpl(InstrumentingAgents& instrumentingAgents)
1223 {
1224     if (InspectorLayerTreeAgent* layerTreeAgent = instrumentingAgents.inspectorLayerTreeAgent())
1225         layerTreeAgent->layerTreeDidChange();
1226 }
1227
1228 void InspectorInstrumentation::renderLayerDestroyedImpl(InstrumentingAgents& instrumentingAgents, const RenderLayer& renderLayer)
1229 {
1230     if (InspectorLayerTreeAgent* layerTreeAgent = instrumentingAgents.inspectorLayerTreeAgent())
1231         layerTreeAgent->renderLayerDestroyed(renderLayer);
1232 }
1233
1234 } // namespace WebCore