Allow for call args in incoming stack slots.
A value passed as an argument to a function call may live in an incoming stack slot initially. Fix the call legalizer so it copies such an argument into the expected outgoing stack slot for the call.
This commit is contained in:
@@ -18,3 +18,15 @@ function %f() {
|
||||
ebb0:
|
||||
return
|
||||
}
|
||||
|
||||
function %pass_stack_int64(i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64 vmctx) spiderwasm {
|
||||
sig0 = (i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64, i64 vmctx) spiderwasm
|
||||
fn0 = sig0 #00000000
|
||||
|
||||
ebb0(v0: i64, v1: i64, v2: i64, v3: i64, v4: i64, v5: i64, v6: i64, v7: i64, v8: i64, v9: i64, v10: i64, v11: i64, v12: i64, v13: i64, v14: i64, v15: i64, v16: i64, v17: i64, v18: i64, v19: i64, v20: i64):
|
||||
call fn0(v0, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20)
|
||||
jump ebb1
|
||||
|
||||
ebb1:
|
||||
return
|
||||
}
|
||||
|
||||
@@ -21,7 +21,7 @@ use abi::{legalize_abi_value, ValueConversion};
|
||||
use cursor::{Cursor, FuncCursor};
|
||||
use flowgraph::ControlFlowGraph;
|
||||
use ir::{Function, DataFlowGraph, Inst, InstBuilder, Ebb, Type, Value, Signature, SigRef,
|
||||
ArgumentType, ArgumentPurpose, ArgumentLoc, ValueLoc, StackSlotKind};
|
||||
ArgumentType, ArgumentPurpose, ArgumentLoc, ValueLoc};
|
||||
use ir::instructions::CallInfo;
|
||||
use isa::TargetIsa;
|
||||
use legalizer::split::{isplit, vsplit};
|
||||
@@ -651,21 +651,14 @@ fn spill_call_arguments(pos: &mut FuncCursor) -> bool {
|
||||
.filter_map(|(idx, (&arg, abi))| {
|
||||
match abi.location {
|
||||
ArgumentLoc::Stack(offset) => {
|
||||
// Is `arg` already in the right kind of stack slot?
|
||||
match locations.get(arg) {
|
||||
Some(&ValueLoc::Stack(ss)) => {
|
||||
// We won't reassign `arg` to a different stack slot. Assert out of
|
||||
// the stack slot is wrong.
|
||||
assert_eq!(stack_slots[ss].kind, StackSlotKind::OutgoingArg);
|
||||
assert_eq!(stack_slots[ss].offset, offset);
|
||||
assert_eq!(stack_slots[ss].size, abi.value_type.bytes());
|
||||
None
|
||||
}
|
||||
_ => {
|
||||
// Assign `arg` to a new stack slot.
|
||||
let ss = stack_slots.get_outgoing_arg(abi.value_type, offset);
|
||||
Some((idx, arg, ss))
|
||||
}
|
||||
// Assign `arg` to a new stack slot, unless it's already in the correct
|
||||
// slot. The legalization needs to be idempotent, so we should see a
|
||||
// correct outgoing slot on the second pass.
|
||||
let ss = stack_slots.get_outgoing_arg(abi.value_type, offset);
|
||||
if locations[arg] != ValueLoc::Stack(ss) {
|
||||
Some((idx, arg, ss))
|
||||
} else {
|
||||
None
|
||||
}
|
||||
}
|
||||
_ => None,
|
||||
|
||||
Reference in New Issue
Block a user