Commit Graph

23 Commits

Author SHA1 Message Date
Jakob Stoklund Olesen
13af22b46b Track register pressure for dead EBB parameters.
The spiller wasn't tracking register pressure correctly for dead EBB
parameters in visit_ebb_header(). Make sure we free any dead EBB
parameters.

Fixes #223
2018-01-17 13:19:08 -08:00
Jakob Stoklund Olesen
feaea238bc Use bforest::Map for representing live ranges.
Get rid of the per-value Vec in the LiveRange data type and use a
bforest::Map instead to represent the live-in intervals for non-local
live ranges.

This has some advantages:

- The memory footprint of a local live range is reduced from 40 to 20
  bytes, and
- Clearing the Liveness data structure is now a constant time operation
  which doesn't call free().
- The potentially quadratic behavior when computing large live ranges is
  controlled by the logarithmic B-tree operations.
2017-12-06 14:14:21 -08:00
Dan Gohman
3ab4349c1b Use Self instead of repeating the type name. 2017-11-08 10:43:11 -08:00
Jakob Stoklund Olesen
921bcc6c25 Use the term "EBB parameter" everywhere.
Add EBB parameter and EBB argument to the langref glossary to clarify
the distinction between formal EBB parameter values and arguments passed
to branches.

- Replace "ebb_arg" with "ebb_param" in function names that deal with
  EBB parameters.
- Rename the ValueDef variants to Result and Param.
- A bunch of other small langref fixes.

No functional changes intended.
2017-10-19 16:17:09 -07:00
Jakob Stoklund Olesen
994af598f5 Avoid interference on CFG edges.
Track allocatable registers both locally and globally: Add a second
AllocatableSet which tracks registers allocated to global values without
accounting for register diversions. Since diversions are only local to
an EBB, global values must be assigned un-diverted locations that don't
interfere.

Handle the third "global" interference domain in the constraint solver in
addition to the existing "input" and "output" domains.

Extend the solver error code to indicate when a global define just can't
be allocated because there are not enough available global registers.
Resolve this problem by replacing the instruction's global defines with
local defines that are copied into their global destinations
afterwards.
2017-10-11 15:38:30 -07:00
Dan Gohman
2efdc0ed37 Update rustfmt to 0.9.0. 2017-08-31 10:44:59 -07:00
Jakob Stoklund Olesen
9cb0529be4 Move EntityList and SparseMap into the entity module.
These data structures are dependent on EntityRef and EntityMap, so it
makes sense to keep them in the same module.
2017-08-18 16:14:06 -07:00
Jakob Stoklund Olesen
2b999d9bd6 Add an Index<Value> implementation to Liveness.
Use it to access live ranges that are supposed to be there.
2017-06-29 15:13:04 -07:00
Jakob Stoklund Olesen
165e80d9bf Process ghost instruction kills during coloring.
Ghost instructions don't generate code, but they can keep registers
alive. The coloring pass needs to process values killed by ghost
instructions so it knows when the registers are freed up.

Also track register pressure changes from ghost kills in the spiller.
2017-06-27 16:35:11 -07:00
Jakob Stoklund Olesen
63a372fd80 Basic spilling implementation.
Add a spilling pass which lowers register pressure by assigning SSA
values to the stack. Important missing features:

- Resolve conflicts where an instruction uses the same value more than
  once in incompatible ways.
- Deal with EBB arguments.

Fix bugs in the reload pass exposed by the first test case:

- Create live ranges for temporary registers.
- Set encodings on created spill and fill instructions.
2017-06-13 13:58:20 -07:00
Jakob Stoklund Olesen
94944d2057 Keep dead EBB arguments around in LiveValueTracker::ebb_top().
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.
2017-05-11 11:28:39 -07:00
Jakob Stoklund Olesen
2c0d4136b0 Propagate a few more LiveRange properties to LiveValue.
The live value tracker goes through the trouble of looking up the live
range for each value it tracks. We can cache a few more interesting
properties from the live range in the LiveValue struct.
2017-05-11 11:28:39 -07:00
Jakob Stoklund Olesen
402e437a4a Also return live-through values from process_inst().
The coloring algorithm will need to look at the live-through values to
check if they interfere with fixed-register outputs for calls etc.
2017-05-08 13:57:39 -07:00
Jakob Stoklund Olesen
ee5f035e31 Upgrade to Rust 1.17.
- Remove some uses of 'static in const and static globals that are no
  longer needed.
- Use the new struct initialization shorthand.
2017-04-27 12:46:44 -07:00
Jakob Stoklund Olesen
322a8db839 Change dfg.inst_results to return a slice.
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.
2017-04-11 16:57:15 -07:00
Jakob Stoklund Olesen
dd0a61cc91 Keep EBB arguments in a ValueList.
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.
2017-04-11 11:36:50 -07:00
Jakob Stoklund Olesen
1984c96f7c rustfmt 0.8.1 2017-04-05 09:00:11 -07:00
Jakob Stoklund Olesen
010861d58e Upgrade to rustfmt 0.8.0.
Lots of changes this time.

Worked around what looks like a rustfmt bug in parse_inst_operands where
a large match was nested inside Ok().
2017-03-14 10:48:05 -07:00
Jakob Stoklund Olesen
5170ef6b5f Convert the Branch and Jump instruction formats to value_list.
The Branch format also stores its fixed argument in the value list. This
requires the value pool to be passed to a few more functions.

Note that this actually makes the Branch and Jump variants of
InstructionData identical. The instruction format hashing does not yet
understand that all value operands are stored in the value list. We'll
fix that in a later patch.

Also convert IndirectCall, noting that Call and IndirectCall remain
separate instruction formats because they have different immediate
fields.
2017-03-09 15:38:12 -08:00
Jakob Stoklund Olesen
a20afbefe0 Improve assertion text for missing live ranges. 2017-02-21 12:24:37 -08:00
Jakob Stoklund Olesen
b1769ac7e4 Cache the affinity in LiveValue.
Most of the register allocator algorithms will only have to look at the
currently live values as presented by LiveValueTracker. Many also need
the value's affinity which is stored in the LiveRange associated with
the value.

Save the extra table lookup by caching the affinity value inside
LiveValue.
2017-02-15 13:53:01 -08:00
Jakob Stoklund Olesen
96e0a3273c Return slices of live-ins and arguments from ebb_top().
The coloring algorithm needs to process these two types of live values
differently, so we may as well provide the needed info.
2017-02-14 16:05:54 -08:00
Jakob Stoklund Olesen
2c31041640 Live Value Tracker.
Keep track of which values are live and dead as we move through the
instructions in an EBB.
2017-02-14 10:17:24 -08:00