A CallConv enum on every function signature makes it possible to
generate calls to functions with different calling conventions within
the same ISA / within a single function.
The calling conventions also serve as a way of customizing Cretonne's
behavior when embedded inside a VM. As an example, the SpiderWASM
calling convention is used to compile WebAssembly functions that run
inside the SpiderMonkey virtual machine.
All function signatures must have a calling convention at the end, so
this changes the textual IL syntax.
Before:
sig1 = signature(i32, f64) -> f64
After
sig1 = (i32, f64) -> f64 native
sig2 = (i32) spiderwasm
When printing functions, the signature goes after the return types:
function %r1() -> i32, f32 spiderwasm {
ebb1:
...
}
In the parser, this calling convention is optional and defaults to
"native". This is mostly to avoid updating all the existing test cases
under filetests/. When printing a function, the calling convention is
always included, including for "native" functions.
When making an outgoing call, some arguments may have to be passed on
the stack. Allocate OutgoingArg stack slots for these arguments and
write them immediately before the outgoing call instruction.
Do the same for incoming function arguments on the stack, but use
IncomingArg stack slots instead. This was previously done in the
spiller, but we move it to the legalizer so it is done at the same time
as outgoing stack arguments.
These stack slot assignments are done in the legalizer before live
range analysis because the outgoing arguments usually are in different
SSSA values with their own short live ranges.
* Function names should start with %
* Create FunctionName from string
* Implement displaying of FunctionName as %nnnn with fallback to #xxxx
* Run rustfmt and fix FunctionName::with_string in parser
* Implement FunctionName::new as a generic function
* Binary function names should start with #
* Implement NameRepr for function name
* Fix examples in docs to reflect that function names start with %
* Rebase and fix filecheck tests
These special-purpose arguments and return values are only relevant for
the function being compiled, so add a `current` flag to
legalize_signature().
- Add the necessary argument values to the entry block to represent
the special-purpose arguments.
- Propagate the link and sret arguments to return instructions if the
legalized signature asks for it.
When converting from ABI types to original program types, the final
conversion instruction can place its result into the original value, so
it doesn't need to be changed to an alias.
All values are now references into the value table, so drop the
distinction between direct and table values. Direct values don't exist
any more.
Also remove the parser support for the 'vxNN' syntax. Only 'vNN' values
can be parsed now.
We only ever create table values now.
Simplify legalizer::legalize_inst_results. Instead of calling
detach_secondary_results, just detach all the results and don't treat
the first result specially.
The carry and borrow values are boolean, so we have to convert them to
an integer type with bint(c) before we can add them to the result.
Also tweak the default legalizer action for unsupported types: Only
attempt a narrowing pattern for lane types > 32 bits.
This was found by @angusholder's new type checks in the verifier.
The EBB argument splitting may generate concat-split dependencies when
it repairs branch arguments in EBBs that have not yet been fully
legalized. Add a branch argument simplification step that can resolve
these dependency chains.
This means that all split and concatenation instructions will be dead
after legalization for types that have no legal instructions using them.
The call arguments on call_indirect should not include the fixed callee
argument.
Add legalizer assertions to verify that signatures are actually valid
after legalization. If not, we would get infinite legalizer loops.
Like the entry block arguments, the return values from a call
instruction need to be converted back from their ABI representation.
Add tests of call instruction legalization.
- abi.cton is for testing the actual RISC-V ABI.
- legalize-abi.cton is for testing the legalizer around ABI boundaries.
- parse-encoding.cton is for testing the parser's handling of RISC-V
encoding and register annotations.