Hi,

It seems increasingly common for libraries, compilers and runtimes
targeting JS to end up generating new JS on the fly and passing it to
the VM via | eval() | or | new Function() |. In some cases the
resulting code replaces an existing function on an object prototype,
or gets called a few times to perform some work and then never used
again. To my knowledge embind, Shumway and JSIL are all production or
near-production examples of software that relies heavily on
machine-generating code at runtime. I recently wrote a detailed
article on just one of the ways JSIL uses machine-generated code [1].

My profiling and research so far suggests that sometimes this
machine-generated code ends up defying the assumptions that VMs make
about typical user-authored JS (and for good reason - those tend to
apply to user-authored JS). Some of this code runs up against
heuristics used to avoid degenerate cases, and incurs an extra
unnecessary cost in terms of things like type inference.

Does it seem reasonable that a JS library or application could hint to
the VM that the code being loaded is machine-generated, and perhaps
provide some general information about the nature of the code?

For example, JSIL generates the equivalent of polymorphic inline
caches on-demand, and also generates call forwarding stubs that are
effectively no-ops. In both of those cases, the on-demand code gen is
*exclusively* done to provide the VM with better type information and
turn a dynamic invocation into a less-dynamic (or effectively static,
in some cases) invocation. For generated code like this, you'd ideally
want to route around some of the optimizations and data-gathering
performed by the VM, and you'd want to disable heuristics like (just
as an example) V8's 'compilation disabled for this method because it
has been recompiled too many times'. For a no-op forwarder you'd also
want to bias *towards* inlining on the assumption that it will always
pay off (the target is simple and may entirely optimize away if
inlining occurs.), so in that case you actually want to be *more
aggressive* about certain optimizations than you would be normally.

I can imagine a vendor-specific API for this - though I don't know
where you'd tuck it - or a no-op pragma of the "use asm" variety (it's
my impression that es-discuss/TC39 hates these, though.) In practice
these would be an improvement to real-world performance, not something
your application would depend on to function.

I guess the main question from my POV is 'is it actually possible to
do this and see a benefit' - I don't know how realistic it would be to
do some of the things I suggest without creating a risk that the
resulting JS would have safety issues.

Thanks,
-kg

[1] 
https://github.com/sq/JSIL/wiki/Optimizing-dynamic-JavaScript-with-inline-caches
_______________________________________________
dev-tech-js-engine-internals mailing list
[email protected]
https://lists.mozilla.org/listinfo/dev-tech-js-engine-internals

Reply via email to