Skip to content

is_riscv_feature_detected doesn't seem to actually detect anything at runtime #139139

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

Open
ThomasHabets opened this issue Mar 30, 2025 · 4 comments
Assignees
Labels
A-target-feature Area: Enabling/disabling target features like AVX, Neon, etc. C-bug Category: This is a bug. O-riscv Target: RISC-V architecture T-libs Relevant to the library team, which will review and decide on the PR/issue.

Comments

@ThomasHabets
Copy link

ThomasHabets commented Mar 30, 2025

I tried this code

fn check_rvv() {
    let enabled = cfg!(target_feature="v");
    let detected = std::arch::is_riscv_feature_detected!("v");
    println!("RVV enabled={enabled} detected={detected}");
}  

I expected to see this happen

Any way at all under hardware with and without RVV support, with and without -Ctarget-feature=+v, to be able to return something other than "enabled and detected", or "not enabled and not detected".

I.e. for this feature to be useful for:

  1. Saying: Hey, you have a CPU capable of vector instructions, but this binary is not, or
  2. Having a hand coded RVV function, built with #[target_feature(enable = "v")], that can be selected at runtime, while the rest of the Rust code does not assume +v.

I do realise that if I compile with +v (thus cfg!(target_feature = "v") returns true everywhere), then the binary will probably be broken on non-rvv hardware. E.g. println!() could use the very instructions that are not supported, so I can't even print an error.

But for the cases above:

  1. Should be safe, just tell user to rebuild.
  2. It's apparently not actually runtime detecting anything.

Instead, this happened

It seems that if -Ctarget-feature=+v is not enabled, then std::arch::is_riscv_feature_detected!("v") always returns false.

It's also curious that inside a #[target_feature(enable = "v")] function, cfg!(target_feature="v") doesn't return true, unless the whole program was built with +v. Is that working as intended?

It seems to me that this should not be the same as #138789, where the reason is that LLVM doesn't have the CPU in its database. Because if it were, then the example code should never show enabled=true detected=true, but it does.

Not sure if it helps at all, but the code base I'm working on is rvv-vroom. You can run the code related to this bug using cargo +nightly run.

Meta

rustc --version --verbose:

$ cargo +nightly version --verbose
cargo 1.87.0-nightly (6cf826701 2025-03-14)
release: 1.87.0-nightly
commit-hash: 6cf8267012570f63d6b86e85a2ae5627de52df9e
commit-date: 2025-03-14
host: riscv64gc-unknown-linux-gnu
libgit2: 1.9.0 (sys:0.20.0 vendored)
libcurl: 8.12.1-DEV (sys:0.4.80+curl-8.12.1 vendored ssl:OpenSSL/3.4.1)
ssl: OpenSSL 3.4.1 11 Feb 2025
os: Ubuntu 24.4.0 (noble) [64-bit]
@ThomasHabets ThomasHabets added the C-bug Category: This is a bug. label Mar 30, 2025
@rustbot rustbot added the needs-triage This issue may need triage. Remove it if it has been sufficiently triaged. label Mar 30, 2025
@taiki-e
Copy link
Member

taiki-e commented Mar 30, 2025

The result of is_riscv_feature_detected!("v") becomes false even though it is available on the CPU, because runtime detection of the v target feature is not yet implemented.

#138789 is unrelated because we and LLVM implement feature detection in different places.

As always, this can be implemented by adjust & upstream what is in the portable-atomic.

@rustbot claim
@rustbot label +O-RISCV

@rustbot rustbot added the O-riscv Target: RISC-V architecture label Mar 30, 2025
@ehuss
Copy link
Contributor

ehuss commented Mar 30, 2025

It's also curious that inside a #[target_feature(enable = "v")] function, cfg!(target_feature="v") doesn't return true, unless the whole program was built with +v. Is that working as intended?

I believe this is #42515. cfg does not know about #[target_feature] attributes.

@Noratrieb Noratrieb added T-libs Relevant to the library team, which will review and decide on the PR/issue. A-target-feature Area: Enabling/disabling target features like AVX, Neon, etc. and removed needs-triage This issue may need triage. Remove it if it has been sufficiently triaged. labels Mar 30, 2025
@taiki-e
Copy link
Member

taiki-e commented Mar 30, 2025

Filed rust-lang/stdarch#1762 for is_riscv_feature_detected.

@a4lg
Copy link
Contributor

a4lg commented Apr 21, 2025

rust-lang/stdarch#1770 (based on @taiki-e's rust-lang/stdarch#1762) is merged so that large portions of supported extensions can be detected by runtime.

And, to avoid pitfalls finding an extension / using something after depending extension is detected, I filed rust-lang/stdarch#1779 which adds the platform guide documentation.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-target-feature Area: Enabling/disabling target features like AVX, Neon, etc. C-bug Category: This is a bug. O-riscv Target: RISC-V architecture T-libs Relevant to the library team, which will review and decide on the PR/issue.
Projects
None yet
Development

Successfully merging a pull request may close this issue.

6 participants