-
Notifications
You must be signed in to change notification settings - Fork 12.7k
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
Wasm code failing regression probably related to update to LLVM 9 trunk #63918
Comments
I changed an example a bit, minimized it from the size of wasm binary prespective and used some c-reduce (which hasn't yield much improvements). #![no_std]
use core::arch::wasm32::unreachable;
#[panic_handler]
fn panic_handler(_: &core::panic::PanicInfo) -> ! {
unsafe { unreachable() }
}
#[no_mangle]
fn main() {
let b = c();
if b != 8000000000000000000u128 {
unsafe { unreachable() }
}
}
pub fn c() -> u128 {
let d = [0, 0, 32, 59, 157, 181, 5, 111, 0, 0, 0, 0, 0, 0, 0, 0];
match e(&mut &d[..]) {
Ok(f) => f,
_ => unsafe { unreachable() },
}
}
#[inline(never)]
fn e(g: &&[u8]) -> Result<u128, ()> {
let mut buf = [0; 16];
h(g, &mut buf).ok_or_else(|| ())?;
Ok(u128::from_le_bytes(buf))
}
fn h(g: &&[u8], i: &mut [u8]) -> Option<()> {
if i.len() != g.len() {
return None;
}
i.copy_from_slice(g);
Some(())
} compiling with
there is no notable difference in LLVM IR, only some identifiers and added imm arg in e.g. The miscompilation seems to happen around ;; local 1 = SP
;; local.2 = i64.load(sp + 16)
get_local 1
i32.const 16
i32.add
i64.load
set_local 2
;; *out.0 = i64.load(sp + 8)
get_local 0
get_local 1
i64.load offset=8
i64.store
;; *(out.0+8) = local.2
get_local 0
get_local 2
i64.store offset=8 in miscompiled version we just do this (gist): ;; *out.0 = local.2
get_local 0
get_local 2
i64.store which doesn't make a lot of sense since All this makes me think (although I am of course not sure) that this is a LLVM IR to wasm32 lowering bug, so cc @sunfishcode |
I haven't investigated this in detail yet, but in your analysis, in the reduced version, |
What I meant is that the descriminator of the Or in other words, it attempts to squeeze the descriminator of |
I think I've reduced this a bit further: ; ModuleID = 'foo.ll'
source_filename = "foo.ll"
target triple = "wasm32-unknown-unknown"
@wut = private constant i128 8000000000000000000
define i128 @get() {
start:
%0 = tail call { i64, i128 } @decode(i8* bitcast (i128* @wut to i8*))
%1 = extractvalue { i64, i128 } %0, 1
ret i128 %1
}
declare hidden { i64, i128 } @decode(i8* nocapture readonly) generates: (func (;1;) (type 0) (param i32)
(local i32)
global.get 0
i32.const 32
i32.sub
local.tee 1
global.set 0
local.get 1
i32.const 8
i32.add
i32.const 0
call 0
local.get 0
local.get 1
i64.load offset=8
i64.store
local.get 1
i32.const 32
i32.add
global.set 0) and it looks like the upper or lower bits (dunno which, but at least one) isn't being copied over I've opened an upstream bug at https://bugs.llvm.org/show_bug.cgi?id=43132 |
Visiting for compiler triage meeting. I'm marking this as a "P-medium" bug since it is specific to WASM and also due to an LLVM bug. I'm not sure if we plan to fix this on our side in any way? |
The reduced testcase is now fixed in r370430. |
Summary:
The following piece of code fail when compiled to wasm32-unknown-unknown since nightly-2019-07-18. This nightly introduces https://github.com/rust-lang/rust/pull/62592/files so probably related.
Regression test:
with configuration:
Reproduce:
see the repo: https://github.com/thiolliere/wasm-llvm9-issue it contains:
t.js
used to execute test with node.make.sh
file to execute the test on rust version 2019-07-17 and 2019-07-18.Notes:
"rlib"
oropt-level = "z"
it works (it is not failing anymore)cc @pepyakin
The text was updated successfully, but these errors were encountered: