monoclex / jssat

Compile JS into LLVM IR - JavaScript Static Analysis Tool
https://sirjosh3917.com/posts/jssat-compiling-javascript-to-llvm-ir
Apache License 2.0
38 stars 1 forks source link

Errors building project, and question about use case #2

Open mdittmer opened 1 year ago

mdittmer commented 1 year ago

Greeting! I see that this project isn't currently under active development, but I have a couple questions I am hoping you might have time to answer.

Question 1: How can I get this to build

I tried building using cargo build and found that some File::with_options() needed to be replaced with OpenOptions::new(); that was straightforward. Then I found a series of errors related to (probably just out-of-date?) webpack, thread 'main' panicked at 'build artifactlibjssatrt.adoes not exist at/path/to/jssat/target/debug/libjssatrt.a`, and one big one roughly of the form:

error: failed to run custom build command for `jssat_frontend_js v0.1.0 (/usr/local/google/Projects/jssat/jssat_frontend_js)`

Caused by:
  process didn't exit successfully: `/usr/local/google/Projects/jssat/target/debug/build/jssat_frontend_js-5088213abf4c0837/build-script-build` (exit status: 101)
  --- stdout
  cargo:rerun-if-changed=./src/ecmascript/ECMA262Methods.lisp
  cargo:rerun-if-changed=./src/ast/parse_nodes.json
  debuggy:::
  Production {
[[lots-of-ast]]
  }

Suffice it to say that, if you have the time to do the minimal effort to get things building "out of the box", that would be great. For context, I have:

cargo --version
cargo 1.64.0-nightly (d8d30a753 2022-07-19)

Question 2: Does this project have solid source maps and language feature coverage for ECMAScript?

For my own purposes, I am hoping to use the simplified (JSSAT IR + Lifting BBs) IR to perform code analysis on "modern JavaScript" (which has a constantly changing definition, as I am sure you are aware). For reference, I am trying to improve on the following set up:

  1. Use SWC to compile "modern JavaScript" down to ECMAScript3 (with sourcemaps);
  2. Use TAJS to generate flowgraphs from ECMAScript3 code;
  3. Perform analysis on flowgraph nodes as an IR.

I am interested in cutting out the compile-down-to-ECMAScript3 part, but I need a simple IR that supports newer JavaScript to make the leap to a different IR.

Once I can get it building, would you say that JSSAT is in good enough shape to try programming against its IR in this context?

monoclex commented 1 year ago

Does this project have solid source maps and language feature coverage for ECMAScript?

Definitely not. My primary focus was getting a working prototype out as fast as possible with all the complexities involved in [abstract interpretation/symbolic execution], causing a significant tradeoff in code quality (the first prototype will never be perfect), and as such I've only done just enough to get function calls somewhat working (albeit completely to the spec!). Furthermore, source maps would be another significant undertaking in addition to the remaining stuff that has yet to be done.

Regarding your usecase, your analysis would be further complicated by the extreme amount of waste using a direct port of ECMAScript to JS would entail. For a program as trivial as a function declaration, there are pages upon pages of wasteful code - and I haven't even began to scratch the surface of implementing the totality of ECMAScript.

For example, the trivial program

function f(x) {
    x('Hello, World!');
}

f(print);

when ran (in release mode) as-is in the source (i.e. with collecting type information along the way) takes 30 seconds on my machine to complete. It collects 18533 different moments in time (roughly correlated to total instructions executed). The massive wad of IR code it generates sets up an AST with JSSAT IR objects, then executes it, going through the multitude of layers of abstraction for every instruction. Even something as simple as getting a property from an object is a huge amount of work. Needless to say, there would need to be an optimizer solely for the JSSAT IR to make your usecase (and the work of the JSSAT IR compiler) viable.

If you're curious, here's the JSSAT IR generated for the above program. Keep in mind that this is only meant to be in a prototype stage, so it should get better eventually.

How can I get this to build

Aside from correcting those errors as you mentioned, the other error is because the JSSAT Runtime wasn't built. If I had gotten further, that'd be used for things like talking to a garbage collector (which would theoretically be an optional part if enough analysis could be done).

cargo build -p jssatrt
(cd domino/webapp && npm i && npm build)
cargo build

Of course if you'd like to see the output from running the simple program with Domino, you'd need to modify the match statement in src/compiler/main.rs to start domino in the Ok(_) case, and also be sure you're running in release mode (which includes the jssatrt) so that it completes before the death of the universe.