Search code examples
reverse-engineeringv8

How to read assembler code for NodeJS in 2021


I wanted to read generated opt codes for my simple program:

function test() {
  const i = 2845884;
  const k = 3;

  return i == 2845884 ? k : 7;
}

test();

I found this gist that says that I need to build d8 from sources and run it with --trace-opt-verbose flag.

https://gist.github.com/kevincennis/0cd2138c78a07412ef21

That approach doesn't work for me neither other approaches I found on the web. Looks like all current solutions are outdated.

How can I see what opt codes will be generated for this program?


Solution

  • How can I see what opt codes will be generated for this program?

    For this program, you are already seeing all optimized code, because no optimized code will be generated for it, because it doesn't run anywhere near long enough for optimized compilation to be worth the effort.

    In general, to print optimized code that V8 generates, you need three things:

    (1) A binary that has disassembler support. This is on-by-default in Debug and "optdebug" builds; for Release builds you need the GN arg v8_enable_disassembler = true.

    (2) The command-line flag --print-opt-code.

    (3) A function that runs hot enough to get optimized.

    Try calling your test() in a loop. If you still don't see anything, run the loop more often.
    (The threshold varies depending on V8 version, test program size and behavior, and due to background compilation possibly also your hardware, so there is no general rule-of-thumb number I could state here. For one-liner functions, expect to need several thousand calls.)


    To answer your other question: yes, V8's optimizing compiler supports constant folding, and your test program will be folded to just return 3.


    Side notes:

    I found this gist that says that I need to build d8 from sources and run it with --trace-opt-verbose flag.

    --trace-opt-verbose has never printed optimized code, and the gist you linked doesn't claim that it does. (That said, that gist makes a bunch of rather dubious claims, so it's not a particularly good source to begin with.)

    Looks like all current solutions are outdated.

    Or slightly more accurately: that one gist didn't solve your problem.

    On SO alone, you could have found How to print the compiled instructions in V8 engine? or V8 will not print out disassembly or Are there ways to see the assembly code for the code generated by any of the JavaScript jits, especially V8's?, all dealing with variations of this question.

    None of this has changed recently; the build flag is a requirement since at least 2014, the command-line flag as well as the fact that optimization only kicks in after a while have been unchanged since at least 2011.

    FWIW, the easiest way to build V8 yourself is to follow the official documentation. The gm.py helper script used by that flow even sets the v8_enable_disassembler flag for you automatically.