Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Support pulling type information directly from .wasm modules #39784

Closed
wants to merge 7 commits into from

Conversation

weswigham
Copy link
Member

@weswigham weswigham commented Jul 28, 2020

To better support wasm modules under node's --experimental-wasm-modules flag.

In this PR, I add a new experimentalWasmModules typescript flag, which allows one to import .wasm files directly in TS code without us issuing an error (this is only supported at runtime in node using the node flag mentioned above). When enabled, we parse the contents of referenced .wasm files for their exported function names and types, and generate a declaration file on-the-fly in memory for it based on those types (and that declaration file is what we then bind/check against).

This is still very much a limited experiment, with only a small subset of possible features implemented thus far, but is far enough along to be able to show some new behavior:

assemblyscript_to_wasm_to_ts

In the above, on the left, I'm watch-rebuilding an assemblyscript program into a wasm module. On the right, I'm consuming that module in the editor, and getting live updates (with auto imports) as the backing .wasm module updates. Repo available here.

In any case, this should be a complete enough implementation to be able to gauge interest in the feature.

TODO:

  • Iterate on or amend our readFile compiler API so it can more easily return UInt8Array instances, rather than strings (since wasm file contents are most definitely not strings). (You'll note that right now I have a separate host API call for it, which is very painful). Pretty much our entire file pipeline is geared for strings only (especially in the language service) - this is probably the biggest practical blocker for this.
  • Issue parse diagnostics for malformed .wasm files (and introduce more early sanity checks on index bounds)
  • Traverse .wasm imports when building the program (wasm files may import other wasm (or JS?) files - while this has no bearing on the types of the exports, it may result in the inclusion of more files in the program (which may in turn impact declaration emit))
  • Introduce first-class i32/i64/f32/f64 subtypes of number and strongly check that the inputs/outputs of a wasm module are bounds-checked
  • Investigate how exported wasm globals, memories, and tables are exposed to a JS importer (if they are at all)
  • Actually emit the generated declaration file when declaration: true is set
  • Incremental .wasm parsing/tree reuse in the language service (I had to wholly disable incremental LS operations on wasm files to get the LS to function, since they both need nonstring file reads, and are not updatable with the normal incremental parser)

@weswigham weswigham added Breaking Change Would introduce errors in existing code Experiment A fork with an experimental idea which might not make it into master labels Jul 28, 2020
@typescript-bot typescript-bot added Author: Team For Uncommitted Bug PR for untriaged, rejected, closed or missing bug labels Jul 28, 2020
@weswigham
Copy link
Member Author

@typescript-bot pack this

@typescript-bot
Copy link
Collaborator

typescript-bot commented Jul 28, 2020

Heya @weswigham, I've started to run the tarball bundle task on this PR at 0f6b16e. You can monitor the build here.

@typescript-bot
Copy link
Collaborator

Hey @weswigham, I've packed this into an installable tgz. You can install it for testing by referencing it in your package.json like so:

{
    "devDependencies": {
        "typescript": "https://typescript.visualstudio.com/cf7ac146-d525-443c-b23c-0d58337efebc/_apis/build/builds/80811/artifacts?artifactName=tgz&fileId=1380FCF7BD82EFBC97A07E1949B757ECB181FE3000C238A5C485E5901051D6B602&fileName=/typescript-4.0.0-insiders.20200728.tgz"
    }
}

and then running npm install.

@trusktr
Copy link
Contributor

trusktr commented Jul 29, 2020

This would be amazing to have, especially for AssemblyScript users, but also anyone importing Wasm with type declarations. This would help reduce the barrier of entry for people wanting to try WebAssembly.

What would it do to existing JS projects that rely on number?

@trusktr
Copy link
Contributor

trusktr commented Aug 4, 2020

Related: #31713



//// [wasmImportsSimple.js]
import * as mod from "test.wasm";
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The emitted module specifier doesn’t look right.

Copy link
Member Author

@weswigham weswigham Aug 5, 2020

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The test harness strips the leading /.lib/ because it's on the real disk from the host machine (and has the corresponding full, real path) - it only does this in the test harness~

@weswigham
Copy link
Member Author

@typescript-bot pack this

@typescript-bot
Copy link
Collaborator

typescript-bot commented Oct 4, 2020

Heya @weswigham, I've started to run the tarball bundle task on this PR at 0f6b16e. You can monitor the build here.

@typescript-bot
Copy link
Collaborator

Hey @weswigham, I've packed this into an installable tgz. You can install it for testing by referencing it in your package.json like so:

{
    "devDependencies": {
        "typescript": "https://typescript.visualstudio.com/cf7ac146-d525-443c-b23c-0d58337efebc/_apis/build/builds/87299/artifacts?artifactName=tgz&fileId=61B1B6F57722D3FD3FAF0A139FA54A9A7D6B0ED73C303429C2A43A9235E7276F02&fileName=/typescript-4.0.0-insiders.20201004.tgz"
    }
}

and then running npm install.

@Jack-Works
Copy link
Contributor

Is it possible to extends this possibility to a set of public APIs that allow custom file types (e.g. CSS Modules, GraphQL, ...) to be able to generate in-memory declarations and join the incremental building / watch mode building?

Does this PR copy the .wasm file to the output folder like what tsc already did to the .json files?

@sandersn
Copy link
Member

This experiment is pretty old, so I'm going to close it to reduce the number of open PRs.

@sandersn sandersn closed this May 24, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Author: Team Breaking Change Would introduce errors in existing code Experiment A fork with an experimental idea which might not make it into master For Uncommitted Bug PR for untriaged, rejected, closed or missing bug
Projects
None yet
Development

Successfully merging this pull request may close these issues.

6 participants