13 ms·
Asm.js: a strict subset of js for compilers – working draft
- dakimov 14y agoI've had similar ideas back when BlackBerry was popular with its Java-only SDK in order to port our huge C++ app, and also when Windows Phone was C#-only. Eventually it's worked itself out, as C++ has become available everywhere. Nevertheless, if they succeed, the same thing can be easily made for Java and C#, so we can make our C++ app ultra-portable. It will be an absurd toolchain though. People are so unable to communicate and adopt standards as if they were retarded. Sophisticated solutions atop idiotic problems. It's actually the slogan of the overall field.
- onassar 14y agoAny thoughts on where this could be useful? The context and purpose of it goes a little over my head.
- kevingadd 14y agoIt lets a cross-compiler like Emscripten (and theoretically more weird ones like JSIL, GWT, etc) generate JavaScript that can be jitted into code that has performance (and semantics) closer to native code. So, for example, you can provide clear hints that value x should be an int32, value y should be a float, etc. And if you create a virtual heap out of a Typed Array, asm.js lets you ensure that the JIT maps uses of that array to direct memory accesses where possible (instead of bounds-checked array lookups).
- dherman 14y agoCompilers like Emscripten and Mandreel, which already generate code similar to asm.js, can be modified (we already have it implemented for Emscripten, it's not a big change) to generate valid asm.js. Then engines that recognize it can optimize the code even further than existing optimizations. Some of the technical benefits: * ahead-of-time compilation and optimization instead of heuristic JIT compilation * heap access can be made extremely efficient, close to native pointer accesses on most (all? still experimenting) major platforms * integers and doubles are represented completely unboxed -- no dynamic type guards * absolutely no GC interaction or pauses * no JIT guards, bailouts, deoptimizations, etc. necessary But the bottom line here is: asm.js can be implemented massively faster than anything existing JS engines can do, and it's closing the gap to native more than ever. Not only that, it's significantly easier to implement in an existing JS engine than from-scratch technologies like NaCl/PNaCl. Luke Wagner has implemented our optimizing asm.js engine entirely by himself in the matter of a few months. As the site says, the spec is a work in progress but it's nearly done. Our prototype implementation in Firefox is almost done and will hopefully land in the coming few months. Alon Zakai is presenting some of the ideas at http://mloc-js.com http://mloc-js.com tomorrow, including an overview of the ideas and some preliminary benchmarks. We'll post his slides afterwards.
- espadrine 14y agoAre there any thoughts on debugging this kind of code? How do we know that the code was correctly treated as asm.js, and if not, can we know why?
- dherman 14y agoThe code has to be explicitly marked as asm.js, using a pragma similar to ES5 strict mode. This way if the code fails to validate, the errors can be reported to the browser's developer tools. As for debugging, the story is the same as Emscripten. I believe there's plenty of work to do to make it better, but it's no different than the existing state of affairs. All we're doing is formalizing existing practice so that engines can capitalize on it and optimize better.
- pcwalton 14y agoIt's basically a way to ship native code on the Web that's compatible with existing browsers, with the same performance as native code in engines with full support for it. (Getting to complete parity with native code will take time, but the language has been carefully designed to allow that — and we're close already.)
- mhd 14y agoReminds me a bit of efforts like C--, which sought to seek a simpler pseudo-assembly used as some kind of intermediate language for compilers. But those efforts never gained much traction, whereas I think that some transpilers actually exploited a few features beyond even normal, full-fleged C -- namely GCC extensions -- to make some features easier and/or faster (it's been a while, but it was probably some trampolining optimization). Let's see how it turns out. As for something completely different, I've always wondered how it would be to program a webapp in a rather different language than JS -- most transpiled languages aren't that fundamentally different from JS. And Emscripten seems mostly used to port some code that "runs in a box". Wonder how far one could come doing some stereotypically Web 2.0 things in e.g. Pascal.
- aaronblohowiak 14y agoElm and Roy are quite different in that they abandon normal js semantics.. as far as going to a more blub language, please do report your experimental results!
- swannodette 14y agoClojureScript is also quite different from JavaScript - http://himera.herokuapp.com/synonym.html http://himera.herokuapp.com/synonym.html
- mhd 14y agoThat's mostly what I was talking about, programming in a more restrictive language, probably strictly imperative, without closures etc.
- nnethercote 14y agoIf C-- had been a subset of C, then it would be more comparable. Having immediate compatibility with existing implementations makes adoption vastly easier.
- tachyonbeam 14y agoSitting about 10 feet away from Luke Wagner right now. He has told me that asm.js is Mozilla's response to NaCl. You compile code with Clang (or another compiler) into the asm.js subset of JavaScript, which they know how to optimize well, and their JIT compiler will offer you performance very close to that of native C (they claim a factor of at most 2x). They use special tricks, like (a+b)|0, to force results to be in the int32 range, and avoid overflow checks. The heap views uses multiple typed arrays pointing to the same data to give asm.js code a typed heap of aligned values, avoiding the JS garbage collector (you can manage this heap as you wish). They already have sample apps, including some using libraries like Qt (I believe OpenGL as well), compiling to asm.js. I believe it has potential, so long as they have good support for standard and common C libraries (i.e.: porting to asm.js is almost effortless).
- duaneb 14y ago> They use special tricks, like (a+b)|0, to force results to be in the int32 range, and avoid overflow checks. Why is this not seen as the worst idea ever? Why this great resistance to moving away from javascript?
- mccr8 14y ago> Why this great resistance to moving away from javascript? To what? What scenario do you envision where Apple, Google, Microsoft and Mozilla are all willing to implement a single new language for the web?
- duaneb 14y ago> To what? What scenario do you envision where Apple, Google, Microsoft and Mozilla are all willing to implement a single new language for the web? Well hopefully we wouldn't make the same mistake again by going with a language and we would just implement a VM on which JS is implemented. It would be much easier to validate the correctness of a VM anyway, achieve better speed than was possible before, and not tie people down to a (painful) language. On a personal note I would actually start to view the web browser as a platform instead of a bunch of tangled strings, cans, and tape. EDIT: I didn't answer your question. But, as a developer, I will only move to the web for my default programming language when I have bytecode or assembly to look at, not some convoluted scripting language. Hopefully, Asm.js is a minor, minor bump on the way towards the browser as a usable platform for arbitrary development.
- niggler 14y agoWhat happened with javascript in pypy? I thought they were working on the restricted subset suitable for static analysis.
- tachyonbeam 14y agoYou mean this: http://www.formal-methods.de/mediawiki/images/e/e5/Bachelor_zalewski.pdf http://www.formal-methods.de/mediawiki/images/e/e5/Bachelor_... ?
- juiceandjuice 14y agoThis is the same concept.
- shanselman 14y agoMadness! ;) http://www.hanselman.com/blog/JavaScriptIsAssemblyLanguageForTheWebSematicMarkupIsDeadCleanVsMachinecodedHTML.aspx http://www.hanselman.com/blog/JavaScriptIsAssemblyLanguageFo...
- dherman 14y agoDon't think I haven't explicitly referenced you in my talks already! :D http://vimeo.com/43380479 http://vimeo.com/43380479
- adamnemecek 14y agoI've become increasingly convinced that a standardized VM in the browser that other languages could target would be the best idea. And we could forget that the whole JS thing ever happened.
- jws 14y agoLLVM byte code in an OS secured jail/sandbox? The JIT is already there and BSD licensed so all the players can use it. You'd really have to trust your sandbox though. The API for what you what you can do out of your sandbox would be the hard part. Every capability you add to the API is also a lurking attack vector in each implementation.
- adamnemecek 14y agoMicrokernels in the browser to the rescue :-). But yeah, I had something like that in mind. I do realize that getting security right would be tricky, but I'm not sure if it would be that much trickier than say the security of any given JS engine. Since the semantics of said VM would be probably simpler, I would make the argument that getting the security right would be easier to do than the security of said JS engine.
- cbhl 14y agoIt sounds like you want Chrome's NaCl.
- lucian1900 14y agoYou're describing PNaCl.
- jws 14y agoThere was a company in the '90s that was working on a byte code representation of programs which was designed to be “optimally” small by encoding more at the AST level than the ASM level. There were papers, but they were acquired by Microsoft (I think) and vanished. Does anyone remember them? The papers would be interesting in light of this, and conveniently near the end of patent lifetimes if patented and solid prior art if not. Edit: Maybe I'm thinking of Michael Franz and Thomas Kistler's work on “Slim Binaries”. It matches the content if not the ambiance that I remember. It's been a while. My brain tapes could have print-through. “A Tree-Based Alternative to Jave Byte-Codes” http://www.ics.uci.edu/~franz/Site/pubs-pdf/C05.pdf http://www.ics.uci.edu/~franz/Site/pubs-pdf/C05.pdf “Adaptive Compression of Syntax Trees and Iterative Dynamic Code Optimization: Two Basic Technologies for Mobile-Object Systems” http://www.ics.uci.edu/~franz/Site/pubs-pdf/BC01.pdf http://www.ics.uci.edu/~franz/Site/pubs-pdf/BC01.pdf
- JoshTriplett 14y agoI like the idea of this, but it bugs me that it still uses doubles and only simulates integers via optimizations in the JavaScript compiler. Why has no JavaScript extension arisen to supply real integers? One notable side effect of this: asm.js only seems to support 32-bit integers, not 64-bit or larger integers.
- kevingadd 14y agoJS has 'real integers', they're not being simulated. If you put the appropriate hints in your JS the JITted output will never use a float anywhere. Your complaint is more that all the operators (with the exception of the bitwise ones) operate on floats, and yes, that is kind of a problem. 64 bit integer support is being worked on for JS elsewhere; asm.js probably doesn't offer it yet since you can't use 64 bit ints in any browser yet.
- dherman 14y agoThat's true, but JoshTriplett has a reasonable point. In point of fact, we are discussing custom value types like int32 and uint32, as well as compound value types like immutable records, for the future of ECMAScript: http://wiki.ecmascript.org/doku.php?id=strawman:value_objects http://wiki.ecmascript.org/doku.php?id=strawman:value_object... But standardization takes time, and we wanted to get asm.js working now. In the future if ECMAScript gains these other features we'll happily incorporate whichever ones make sense. For example, if having more straightforward syntax can help decrease code size that's a clear win. (Though gzipping source tends to mask a multitude of sins.)
- AshleysBrain 14y agoAny thoughts on whether there could be a JS -> Asm.JS compiler? Might be a handy way to get rid of GC pauses - and maybe even improve performance - for existing JS code. Or even a JS -> Asm.JS compiler written in JS... so you can feature-detect and enable on demand :)
- tachyonbeam 14y agoYes, you could comple JS to asm.js, but then, unless you change the JS semantics, you'll have to implement a GC, and your GC might have pauses. Note that an interesting possibility would be to be able to generate asm.js at run-time for a domain-specific language. You could easily implement this as a JS library.
- azakai 14y agoIt would be very hard to compile regular JS to asm.js: It would be exactly as hard as compiling regular JS to C, in fact. The problem is you don't know the types of everything. However, some regular JS might be easy to compile to asm.js. For example a matrix multiplication library.
- btipling 14y agoCan it still be considered a 'subset' if it adds new traits like 'int' and 'intish'? If it both adds and remove things wouldn't that make it more of a variant like scheme is to lisp?
- dherman 14y agoYes, the observable semantics is 100% identical to running the same code in an existing JS engine. That's the genius behind Emscripten (i.e., the genius of Alon Zakai) -- he figured out that you can effectively simulate the semantics of machine integer operations by exploiting the various parts of the JS semantics that internally does ToInt32/ToUint32 on its arguments. What asm.js is simply formalize those tricks in order to guarantee that you're only using those parts of the JS semantics, so that it's sound for an optimizing engine to directly implement them with machine arithmetic and unboxed integers. But the behavior is absolutely identical to a standard JS interpreter/JIT/etc.
- edtechdev 14y agoIt's still a bit surprising that types were never (and still haven't been) added to javascript, as proposed for javascript 2.0 back in 1999: http://web.archive.org/web/20000817085058/http://www.mozilla.org/js/language/js20.html http://web.archive.org/web/20000817085058/http://www.mozilla... Now we have Google's Dart & Closure compilers, Microsoft's TypeScript, and Mozilla's asm, all of which essentially add types back to javascript, not to mention about two dozen other statically typed javascript compilers: https://github.com/jashkenas/coffee-script/wiki/List-of-languages-that-compile-to-JS https://github.com/jashkenas/coffee-script/wiki/List-of-lang... If types were approved 13 years ago, javascript apps could have been made to run much faster (fast enough for games even), perhaps negating a need for 'native' mobile apps that we have today, and either hastening the demise or spurring the optimization of competitors like Flash and Java and .NET/Silverlight. (I'm already aware of arguments against static typing, and against having a VM in the browser or treating javascript like one.)
- dherman 14y agoIt's a lot harder to add types to a general purpose programming language. Your types have to match actual programming idioms, and if you care about them being safe (which, to be fair, recent languages like Dart and TypeScript don't), you have to consider every possible loophole that could lead to a dynamic error -- and the legacy language fights you, because all of its dynamism was designed back when nobody was thinking about respecting some not-yet-existent type system. The type system for asm.js is a far more restricted problem, which is why we were able to come up with a solution so quickly (we only started this project in late 2012). The type hierarchy is extremely spartan, and it's just designed to map a low-level language (intended for compilers to be writing in) to the low-level machine model of modern computers.
- kevingadd 14y agoAdding a static type system to JavaScript would have, IMO, been a losing effort. You can take a look at ActionScript 3 for an example of the challenges that come up. Once you've got a static type system, you need a GOOD static type system, and imposing one of those on JS without breaking backwards compatibility would have been an ordeal and complicated code tremendously.
- willvarfar 14y agoThe cool thing is that those of us who have small performance-critical javascript routines e.g. game engines have a whole new cheatsheet of 'optimal' javascript. I can't wait for box2d, octrees and matrix libraries to adopt it; a whole new generation of hand-optimised assembler!
- shardling 14y agoLast I read up on it, the version of box2d compiled with emscripten performed a lot better than any of the "hand tuned" js versions! :)
- juiceandjuice 14y agoAKA RPython for Javascript
- msvan 14y agoThis seems more realistic than Google's grand plans of displacing JavaScript with Dart. Let's hope it gains traction!
- spankalee 14y agoThis would probably help the Dart effort a lot by providing a sane compilation target.
- evilpie 14y agohttps://bugzilla.mozilla.org/show_bug.cgi?id=840282 https://bugzilla.mozilla.org/show_bug.cgi?id=840282 has some measurements on how fast the implementation of asm.js (called OdinMonkey) already is. "sm" is SpiderMonkey, that is the normal JS engine. v8 is Chrome's JavaScript engine. Current results on large Emscripten codebases are as follows, reported as factor slowdown compared to gcc -O2 (so 1.0 would mean "same speed") odin (now) odin (next) sm v8 skinning 2.80 2.46 12.90 59.35 zlib 2.02 1.61 5.15 5.95 bullet 2.16 1.79 12.31 9.30
- shardling 14y agoI kinda hope that someone at Mozilla keeps a count of just how many monkeys have gone into the code base. Off the top of my head, there's SpiderMonkey, TraceMonkey, JagerMonkey, IonMonkey, ScreamingMonkey, IronMonkey, and perhaps you should count Tamarin. It would be neat to see mascot like versions of them all... :)
- evilpie 14y agoWe have/had t-shirts and posters for JägerMonkey and IonMonkey. https://secure.flickr.com/photos/vikingkarwur/8312701001/ https://secure.flickr.com/photos/vikingkarwur/8312701001/
- nnethercote 14y agoI've never heard of ScreamingMonkey or IronMonkey, and I'm a member of Mozilla's JavaScript team...
- grayrest 14y agoI've never heard of IronMonkey but ScreamingMonkey was at least planned as a Tamarin replaces js engine in IE project: https://wiki.mozilla.org/Tamarin:ScreamingMonkey https://wiki.mozilla.org/Tamarin:ScreamingMonkey
- shardling 14y agoIronMonkey was apparently for "mapping IronPython and IronRuby (and maybe IronPHP) to Tamarin". I just vaguely recalled seeing the name pop up in a Mozilla related context -- I certainly couldn't have told you what it was without looking it up. :) https://wiki.mozilla.org/Tamarin:IronMonkey https://wiki.mozilla.org/Tamarin:IronMonkey
- frozenport 14y agoWill Javascript become Java?
- cromwellian 14y agoThis seems very much targeted at emscripten and not to cross-compilers that start with GC'ed languages like GWT, Dart, ClojureScript, et al. If you are cross-compiling Java or C# to asm.js, you don't really want to manage memory manually. I work on GWT, and asm.js as an output target is very interesting to me (I've worked on a number of performance Web games using it, GwtQuake, AngryBirds, etc), but the starting assumption is GC, so I want to leverage non-boxed numerics, and all of the other nice stuff, but don't want to stuff everything into a TypedArray. It's also unclear to me how this solves the problem of startup time on mobile. A giant glob of Javascript takes a non-trivial amount of time to load even on today's fastest smartphones. The spec seems to argue that Browser VMs could recognize asm.js and if I read between the lines, employ snapshoting the app and caching it for later quick startup? In all likelihood, the majority of asm.js outputs would be actually be non-human readable output of optimizing cross-compilers, so there isn't much benefit from having a readable syntax that humans could read, so what's the real justification for using JS as an intermediate representation over say, a syntax specifically designed for minimum network overhead and maximum startup speed? Seems like it might be worthwhile for Mozilla to also work on efficient representations of asm.js that minimize this overhead. The usual response is minify + gzip, but it's not a panacea.
- azakai 14y ago> This seems very much targeted at emscripten and not to cross-compilers that start with GC'ed languages like GWT, Dart, ClojureScript Those languages can benefit as well (but might not make sense in all cases). You can compile Java to C and then to JS, here's a demo http://xmlvm.org/html5/ http://xmlvm.org/html5/ Yes, this has downsides like compiling your own GC. For GC heavy code it might be slow. But for raw computation you would probably get faster results than source-to-source like GWT does - you get LLVM optimizations, and you get asm.js which is easier for JS engines to run quickly. > It's also unclear to me how this solves the problem of startup time on mobile. Yeah, that is a problem. It's a problem on normal JS too, and also for things like PNaCl. Only shipping final native binaries can fully avoid that (but that is nonportable). > The spec seems to argue that Browser VMs could recognize asm.js and if I read between the lines, employ snapshoting the app and caching it for later quick startup? Yes, that is one possibility. It could work for normal JS too, I'm not sure why it hasn't been done yet. Worth investigating. > In all likelihood, the majority of asm.js outputs would be actually be non-human readable output of optimizing cross-compilers, Yes. > so there isn't much benefit from having a readable syntax that humans could read, so what's the real justification for using JS as an intermediate representation over say, a syntax specifically designed for minimum network overhead and maximum startup speed? The justification is that asm.js code will work, right now, in all browsers. (And it can fairly easily be optimized by them to run much faster than compiled code in JS.) Any new format would require standardization and take a long time. asm.js is just JS. For network transmission, we should implement a special minifier for it (written in JS of course).
- rntz 14y agoThe fact that you can't represent function pointers (not closures, just plain old C-style function pointers) in asm.js severely limits its usability as a target language for even C-like languages.
- marijn 14y agoCan you explain the use case where you need need function pointers but closure pointers won't do?
- rntz 14y agoOh! Closure pointers would absolutely suffice. But as far as I could tell, asm.js doesn't support closure pointers either. Obviously I could use a value of "unknown" type to pass them in, but section 2.1.9 says "Since asm.js does not allow general JavaScript values, the result must be immediately coerced to an integer or double." So I'm under the impression that asm.js can't really deal with closures or functions as values. Am I reading the docs wrong? I hope I am.
- evincarofautumn 14y agoLooks like it’s in the works. https://github.com/dherman/asm.js/issues/4 https://github.com/dherman/asm.js/issues/4
- deleted 14y ago[deleted]
- pjmlp 14y agoCan we please replace JavaScript or use a proper VM instead of this nonsense? Or better yet, just use native applications.
- MatthewPhillips 14y agoLove it. When can we expect a JavaScript to asm.js compiler?
- evanprodromou 14y ago@dherman The document says, "extraordinarily optimizable". Do you have any numbers on that? I'd love to see benchmarks from running asm.js-compatible JavaScript on e.g. SpiderMonkey versus an asm.js-optimizing SpiderMonkey. Are we talking about incremental differences of 5%, 25%, even 50%, or orders-of-magnitude improvement?
- marijn 14y agoSee evilpie's comment below.
- kibwen 14y agoevilpie posted some numbers below: http://news.ycombinator.com/item?id=5227841 http://news.ycombinator.com/item?id=5227841 and I'll reproduce the salient points here: odin (now) odin (next) sm v8 skinning 2.80 2.46 12.90 59.35 zlib 2.02 1.61 5.15 5.95 bullet 2.16 1.79 12.31 9.30 https://bugzilla.mozilla.org/show_bug.cgi?id=840282 https://bugzilla.mozilla.org/show_bug.cgi?id=840282
- jlebar 14y agoHave you guys thought about memory management in the ArrayBuffer "heap"? One can decommit pages from a real heap, which can be a pretty important optimization.
- deleted 14y ago[deleted]
- SparrowOS 14y agotower of babbel
- likeclockwork 14y agoWow. The devs at Mozilla are really working it. I mean, with empscripten, Firefox OS, Firefox browser, and now asm.js... they're about to force everyone onto their own terms. This is clearly a big move and the beginning of a major victory for Mozilla and all users and developers. Serving native apps, in the browser, with JS. And everyone is going to have no choice but to follow them, because all other browsers will fallback to their regular JS interpretter/JIT if they don't optimize on asm.js. We're talking games and applications that will run an order of magnitude faster on Firefox than in other platforms out of the gate. But they'll still run everywhere, just very slowly.
- halacsy 14y agofirst announcement of asm.js in Budapest on @mlocjs
- ksec 14y agoWould asm.js reduce JS memory usage? Would non computational scripts benefits from this? Things that are widely used like jQuery.