Closed Bug 1749521 Opened 2 years ago Closed 2 years ago

We should have "relevant for JS" label frames for JavaScript static API methods

Categories

(Core :: Gecko Profiler, enhancement, P2)

enhancement

Tracking

()

RESOLVED FIXED
104 Branch
Tracking Status
firefox104 --- fixed

People

(Reporter: julienw, Assigned: julienw)

References

(Blocks 1 open bug)

Details

Attachments

(14 files)

496 bytes, text/html
Details
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
756 bytes, text/html
Details
Attached file object.html

From the attachment, I generated this profile:
https://share.firefox.dev/3qfp4q7

We clearly see that obj_keys is present, which is the implementation for Object.keys.

Now if we switch to "JavaScript" stacks we don't see it anymore.

I believe there should be a label frame for this function as well as similar ones.

See https://searchfox.org/mozilla-central/rev/7271a078fa0c1b858a52614ea60ac82fdd8b3d23/js/src/builtin/Object.cpp#2166-2191 for other functions that probably share the same issue (but I haven't double checked for those). I double checked that instance methods have the same issue though (eg: Object.prototype.propertyIsEnumerable).

I also double-checked this for the methods in Array: they share the same issue, for example Array.of has the same issue. However methods on the prototype have a correct label frame.

Therefore it would be good to have a fix that span all builtins implemented with JS_FN.

Severity: -- → S3
Priority: -- → P2

We looked at it with Nazim, and we've noticed that the methods of Array that "works" have manually specified a label frame (eg [1]) but it looks like that it's not done for all of them.

We were wondering if we could wrap the call function pointer in [2] in a lambda for example.

Last solution would be to manually specify all label frames in all the proper locations. That's tedious and not future proof, but it may be the only practical solution.

Hey jandem, by chance, would you have any insight about this?

[1] https://searchfox.org/mozilla-central/rev/83e67336083df9f9a3d1e0c33f2ba19703d57161/js/src/builtin/Array.cpp#1277-1279
[2] https://searchfox.org/mozilla-central/rev/83e67336083df9f9a3d1e0c33f2ba19703d57161/js/public/PropertySpec.h#444-445

Flags: needinfo?(jdemooij)

