Stream: wasmtime

Topic: Question about 64-bit RISC-V fiber implementation


view this post on Zulip Max D. (Jan 30 2026 at 17:29):

While working on a fiber implementation for 32-bit RISC-V, we noticed that the implementation for 64-bit RISC-V uses instructions specific to the F extension, which includes additional registers for floating point values, regardless whether the CPU has the extension or not.

When using an analogous implementation for a 32-bit RISC-V processor without the F extension, execution stops at the first F-specific instruction without an error (we assume a trap handler is activated). We do not have a 64-bit RISC-V chip without the F-extension to test this with, but we assume it would show the same behaviour.

For our implementation for 32-bit RISC-V, we plan on solving this by checking for the target_feature in addition to the target_arch and only select the implementation if both match the implementation (see the version of stackswitch.rs in our fork).

We're wondering whether the 64-bit RISC-V implementation being used regardless of the F extension being present on the target CPU actually is a bug or is there something we're missing/misunderstanding?

A lightweight WebAssembly runtime that is fast, secure, and standards-compliant - bytecodealliance/wasmtime
A lightweight WebAssembly runtime that is fast, secure, and standards-compliant - Added fiber implementation for riscv32 · COLORADIO-Project/wasmtime@170042d

view this post on Zulip Chris Fallin (Jan 30 2026 at 17:35):

The riscv64 port targets riscv64gc, which includes F (and D); these are required for the code that we generate on that platform

view this post on Zulip Chris Fallin (Jan 30 2026 at 17:35):

(and the code that rustc will compile since we build with riscv64gc-unknown-linux-gnu)

view this post on Zulip Chris Fallin (Jan 30 2026 at 17:36):

You'll need to either do some sort of dynamic feature detection if you want to work on riscv32imac (for example), or build fully for an FPU-free environment

view this post on Zulip bjorn3 (Feb 02 2026 at 19:35):

Rustc only has a baremetal riscv64imac target (Linux requires full gc support and other OSes probably do too). For baremetal targets wasmtime doesn't use fibers at all.

view this post on Zulip Antoine Lavandier (Feb 02 2026 at 19:52):

It's perhaps not intended but fibers (as in wasmtime-fiber and the async feature of wasmtime) do work on baremetal ARM Thumbv7/Thumbv8 targets

view this post on Zulip Chris Fallin (Feb 02 2026 at 19:57):

indeed, fibers do work in a no_std build and that's intended -- I added that a bit ago for our no_std x86-64 embedding

view this post on Zulip Max D. (Feb 03 2026 at 17:08):

Thanks for the clarifications!

Quick sanity check about your messages, @Chris Fallin:
So there does not need to be a check for the features in stackswitch.rs because wasmtime only supports riscv64gc.
For the riscv32 implementation, this means we also only need to check for the riscv32 architecture, because only riscv32imac is supported by wasmtime.

Do we understand your comments correctly?

view this post on Zulip Chris Fallin (Feb 03 2026 at 17:13):

Max D. said:

For the riscv32 implementation, this means we also only need to check for the riscv32 architecture, because only riscv32imac is supported by wasmtime.

Well, no, not quite; I never said that Wasmtime supports only riscv32imac. In fact (with Pulley) it should run fine (without async/fibers) on all sorts of riscv32 platforms, whatever is supported by rustc.

I would expect that we'd need some sort of feature detection to select between different fiber-switching assembly sequences for different variants...

view this post on Zulip Max D. (Feb 03 2026 at 17:50):

Chris Fallin said:

I never said that Wasmtime supports only riscv32imac.

Oh, sorry, we got that from the documentation, which we forgot to link. Our implementation only uses instructions from riscv32i, so it should work for any architecture without additional registers, which to our knowledge just means the f and v extensions cannot be present (as the d extension implies the f extension being present).

I would expect that we'd need some sort of feature detection to select between different fiber-switching assembly sequences for different variants...

If our assumptions above are correct, the implementation in our fork should do this by only using our implementation if target_arch is riscv32 and target_feature does not include f or v. Is this what you mean by feature detection?

A lightweight WebAssembly runtime that is fast, secure, and standards-compliant - Comparing bytecodealliance:release-38.0.0...COLORADIO-Project:release-38.0.0 · bytecodealliance/wasmtime

view this post on Zulip Alex Crichton (Feb 03 2026 at 17:54):

Feature-detection-wise yeah you'll want to be using cfg(target_feature = "...") in Rust. In theory it would be best to do runtime feature detection but that's not really suitable given the low-level nature of this crate.

view this post on Zulip Alex Crichton (Feb 03 2026 at 17:55):

In theory what we'll want is something like #[cfg(target_feature = "f")] compile_error!("this isn't ready for the \"f\" feature yet");

view this post on Zulip Chris Fallin (Feb 03 2026 at 17:55):

Ah, that's just the list of builds that we check I think, but we don't want to bake in any assumptions that riscv32 == riscv32imac. I think your compile-time feature checks there make sense; let's call the arch-specific file riscv32imac.rs or something more specific like that

view this post on Zulip Alex Crichton (Feb 03 2026 at 17:56):

I'll note though that rustc hasn't stabilized all risc-v features, so for example even the riscv64gc target looks like it has "f" disabled

view this post on Zulip Alex Crichton (Feb 03 2026 at 17:56):

in the sense that cfg(target_feature = "f") isn't set

view this post on Zulip Chris Fallin (Feb 03 2026 at 17:57):

Alex Crichton said:

I'll note though that rustc hasn't stabilized all risc-v features, so for example even the riscv64gc target looks like it has "f" disabled

that's... extremely odd and sounds like a bug? egads

view this post on Zulip Alex Crichton (Feb 03 2026 at 17:57):

I don't think this is a situation we can be 100% sound right now -- with a combination of rustc not exposing features to us and there being no reasonable path to runtime feature detection all we can do is try our best to provide guard rails

view this post on Zulip Alex Crichton (Feb 03 2026 at 17:57):

It's not a bug per se, it's that the "f" target feature name in rust isn't stable

view this post on Zulip Chris Fallin (Feb 03 2026 at 17:57):

ah, gotcha

view this post on Zulip Alex Crichton (Feb 03 2026 at 17:58):

for example this is stable rust right now

Empowering everyone to build reliable and efficient software. - rust-lang/rust

view this post on Zulip Alex Crichton (Feb 03 2026 at 17:58):

and on current main it's still unstable

Empowering everyone to build reliable and efficient software. - rust-lang/rust

view this post on Zulip Alex Crichton (Feb 03 2026 at 17:59):

another way to put what I'm saying, @Max D. feel free to send a PR with what you have. I don't think it's currently possible to be 100% correct on riscv32 at this time. We'll just have to document that riscv32 for wasmtime is incompatible with floats and that's the best we can do

view this post on Zulip Max D. (Feb 03 2026 at 19:22):

Thanks a lot again for your help! We've cleaned up our git history and created a pull request on GitHub: https://github.com/bytecodealliance/wasmtime/pull/12506

Looking forward to any feedback on this!

This adds an implementation for riscv32imac (and other architectures with identical registers) to the internal fiber crate. This enables usage of the async feature of wasmtime on such platforms. Th...

Last updated: Feb 24 2026 at 04:36 UTC