Reimplement coalescer following the Budimlic paper.
The old coalescing algorithm had some algorithmic complexity issues when dealing with large virtual registers. Reimplement to use a proper union-find algorithm so we only need one pass through the dominator forests for virtual registers that are interference free. Virtual registers that do have interference are split and new registers built. This pass is about twice as fast as the old one when dealing with complex virtual registers.
This commit is contained in:
@@ -2,6 +2,7 @@
|
||||
|
||||
use entity::{PrimaryMap, EntityMap};
|
||||
use isa::TargetIsa;
|
||||
use ir;
|
||||
use ir::builder::ReplaceBuilder;
|
||||
use ir::extfunc::ExtFuncData;
|
||||
use ir::instructions::{InstructionData, CallInfo, BranchInfo};
|
||||
@@ -315,7 +316,7 @@ impl DataFlowGraph {
|
||||
}
|
||||
|
||||
/// Where did a value come from?
|
||||
#[derive(Debug, PartialEq, Eq)]
|
||||
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
|
||||
pub enum ValueDef {
|
||||
/// Value is the n'th result of an instruction.
|
||||
Result(Inst, usize),
|
||||
@@ -331,6 +332,22 @@ impl ValueDef {
|
||||
_ => panic!("Value is not an instruction result"),
|
||||
}
|
||||
}
|
||||
|
||||
/// Get the program point where the value was defined.
|
||||
pub fn pp(self) -> ir::ExpandedProgramPoint {
|
||||
self.into()
|
||||
}
|
||||
|
||||
/// Get the number component of this definition.
|
||||
///
|
||||
/// When multiple values are defined at the same program point, this indicates the index of
|
||||
/// this value.
|
||||
pub fn num(self) -> usize {
|
||||
match self {
|
||||
ValueDef::Result(_, n) |
|
||||
ValueDef::Param(_, n) => n,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Internal table storage for extended values.
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user