 Do you know what I did? Accidentally took my family to a strip club. Wow. Too long a story, though. So if you want to hear about that, go listen to the podcast. The branding, the branding. I mean, it's not going to be surprising that I've been working with WebAssembly. Have you been working with WebAssembly again? I've been working with WebAssembly a little bit, yeah. So there's a new proposal, because I think it's time that we talked about things that don't exist in WebAssembly yet. We've been doing that recently with other features, like the important things. So we're carrying on doing that. Good stuff to WebAssembly. Talk about stuff that doesn't exist yet. And we'll probably change by the time it does exist. Yep. So. OK. Good, good. Useful stuff. As such, WebAssembly interface types are a new proposal that basically consists of an explainer. So there's actually no spec text in there. It's a couple of examples. Oh, we've shipped stuff like that before. That's fine. Mozilla wrote a blog post on it, and therefore it's real. Right? Fair enough. Mozilla written. I'm happy. So I thought I'd start with the problem. Right. So this is how you currently use WebAssembly on the web. If you want to load a module, you fetch it, you throw it in to instantiate streaming, and you get back an instance. And on this instance, you can call the function that are exported from. Still really annoys me that this is a bit- I know. It really bugs you, doesn't it? That it takes a promise. Yeah, it should take a response, and you should await it. Anyway, sorry. So this is how it normally works. How it normally works. And that will not change. That will continue to work, because web. And we're recalling a function parameters 123. Great. Now, the bit that is a big pain point to many people is that 123 is pretty much as capable as WebAssembly is, and that it can only work with numbers. You can only pass numbers in and only get numbers back. And here's actually a screenshot from the spec that says, these are the values of WebAssembly can do. And they're integers and floats in different precisions. And that's it. That's all WebAssembly has to work with. And that's why, if you have something that takes a string, then you end up with them scripting or something similar, that's going to pack that into a memory. Exactly. A reference to memory, a reference to memory, whichever you want. Yeah, so let's say you have an instance of a module that expects a string in one way or another. Oh, I'm really glad I spoiled all of your supplies. This was a perfect segue, basically. Sorry, carry on. What you have to do is turn that string into numbers. And so one version of that is to turn a string into a series of UTF-8 encoded bytes, because that's a way to turn a string into numbers by agreeing on an encoding. So now you have a buffer full of numbers, and you have a length of the buffer. Now you need to, if you are assuming we're in C land, you have to tell C that give me a chunk of memory where I can put this in so that C knows that that piece of memory is now in use and shouldn't be used for anything else, so that the powerful program doesn't start overriding it. And that's what malloc is usually used for. And then you get back an address in the memory. And then you have to turn your WebAssembly memory into a UTF-8 array so you can actually write stuff in it. And then you have to use set to copy in the string. And then eventually, finally, you can call a function that does something with a string by passing in sad address. This is horrible. Hang on. Where is it? It is supposed to be overwhelming. Yeah. I'm overwhelmed. So because we need to tell, oh, OK. So this is the memory buffer. And so we're turning that into a UTF-8 array. And then we're setting that. OK, I follow now. I couldn't see how the Meme8 was actually part of WebAssembly, but it's because it's exported memory. So WebAssembly has a buffer. And then we turned it into, because that's just a series of bits, you need to decide on how you want to interpret those use of bits. In this case, a series of U and 8 of bytes. This is what we did in Squoosh to get the images into WebAssembly. So in this case, we take a string. We turn it into a UTF-8 encoded byte array and copy that into the WebAssembly memory. And it agreed upon location. Now, this is obviously not a great developer experience. No. And also, you need to know what your language expects because this is how C would do it. Rust would do it differently because they actually encode the length of the string into a data structure while C doesn't. And that's part of how it stops overflows. And Go will do it differently yet again. So it is really language dependent. And so what most languages currently do is that instead of giving you this, they give you so-called Glucode, which then you use to instantiate the module. And then you get a kind of wrapped instance that does all this magic under the hood. So with this, you're just able to pass in a string. And the code we just saw is basically now just hidden away and contains all the language-specific knowledge. And we end up with cases where the Glucode can be just as big, if not bigger, than the double-hasm system. Yeah, we've seen it with MScript. Now, MScript does a lot of work for you, more than just string encoding. So it's not like the size is uncalled for, but it turns out to be quite big. But this is kind of where you're like, well, WebAssembly can do numbers, but strings are extremely common in pretty much any language. So are probably lists or dictionaries or booleans. And all of these need to be mapped to numbers somehow. But again, every language is differently. So can WebAssembly at a standards level maybe make this easier? Oh, OK. And that is what interface types are. The name is not great. It's actually the third name, I think, of this proposal. So bear with me. I will explain the name. And then it will kind of make sense. But really what it is, it brings more types. It's just types. Types. Yeah, because when I heard interface, I was thinking of, well, typescript. And how it's more of a struct than the UI. Yeah, no. It is types for the module interface, as in the interface of the WebAssembly module. Oh, OK. Yeah, yeah, yeah. Interface types. So there is actually a little graphic in the explainer. So this is. Is this how babies happen? So. I mean, this is some science book, right? OK, come on, explain this to me. Right, so when you use WebAssembly, you usually get the blue bit. The blue bit is just like you have a module. The module has the types that WebAssembly knows, like the integers and the floats and functions. And you can call these functions with those types, the numbers. Now interface types are basically a adapter layer on top of this core module and gives the whole module a new interface. So if you have an interface type, the original module will be completely hidden from you. And instead, a new interface will be exposed to you as a developer that can use these high level types. Essentially at the glue code, yeah. But now the glue code, the stuff that translate from high level types like strings or dictionaries to low level, is bundled with the WebAssembly module. As wasm. As wasm. Right, OK, OK. So because it is inherently language specific, it's not necessary if something can be reused. A C module will have to use different adapter code than a Go module or a Rust module. And so it's packaged within the WebAssembly binary. And whenever you call a high level function with a string, then these adapter codes will run first, translate all the parameters and or return values, and then call the old core module function. So it is actually just like a completely abstract layer on top of the old interface. So with that in place, what you can do, especially instantiate a module and call it with a string, which as a function is now much nicer and much more convenient, there is obviously a question about progressive enhancement, because we have now reached the point where browsers ship new WebAssembly features at different paces. Threads, SIMD, all this stuff is on its way. And that's the start. Like I think Chrome is the only one with threads so far, because the Shared Ray Buffer thing is really complicated for some browsers to actually ship. SIMD is probably going to be similar in that we ship it first and then others might catch up. But it's not going to be a synchronized launch as it was with WebAssembly MVP. And even SIMD is like there's multiple levels of SIMD support. Yeah, OK, OK. Now for the progressive enhancement, I actually envision that something like this will be a fairly common pattern where you instantiate your module, then do a quick check if this browser has interface type support. And if not, you basically fall back to the old glue code pattern, which means that only if you have an unsupported browser, you have to load that additional piece of JavaScript. So hang on. So if this instantiate thing, so this is going to be a fetch of a resource possibly, so is the idea that is it compatible in a way where if an older browser loads the thing with the glue code, it ignores the glue code? It's so it's bundled within. It's an annotation. And so if a browser doesn't have support for this special type of annotation, these sections are just skipped and ignored. Right. And that was very much a core part of WebAssembly that they have support for custom sections, as they called, which can give an arbitrary name. And only if the browser has, I know what this name means, it will actually start respecting that custom section in the WebAssembly binary. And it doesn't fail if it doesn't. Right, OK, OK. And so in this way, it will basically mean that only the browser don't have interface type support will actually pay the cost of the glue code. Or actually, it might not just be glue code, but just a generic interface type polyfill that is also being worked on. So that will be kind of nice. Yeah, I like it. Now, I've only talked about strings because literally every other type is in a to-do section on the experience. That's how early we are talking. The mechanism has been kind of like sounded out and kind of explored, but it hasn't actually been specified on how other types would work. And that's what they're going to still have to figure out to actually make this real. But I still think it's kind of interesting to talk about. Now, for example, one thing that would become better is we use high level types in Scrooge, quite a bit in our WebAssembly modules, because we have codecs that, A, take an image, it's a fairly high level type. And usually, options for the codec and quite the substantial set of options. So what we have is a struct in C++ land. Yeah, so we have an encode function, for example, on our ModsJPEG WebAssembly module that takes, A, the image, and B, just a set of options. And these things would now just work with WebAssembly, which is really cool. And then, of course, it's up to the language to define how does a JSON object like this actually map to something that is good in my language? Like in Rust, it would probably be a struct in C as well. But in Go, it might be something different, or maybe Python at some point. Every language now is in control on how these things get mapped to their native types. Nice. And another thing, which actually is really nice, because it's not just about developers calling functions. It's also about this thing that we see in Squoosh in that we have image data, and we basically just pass it back and forth between JavaScript and different WebAssembly modules. We used a set of script to rotate images. We used a Rust code to resize images. Then we used C code to actually compress the image. And that's sort of jumping back and forth between JavaScript types and Glue code and WebAssembly and back. If interface types actually become a thing, we could actually live in a world where this is possible. Interesting. Because these types are defined completely abstract without an actual implementation detail. So strings and lists are just that, and not much more is defined about them. And so that means now we can pass a string from assembly script to Rust without having to go via JavaScript, because both modules will contain the code to translate. OK, so this Glue code isn't just about turning a string into something the language understands. It will do the reverse as well. So this will work for return types, right? Which I think is very interesting. Exactly, so there's the concept of lowering values and raising values from a high abstraction to a low abstraction and back. And so if a assembly script function returns a string and the Rust function accepts a string, we can actually do a fast path and skip the whole JavaScript in between. So it'll be, I guess, yeah, like you say, it's going to be a finite set of types, right? As far as I can tell, it's basically going to be roughly JSON, all the types that JSON can do plus a couple of extra bits. Because another old proposal that has been merged into this is the Web IDL proposal. So what that would allow us, this was a perfect setup, is that with interface types and a proposal called anyref, which allows WebAssembly to hold on to anything from JavaScript lands and even call functions on it, we could now do the thing that so many people want is have the DOM in WebAssembly. And that we can just basically give the entire document object to WebAssembly and be allowed to call functions, because now we have a way to communicate with strings and objects. Oh, interesting. And so while you won't have access to the actual low-level DOM item, you have a reference to it and you can call functions on it. And as long as one of these interface-compatible types is being returned or accepted by the methods, you can actually communicate with that now. And so something like createElement, you can now call that from WebAssembly without glue code, because strings are a thing. And with anyref, you can call that function. And so now you kind of have DOM or other APIs in WebAssembly. Nice. So in Scrooge, we use image data a lot. So I guess that's one of the types that's unlikely to be mapped. So we would just use a unitate. I mean, it maps very easily to a JSON object. With height data is really what image data is. So that would just be a struct with these three properties. And we just have a very small wrapper at the end that is just create the new. So for example, I think all the array buffer types will also be supported by interface types, because that's fairly easy to map to a piece of memory, right? Yes. It will probably be a copy, because. WebAssembly memory and JavaScript memory. But copying a chunk of memory is a fairly fast operation anyway. So I mean, now that you say that, there is an upcoming proposal about allowing multiple memories in a WebAssembly module. So maybe we could even just mount a memory into WebAssembly so that there's no copy, but you actually have a reference to it now. And I've heard one of the use cases for this is to create where you could have a section of memory that is essentially an M mapped file. Yeah, exactly. So now it wouldn't have to be like, oh, we reserve a piece of a part of the old memory, but just create a second piece of memory that is completely independent from the main memory. And you just have to figure out which memory to work on with your instructions. So yeah, this is, I think, really cool. I think most of this will be taken care of by compilers of languages who will just basically give you now a module that suddenly accepts a string, and there's nothing for you to do to make use of this new API. But I think the doors it opens is going to be really interesting for WebAssembly. Nice. And it's going to be a while, though. Look, I was really happy there in the magazine. I'm super excited about this. By the time you retire, you might get to play with this. I have no idea how fast it's going to be, but I'm going to keep a close eye out, and I'm going to be tweeting like crazy once we can play with this in Canary. Looking forward to that. There were people at ViewSource. Good, because that's what a conference needs to really work. And they were like, wait, you do a podcast. They were like, talk to me about the videos, and I'm like, you don't watch the videos. We need to advertise the podcast more, just like this.