Closed
Bug 1468789
Opened 5 years ago
Closed 3 years ago
No obvious way to map from slow JS to the relevant web page
Categories
(Core :: Gecko Profiler, enhancement, P2)
Core
Gecko Profiler
Tracking
()
RESOLVED
FIXED
mozilla72
Tracking | Status | |
---|---|---|
firefox72 | --- | fixed |
People
(Reporter: bzbarsky, Assigned: canova)
References
(Blocks 1 open bug)
Details
Attachments
(3 files)
I am looking at a profile in which all the JS stacks are from https://static.licdn.com/sc/h/br/8gesdixxb0mdd0yupx7pukf2q Unfortunately, that tells me nothing about which site is involved... Would it be possible to expose that information as well?
Comment 1•5 years ago
|
||
Perhaps the docshell info from bug 1417976 will help with this?
Comment 2•5 years ago
|
||
That bug is for markers while here it's about samples. But yeah, the source of info is likely the same :)
Comment 3•5 years ago
|
||
Are you interested in this information per stack frame or per sample? If we stored the tab group of the currently-executing runnable, would that be enough information? Would we also need a list / tree of documents + urls that are in a given tab group?
Flags: needinfo?(bzbarsky)
![]() |
Reporter | |
Comment 4•5 years ago
|
||
> Are you interested in this information per stack frame or per sample? Which one is easier? Really, I guess, I want to know the url of the toplevel window involved or something like that, for my initial use case. That should be more or less an invariant across all stackframes in a sample as long as we don't have event loops spinning and cross-window calls, so I don't care too much where the info is attached, I think. That said, in terms of UI I'm looking at a stackframe that has a bunch of time spent in it, not at a specific sample. > If we stored the tab group of the currently-executing runnable, would that be enough information? I'm not sure, because I suspect a lot of my tabs are in the same tabgroup (got opened by me clicking a link in my RSS reader).
Flags: needinfo?(bzbarsky)
Comment 5•5 years ago
|
||
Do you know how we might obtain that information? Do we need to instrument every C++ -> JS call site? I suppose we could start by instrumenting just DOM event dispatching and rAF callback firing, and see how far that gets us.
Flags: needinfo?(bzbarsky)
Comment 6•5 years ago
|
||
I brought up tab groups because I was hoping that we could piggyback on the Quantum DOM runnable labeling work for this.
![]() |
Reporter | |
Comment 7•5 years ago
|
||
> Do you know how we might obtain that information?
What data structure are you starting with?
Flags: needinfo?(bzbarsky)
Comment 8•5 years ago
|
||
(In reply to Boris Zbarsky [:bz] (no decent commit message means r-) from comment #7) > What data structure are you starting with? Nothing, really, other than a TLS object (ProfilingStack) that we can store this information in. If you're asking about the existing code that associates JavaScript stack frames with URLs, that code is in the JS engine and gets the information from the JSScript*: https://searchfox.org/mozilla-central/rev/403038737ba75af3842ba6b43b6e2fb47eb06609/js/src/vm/GeckoProfiler.cpp#283 https://searchfox.org/mozilla-central/rev/403038737ba75af3842ba6b43b6e2fb47eb06609/js/src/jit/JitcodeMap.cpp#323
![]() |
Reporter | |
Comment 9•5 years ago
|
||
OK, so you're starting with a JSScript/JSFunction. From which you can get the global, check whether it's a window, if so get the top window and get its document's url, right?
Updated•5 years ago
|
Priority: -- → P2
Updated•5 years ago
|
Assignee: nobody → gtatum
Comment 10•5 years ago
|
||
I was chatting a bit with Markus about this bug. I wrote some notes which I will include here: * We need some way to map JSScripts to docshell ids * I should look at Nazim's work on keeping the list of the docshells in the profiler (in CorePS?) * The JS Engine does not know about docshells * We have the JSScript in the profiling stack frame, we can look at the this pointer at sampling time, then we need to figure out how to get the docshell id from there
Comment 11•5 years ago
|
||
We also need to decide at what time we want to do the mapping. The string "functionName (url:line)" for a JS frame gets computed - for interpreter frames: the first time this function is called (via GeckoProfilerThread::enter) - for JIT frames: when this function is compiled (via BaselineCompiler::compile or JitcodeIonTable::makeIonEntry) This happens in the JS engine. I don't think we want to call out to the profiler to compute the docshell ID for the JSScript from these places - I'd imagine that it would happen way too often and have too much overhead. Instead, maybe we could hook the creation + destruction of JS global for windows in Gecko, and notify the profiler every time this happens, so that the profiler could keep a map of JS globals -> nsID of the top window's DocShell. Then, at sampling time, when we encounter a JS frame in the stack, we can get the global from the JSScript (I hope this can be done off-thread?) and look up the global in the stored hashmap. This gives us the DocShell ID, which we can then write into the profile buffer. At JSON serialization time, we can put that ID into a new "docShellID" column in the frameTable. I think this should work for interpreter frames. For JIT frames, we don't have the JSScript at sampling time. We only have a JIT return address and we store that in the profile buffer. Then, at JSON serialization time, we map that JIT return address to a ProfiledFrameHandle, from which we can look up the JSScript for it. (The first patch in bug 1441689 adds the necessary infrastructure to get the JSScript from a ProfiledFrameHandle.) From here on out we can do the same as for interpreter frames: get the global, map it to the DocShell ID, write out the DocShell ID.
Updated•4 years ago
|
Assignee: gtatum → nobody
Comment 12•4 years ago
|
||
I'm not planning on working on this right now, but wanted to leave some local notes I had written for the future in case I do.
changeset: 432845:0893dcddbf94
user: Greg Tatum <gtatum@mozilla.com>
date: Wed Aug 22 14:08:27 2018 -0500
summary: WIP - Notes for identifying docshells for JS frames
diff --git a/dom/base/nsGlobalWindowOuter.cpp b/dom/base/nsGlobalWindowOuter.cpp
--- a/dom/base/nsGlobalWindowOuter.cpp
+++ b/dom/base/nsGlobalWindowOuter.cpp
@@ -1985,16 +1985,21 @@ nsGlobalWindowOuter::SetNewDocument(nsID
kungFuDeathGrip->DidInitializeContext();
// We wait to fire the debugger hook until the window is all set up and hooked
// up with the outer. See bug 969156.
if (createdInnerWindow) {
nsContentUtils::AddScriptRunner(
NewRunnableMethod("nsGlobalWindowInner::FireOnNewGlobalObject",
newInnerWindow,
+/**
+ * Markus linked me here when referring to the JS global object.
+ * mstange: I’m referring to the JS definition: https://developer.mozilla.org/en-US/docs/Glossary/Global_object
+ * mstange: in terms of implementation, I think a `window` object maps to an `nsGlobalWindowInner` object
+ */
&nsGlobalWindowInner::FireOnNewGlobalObject));
}
if (newInnerWindow && !newInnerWindow->mHasNotifiedGlobalCreated && mDoc) {
// We should probably notify. However if this is the, arguably bad,
// situation when we're creating a temporary non-chrome-about-blank
// document in a chrome docshell, don't notify just yet. Instead wait
// until we have a real chrome doc.
Assignee | ||
Updated•4 years ago
|
Assignee: nobody → canaltinova
Status: NEW → ASSIGNED
Assignee | ||
Comment 13•3 years ago
|
||
Assignee | ||
Comment 14•3 years ago
|
||
Depends on D51859
Assignee | ||
Comment 15•3 years ago
|
||
Depends on D51860
Assignee | ||
Comment 16•3 years ago
|
||
Front-end side of this work: https://github.com/firefox-devtools/profiler/pull/2300.
It's landed and deployed. Landing the platform side now.
Comment 17•3 years ago
|
||
Pushed by canaltinova@gmail.com: https://hg.mozilla.org/integration/autoland/rev/0c93e34bc1f3 Part 1: Add window id inside realm creation options. r=jandem,bzbarsky https://hg.mozilla.org/integration/autoland/rev/1c3c775faf99 Part 2: Collect inner window id information for js interpreter frames and add a mechanism to get that for jit frames r=gerald,jandem,mstange https://hg.mozilla.org/integration/autoland/rev/e4ed5d091e3d Part 3: Serialize innerWindowID for js/jit frames. r=gerald
Comment 18•3 years ago
|
||
bugherder |
https://hg.mozilla.org/mozilla-central/rev/0c93e34bc1f3
https://hg.mozilla.org/mozilla-central/rev/1c3c775faf99
https://hg.mozilla.org/mozilla-central/rev/e4ed5d091e3d
Status: ASSIGNED → RESOLVED
Closed: 3 years ago
status-firefox72:
--- → fixed
Resolution: --- → FIXED
Target Milestone: --- → mozilla72
Comment 19•3 years ago
|
||
FYI, this appears to have caused an ~100K Base Content Heap Unclassified regression:
I'm not sure why this didn't trigger a perf alert; perhaps it was below a threshold
Flags: needinfo?(canaltinova)
Assignee | ||
Updated•2 months ago
|
Flags: needinfo?(canaltinova)
You need to log in
before you can comment on or make changes to this bug.
Description
•