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.
This commit is contained in:
Jakob Stoklund Olesen
2017-12-04 13:43:10 -08:00
parent 27d5543adc
commit feaea238bc
9 changed files with 279 additions and 215 deletions

View File

@@ -300,16 +300,17 @@ impl<'a> Context<'a> {
for (idx, (op, &arg)) in constraints.ins.iter().zip(args).enumerate() {
let mut reguse = RegUse::new(arg, idx, op.regclass.into());
let lr = &self.liveness[arg];
let ctx = self.liveness.context(&self.cur.func.layout);
match op.kind {
ConstraintKind::Stack => continue,
ConstraintKind::FixedReg(_) => reguse.fixed = true,
ConstraintKind::Tied(_) => {
// A tied operand must kill the used value.
reguse.tied = !lr.killed_at(inst, ebb, &self.cur.func.layout);
reguse.tied = !lr.killed_at(inst, ebb, ctx);
}
ConstraintKind::FixedTied(_) => {
reguse.fixed = true;
reguse.tied = !lr.killed_at(inst, ebb, &self.cur.func.layout);
reguse.tied = !lr.killed_at(inst, ebb, ctx);
}
ConstraintKind::Reg => {}
}