(In reply to Julien Wajsberg [:julienw] from comment #1)

We were wondering if we could wrap the call function pointer in [2] in a lambda for example.

Last solution would be to manually specify all label frames in all the proper locations. That's tedious and not future proof, but it may be the only practical solution.

I think both of these would have too much overhead. Performance overhead, but it would also bloat the binary and source code because there are a lot of built-ins.

We don't have a great solution for this atm. Maybe a generic "non-JS" frame in the profiler's JS view that we use for all C++ frames?

Flags: needinfo?(jdemooij)

For WebIDL calls I've invested significant effort into making its generated code as small as possible, see bug 1499507 comment 1 for some history. If it's good enough for WebIDL (>10000 calls), I'd hope it would be good enough for Spidermonkey too.

(In reply to Markus Stange [:mstange] from comment #3)

For WebIDL calls I've invested significant effort into making its generated code as small as possible, see bug 1499507 comment 1 for some history. If it's good enough for WebIDL (>10000 calls), I'd hope it would be good enough for Spidermonkey too.

Oh right, I forgot we already do this for WebIDL natives. For SpiderMonkey we'd have to add this manually to all natives though which is a bit of a pain (we have some vague ideas around using a WebIDL-like scheme to generate code but that's not happening anytime soon).

Blocks: 1329161
See Also: → 1752861

To reduce the bloat, we could pick only the ones that are more likely to bring performance problems, such as loops like Object.keys.

I went with the approach of adding directly to the c++ methods.

Nice work.

To reduce the size taken up by strings, I recommend making use of ProfilingStackFrame::Flags::STRING_TEMPLATE_METHOD and its friends, like we do for WebIDL:

https://searchfox.org/mozilla-central/rev/6d0ba065e3d41822337c708c8c0aca334ddd9218/dom/bindings/Codegen.py#10724-10727

AUTO_PROFILER_LABEL_DYNAMIC_FAST(
  "${interface_name}", "${method_name}", DOM, cx,
  uint32_t(js::ProfilingStackFrame::Flags::STRING_TEMPLATE_METHOD) |
  uint32_t(js::ProfilingStackFrame::Flags::RELEVANT_FOR_JS));

See this commit https://hg.mozilla.org/mozilla-central/rev/5ec157cbbdd11c216e996e2cc763bd087620cb11 :

This means that our binary does not need to include concatenated strings such
as "set CanvasRenderingContext2D.fillStyle". It only needs to contain the
individual strings "CanvasRenderingContext2D" and "fillStyle" which are most
likely already present in the binary.

Depends on: 1776721
Attachment #9282596 - Attachment description: WIP: Bug 1749521 - Add label frames relevant for JavaScript developers to some methods of the Intl objects r=jandem → WIP: Bug 1749521 - Add label frames relevant for JavaScript developers to constructors of the Intl objects r=jandem

Try: https://treeherder.mozilla.org/jobs?repo=try&revision=c448390f63b03fa4688586c256281013fc1b42f2
Example profile: https://share.firefox.dev/3R4Noqe (captured with the Web Developer preset, that is without native stacks, and inverted). We can clearly see some new constructors as well as new instumented methods.

Assignee: nobody → felash
Attachment #9282592 - Attachment description: WIP: Bug 1749521 - Add label frames relevant for JavaScript developers to most methods of the Object object r=jandem → Bug 1749521 - Add label frames relevant for JavaScript developers to most methods of the Object object r=jandem
Status: NEW → ASSIGNED
Attachment #9282593 - Attachment description: WIP: Bug 1749521 - Add label frames relevant for JavaScript developers to some methods of the TypedArray object r=jandem → Bug 1749521 - Add label frames relevant for JavaScript developers to some methods of the TypedArray object r=jandem
Attachment #9282594 - Attachment description: WIP: Bug 1749521 - Add label frames relevant for JavaScript developers to some methods of numbers r=jandem → Bug 1749521 - Add label frames relevant for JavaScript developers to some methods of numbers r=jandem
Attachment #9282595 - Attachment description: WIP: Bug 1749521 - Add label frames relevant for JavaScript developers to some methods of the Date object r=jandem → Bug 1749521 - Add label frames relevant for JavaScript developers to some methods of the Date object r=jandem
Attachment #9282596 - Attachment description: WIP: Bug 1749521 - Add label frames relevant for JavaScript developers to constructors of the Intl objects r=jandem → Bug 1749521 - Add label frames relevant for JavaScript developers to constructors of the Intl objects r=jandem
Attachment #9282597 - Attachment description: WIP: Bug 1749521 - Add label frames relevant for JavaScript developers to some methods of RegExp objects r=jandem → Bug 1749521 - Add label frames relevant for JavaScript developers to some methods of RegExp objects r=jandem
Attachment #9282598 - Attachment description: WIP: Bug 1749521 - Add label frames relevant for JavaScript developers to some methods and functions of String r=jandem → Bug 1749521 - Add label frames relevant for JavaScript developers to some methods and functions of String r=jandem
Attachment #9282599 - Attachment description: WIP: Bug 1749521 - Add label frames relevant for JavaScript developers to some static methods of Reflect r=jandem → Bug 1749521 - Add label frames relevant for JavaScript developers to some static methods of Reflect r=jandem
Attachment #9282600 - Attachment description: WIP: Bug 1749521 - Add label frames relevant for JavaScript developers to some methods of Map and Set r=jandem → Bug 1749521 - Add label frames relevant for JavaScript developers to some methods of Map and Set r=jandem
Attachment #9282601 - Attachment description: WIP: Bug 1749521 - Add label frames relevant for JavaScript developers to the static methods of the JSON object r=jandem → Bug 1749521 - Add label frames relevant for JavaScript developers to the static methods of the JSON object r=jandem
Attachment #9282602 - Attachment description: WIP: Bug 1749521 - Add label frames relevant for JavaScript developers to some methods of BigInt r=jandem → Bug 1749521 - Add label frames relevant for JavaScript developers to some methods of BigInt r=jandem
Attachment #9282603 - Attachment description: WIP: Bug 1749521 - Add label frames relevant for JavaScript developers to more methods of Array r=jandem → Bug 1749521 - Add label frames relevant for JavaScript developers to more methods of Array r=jandem

Could you share some perf numbers for a micro-benchmark? Call one of the faster builtins (Date.now() or date.toSource() maybe?) N times in a loop in a JS function and measure how long this takes before/after these changes. (Either JS shell or an HTML file would work, avoid devtools because it has known perf issues.)

Flags: needinfo?(felash)

"".toLowerCase() is also a good one to check.

With this HTML file, I checked Date.now(), "".toLowerCase(), as well as [].includes() which had a label frame already, to measure impact of bug 1776721 as well.

The results are:

[].includes(): 17% improvement
Date.now(): 1% regression
"".toLowerCase(): 1% regression

Flags: needinfo?(felash)
Pushed by jwajsberg@mozilla.com:
https://hg.mozilla.org/integration/autoland/rev/2fe38b091446
Add label frames relevant for JavaScript developers to most methods of the Object object r=jandem
https://hg.mozilla.org/integration/autoland/rev/3fa44d29b206
Add label frames relevant for JavaScript developers to some methods of the TypedArray object r=jandem
https://hg.mozilla.org/integration/autoland/rev/59206e90e55a
Add label frames relevant for JavaScript developers to some methods of numbers r=jandem
https://hg.mozilla.org/integration/autoland/rev/bb4018ade890
Add label frames relevant for JavaScript developers to some methods of the Date object r=jandem
https://hg.mozilla.org/integration/autoland/rev/057335805cd9
Add label frames relevant for JavaScript developers to constructors of the Intl objects r=jandem
https://hg.mozilla.org/integration/autoland/rev/6e9d12f5a336
Add label frames relevant for JavaScript developers to some methods of RegExp objects r=jandem
https://hg.mozilla.org/integration/autoland/rev/dbe28d550837
Add label frames relevant for JavaScript developers to some methods and functions of String r=jandem
https://hg.mozilla.org/integration/autoland/rev/b210832c5ada
Add label frames relevant for JavaScript developers to some static methods of Reflect r=jandem
https://hg.mozilla.org/integration/autoland/rev/8c577e3df203
Add label frames relevant for JavaScript developers to some methods of Map and Set r=jandem
https://hg.mozilla.org/integration/autoland/rev/f3500cbcfe2c
Add label frames relevant for JavaScript developers to the static methods of the JSON object r=jandem
https://hg.mozilla.org/integration/autoland/rev/40b0333164e2
Add label frames relevant for JavaScript developers to some methods of BigInt r=jandem
https://hg.mozilla.org/integration/autoland/rev/a81add5fb3b0
Add label frames relevant for JavaScript developers to more methods of Array r=jandem
QA Whiteboard: [qa-104b-p2]
You need to log in before you can comment on or make changes to this bug.

Attachment

General

Created:
Updated:
Size: