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

Source maps applied to wasm binaries #1051

Open
wants to merge 10 commits into
base: main
Choose a base branch
from
Open

Source maps applied to wasm binaries #1051

wants to merge 10 commits into from

Conversation

dschuff
Copy link
Member

@dschuff dschuff commented May 2, 2017

This PR proposes applying source maps to wasm binaries. Source maps obviously have a lot of known limitations and are not a long-term debugging solution. However they are widely supported (including by emscripten for asm.js code) and based on conversations with Chrome and Firefox dev tools folks, my hope is that it will be easy and straightforward to adapt the existing dev tools code to apply to wasm binaries in the meantime, and bring wasm to parity with asm.js.

@kanaka
Copy link

kanaka commented May 2, 2017

Couldn't the wasm be disassembled to wast textual format and the links to the original source be attached to lines in the wast (rather than an offset into the wasm binary)? Or perhaps both?

Web.md Outdated
generate a stack trace). However existing developer tools implementations are
designed around the source map model of passing a URL from the VM to the dev
tools code, which fetches and interprets the information. Therefore it is
epxected that it will be much simpler to use "real" source maps than to design
Copy link
Member

Choose a reason for hiding this comment

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

sp: expected

Web.md Outdated

Source maps specify how to map a (zero-based) line and column position in
generated code to a file, line, and column location in the source. For
wasm binary locations, the line number is always 0, and the column number
Copy link
Member

Choose a reason for hiding this comment

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

You could use the generated "line number" as the function index instead (or perhaps just the defined function index, skipping imported functions), and the generated "column" as the instruction offset in the function. But I suppose it's best to align w/ what's being discussed here.

Is it worth mentioning this in some rationale?

Copy link
Member Author

Choose a reason for hiding this comment

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

Hm, On one hand the source map itself is not really meant to be read by humans. But if some tool displays it, then yeah I think it would make sense to display the offsets the way they'd be displayed in tools or browsers, yeah. And yeah it probably is worth mentioning. Maybe I'll do a PR for #990 too and add that to the rationale.

Choose a reason for hiding this comment

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

Using column number (vs line number) in JS source maps gives a really good savings, to be precise the size of the wasm bytes (the ; used to separate every encoded line and since we will have only one line, smaller number of column separators will be used)

Copy link

@yurydelendik yurydelendik May 10, 2017

Choose a reason for hiding this comment

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

We cannot use line number == 0 due to map encoding specifics. And 'source-map' library throws when line == 0. We need to change that to "the line number is always 1"

Copy link
Member Author

Choose a reason for hiding this comment

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

Fixed. I had thought I used 0 in my original prototype, but it was actually 1.

@dschuff
Copy link
Member Author

dschuff commented May 2, 2017

@kanaka IIRC In Chrome and Firefox, currently when displaying wast (instead of original source) the JS engine disassembles the wasm binary and passes the wast text to the devtools. Using source maps would mean the source would be displayed instead of the wast. So in that case you wouldn't need the wast at all.
Are you suggesting that the wast be generated offline, and then passed to the browser along with a source map? In that case we'd still need a way to link from the wasm binary to the wast. In that sense the wast would be sort of like a mapped source for the binary. But it wouldn't really save much because browsers would probably still want to have some support for the case where there is nothing but the binary. Which means they'd probably still have to support disassembling it themselves, so I would guess that passing the disassembly from the outside wouldn't really save anything or make things any simpler.

@RyanLamansky
Copy link

I was thinking a binary source map format designed for WASM specifically would be more desirable than re-using the JavaScript format. But I'm not a browser vendor so I'm not sure how troublesome that might be.

@dschuff
Copy link
Member Author

dschuff commented May 3, 2017

@RyanLamansky I agree that in principle a source-mapping format meant for wasm would not look like JavaScript source maps. However the intention of this convention is just to capture some really low-hanging fruit, because what we ultimately want is something much more capable than sourcemaps, and that will either have to be designed independently, or re-used from some other existing format (e.g. DWARF). So in one sense, this isn't worth doing at all if it isn't really simple, because it will be superseded, hopefully before too long. Therefore it should fit best with what browsers or devtools are already doing with source maps, which means that it would be nice not to require them to parse a format which is new, but also not the final form that we want.

Web.md Outdated
the URL is defined as in [RFC3986](https://tools.ietf.org/html/rfc3986) (e.g.
it must be percent-encoded if necessary) and it may be a data URI. The URL
is also resolved according to the source map spec, and may also be specified
with the `SourceMap:` HTTP header.

Choose a reason for hiding this comment

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

Is there a spec/reference to how HTTP headers will be associated with wasm module (assuming it's coming from Response)?

Copy link
Member

Choose a reason for hiding this comment

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

I would think this would only work for the new Response-taking compile and instantiate overloads.

Web.md Outdated
section named `"sourceMappingURL"` contains the URL.
As with source maps,
the URL is defined as in [RFC3986](https://tools.ietf.org/html/rfc3986) (e.g.
it must be percent-encoded if necessary) and it may be a data URI. The URL
Copy link
Member

Choose a reason for hiding this comment

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

This isn't sufficiently precise for web APIs; a real spec will need to reference http://url.spec.whatwg.org/

Web.md Outdated
it must be percent-encoded if necessary) and it may be a data URI. The URL
is also resolved according to the source map spec, and may also be specified
with the `SourceMap:` HTTP header.
The URL is defined as in the the WHATWG
Copy link
Member

