Commit 43a5f208 authored by Camillo Bruni's avatar Camillo Bruni Committed by Commit Bot

[tools] Fix system-analyzer deopt position

Associate DeoptLogEntry with both, the function's source position and
the deopt location's source position.

Also fixes the list-panel click handler to support all clickable entry
types.

Bug: v8:10644, v8:10754
Change-Id: If10272a926d5dad10b29322e237610900715b9dd
Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/2584955
Commit-Queue: Camillo Bruni <cbruni@chromium.org>
Reviewed-by: 's avatarSathya Gunasekaran  <gsathya@chromium.org>
Cr-Commit-Position: refs/heads/master@{#71732}
parent c2e10ac6
...@@ -219,6 +219,7 @@ class App { ...@@ -219,6 +219,7 @@ class App {
await this._startupPromise; await this._startupPromise;
try { try {
const processor = new Processor(e.detail); const processor = new Processor(e.detail);
this._state.profile = processor.profile;
const mapTimeline = processor.mapTimeline; const mapTimeline = processor.mapTimeline;
const icTimeline = processor.icTimeline; const icTimeline = processor.icTimeline;
const deoptTimeline = processor.deoptTimeline; const deoptTimeline = processor.deoptTimeline;
......
...@@ -5,15 +5,17 @@ import {LogEntry} from './log.mjs'; ...@@ -5,15 +5,17 @@ import {LogEntry} from './log.mjs';
export class DeoptLogEntry extends LogEntry { export class DeoptLogEntry extends LogEntry {
constructor( constructor(
type, time, deoptReason, deoptLocation, scriptOffset, instructionStart, type, time, entry, deoptReason, deoptLocation, scriptOffset,
codeSize, inliningId) { instructionStart, codeSize, inliningId) {
super(type, time); super(type, time);
this._entry = entry;
this._reason = deoptReason; this._reason = deoptReason;
this._location = deoptLocation; this._location = deoptLocation;
this._scriptOffset = scriptOffset; this._scriptOffset = scriptOffset;
this._instructionStart = instructionStart; this._instructionStart = instructionStart;
this._codeSize = codeSize; this._codeSize = codeSize;
this._inliningId = inliningId; this._inliningId = inliningId;
this.fileSourcePosition = undefined;
} }
get reason() { get reason() {
...@@ -24,6 +26,14 @@ export class DeoptLogEntry extends LogEntry { ...@@ -24,6 +26,14 @@ export class DeoptLogEntry extends LogEntry {
return this._location; return this._location;
} }
get entry() {
return this._entry;
}
get functionName() {
return this._entry.functionName;
}
toString() { toString() {
return `Deopt(${this.type})`; return `Deopt(${this.type})`;
} }
...@@ -33,7 +43,10 @@ export class DeoptLogEntry extends LogEntry { ...@@ -33,7 +43,10 @@ export class DeoptLogEntry extends LogEntry {
} }
static get propertyNames() { static get propertyNames() {
return ['type', 'reason', 'sourcePosition', 'script']; return [
'type', 'reason', 'functionName', 'sourcePosition',
'functionSourcePosition', 'script'
];
} }
} }
...@@ -60,10 +73,6 @@ export class CodeLogEntry extends LogEntry { ...@@ -60,10 +73,6 @@ export class CodeLogEntry extends LogEntry {
return this._entry.size; return this._entry.size;
} }
get script() {
return this.sourcePosition?.script;
}
get source() { get source() {
return this._entry?.getSourceCode() ?? ''; return this._entry?.getSourceCode() ?? '';
} }
......
...@@ -225,11 +225,25 @@ export class Processor extends LogReader { ...@@ -225,11 +225,25 @@ export class Processor extends LogReader {
timestamp, codeSize, instructionStart, inliningId, scriptOffset, timestamp, codeSize, instructionStart, inliningId, scriptOffset,
deoptKind, deoptLocation, deoptReason) { deoptKind, deoptLocation, deoptReason) {
this._lastTimestamp = timestamp; this._lastTimestamp = timestamp;
const codeEntry = this._profile.findEntry(instructionStart);
const logEntry = new DeoptLogEntry( const logEntry = new DeoptLogEntry(
deoptKind, timestamp, deoptReason, deoptLocation, scriptOffset, deoptKind, timestamp, codeEntry, deoptReason, deoptLocation,
instructionStart, codeSize, inliningId); scriptOffset, instructionStart, codeSize, inliningId);
this._deoptTimeline.push(logEntry); this._deoptTimeline.push(logEntry);
this.addSourcePosition(this._profile.findEntry(instructionStart), logEntry); this.addSourcePosition(codeEntry, logEntry);
logEntry.functionSourcePosition = logEntry.sourcePosition;
// custom parse deopt location
if (deoptLocation !== '<unknown>') {
const colSeparator = deoptLocation.lastIndexOf(':');
const rowSeparator = deoptLocation.lastIndexOf(':', colSeparator - 1);
const script = this.getScript(deoptLocation.substring(1, rowSeparator));
const line =
parseInt(deoptLocation.substring(rowSeparator + 1, colSeparator));
const column = parseInt(
deoptLocation.substring(colSeparator + 1, deoptLocation.length - 1));
logEntry.sourcePosition =
script.addSourcePosition(line, column, logEntry);
}
} }
processScriptSource(scriptId, url, source) { processScriptSource(scriptId, url, source) {
...@@ -430,4 +444,8 @@ export class Processor extends LogReader { ...@@ -430,4 +444,8 @@ export class Processor extends LogReader {
get scripts() { get scripts() {
return this._profile.scripts_.filter(script => script !== undefined); return this._profile.scripts_.filter(script => script !== undefined);
} }
get profile() {
return this._profile;
}
} }
...@@ -6,6 +6,9 @@ found in the LICENSE file. --> ...@@ -6,6 +6,9 @@ found in the LICENSE file. -->
<link href="./index.css" rel="stylesheet"> <link href="./index.css" rel="stylesheet">
</head> </head>
<style> <style>
#sourceCode {
white-space: pre-line;
}
</style> </style>
<div class="panel"> <div class="panel">
<h2>Code Panel</h2> <h2>Code Panel</h2>
......
...@@ -3,8 +3,7 @@ ...@@ -3,8 +3,7 @@
// found in the LICENSE file. // found in the LICENSE file.
import {SourcePosition} from '../../profile.mjs'; import {SourcePosition} from '../../profile.mjs';
import {IcLogEntry} from '../log/ic.mjs'; import {LogEntry} from '../log/log.mjs';
import {MapLogEntry} from '../log/map.mjs';
import {FocusEvent, SelectionEvent, SelectTimeEvent} from './events.mjs'; import {FocusEvent, SelectionEvent, SelectTimeEvent} from './events.mjs';
import {groupBy, LazyTable} from './helper.mjs'; import {groupBy, LazyTable} from './helper.mjs';
...@@ -18,8 +17,7 @@ DOM.defineCustomElement('view/list-panel', ...@@ -18,8 +17,7 @@ DOM.defineCustomElement('view/list-panel',
_timeline; _timeline;
_detailsClickHandler = this._handleDetailsClick.bind(this); _detailsClickHandler = this._handleDetailsClick.bind(this);
_mapClickHandler = this._handleMapClick.bind(this); _logEntryClickHandler = this._handleLogEntryClick.bind(this);
_fileClickHandler = this._handleFilePositionClick.bind(this);
constructor() { constructor() {
super(templateText); super(templateText);
...@@ -118,15 +116,9 @@ DOM.defineCustomElement('view/list-panel', ...@@ -118,15 +116,9 @@ DOM.defineCustomElement('view/list-panel',
return map; return map;
} }
_handleMapClick(e) { _handleLogEntryClick(e) {
const group = e.currentTarget.group; const group = e.currentTarget.group;
this.dispatchEvent(new FocusEvent(group.entries[0].map)); this.dispatchEvent(new FocusEvent(group.key));
}
_handleFilePositionClick(e) {
const group = e.currentTarget.group;
const sourcePosition = group.entries[0].sourcePosition;
this.dispatchEvent(new FocusEvent(sourcePosition));
} }
_handleDetailsClick(event) { _handleDetailsClick(event) {
...@@ -186,14 +178,17 @@ DOM.defineCustomElement('view/list-panel', ...@@ -186,14 +178,17 @@ DOM.defineCustomElement('view/list-panel',
tr.appendChild(DOM.td(`${group.percent.toFixed(2)}%`, 'percentage')); tr.appendChild(DOM.td(`${group.percent.toFixed(2)}%`, 'percentage'));
tr.appendChild(DOM.td(group.count, 'count')); tr.appendChild(DOM.td(group.count, 'count'));
const valueTd = tr.appendChild(DOM.td(`${group.key}`, 'key')); const valueTd = tr.appendChild(DOM.td(`${group.key}`, 'key'));
if (group.key instanceof MapLogEntry) { if (this._isClickable(group.key)) {
tr.onclick = this._mapClickHandler; tr.onclick = this._logEntryClickHandler;
valueTd.classList.add('clickable'); valueTd.classList.add('clickable');
} else if (group.key instanceof SourcePosition) {
valueTd.classList.add('clickable');
tr.onclick = this._fileClickHandler;
} }
return tr; return tr;
}, 10); }, 10);
} }
_isClickable(object) {
if (typeof object !== 'object') return false;
if (object instanceof LogEntry) return true;
return object instanceof SourcePosition;
}
}); });
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment