OLD | NEW |
1 /* | 1 /* |
2 * Copyright (C) 2012 Google Inc. All rights reserved. | 2 * Copyright (C) 2012 Google Inc. All rights reserved. |
3 * | 3 * |
4 * Redistribution and use in source and binary forms, with or without | 4 * Redistribution and use in source and binary forms, with or without |
5 * modification, are permitted provided that the following conditions are | 5 * modification, are permitted provided that the following conditions are |
6 * met: | 6 * met: |
7 * | 7 * |
8 * * Redistributions of source code must retain the above copyright | 8 * * Redistributions of source code must retain the above copyright |
9 * notice, this list of conditions and the following disclaimer. | 9 * notice, this list of conditions and the following disclaimer. |
10 * * Redistributions in binary form must reproduce the above | 10 * * Redistributions in binary form must reproduce the above |
(...skipping 29 matching lines...) Expand all Loading... |
40 { | 40 { |
41 WebInspector.Object.call(this); | 41 WebInspector.Object.call(this); |
42 this._filters = []; | 42 this._filters = []; |
43 this._tracingModel = tracingModel; | 43 this._tracingModel = tracingModel; |
44 this._recordFilter = recordFilter; | 44 this._recordFilter = recordFilter; |
45 this._targets = []; | 45 this._targets = []; |
46 this.reset(); | 46 this.reset(); |
47 WebInspector.targetManager.observeTargets(this); | 47 WebInspector.targetManager.observeTargets(this); |
48 } | 48 } |
49 | 49 |
| 50 /** |
| 51 * @enum {string} |
| 52 */ |
50 WebInspector.TimelineModel.RecordType = { | 53 WebInspector.TimelineModel.RecordType = { |
51 Task: "Task", | 54 Task: "Task", |
52 Program: "Program", | 55 Program: "Program", |
53 EventDispatch: "EventDispatch", | 56 EventDispatch: "EventDispatch", |
54 | 57 |
55 GPUTask: "GPUTask", | 58 GPUTask: "GPUTask", |
56 | 59 |
57 Animation: "Animation", | 60 Animation: "Animation", |
58 RequestMainThreadFrame: "RequestMainThreadFrame", | 61 RequestMainThreadFrame: "RequestMainThreadFrame", |
59 BeginFrame: "BeginFrame", | 62 BeginFrame: "BeginFrame", |
(...skipping 187 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
247 * @return {boolean} | 250 * @return {boolean} |
248 */ | 251 */ |
249 isWorker: function() | 252 isWorker: function() |
250 { | 253 { |
251 return this.name === WebInspector.TimelineModel.WorkerThreadName; | 254 return this.name === WebInspector.TimelineModel.WorkerThreadName; |
252 } | 255 } |
253 } | 256 } |
254 | 257 |
255 /** | 258 /** |
256 * @constructor | 259 * @constructor |
257 * @param {!WebInspector.TimelineModel} model | |
258 * @param {!WebInspector.TracingModel.Event} traceEvent | 260 * @param {!WebInspector.TracingModel.Event} traceEvent |
259 */ | 261 */ |
260 WebInspector.TimelineModel.Record = function(model, traceEvent) | 262 WebInspector.TimelineModel.Record = function(traceEvent) |
261 { | 263 { |
262 this._model = model; | |
263 this._event = traceEvent; | 264 this._event = traceEvent; |
264 traceEvent._timelineRecord = this; | |
265 this._children = []; | 265 this._children = []; |
266 } | 266 } |
267 | 267 |
268 /** | 268 /** |
269 * @param {!WebInspector.TimelineModel.Record} a | 269 * @param {!WebInspector.TimelineModel.Record} a |
270 * @param {!WebInspector.TimelineModel.Record} b | 270 * @param {!WebInspector.TimelineModel.Record} b |
271 * @return {number} | 271 * @return {number} |
272 */ | 272 */ |
273 WebInspector.TimelineModel.Record._compareStartTime = function(a, b) | 273 WebInspector.TimelineModel.Record._compareStartTime = function(a, b) |
274 { | 274 { |
275 // Never return 0 as otherwise equal records would be merged. | 275 // Never return 0 as otherwise equal records would be merged. |
276 return a.startTime() <= b.startTime() ? -1 : 1; | 276 return a.startTime() <= b.startTime() ? -1 : 1; |
277 } | 277 } |
278 | 278 |
279 WebInspector.TimelineModel.Record.prototype = { | 279 WebInspector.TimelineModel.Record.prototype = { |
280 /** | 280 /** |
281 * @return {?Array.<!ConsoleAgent.CallFrame>} | |
282 */ | |
283 callSiteStackTrace: function() | |
284 { | |
285 var initiator = this._event.initiator; | |
286 return initiator ? initiator.stackTrace : null; | |
287 }, | |
288 | |
289 /** | |
290 * @return {?WebInspector.TimelineModel.Record} | |
291 */ | |
292 initiator: function() | |
293 { | |
294 var initiator = this._event.initiator; | |
295 return initiator ? initiator._timelineRecord : null; | |
296 }, | |
297 | |
298 /** | |
299 * @return {?WebInspector.Target} | 281 * @return {?WebInspector.Target} |
300 */ | 282 */ |
301 target: function() | 283 target: function() |
302 { | 284 { |
303 var threadName = this._event.thread.name(); | 285 var threadName = this._event.thread.name(); |
304 //FIXME: correctly specify target | 286 //FIXME: correctly specify target |
305 return threadName === WebInspector.TimelineModel.RendererMainThreadName
? WebInspector.targetManager.targets()[0] || null : null; | 287 return threadName === WebInspector.TimelineModel.RendererMainThreadName
? WebInspector.targetManager.targets()[0] || null : null; |
306 }, | 288 }, |
307 | 289 |
308 /** | 290 /** |
309 * @return {number} | |
310 */ | |
311 selfTime: function() | |
312 { | |
313 return this._event.selfTime; | |
314 }, | |
315 | |
316 /** | |
317 * @return {!Array.<!WebInspector.TimelineModel.Record>} | 291 * @return {!Array.<!WebInspector.TimelineModel.Record>} |
318 */ | 292 */ |
319 children: function() | 293 children: function() |
320 { | 294 { |
321 return this._children; | 295 return this._children; |
322 }, | 296 }, |
323 | 297 |
324 /** | 298 /** |
325 * @return {number} | 299 * @return {number} |
326 */ | 300 */ |
327 startTime: function() | 301 startTime: function() |
328 { | 302 { |
329 return this._event.startTime; | 303 return this._event.startTime; |
330 }, | 304 }, |
331 | 305 |
332 /** | 306 /** |
| 307 * @return {number} |
| 308 */ |
| 309 endTime: function() |
| 310 { |
| 311 return this._event.endTime || this._event.startTime; |
| 312 }, |
| 313 |
| 314 /** |
333 * @return {string} | 315 * @return {string} |
334 */ | 316 */ |
335 thread: function() | 317 thread: function() |
336 { | 318 { |
337 if (this._event.thread.name() === WebInspector.TimelineModel.RendererMai
nThreadName) | 319 if (this._event.thread.name() === WebInspector.TimelineModel.RendererMai
nThreadName) |
338 return WebInspector.TimelineModel.MainThreadName; | 320 return WebInspector.TimelineModel.MainThreadName; |
339 return this._event.thread.name(); | 321 return this._event.thread.name(); |
340 }, | 322 }, |
341 | 323 |
342 /** | 324 /** |
343 * @return {number} | 325 * @return {!WebInspector.TimelineModel.RecordType} |
344 */ | |
345 endTime: function() | |
346 { | |
347 return this._endTime || this._event.endTime || this._event.startTime; | |
348 }, | |
349 | |
350 /** | |
351 * @param {number} endTime | |
352 */ | |
353 setEndTime: function(endTime) | |
354 { | |
355 this._endTime = endTime; | |
356 }, | |
357 | |
358 /** | |
359 * @return {!Object} | |
360 */ | |
361 data: function() | |
362 { | |
363 return this._event.args["data"]; | |
364 }, | |
365 | |
366 /** | |
367 * @return {string} | |
368 */ | 326 */ |
369 type: function() | 327 type: function() |
370 { | 328 { |
371 if (this._event.hasCategory(WebInspector.TracingModel.ConsoleEventCatego
ry)) | 329 if (this._event.hasCategory(WebInspector.TracingModel.ConsoleEventCatego
ry)) |
372 return WebInspector.TimelineModel.RecordType.ConsoleTime; | 330 return WebInspector.TimelineModel.RecordType.ConsoleTime; |
373 return this._event.name; | 331 return /** @type !WebInspector.TimelineModel.RecordType */ (this._event.
name); |
374 }, | 332 }, |
375 | 333 |
376 /** | 334 /** |
377 * @return {string} | |
378 */ | |
379 frameId: function() | |
380 { | |
381 switch (this._event.name) { | |
382 case WebInspector.TimelineModel.RecordType.UpdateLayoutTree: | |
383 case WebInspector.TimelineModel.RecordType.RecalculateStyles: | |
384 case WebInspector.TimelineModel.RecordType.Layout: | |
385 return this._event.args["beginData"]["frame"]; | |
386 default: | |
387 var data = this._event.args["data"]; | |
388 return (data && data["frame"]) || ""; | |
389 } | |
390 }, | |
391 | |
392 /** | |
393 * @return {?Array.<!ConsoleAgent.CallFrame>} | |
394 */ | |
395 stackTrace: function() | |
396 { | |
397 return this._event.stackTrace; | |
398 }, | |
399 | |
400 /** | |
401 * @param {string} key | 335 * @param {string} key |
402 * @return {?Object} | 336 * @return {?Object} |
403 */ | 337 */ |
404 getUserObject: function(key) | 338 getUserObject: function(key) |
405 { | 339 { |
406 if (key === "TimelineUIUtils::preview-element") | 340 if (key === "TimelineUIUtils::preview-element") |
407 return this._event.previewElement; | 341 return this._event.previewElement; |
408 throw new Error("Unexpected key: " + key); | 342 throw new Error("Unexpected key: " + key); |
409 }, | 343 }, |
410 | 344 |
411 /** | 345 /** |
412 * @param {string} key | 346 * @param {string} key |
413 * @param {?Object|undefined} value | 347 * @param {?Object|undefined} value |
414 */ | 348 */ |
415 setUserObject: function(key, value) | 349 setUserObject: function(key, value) |
416 { | 350 { |
417 if (key !== "TimelineUIUtils::preview-element") | 351 if (key !== "TimelineUIUtils::preview-element") |
418 throw new Error("Unexpected key: " + key); | 352 throw new Error("Unexpected key: " + key); |
419 this._event.previewElement = /** @type {?Element} */ (value); | 353 this._event.previewElement = /** @type {?Element} */ (value); |
420 }, | 354 }, |
421 | 355 |
422 /** | 356 /** |
423 * @return {?Array.<string>} | |
424 */ | |
425 warnings: function() | |
426 { | |
427 if (this._event.warning) | |
428 return [this._event.warning]; | |
429 return null; | |
430 }, | |
431 | |
432 /** | |
433 * @return {!WebInspector.TracingModel.Event} | 357 * @return {!WebInspector.TracingModel.Event} |
434 */ | 358 */ |
435 traceEvent: function() | 359 traceEvent: function() |
436 { | 360 { |
437 return this._event; | 361 return this._event; |
438 }, | 362 }, |
439 | 363 |
440 /** | 364 /** |
441 * @param {!WebInspector.TimelineModel.Record} child | 365 * @param {!WebInspector.TimelineModel.Record} child |
442 */ | 366 */ |
443 _addChild: function(child) | 367 _addChild: function(child) |
444 { | 368 { |
445 this._children.push(child); | 369 this._children.push(child); |
446 child.parent = this; | 370 child.parent = this; |
447 }, | 371 }, |
448 | |
449 /** | |
450 * @return {!WebInspector.TimelineModel} | |
451 */ | |
452 timelineModel: function() | |
453 { | |
454 return this._model; | |
455 } | |
456 } | 372 } |
457 | 373 |
458 /** @typedef {!{page: !Array<!WebInspector.TracingModel.Event>, workers: !Array<
!WebInspector.TracingModel.Event>}} */ | 374 /** @typedef {!{page: !Array<!WebInspector.TracingModel.Event>, workers: !Array<
!WebInspector.TracingModel.Event>}} */ |
459 WebInspector.TimelineModel.MetadataEvents; | 375 WebInspector.TimelineModel.MetadataEvents; |
460 | 376 |
461 WebInspector.TimelineModel.prototype = { | 377 WebInspector.TimelineModel.prototype = { |
462 /** | 378 /** |
463 * @param {boolean} captureCauses | 379 * @param {boolean} captureCauses |
464 * @param {boolean} enableJSSampling | 380 * @param {boolean} enableJSSampling |
465 * @param {boolean} captureMemory | 381 * @param {boolean} captureMemory |
(...skipping 464 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
930 | 846 |
931 // First Paint is actually a DrawFrame that happened after first Composi
teLayers following last CommitLoadEvent. | 847 // First Paint is actually a DrawFrame that happened after first Composi
teLayers following last CommitLoadEvent. |
932 var recordTypes = WebInspector.TimelineModel.RecordType; | 848 var recordTypes = WebInspector.TimelineModel.RecordType; |
933 var i = insertionIndexForObjectInListSortedByFunction(this._firstComposi
teLayers, this._inspectedTargetEvents, WebInspector.TracingModel.Event.compareSt
artTime); | 849 var i = insertionIndexForObjectInListSortedByFunction(this._firstComposi
teLayers, this._inspectedTargetEvents, WebInspector.TracingModel.Event.compareSt
artTime); |
934 for (; i < this._inspectedTargetEvents.length && this._inspectedTargetEv
ents[i].name !== recordTypes.DrawFrame; ++i) { } | 850 for (; i < this._inspectedTargetEvents.length && this._inspectedTargetEv
ents[i].name !== recordTypes.DrawFrame; ++i) { } |
935 if (i >= this._inspectedTargetEvents.length) | 851 if (i >= this._inspectedTargetEvents.length) |
936 return; | 852 return; |
937 var drawFrameEvent = this._inspectedTargetEvents[i]; | 853 var drawFrameEvent = this._inspectedTargetEvents[i]; |
938 var firstPaintEvent = new WebInspector.TracingModel.Event(drawFrameEvent
.categoriesString, recordTypes.MarkFirstPaint, WebInspector.TracingModel.Phase.I
nstant, drawFrameEvent.startTime, drawFrameEvent.thread); | 854 var firstPaintEvent = new WebInspector.TracingModel.Event(drawFrameEvent
.categoriesString, recordTypes.MarkFirstPaint, WebInspector.TracingModel.Phase.I
nstant, drawFrameEvent.startTime, drawFrameEvent.thread); |
939 this._mainThreadEvents.splice(insertionIndexForObjectInListSortedByFunct
ion(firstPaintEvent, this._mainThreadEvents, WebInspector.TracingModel.Event.com
pareStartTime), 0, firstPaintEvent); | 855 this._mainThreadEvents.splice(insertionIndexForObjectInListSortedByFunct
ion(firstPaintEvent, this._mainThreadEvents, WebInspector.TracingModel.Event.com
pareStartTime), 0, firstPaintEvent); |
940 var firstPaintRecord = new WebInspector.TimelineModel.Record(this, first
PaintEvent); | 856 var firstPaintRecord = new WebInspector.TimelineModel.Record(firstPaintE
vent); |
941 this._eventDividerRecords.splice(insertionIndexForObjectInListSortedByFu
nction(firstPaintRecord, this._eventDividerRecords, WebInspector.TimelineModel.R
ecord._compareStartTime), 0, firstPaintRecord); | 857 this._eventDividerRecords.splice(insertionIndexForObjectInListSortedByFu
nction(firstPaintRecord, this._eventDividerRecords, WebInspector.TimelineModel.R
ecord._compareStartTime), 0, firstPaintRecord); |
942 }, | 858 }, |
943 | 859 |
944 _buildTimelineRecords: function() | 860 _buildTimelineRecords: function() |
945 { | 861 { |
946 var topLevelRecords = this._buildTimelineRecordsForThread(this.mainThrea
dEvents()); | 862 var topLevelRecords = this._buildTimelineRecordsForThread(this.mainThrea
dEvents()); |
947 for (var i = 0; i < topLevelRecords.length; i++) { | 863 for (var i = 0; i < topLevelRecords.length; i++) { |
948 var record = topLevelRecords[i]; | 864 var record = topLevelRecords[i]; |
949 if (WebInspector.TracingModel.isTopLevelEvent(record.traceEvent())) | 865 if (WebInspector.TracingModel.isTopLevelEvent(record.traceEvent())) |
950 this._mainThreadTasks.push(record); | 866 this._mainThreadTasks.push(record); |
(...skipping 17 matching lines...) Expand all Loading... |
968 var gpuProcess = this._tracingModel.processByName("GPU Process"); | 884 var gpuProcess = this._tracingModel.processByName("GPU Process"); |
969 if (!gpuProcess) | 885 if (!gpuProcess) |
970 return; | 886 return; |
971 var mainThread = gpuProcess.threadByName("CrGpuMain"); | 887 var mainThread = gpuProcess.threadByName("CrGpuMain"); |
972 if (!mainThread) | 888 if (!mainThread) |
973 return; | 889 return; |
974 var events = mainThread.events(); | 890 var events = mainThread.events(); |
975 var recordTypes = WebInspector.TimelineModel.RecordType; | 891 var recordTypes = WebInspector.TimelineModel.RecordType; |
976 for (var i = 0; i < events.length; ++i) { | 892 for (var i = 0; i < events.length; ++i) { |
977 if (events[i].name === recordTypes.GPUTask) | 893 if (events[i].name === recordTypes.GPUTask) |
978 this._gpuTasks.push(new WebInspector.TimelineModel.Record(this,
events[i])); | 894 this._gpuTasks.push(new WebInspector.TimelineModel.Record(events
[i])); |
979 } | 895 } |
980 }, | 896 }, |
981 | 897 |
982 /** | 898 /** |
983 * @param {!Array.<!WebInspector.TracingModel.Event>} threadEvents | 899 * @param {!Array.<!WebInspector.TracingModel.Event>} threadEvents |
984 * @return {!Array.<!WebInspector.TimelineModel.Record>} | 900 * @return {!Array.<!WebInspector.TimelineModel.Record>} |
985 */ | 901 */ |
986 _buildTimelineRecordsForThread: function(threadEvents) | 902 _buildTimelineRecordsForThread: function(threadEvents) |
987 { | 903 { |
988 var recordStack = []; | 904 var recordStack = []; |
989 var topLevelRecords = []; | 905 var topLevelRecords = []; |
990 | 906 |
991 for (var i = 0, size = threadEvents.length; i < size; ++i) { | 907 for (var i = 0, size = threadEvents.length; i < size; ++i) { |
992 var event = threadEvents[i]; | 908 var event = threadEvents[i]; |
993 for (var top = recordStack.peekLast(); top && top._event.endTime <=
event.startTime; top = recordStack.peekLast()) | 909 for (var top = recordStack.peekLast(); top && top._event.endTime <=
event.startTime; top = recordStack.peekLast()) |
994 recordStack.pop(); | 910 recordStack.pop(); |
995 if (event.phase === WebInspector.TracingModel.Phase.AsyncEnd || even
t.phase === WebInspector.TracingModel.Phase.NestableAsyncEnd) | 911 if (event.phase === WebInspector.TracingModel.Phase.AsyncEnd || even
t.phase === WebInspector.TracingModel.Phase.NestableAsyncEnd) |
996 continue; | 912 continue; |
997 var parentRecord = recordStack.peekLast(); | 913 var parentRecord = recordStack.peekLast(); |
998 // Maintain the back-end logic of old timeline, skip console.time()
/ console.timeEnd() that are not properly nested. | 914 // Maintain the back-end logic of old timeline, skip console.time()
/ console.timeEnd() that are not properly nested. |
999 if (WebInspector.TracingModel.isAsyncBeginPhase(event.phase) && pare
ntRecord && event.endTime > parentRecord._event.endTime) | 915 if (WebInspector.TracingModel.isAsyncBeginPhase(event.phase) && pare
ntRecord && event.endTime > parentRecord._event.endTime) |
1000 continue; | 916 continue; |
1001 var record = new WebInspector.TimelineModel.Record(this, event); | 917 var record = new WebInspector.TimelineModel.Record(event); |
1002 if (WebInspector.TimelineUIUtils.isMarkerEvent(event)) | 918 if (WebInspector.TimelineUIUtils.isMarkerEvent(event)) |
1003 this._eventDividerRecords.push(record); | 919 this._eventDividerRecords.push(record); |
1004 if (!this._recordFilter.accept(record) && !WebInspector.TracingModel
.isTopLevelEvent(event)) | 920 if (!this._recordFilter.accept(record) && !WebInspector.TracingModel
.isTopLevelEvent(event)) |
1005 continue; | 921 continue; |
1006 if (parentRecord) | 922 if (parentRecord) |
1007 parentRecord._addChild(record); | 923 parentRecord._addChild(record); |
1008 else | 924 else |
1009 topLevelRecords.push(record); | 925 topLevelRecords.push(record); |
1010 if (event.endTime) | 926 if (event.endTime) |
1011 recordStack.push(record); | 927 recordStack.push(record); |
(...skipping 1444 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2456 /** @type {!Object.<string, !Array.<!WebInspector.InvalidationTrackingEv
ent>>} */ | 2372 /** @type {!Object.<string, !Array.<!WebInspector.InvalidationTrackingEv
ent>>} */ |
2457 this._invalidations = {}; | 2373 this._invalidations = {}; |
2458 /** @type {!Object.<number, !Array.<!WebInspector.InvalidationTrackingEv
ent>>} */ | 2374 /** @type {!Object.<number, !Array.<!WebInspector.InvalidationTrackingEv
ent>>} */ |
2459 this._invalidationsByNodeId = {}; | 2375 this._invalidationsByNodeId = {}; |
2460 | 2376 |
2461 this._lastRecalcStyle = undefined; | 2377 this._lastRecalcStyle = undefined; |
2462 this._lastPaintWithLayer = undefined; | 2378 this._lastPaintWithLayer = undefined; |
2463 this._didPaint = false; | 2379 this._didPaint = false; |
2464 } | 2380 } |
2465 } | 2381 } |
OLD | NEW |