Choose a reason for hiding this comment

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

the the

@jfbastien
Copy link
Member

@flagxor
Copy link
Member

flagxor commented Aug 23, 2017

Pinging this back to life :-)
Looks like this is waiting on some fixes from Derek.

@dschuff
Copy link
Member Author

dschuff commented Aug 24, 2017

OK, I think have addressed the comments, although I'm not 100% sure if @domenic had anything more in mind beyond what I did about URLs and resolution.

@domenic
Copy link
Member

domenic commented Aug 24, 2017

It seems reasonable given the general level of detail here. Thanks!

@yurydelendik
Copy link

Demo compiled using emscripten that is using source maps https://yurydelendik.github.io/sqlite-playground/src/playground.html (source at https://github.com/yurydelendik/sqlite-playground)

@tschneidereit
Copy link
Member

@codehag please invite @yurydelendik to this call, too.

@fitzgen
Copy link
Contributor

fitzgen commented Apr 25, 2018

As wasm can be run on mobile devices and we can't run DevTool there, so wasm should support some kind remote debug protocol, that allows debug wasm modules on mobile devices.
Will remote debug protocol be part of the wasm debug specification or it will be handled by each browser by own remote debugging protocol?

I expect wasm debug info and remote debug prototcols to be largely orthogonal concerns.

For example, the Firefox debugger used to apply source maps on the server side (ie the debuggee device) and has switched to applying them on the client side (ie the desktop displaying the UI). This tells me that they needn't be intertwined.

Did you have something in mind that requires them to be developed together?

@alexkozy
Copy link

alexkozy commented Apr 25, 2018 via email

@gskachkov
Copy link

@fitzgen Thanks for answer, I see now that my question is not related to current thread.

@ak239 offtopic I'm just curious, if proposal for dynamic service API, that you spoke about, will be part of the TC39 or W3C spec?

@codehag
Copy link

codehag commented Apr 27, 2018

I've created a doodle, please let me know of those times work / if we should alter the times a bit to make it easier for more to attend: https://doodle.com/poll/w7brfrgcbehv9zre

@codehag
Copy link

codehag commented Apr 30, 2018

Hi everyone. I will close the doodle on wednesday, so please make sure to vote for a date.

In the meantime -- I have created an agenda, please comment if you want to add or remove something from the discussion: https://docs.google.com/document/d/1mMFN-OksiJZm1PD3XmBpAVq0vhT0df1rGKwYq2jfn58/edit#

@codehag
Copy link

codehag commented May 2, 2018

Hi everyone, based on the votes we have a tie between Monday and Wednesday. I would propose that we do Wednesday so that we have a little more time to prepare, @chicoxyzzy would you be able to make it?

@chicoxyzzy
Copy link
Member

@codehag I'm not sure, but I can try.

@codehag
Copy link

codehag commented May 2, 2018

@chicoxyzzy In case you cant make it, and if there is anything you want to ask / propose please add it to the doc and we will make sure to cover it, there will be notes

hopefully you can make it!

@kumpera
Copy link

kumpera commented May 4, 2018

I'd love to join the call and Wednesday works great for me.

I'm currently working on doing C# debugging on top of WebAssembly and our current design aligns with the API proposals.

@dschuff
Copy link
Member Author

dschuff commented May 4, 2018

Hi Yulia, Sorry I've been out of office for a couple of weeks. I'm back now and any of those dates are fine for me.

@fitzgen
Copy link
Contributor

fitzgen commented May 5, 2018

Hello everyone :)

In preparation for our meeting next week, I've compiled a list of requirements for wasm debugging capabilities. I've tried to focus solely on the kinds of tooling and queries we would like to support, and completely divorce these requirements from their eventual implementation (static format vs language server vs combo of those vs ...) Rather than proposing a particular solution, this is an attempt to enumerate the requirements and constraints that any solution must satisfy.

This is what I've come up with: https://github.com/fitzgen/requirements-for-wasm-debugging-capabilities/blob/master/README.md

Let me know what I missed ;)

Looking forward to talking to y'all next week!

@codehag
Copy link

codehag commented May 7, 2018

Hey everyone, just a reminder -- meeting is at 7 pm CET (or 10:00am Pacific Time (PT)) on May 9th, there was a wrong date in the doc that i linked.

@codehag
Copy link

codehag commented May 7, 2018

Sorry again, its 10 AM* pt

@fitzgen
Copy link
Contributor

fitzgen commented May 10, 2018

Thanks again to everyone who came to the meeting today :)

I have completed my action item, a comparison between the requirements document and the "First version of DebuggingFramework.md" pull request. The comparison is here: fitzgen/wasm-debugging-capabilities#2

@alexkozy
Copy link

