The EntityRef trait is used by more than just the EntityMap now, so it
should live in its own module.
Also move the entity_impl! macro into the new module so it can be used
for defining new entity references anywhere.
* Replace a single-character string literal with a character literal.
* Use is_some() instead of comparing with Some(_).
* Add code-quotes around type names in comments.
* Use !...is_empty() instead of len() != 0.
* Tidy up redundant returns.
* Remove redundant .clone() calls.
* Remove unnecessary explicit lifetime parameters.
* Tidy up unnecessary '&'s.
* Add parens to make operator precedence explicit.
* Use debug_assert_eq instead of debug_assert with ==.
* Replace a &Vec argument with a &[...].
* Replace `a = a op b` with `a op= b`.
* Avoid unnecessary closures.
* Avoid .iter() and .iter_mut() for iterating over containers.
* Remove unneeded qualification.
Use a new StackSlots struct to keep track of a function's stack slots
instead of just an entity map. This let's us build more internal data
structures for tracking the stack slots if necessary.
Start by adding a make_spill_slot() function that will be used by the
register allocator.
Add a StackSlotKind enumeration to help keep track of the different
kinds of stack slots supported:
- Incoming and outgoing function arguments on the stack.
- Spill slots and locals.
Change the text format syntax for declaring a stack slot to use a kind
keyword rather than just 'stack_slot'.
An instruction may have fixed operand constraints that make it
impossibly to use a single register value to satisfy two at a time.
Detect when the same value is used for multiple fixed register operands
and insert copies during the spilling pass.
When comparing instructions in the same EBB, behave like the RPO visits
instructions in program order.
- Add a Layout::pp_ebb() method for convenience. It gets the EBB
containing any program point.
- Add a conversion from ValueDef to ExpandedProgramPoint so it can be
used with the rpo_cmp method.
* 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
The reload pass inserts spill and fill instructions as needed so
instructions that operate on registers will never see a value with stack
affinity.
This is a very basic implementation, and we can't write good test cases
until we have a spilling pass.
* Implemented in two passes
* First pass discovers the loops headers (they dominate one of their predecessors)
* Second pass traverses the blocks of each loop
* Discovers the loop tree structure
* Offers a new LoopAnalysis data structure queried from outside the module
* Fix GVN skipping the instruction after a deleted instruction.
* Teach GVN to resolve aliases as it proceeds.
* Clean up an obsolete reference to extended_values.
* Skeleton simple_gvn pass.
* Basic testing infrastructure for simple-gvn.
* Add can_load and can_store flags to instructions.
* Move the replace_values function into the DataFlowGraph.
* Make InstructionData derive from Hash, PartialEq, and Eq.
* Make EntityList's hash and eq functions panic.
* Change Ieee32 and Ieee64 to store u32 and u64, respectively.
Provide a drop_dead_args() function which deletes them instead.
We still need to assign a register to dead EBB arguments, so they can't
just be ignored.
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.
Enumerate a set of special purposes for function arguments that general
purpose code needs to know about. Some of these argument purposes will
only appear in the signature of the current function, representing
things the prologue and epilogues need to know about like the link
register and callee-saved registers.
Get rid of the 'inreg' argument flag. Arguments can be pre-assigned to a
specific register instead.
- The detach_secondary_results() is a leftover from the two-plane value
representation. Use detach_results() instead to remove all instruction
results.
- Make the append_* DFG methods more direct. Don't depend on calling the
corresponding attach_* methods. Just create a new value directly,
using the values.next_key() trick.
This makes it possible to reuse one or more result values in the
instruction that is being inserted.
Also add a with_result(v) method for the common case of reusing a single
result value. This could be specialized in the future.
These methods are used to reattach detached values:
- change_to_alias
- attach_result
- attach_ebb_arg
Add an assertion to all of them to ensure that the provided value is not
already attached somewhere else. Use a new value_is_attached() method
for the test.
Also include a verifier check for uses of detached values.
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.
Soon, InstructionData won't have sufficient information to compute this.
Give TargetIsa::encode() an explicit ctrl_typevar argument. This
function does not require the instruction to be inserted in the DFG
tables.
Since results are in a value list, they don't need to form a linked
list any longer.
- Simplify make_inst_results() to create values in the natural order.
- Eliminate the last use of next_secondary_value().
- Delete unused result manipulation methods.
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.
We don't want to distinguish between single-result and multiple-result
instructions any longer.
- Merge the simple_instruction() and complex_instruction() builder
methods into a single build() that can handle all cases.
- All format constructors now take a ctrl_type argument. Previously,
some would take a result_type argument.
- Instruction constructors no longer attempt to compute a single result
type. Just pass a ctrl_type and let the backend decide.
Fix one format constructor call in legalizer/split.rs which now takes a
ctrl_type instead of a result type.
Now we can access instruction results and arguments as well as EBB
arguments as slices.
Delete the Values iterator which was traversing the linked lists of
values. It is no longer needed.
This is the first step of a larger refactoring to represent instruction
results as value lists instead of using linked lists. The refactoring
will also eliminate the special treatment of first results such that all
result values can be detached and redefined.
This change put us in a temporary state where results are represented
both as linked lists and ValueList vectors.
- Add a dfg.results table.
- Add the first result in make_inst(). This behavior will change.
- Recompute the result list in make_inst_results().
- Make dfg.first_result(inst) crash if the instruction has no results.
- Add a dfg.is_inst_valid() method for the verifier.
- Use the inst_args_mut() method when rewriting values in the parser.
- Add a new branch_destination_mut() to use when rewriting EBBs.
This also gets rid of one of the large instruction format switches in
the parser.
Now that we have a value list of the arguments, we can get rid of:
- The first_arg and last_arg members in EbbData,
- The next member in the ValueData::Arg variant.
Rather than returning the head of a linked list of EBB arguments, just
return the whole value list of all the arguments.
Delete the next_ebb_arg() method which was only used for traversing that
list.
This is the first step of the value list refactoring which will replace
linked lists of values with value lists.
- Keep a ValueList in the EbbData struct containing all the EBB
arguments.
- Change dfg.ebb_args() to return a slice instead of an iterator.
This leaves us in a temporary hybrid state where we maintain both a
linked list and a ValueList vector of the EBB arguments.
Any *.cton files in the docs directory are now included when running the
test-all.sh script. This is to ensure that the examples are in fact
correct IL.
Always print NaN and Inf floats with a sign. Print the positive ones as
+NaN and +Inf to make them easier to parse.