5 ms·
WASM is not designed to work around the shortcomings of C. The fact that nowadays the program crashes with a segmentation fault error after a null pointer deref
by s-macke 4y ago
WASM is not designed to work around the shortcomings of C. The fact that nowadays the program crashes with a segmentation fault error after a null pointer dereference is only because modern operating systems are being nice to you.
But a proper error handling can still be implemented into WASM. Maybe, the following proposal on memory control will add the option:
https://github.com/WebAssembly/memory-control/blob/master/proposals/memory-control/Overview.md https://github.com/WebAssembly/memory-control/blob/master/pr...
- kllrnohj 4y ago> WASM is not designed to work around the shortcomings of C. That's not the question. The question is why was WASM designed to be hostile to C (or C-likes)? There's seemingly no benefit since WASM has to be relocated anyway, the actual memory addresses aren't 0x0 after all. So the WASM runtime is already doing an offset. Therefore there's no cost (and seemingly no implementation burden) to not starting at 0x0, so why would you? Why would you be aggressively hostile to what's going to almost certainly be your 2 largest users?
- tcfhgj 4y agoC# has introduced nullables; safe Rust simply doesn't have nullptrs
- erichdongubler 4y agoNitpick: Safe Rust [_does_][0] let you construct null pointers -- it's _dereferencing_ them that's not allowed in safe Rust. [0]: https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=800d015d6a7facf22209bf708c1e1d76 https://play.rust-lang.org/?version=stable&mode=debug&editio...
- OskarS 4y agoMy guess is probably that it's performance issue. You would have to do a `if (addr == 0) trap()` branch on EVERY memory access in the WASM runtime, which is not free. I guess it would still has to do some kind of bounds check to see that you're not overflowing your allotted buffer, but I could imagine that adding that kind of null-check to every memory access is not something you just get for free. The other option would maybe be to make the entire first page of memory non-readable, and then have the MMU execute the trap for you (this is how real OSes does this null check, right?), but then you're wasting 4kb in every WASM runtime. Doesn't seem ideal. I agree with you, this is a real shame, and it's going to lead to a LOT of bugs that would have been discovered otherwise. But I can see the reasoning why you wouldn't do this in WASM.
- deleted 4y ago[deleted]
- sudosysgen 4y agoYou can use the MMU of the CPU to trap a null pointer dereference for free.
- kevingadd 4y agoNot all execution targets for wasm can do this.
- sudosysgen 4y agoThere are very few such targets, thus they will simply have to pay the extra cost. It's a very, very good tradeoff to make. If you're trying to get every ounce of performance out of a CPU lacking very basic memory management facilities, it's probably a good idea not to use wasm.
- kllrnohj 4y ago> The other option would maybe be to make the entire first page of memory non-readable, and then have the MMU execute the trap for you (this is how real OSes does this null check, right?), but then you're wasting 4kb in every WASM runtime. Doesn't seem ideal. You're only wasting virtual address space, not actual RAM. So the only cost is your max memory possible decreases by 4kb. Hardly a noteworthy expense. And this is an expense that WASM runtimes already have to spend anyway, since none of them are running on bare metal with address 0x0 being available to them. So there's already address translations in play. Multiple of them, in fact, as you have to first translate from the WASM heap to the host's address space, and then from that through the MMU to physical pages. And of course the WASM runtime already needs to trap for invalid addresses (eg, -1 right out the gate). How would trapping the first few pages be any more expensive than any other unmapped range? You're still working with a single contiguous region (at least until mmap finally lands). There doesn't seem to be any benefit to starting from 0x0 vs. starting from any other constant.
- s-macke 4y agoYes, even in the proof of concept, you could have simply added an offset parameter when defining the memory area. They did not.
- josefx 4y ago> WASM is not designed to work around the shortcomings of C. Memory access protection on modern systems is not about C segfaults. But if WASM embraces MS DOS era memory access management then then that is certainly a choice, might even still be an improvement over plain JavaScript. Does it at least have near and far pointers?
- s-macke 4y agoWell, the WASM binary format uses variable-length integer encoding. You can see this as an enhanced version of near and far pointers.
- int_19h 4y agoIt's not segmented, so no... or rather, not yet. The wasm spec already accommodates to some extent the notion of multiple "memories" (i.e. distinct flat heaps), although it only allows for one in practice: https://webassembly.github.io/spec/core/syntax/modules.html#memories https://webassembly.github.io/spec/core/syntax/modules.html#... And there's an active proposal to allow for multiple memories: https://github.com/WebAssembly/multi-memory/blob/main/proposals/multi-memory/Overview.md https://github.com/WebAssembly/multi-memory/blob/main/propos... In an environment like that, you'd need full-fledged pointers to carry both the memory index and the offset; and then you might want a non-fat "pointer to same memory" alternative for perf. Might as well call them far and near.