I just summarized my ideas about API instead of static format: here.
Mine doc is much less detailed than Nick's and I mostly would like to share initial thoughts that we have inside Chrome DevTools team about WASM debugging.

@auchenberg
Copy link

I'm late to the game in this thread. Kenneth here from VS Code. Our JavaScript debuggers are heavily dependent on sourcemaps, and we'd love to be a part of this conversation, and future meetings.

@codehag
Copy link

codehag commented May 14, 2018

@auchenberg hey kenneth! great! we will set up a dedicated communication channel for this. if you want to catch up with the meeting notes from wednesday, you can find them here: https://docs.google.com/document/d/1mMFN-OksiJZm1PD3XmBpAVq0vhT0df1rGKwYq2jfn58/edit#

@fitzgen
Copy link
Contributor

fitzgen commented May 16, 2018

Thanks for sharing @ak239!

Before we go too deep exploring different designs, I think we should focus on defining requirements before proposing potential architectures and solutions. This way we all have a shared, common understanding of the problems we intend to solve, and we can weigh any proposed solution or architecture against these requirements.

Everyone: please read through the requirements and file issues or send PRs for things that you believe are missing! :)

there are two type of clients: IDEs and static analysis tool

It seems that you are grouping browsers' developer tools (stepping debuggers, consoles, time profilers, etc) fall under the IDE umbrella, correct?

I've enumerated a non-exhaustive, but hopefully representative set of tools we would like to support. I don't currently have IDEs listed there, mostly because I'd like to get a better sense of which specific capabilities they need and what their requirements are, but I filed an issue for that here. If there are any folks developing IDEs on this thread, it'd be great to get your comments in that issue!


Here are some fairly unstructured thoughts while reading this, and thinking about the relationship between debugging capabilities and protocols:

  • Static debugging capabilitities are orthogonal to developer tools wire protocols. Supporting evidence is that Firefox DevTools used to apply source maps in the protocol server, and switched to applying them on the protocol client.

    +---------------------+                           +-----------------------+
    | Server @ wasm-level | --- apply debug info ---> | Server @ source-level |
    +---------------------+                           +-----------------------+
              |                                                  |
              |                                                  |
      send over protocol                                 send over protocol
              |                                                  |
              V                                                  V
    +---------------------+                           +-----------------------+
    | Client @ wasm-level | --- apply debug info ---> | Client @ source-level |
    +---------------------+                           +-----------------------+
    

    Whether we apply debug info and then go over a protocol, or go over a protocol and then apply debug info we end up in the same place. Therefore, why constrain ourselves by tying debug info and DevTools protocols together?

  • Dynamic debugging capabilities, on the other hand, must have direct access to the WebAssembly runtime. An extreme example: the only way to get the full list of frames currently on the stack of an interpreter written in Wasm (say Mono/C#) is to ask the running interpreter. A less extreme example: what is the current value of this arbitrary binding that is in scope?

  • The DevTools protocol is Web-centric. I fear that it embeds many Web-isms and JS-isms, and that the debugging capabilities would not be useful for non-Web Wasm embedders. 2.1.2. Must be embedder agnostic.

  • It feels unnecessary for a static analysis tool or code size profiler to even speak any protocol. It has the .wasm binary right there, why shouldn't it also have the debugging capabilities right there?

  • It seems that the primary benefit of using a protocol (or more specifically the Chrome DevTools protocol) is that there are a lot of existing consumers that we can give Wasm support with relatively little effort:

    In modern ecosystem a lot of IDEs (e.g. VSCode, WebStorm) use DevTools protocol (mostly Runtime and Debugger domains) to debug JavaScript, so adding support for new WebAssembly domain should be easy for them.

    However, we can realize this benefit without tying debugging capabilities to any protocol. If the debugging capabilities are applied on the protocol server—as is necessary for dynamic debugging capabilities anyways—then all packets on the protocol will be speaking in terms of the original source, not the generated WebAssembly code. Therefore, all existing protocol clients receive the benefits of the debugging capabilities without any effort on their part.

  • I believe this last point is similar to "Architecture B", but applying the debugging capabilities within the server, rather than as a protocol shim:

    +--------+                    +-------------------------------------+
    | Client | <--- protocol ---> | Server                              |
    +--------+                    |                                     |
                                  |  +--------------+  +-------------+  |
                                  |  | Debugging    |  | WebAssembly |  |
                                  |  | Capabilities |  | Engine      |  |
                                  |  +--------------+  +-------------+  |
                                  |                                     |
                                  +-------------------------------------+
    

@Becavalier
Copy link
Contributor

Becavalier commented Jul 4, 2018

@jfbastien @flagxor @binji
So, what‘s the current status of this spec design? It seems like this feature had already implemented in “Firefox Developer Edition“.

@codehag
Copy link

codehag commented Jul 4, 2018

@Becavalier the spec hasn't been implemented in firefox yet, however we do have debugging capability for wasm (I believe it has been since late last year / early this year). This is distinct from the spec.

With regards to the spec, @dschuff will present a proposal for a subworking group to the web assembly working group and there will probably be a repository opened for iterating on the specification there.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.