Hello,  A cast of a u16 value returned from a C function to a usize is invalid…  when enabling optimization.  I tried this code (with cargo flag --r

LLVM Discussion Forums

submited by
Style Pass
2022-06-21 17:00:05

Hello, A cast of a u16 value returned from a C function to a usize is invalid… when enabling optimization. I tried this code (with cargo flag --release): ```c #include <stdlib.h> #include <stdint.h> #include <stdio.h> struct bloc { uint16_t a; uint16_t b; uint16_t c; }; uint16_t c_read_value(void) { struct bloc *data = malloc(sizeof(struct bloc)); data->a = rand() & 0xFFFF; data->b = rand() & 0xFFFF; data->c = rand() & 0xFFFF; printf("C struct: a = %u, b = %u, c = %u\n", (unsigned) data->a, (unsigned) data->b, (unsigned) data->c); printf("C function returns %u\n", (unsigned) data->b); return data->b; /* leak data */ } ``` ```rust //#![feature(bench_black_box)] #[link(name = "bad")] extern "C" { pub fn c_read_value() -> u16; } fn main() { let value = unsafe { c_read_value() }; dbg!(value); // ok dbg!(value as usize); // nok dbg!(usize::from(value)); // nok dbg!((value as usize) & 0xFFFF); // nok //dbg!(std::hint::black_box(value) as usize); // ok } ``` I expected to print the same value when casting to usize. Instead, the value is wrong, the cast seems to "absorb" the neighboring bytes. Worse, I cannot even mask with `& 0xFFFF`! ``` C struct: a = 17767, b = 9158, c = 39017 C function returns 9158 [src/main.rs:10] value = 9158 [src/main.rs:11] value as usize = 846930886 [src/main.rs:12] usize::from(value) = 846930886 [src/main.rs:13] (value as usize) & 0xFFFF = 846930886 ``` Using black_box with nightly on the value fixes the issue. I'd like to find a good workaround for stable though. No issue in debug mode. To reproduce, this repo can be used: https://github.com/fparat/badcast ### Meta Bug present on stable and nightly. Found on Linux aarch64 (Jetson Nano). No issue found on amd64 or armv7. `rustc +nightly --version --verbose`: ``` rustc 1.63.0-nightly (490324f7b 2022-05-26) binary: rustc commit-hash: 490324f7b29d5f1a1e063a563045d790091ed639 commit-date: 2022-05-26 host: aarch64-unknown-linux-gnu release: 1.63.0-nightly LLVM version: 14.0.4 ``` Same issue with both gcc and clang for the C code ``` clang version 6.0.0-1ubuntu2 (tags/RELEASE_600/final) gcc (Ubuntu/Linaro 7.5.0-3ubuntu1~18.04) 7.5.0 ``` Backtrace: N.A.

Leave a Comment