Rename 'an block' to 'a block'

Missed this in the automatic rename of 'Ebb' to 'Block'.
This commit is contained in:
Ryan Hunt
2020-03-03 13:17:30 -06:00
parent 77e17d8f71
commit 07f335dca6
31 changed files with 96 additions and 96 deletions

View File

@@ -74,7 +74,7 @@ impl<'a> MemoryCodeSink<'a> {
/// A trait for receiving relocations for code that is emitted directly into memory. /// A trait for receiving relocations for code that is emitted directly into memory.
pub trait RelocSink { pub trait RelocSink {
/// Add a relocation referencing an block at the current offset. /// Add a relocation referencing a block at the current offset.
fn reloc_block(&mut self, _: CodeOffset, _: Reloc, _: CodeOffset); fn reloc_block(&mut self, _: CodeOffset, _: Reloc, _: CodeOffset);
/// Add a relocation referencing an external symbol at the current offset. /// Add a relocation referencing an external symbol at the current offset.

View File

@@ -136,7 +136,7 @@ pub trait CodeSink {
/// Add 8 bytes to the code section. /// Add 8 bytes to the code section.
fn put8(&mut self, _: u64); fn put8(&mut self, _: u64);
/// Add a relocation referencing an block at the current offset. /// Add a relocation referencing a block at the current offset.
fn reloc_block(&mut self, _: Reloc, _: CodeOffset); fn reloc_block(&mut self, _: Reloc, _: CodeOffset);
/// Add a relocation referencing an external symbol plus the addend at the current offset. /// Add a relocation referencing an external symbol plus the addend at the current offset.

View File

@@ -163,7 +163,7 @@ fn try_fold_redundant_jump(
} }
}; };
// For the moment, only attempt to fold a branch to an block that is parameterless. // For the moment, only attempt to fold a branch to a block that is parameterless.
// These blocks are mainly produced by critical edge splitting. // These blocks are mainly produced by critical edge splitting.
// //
// TODO: Allow folding blocks that define SSA values and function as phi nodes. // TODO: Allow folding blocks that define SSA values and function as phi nodes.

View File

@@ -13,10 +13,10 @@ pub enum CursorPosition {
/// Cursor is pointing at an existing instruction. /// Cursor is pointing at an existing instruction.
/// New instructions will be inserted *before* the current instruction. /// New instructions will be inserted *before* the current instruction.
At(ir::Inst), At(ir::Inst),
/// Cursor is before the beginning of an block. No instructions can be inserted. Calling /// Cursor is before the beginning of a block. No instructions can be inserted. Calling
/// `next_inst()` will move to the first instruction in the block. /// `next_inst()` will move to the first instruction in the block.
Before(ir::Block), Before(ir::Block),
/// Cursor is pointing after the end of an block. /// Cursor is pointing after the end of a block.
/// New instructions will be appended to the block. /// New instructions will be appended to the block.
After(ir::Block), After(ir::Block),
} }
@@ -368,7 +368,7 @@ pub trait Cursor {
/// Move to the next instruction in the same block and return it. /// Move to the next instruction in the same block and return it.
/// ///
/// - If the cursor was positioned before an block, go to the first instruction in that block. /// - If the cursor was positioned before a block, go to the first instruction in that block.
/// - If there are no more instructions in the block, go to the `After(block)` position and return /// - If there are no more instructions in the block, go to the `After(block)` position and return
/// `None`. /// `None`.
/// - If the cursor wasn't pointing anywhere, keep doing that. /// - If the cursor wasn't pointing anywhere, keep doing that.
@@ -377,7 +377,7 @@ pub trait Cursor {
/// ///
/// # Examples /// # Examples
/// ///
/// The `next_inst()` method is intended for iterating over the instructions in an block like /// The `next_inst()` method is intended for iterating over the instructions in a block like
/// this: /// this:
/// ///
/// ``` /// ```
@@ -438,7 +438,7 @@ pub trait Cursor {
/// Move to the previous instruction in the same block and return it. /// Move to the previous instruction in the same block and return it.
/// ///
/// - If the cursor was positioned after an block, go to the last instruction in that block. /// - If the cursor was positioned after a block, go to the last instruction in that block.
/// - If there are no more instructions in the block, go to the `Before(block)` position and return /// - If there are no more instructions in the block, go to the `Before(block)` position and return
/// `None`. /// `None`.
/// - If the cursor wasn't pointing anywhere, keep doing that. /// - If the cursor wasn't pointing anywhere, keep doing that.
@@ -494,7 +494,7 @@ pub trait Cursor {
/// ///
/// - If pointing at an instruction, the new instruction is inserted before the current /// - If pointing at an instruction, the new instruction is inserted before the current
/// instruction. /// instruction.
/// - If pointing at the bottom of an block, the new instruction is appended to the block. /// - If pointing at the bottom of a block, the new instruction is appended to the block.
/// - Otherwise panic. /// - Otherwise panic.
/// ///
/// In either case, the cursor is not moved, such that repeated calls to `insert_inst()` causes /// In either case, the cursor is not moved, such that repeated calls to `insert_inst()` causes
@@ -532,16 +532,16 @@ pub trait Cursor {
inst inst
} }
/// Insert an block at the current position and switch to it. /// Insert a block at the current position and switch to it.
/// ///
/// As far as possible, this method behaves as if the block header were an instruction inserted /// As far as possible, this method behaves as if the block header were an instruction inserted
/// at the current position. /// at the current position.
/// ///
/// - If the cursor is pointing at an existing instruction, *the current block is split in two* /// - If the cursor is pointing at an existing instruction, *the current block is split in two*
/// and the current instruction becomes the first instruction in the inserted block. /// and the current instruction becomes the first instruction in the inserted block.
/// - If the cursor points at the bottom of an block, the new block is inserted after the current /// - If the cursor points at the bottom of a block, the new block is inserted after the current
/// one, and moved to the bottom of the new block where instructions can be appended. /// one, and moved to the bottom of the new block where instructions can be appended.
/// - If the cursor points to the top of an block, the new block is inserted above the current one. /// - If the cursor points to the top of a block, the new block is inserted above the current one.
/// - If the cursor is not pointing at anything, the new block is placed last in the layout. /// - If the cursor is not pointing at anything, the new block is placed last in the layout.
/// ///
/// This means that it is always valid to call this method, and it always leaves the cursor in /// This means that it is always valid to call this method, and it always leaves the cursor in

View File

@@ -284,9 +284,9 @@ impl DominatorTree {
// //
// 1. Each block is a node, with outgoing edges for all the branches in the block. // 1. Each block is a node, with outgoing edges for all the branches in the block.
// 2. Each basic block is a node, with outgoing edges for the single branch at the end of // 2. Each basic block is a node, with outgoing edges for the single branch at the end of
// the BB. (An block is a linear sequence of basic blocks). // the BB. (A block is a linear sequence of basic blocks).
// //
// The first graph is a contraction of the second one. We want to compute an block post-order // The first graph is a contraction of the second one. We want to compute a block post-order
// that is compatible both graph interpretations. That is, if you compute a BB post-order // that is compatible both graph interpretations. That is, if you compute a BB post-order
// and then remove those BBs that do not correspond to block headers, you get a post-order of // and then remove those BBs that do not correspond to block headers, you get a post-order of
// the block graph. // the block graph.
@@ -302,15 +302,15 @@ impl DominatorTree {
// //
// Edge pruning: // Edge pruning:
// //
// In the BB graph, we keep an edge to an block the first time we visit the *source* side // In the BB graph, we keep an edge to a block the first time we visit the *source* side
// of the edge. Any subsequent edges to the same block are pruned. // of the edge. Any subsequent edges to the same block are pruned.
// //
// The equivalent tree is reached in the block graph by keeping the first edge to an block // The equivalent tree is reached in the block graph by keeping the first edge to a block
// in a top-down traversal of the successors. (And then visiting edges in a bottom-up // in a top-down traversal of the successors. (And then visiting edges in a bottom-up
// order). // order).
// //
// This pruning method makes it possible to compute the DFT without storing lots of // This pruning method makes it possible to compute the DFT without storing lots of
// information about the progress through an block. // information about the progress through a block.
// During this algorithm only, use `rpo_number` to hold the following state: // During this algorithm only, use `rpo_number` to hold the following state:
// //
@@ -348,7 +348,7 @@ impl DominatorTree {
/// Push `block` successors onto `self.stack`, filtering out those that have already been seen. /// Push `block` successors onto `self.stack`, filtering out those that have already been seen.
/// ///
/// The successors are pushed in program order which is important to get a split-invariant /// The successors are pushed in program order which is important to get a split-invariant
/// post-order. Split-invariant means that if an block is split in two, we get the same /// post-order. Split-invariant means that if a block is split in two, we get the same
/// post-order except for the insertion of the new block header at the split point. /// post-order except for the insertion of the new block header at the split point.
fn push_successors(&mut self, func: &Function, block: Block) { fn push_successors(&mut self, func: &Function, block: Block) {
for inst in func.layout.block_insts(block) { for inst in func.layout.block_insts(block) {
@@ -543,7 +543,7 @@ impl DominatorTreePreorder {
} }
} }
/// An iterator that enumerates the direct children of an block in the dominator tree. /// An iterator that enumerates the direct children of a block in the dominator tree.
pub struct ChildIter<'a> { pub struct ChildIter<'a> {
dtpo: &'a DominatorTreePreorder, dtpo: &'a DominatorTreePreorder,
next: PackedOption<Block>, next: PackedOption<Block>,
@@ -580,7 +580,7 @@ impl DominatorTreePreorder {
/// time. This is less general than the `DominatorTree` method because it only works with block /// time. This is less general than the `DominatorTree` method because it only works with block
/// program points. /// program points.
/// ///
/// An block is considered to dominate itself. /// A block is considered to dominate itself.
pub fn dominates(&self, a: Block, b: Block) -> bool { pub fn dominates(&self, a: Block, b: Block) -> bool {
let na = &self.nodes[a]; let na = &self.nodes[a];
let nb = &self.nodes[b]; let nb = &self.nodes[b];

View File

@@ -376,7 +376,7 @@ impl DataFlowGraph {
pub enum ValueDef { pub enum ValueDef {
/// Value is the n'th result of an instruction. /// Value is the n'th result of an instruction.
Result(Inst, usize), Result(Inst, usize),
/// Value is the n'th parameter to an block. /// Value is the n'th parameter to a block.
Param(Block, usize), Param(Block, usize),
} }
@@ -393,7 +393,7 @@ impl ValueDef {
pub fn unwrap_block(&self) -> Block { pub fn unwrap_block(&self) -> Block {
match *self { match *self {
Self::Param(block, _) => block, Self::Param(block, _) => block,
_ => panic!("Value is not an block parameter"), _ => panic!("Value is not a block parameter"),
} }
} }
@@ -419,7 +419,7 @@ enum ValueData {
/// Value is defined by an instruction. /// Value is defined by an instruction.
Inst { ty: Type, num: u16, inst: Inst }, Inst { ty: Type, num: u16, inst: Inst },
/// Value is an block parameter. /// Value is a block parameter.
Param { ty: Type, num: u16, block: Block }, Param { ty: Type, num: u16, block: Block },
/// Value is an alias of another value. /// Value is an alias of another value.
@@ -804,12 +804,12 @@ impl DataFlowGraph {
/// last `block` parameter. This can disrupt all the branch instructions jumping to this /// last `block` parameter. This can disrupt all the branch instructions jumping to this
/// `block` for which you have to change the branch argument order if necessary. /// `block` for which you have to change the branch argument order if necessary.
/// ///
/// Panics if `val` is not an block parameter. /// Panics if `val` is not a block parameter.
pub fn swap_remove_block_param(&mut self, val: Value) -> usize { pub fn swap_remove_block_param(&mut self, val: Value) -> usize {
let (block, num) = if let ValueData::Param { num, block, .. } = self.values[val] { let (block, num) = if let ValueData::Param { num, block, .. } = self.values[val] {
(block, num) (block, num)
} else { } else {
panic!("{} must be an block parameter", val); panic!("{} must be a block parameter", val);
}; };
self.blocks[block] self.blocks[block]
.params .params
@@ -826,7 +826,7 @@ impl DataFlowGraph {
{ {
*old_num = num; *old_num = num;
} else { } else {
panic!("{} should be an Block parameter", last_arg_val); panic!("{} should be a Block parameter", last_arg_val);
} }
} }
num as usize num as usize
@@ -838,7 +838,7 @@ impl DataFlowGraph {
let (block, num) = if let ValueData::Param { num, block, .. } = self.values[val] { let (block, num) = if let ValueData::Param { num, block, .. } = self.values[val] {
(block, num) (block, num)
} else { } else {
panic!("{} must be an block parameter", val); panic!("{} must be a block parameter", val);
}; };
self.blocks[block] self.blocks[block]
.params .params
@@ -853,7 +853,7 @@ impl DataFlowGraph {
*num -= 1; *num -= 1;
} }
_ => panic!( _ => panic!(
"{} must be an block parameter", "{} must be a block parameter",
self.blocks[block] self.blocks[block]
.params .params
.get(index as usize, &self.value_lists) .get(index as usize, &self.value_lists)
@@ -880,7 +880,7 @@ impl DataFlowGraph {
}; };
} }
/// Replace an block parameter with a new value of type `ty`. /// Replace a block parameter with a new value of type `ty`.
/// ///
/// The `old_value` must be an attached block parameter. It is removed from its place in the list /// The `old_value` must be an attached block parameter. It is removed from its place in the list
/// of parameters and replaced by a new value of type `new_type`. The new value gets the same /// of parameters and replaced by a new value of type `new_type`. The new value gets the same
@@ -894,7 +894,7 @@ impl DataFlowGraph {
let (block, num) = if let ValueData::Param { num, block, .. } = self.values[old_value] { let (block, num) = if let ValueData::Param { num, block, .. } = self.values[old_value] {
(block, num) (block, num)
} else { } else {
panic!("{} must be an block parameter", old_value); panic!("{} must be a block parameter", old_value);
}; };
let new_arg = self.make_value(ValueData::Param { let new_arg = self.make_value(ValueData::Param {
ty: new_type, ty: new_type,

View File

@@ -1,6 +1,6 @@
//! Function layout. //! Function layout.
//! //!
//! The order of basic blocks in a function and the order of instructions in an block is //! The order of basic blocks in a function and the order of instructions in a block is
//! determined by the `Layout` data structure defined in this module. //! determined by the `Layout` data structure defined in this module.
use crate::entity::SecondaryMap; use crate::entity::SecondaryMap;
@@ -21,7 +21,7 @@ use log::debug;
/// ///
/// - The order of blocks in the function. /// - The order of blocks in the function.
/// - Which block contains a given instruction. /// - Which block contains a given instruction.
/// - The order of instructions with an block. /// - The order of instructions with a block.
/// ///
/// While data dependencies are not recorded, instruction ordering does affect control /// While data dependencies are not recorded, instruction ordering does affect control
/// dependencies, so part of the semantics of the program are determined by the layout. /// dependencies, so part of the semantics of the program are determined by the layout.
@@ -75,7 +75,7 @@ impl Layout {
/// like line numbers in BASIC: 10, 20, 30, ... /// like line numbers in BASIC: 10, 20, 30, ...
/// ///
/// The block sequence numbers are strictly increasing, and so are the instruction sequence numbers /// The block sequence numbers are strictly increasing, and so are the instruction sequence numbers
/// within an block. The instruction sequence numbers are all between the sequence number of their /// within a block. The instruction sequence numbers are all between the sequence number of their
/// containing block and the following block. /// containing block and the following block.
/// ///
/// The result is that sequence numbers work like BASIC line numbers for the textual form of the IR. /// The result is that sequence numbers work like BASIC line numbers for the textual form of the IR.
@@ -335,7 +335,7 @@ impl Layout {
/// Methods for laying out blocks. /// Methods for laying out blocks.
/// ///
/// An unknown block starts out as *not inserted* in the block layout. The layout is a linear order of /// An unknown block starts out as *not inserted* in the block layout. The layout is a linear order of
/// inserted blocks. Once an block has been inserted in the layout, instructions can be added. An block /// inserted blocks. Once a block has been inserted in the layout, instructions can be added. A block
/// can only be removed from the layout when it is empty. /// can only be removed from the layout when it is empty.
/// ///
/// Since every block must end with a terminator instruction which cannot fall through, the layout of /// Since every block must end with a terminator instruction which cannot fall through, the layout of
@@ -514,7 +514,7 @@ impl<'f> IntoIterator for &'f Layout {
/// Methods for arranging instructions. /// Methods for arranging instructions.
/// ///
/// An instruction starts out as *not inserted* in the layout. An instruction can be inserted into /// An instruction starts out as *not inserted* in the layout. An instruction can be inserted into
/// an block at a given position. /// a block at a given position.
impl Layout { impl Layout {
/// Get the block containing `inst`, or `None` if `inst` is not inserted in the layout. /// Get the block containing `inst`, or `None` if `inst` is not inserted in the layout.
pub fn inst_block(&self, inst: Inst) -> Option<Block> { pub fn inst_block(&self, inst: Inst) -> Option<Block> {
@@ -559,12 +559,12 @@ impl Layout {
self.assign_inst_seq(inst); self.assign_inst_seq(inst);
} }
/// Fetch an block's first instruction. /// Fetch a block's first instruction.
pub fn first_inst(&self, block: Block) -> Option<Inst> { pub fn first_inst(&self, block: Block) -> Option<Inst> {
self.blocks[block].first_inst.into() self.blocks[block].first_inst.into()
} }
/// Fetch an block's last instruction. /// Fetch a block's last instruction.
pub fn last_inst(&self, block: Block) -> Option<Inst> { pub fn last_inst(&self, block: Block) -> Option<Inst> {
self.blocks[block].last_inst.into() self.blocks[block].last_inst.into()
} }
@@ -579,7 +579,7 @@ impl Layout {
self.insts[inst].prev.expand() self.insts[inst].prev.expand()
} }
/// Fetch the first instruction in an block's terminal branch group. /// Fetch the first instruction in a block's terminal branch group.
pub fn canonical_branch_inst(&self, dfg: &DataFlowGraph, block: Block) -> Option<Inst> { pub fn canonical_branch_inst(&self, dfg: &DataFlowGraph, block: Block) -> Option<Inst> {
// Basic blocks permit at most two terminal branch instructions. // Basic blocks permit at most two terminal branch instructions.
// If two, the former is conditional and the latter is unconditional. // If two, the former is conditional and the latter is unconditional.
@@ -724,7 +724,7 @@ struct InstNode {
seq: SequenceNumber, seq: SequenceNumber,
} }
/// Iterate over instructions in an block in layout order. See `Layout::block_insts()`. /// Iterate over instructions in a block in layout order. See `Layout::block_insts()`.
pub struct Insts<'f> { pub struct Insts<'f> {
layout: &'f Layout, layout: &'f Layout,
head: Option<Inst>, head: Option<Inst>,

View File

@@ -10,7 +10,7 @@ use core::u32;
/// begin or end. It can be either: /// begin or end. It can be either:
/// ///
/// 1. An instruction or /// 1. An instruction or
/// 2. An block header. /// 2. A block header.
/// ///
/// This corresponds more or less to the lines in the textual form of Cranelift IR. /// This corresponds more or less to the lines in the textual form of Cranelift IR.
#[derive(PartialEq, Eq, Clone, Copy)] #[derive(PartialEq, Eq, Clone, Copy)]
@@ -47,7 +47,7 @@ impl From<ValueDef> for ProgramPoint {
pub enum ExpandedProgramPoint { pub enum ExpandedProgramPoint {
/// An instruction in the function. /// An instruction in the function.
Inst(Inst), Inst(Inst),
/// An block header. /// A block header.
Block(Block), Block(Block),
} }

View File

@@ -121,7 +121,7 @@ fn static_addr(
pos.func.dfg.replace(inst).iconst(addr_ty, 0); pos.func.dfg.replace(inst).iconst(addr_ty, 0);
// Split Block, as the trap is a terminator instruction. // Split Block, as the trap is a terminator instruction.
let curr_block = pos.current_block().expect("Cursor is not in an block"); let curr_block = pos.current_block().expect("Cursor is not in a block");
let new_block = pos.func.dfg.make_block(); let new_block = pos.func.dfg.make_block();
pos.insert_block(new_block); pos.insert_block(new_block);
cfg.recompute_block(pos.func, curr_block); cfg.recompute_block(pos.func, curr_block);

View File

@@ -95,7 +95,7 @@ pub fn vsplit(
split_any(func, cfg, pos, srcloc, value, Opcode::Vconcat) split_any(func, cfg, pos, srcloc, value, Opcode::Vconcat)
} }
/// After splitting an block argument, we need to go back and fix up all of the predecessor /// After splitting a block argument, we need to go back and fix up all of the predecessor
/// instructions. This is potentially a recursive operation, but we don't implement it recursively /// instructions. This is potentially a recursive operation, but we don't implement it recursively
/// since that could use up too muck stack. /// since that could use up too muck stack.
/// ///
@@ -260,7 +260,7 @@ fn split_value(
} }
} }
ValueDef::Param(block, num) => { ValueDef::Param(block, num) => {
// This is an block parameter. // This is a block parameter.
// We can split the parameter value unless this is the entry block. // We can split the parameter value unless this is the entry block.
if pos.func.layout.entry_block() != Some(block) { if pos.func.layout.entry_block() != Some(block) {
reuse = Some(split_block_param(pos, block, num, value, concat, repairs)); reuse = Some(split_block_param(pos, block, num, value, concat, repairs));

View File

@@ -71,7 +71,7 @@ impl LoopAnalysis {
self.loops[lp].parent.expand() self.loops[lp].parent.expand()
} }
/// Determine if an Block belongs to a loop by running a finger along the loop tree. /// Determine if a Block belongs to a loop by running a finger along the loop tree.
/// ///
/// Returns `true` if `block` is in loop `lp`. /// Returns `true` if `block` is in loop `lp`.
pub fn is_in_loop(&self, block: Block, lp: Loop) -> bool { pub fn is_in_loop(&self, block: Block, lp: Loop) -> bool {

View File

@@ -122,7 +122,7 @@ use cranelift_entity::{PrimaryMap, SecondaryMap};
// ============================================================================================= // =============================================================================================
// Data structures used for discovery of trees // Data structures used for discovery of trees
// `ZeroOneOrMany` is used to record the number of predecessors an Block block has. The `Zero` case // `ZeroOneOrMany` is used to record the number of predecessors a Block block has. The `Zero` case
// is included so as to cleanly handle the case where the incoming graph has unreachable Blocks. // is included so as to cleanly handle the case where the incoming graph has unreachable Blocks.
#[derive(Clone, PartialEq)] #[derive(Clone, PartialEq)]
@@ -184,7 +184,7 @@ struct AvailEnv {
} }
// `ProcessingStackElem` combines AvailEnv with contextual information needed to "navigate" within // `ProcessingStackElem` combines AvailEnv with contextual information needed to "navigate" within
// an Block. // a Block.
// //
// A ProcessingStackElem conceptually has the lifetime of exactly one Block: once the current Block is // A ProcessingStackElem conceptually has the lifetime of exactly one Block: once the current Block is
// completed, the ProcessingStackElem will be abandoned. In practice the top level state, // completed, the ProcessingStackElem will be abandoned. In practice the top level state,
@@ -192,7 +192,7 @@ struct AvailEnv {
// //
// Note that ProcessingStackElem must contain a CursorPosition. The CursorPosition, which // Note that ProcessingStackElem must contain a CursorPosition. The CursorPosition, which
// indicates where we are in the current Block, cannot be implicitly maintained by looping over all // indicates where we are in the current Block, cannot be implicitly maintained by looping over all
// the instructions in an Block in turn, because we may choose to suspend processing the current Block // the instructions in a Block in turn, because we may choose to suspend processing the current Block
// at a side exit, continue by processing the subtree reached via the side exit, and only later // at a side exit, continue by processing the subtree reached via the side exit, and only later
// resume the current Block. // resume the current Block.

View File

@@ -2,7 +2,7 @@
//! //!
//! Conventional SSA (CSSA) form is a subset of SSA form where any (transitively) phi-related //! Conventional SSA (CSSA) form is a subset of SSA form where any (transitively) phi-related
//! values do not interfere. We construct CSSA by building virtual registers that are as large as //! values do not interfere. We construct CSSA by building virtual registers that are as large as
//! possible and inserting copies where necessary such that all argument values passed to an block //! possible and inserting copies where necessary such that all argument values passed to a block
//! parameter will belong to the same virtual register as the block parameter value itself. //! parameter will belong to the same virtual register as the block parameter value itself.
use crate::cursor::{Cursor, EncCursor}; use crate::cursor::{Cursor, EncCursor};
@@ -233,7 +233,7 @@ impl<'a> Context<'a> {
} }
// Check for basic interference: If `arg` overlaps a value defined at the entry to // Check for basic interference: If `arg` overlaps a value defined at the entry to
// `block`, it can never be used as an block argument. // `block`, it can never be used as a block argument.
let interference = { let interference = {
let lr = &self.liveness[arg]; let lr = &self.liveness[arg];
@@ -874,7 +874,7 @@ struct VirtualCopies {
// Filter for the currently active node iterator. // Filter for the currently active node iterator.
// //
// An block => (set_id, num) entry means that branches to `block` are active in `set_id` with // A block => (set_id, num) entry means that branches to `block` are active in `set_id` with
// branch argument number `num`. // branch argument number `num`.
filter: FxHashMap<Block, (u8, usize)>, filter: FxHashMap<Block, (u8, usize)>,
} }
@@ -953,7 +953,7 @@ impl VirtualCopies {
debug_assert_eq!(popped, Some(param)); debug_assert_eq!(popped, Some(param));
// The domtree pre-order in `self.params` guarantees that all parameters defined at the // The domtree pre-order in `self.params` guarantees that all parameters defined at the
// same block will be adjacent. This means we can see when all parameters at an block have been // same block will be adjacent. This means we can see when all parameters at a block have been
// merged. // merged.
// //
// We don't care about the last parameter - when that is merged we are done. // We don't care about the last parameter - when that is merged we are done.

View File

@@ -24,7 +24,7 @@
//! a register. //! a register.
//! //!
//! 5. The code must be in Conventional SSA form. Among other things, this means that values passed //! 5. The code must be in Conventional SSA form. Among other things, this means that values passed
//! as arguments when branching to an block must belong to the same virtual register as the //! as arguments when branching to a block must belong to the same virtual register as the
//! corresponding block argument value. //! corresponding block argument value.
//! //!
//! # Iteration order //! # Iteration order
@@ -35,7 +35,7 @@
//! defined by the instruction and only consider the colors of other values that are live at the //! defined by the instruction and only consider the colors of other values that are live at the
//! instruction. //! instruction.
//! //!
//! The first time we see a branch to an block, the block's argument values are colored to match the //! The first time we see a branch to a block, the block's argument values are colored to match the
//! registers currently holding branch argument values passed to the predecessor branch. By //! registers currently holding branch argument values passed to the predecessor branch. By
//! visiting blocks in a CFG topological order, we guarantee that at least one predecessor branch has //! visiting blocks in a CFG topological order, we guarantee that at least one predecessor branch has
//! been visited before the destination block. Therefore, the block's arguments are already colored. //! been visited before the destination block. Therefore, the block's arguments are already colored.
@@ -224,7 +224,7 @@ impl<'a> Context<'a> {
SingleDest(block, _) => block, SingleDest(block, _) => block,
}; };
// We have a single branch with a single target, and an block with a single // We have a single branch with a single target, and a block with a single
// predecessor. Thus we can forward the diversion set to the next block. // predecessor. Thus we can forward the diversion set to the next block.
if self.cfg.pred_iter(target).count() == 1 { if self.cfg.pred_iter(target).count() == 1 {
// Transfer the diversion to the next block. // Transfer the diversion to the next block.

View File

@@ -4,7 +4,7 @@
//! Sometimes, it is necessary to move register values to a different register in order to satisfy //! Sometimes, it is necessary to move register values to a different register in order to satisfy
//! instruction constraints. //! instruction constraints.
//! //!
//! These register diversions are local to an block. No values can be diverted when entering a new //! These register diversions are local to a block. No values can be diverted when entering a new
//! block. //! block.
use crate::fx::FxHashMap; use crate::fx::FxHashMap;
@@ -38,7 +38,7 @@ impl Diversion {
} }
} }
/// Keep track of diversions in an block. /// Keep track of diversions in a block.
#[derive(Clone)] #[derive(Clone)]
pub struct RegDiversions { pub struct RegDiversions {
current: FxHashMap<Value, Diversion>, current: FxHashMap<Value, Diversion>,

View File

@@ -1,6 +1,6 @@
//! Track which values are live in an block with instruction granularity. //! Track which values are live in a block with instruction granularity.
//! //!
//! The `LiveValueTracker` keeps track of the set of live SSA values at each instruction in an block. //! The `LiveValueTracker` keeps track of the set of live SSA values at each instruction in a block.
//! The sets of live values are computed on the fly as the tracker is moved from instruction to //! The sets of live values are computed on the fly as the tracker is moved from instruction to
//! instruction, starting at the block header. //! instruction, starting at the block header.
@@ -16,13 +16,13 @@ use alloc::vec::Vec;
type ValueList = EntityList<Value>; type ValueList = EntityList<Value>;
/// Compute and track live values throughout an block. /// Compute and track live values throughout a block.
pub struct LiveValueTracker { pub struct LiveValueTracker {
/// The set of values that are live at the current program point. /// The set of values that are live at the current program point.
live: LiveValueVec, live: LiveValueVec,
/// Saved set of live values for every jump and branch that can potentially be an immediate /// Saved set of live values for every jump and branch that can potentially be an immediate
/// dominator of an block. /// dominator of a block.
/// ///
/// This is the set of values that are live *before* the branch. /// This is the set of values that are live *before* the branch.
idom_sets: FxHashMap<Inst, ValueList>, idom_sets: FxHashMap<Inst, ValueList>,

View File

@@ -18,7 +18,7 @@
//! //!
//! The set of `LiveRange` instances can answer these questions through their `def_local_end` and //! The set of `LiveRange` instances can answer these questions through their `def_local_end` and
//! `livein_local_end` queries. The coloring algorithm visits blocks in a topological order of the //! `livein_local_end` queries. The coloring algorithm visits blocks in a topological order of the
//! dominator tree, so it can compute the set of live values at the beginning of an block by starting //! dominator tree, so it can compute the set of live values at the beginning of a block by starting
//! from the set of live values at the dominating branch instruction and filtering it with //! from the set of live values at the dominating branch instruction and filtering it with
//! `livein_local_end`. These sets do not need to be stored in the liveness analysis. //! `livein_local_end`. These sets do not need to be stored in the liveness analysis.
//! //!

View File

@@ -131,7 +131,7 @@ use smallvec::SmallVec;
/// 2. The *live-in intervals* are the local intervals in the remaining blocks. /// 2. The *live-in intervals* are the local intervals in the remaining blocks.
/// ///
/// A live-in interval always begins at the block header, while the def interval can begin at the /// A live-in interval always begins at the block header, while the def interval can begin at the
/// defining instruction, or at the block header for an block argument value. /// defining instruction, or at the block header for a block argument value.
/// ///
/// All values have a def interval, but a large proportion of values don't have any live-in /// All values have a def interval, but a large proportion of values don't have any live-in
/// intervals. These are called *local live ranges*. /// intervals. These are called *local live ranges*.
@@ -139,7 +139,7 @@ use smallvec::SmallVec;
/// # Program order requirements /// # Program order requirements
/// ///
/// The internal representation of a `LiveRange` depends on a consistent `ProgramOrder` both for /// The internal representation of a `LiveRange` depends on a consistent `ProgramOrder` both for
/// ordering instructions inside an block *and* for ordering blocks. The methods that depend on the /// ordering instructions inside a block *and* for ordering blocks. The methods that depend on the
/// ordering take an explicit `ProgramOrder` object, and it is the caller's responsibility to /// ordering take an explicit `ProgramOrder` object, and it is the caller's responsibility to
/// ensure that the provided ordering is consistent between calls. /// ensure that the provided ordering is consistent between calls.
/// ///
@@ -363,7 +363,7 @@ impl<PO: ProgramOrder> GenericLiveRange<PO> {
/// Get the program point where this live range is defined. /// Get the program point where this live range is defined.
/// ///
/// This will be an block header when the value is an block argument, otherwise it is the defining /// This will be a block header when the value is a block argument, otherwise it is the defining
/// instruction. /// instruction.
pub fn def(&self) -> ProgramPoint { pub fn def(&self) -> ProgramPoint {
self.def_begin self.def_begin
@@ -385,7 +385,7 @@ impl<PO: ProgramOrder> GenericLiveRange<PO> {
self.def_end self.def_end
} }
/// Get the local end-point of this live range in an block where it is live-in. /// Get the local end-point of this live range in a block where it is live-in.
/// ///
/// If this live range is not live-in to `block`, return `None`. Otherwise, return the end-point /// If this live range is not live-in to `block`, return `None`. Otherwise, return the end-point
/// of this live range's local interval in `block`. /// of this live range's local interval in `block`.
@@ -409,7 +409,7 @@ impl<PO: ProgramOrder> GenericLiveRange<PO> {
/// Is this value live-in to `block`? /// Is this value live-in to `block`?
/// ///
/// An block argument is not considered to be live in. /// A block argument is not considered to be live in.
pub fn is_livein(&self, block: Block, order: &PO) -> bool { pub fn is_livein(&self, block: Block, order: &PO) -> bool {
self.livein_local_end(block, order).is_some() self.livein_local_end(block, order).is_some()
} }
@@ -594,7 +594,7 @@ mod tests {
assert!(lr.is_local()); assert!(lr.is_local());
assert_eq!(lr.def(), e2.into()); assert_eq!(lr.def(), e2.into());
assert_eq!(lr.def_local_end(), e2.into()); assert_eq!(lr.def_local_end(), e2.into());
// The def interval of an block argument does not count as live-in. // The def interval of a block argument does not count as live-in.
assert_eq!(lr.livein_local_end(e2, PO), None); assert_eq!(lr.livein_local_end(e2, PO), None);
PO.validate(&lr); PO.validate(&lr);
} }

View File

@@ -199,7 +199,7 @@ impl<'a> Context<'a> {
self.pressure.reset(); self.pressure.reset();
self.take_live_regs(liveins); self.take_live_regs(liveins);
// An block can have an arbitrary (up to 2^16...) number of parameters, so they are not // A block can have an arbitrary (up to 2^16...) number of parameters, so they are not
// guaranteed to fit in registers. // guaranteed to fit in registers.
for lv in params { for lv in params {
if let Affinity::Reg(rci) = lv.affinity { if let Affinity::Reg(rci) = lv.affinity {

View File

@@ -5,11 +5,11 @@
//! output. //! output.
//! //!
//! A virtual register is typically built by merging together SSA values that are "phi-related" - //! A virtual register is typically built by merging together SSA values that are "phi-related" -
//! that is, one value is passed as an block argument to a branch and the other is the block parameter //! that is, one value is passed as a block argument to a branch and the other is the block parameter
//! value itself. //! value itself.
//! //!
//! If any values in a virtual register are spilled, they will use the same stack slot. This avoids //! If any values in a virtual register are spilled, they will use the same stack slot. This avoids
//! memory-to-memory copies when a spilled value is passed as an block argument. //! memory-to-memory copies when a spilled value is passed as a block argument.
use crate::dbg::DisplayList; use crate::dbg::DisplayList;
use crate::dominator_tree::DominatorTreePreorder; use crate::dominator_tree::DominatorTreePreorder;

View File

@@ -810,7 +810,7 @@ enum BranchOrderKind {
/// Reorder branches to encourage fallthroughs. /// Reorder branches to encourage fallthroughs.
/// ///
/// When an block ends with a conditional branch followed by an unconditional /// When a block ends with a conditional branch followed by an unconditional
/// branch, this will reorder them if one of them is branching to the next Block /// branch, this will reorder them if one of them is branching to the next Block
/// layout-wise. The unconditional jump can then become a fallthrough. /// layout-wise. The unconditional jump can then become a fallthrough.
fn branch_order(pos: &mut FuncCursor, cfg: &mut ControlFlowGraph, block: Block, inst: Inst) { fn branch_order(pos: &mut FuncCursor, cfg: &mut ControlFlowGraph, block: Block, inst: Inst) {

View File

@@ -13,7 +13,7 @@ use crate::verifier::{VerifierErrors, VerifierStepResult};
/// ///
/// Conventional SSA form is represented in Cranelift with the help of virtual registers: /// Conventional SSA form is represented in Cranelift with the help of virtual registers:
/// ///
/// - Two values are said to be *PHI-related* if one is an block argument and the other is passed as /// - Two values are said to be *PHI-related* if one is a block argument and the other is passed as
/// a branch argument in a location that matches the first value. /// a branch argument in a location that matches the first value.
/// - PHI-related values must belong to the same virtual register. /// - PHI-related values must belong to the same virtual register.
/// - Two values in the same virtual register must not have overlapping live ranges. /// - Two values in the same virtual register must not have overlapping live ranges.

View File

@@ -16,7 +16,7 @@ use crate::verifier::{VerifierErrors, VerifierStepResult};
/// - All values in the program must have a live range. /// - All values in the program must have a live range.
/// - The live range def point must match where the value is defined. /// - The live range def point must match where the value is defined.
/// - The live range must reach all uses. /// - The live range must reach all uses.
/// - When a live range is live-in to an block, it must be live at all the predecessors. /// - When a live range is live-in to a block, it must be live at all the predecessors.
/// - The live range affinity must be compatible with encoding constraints. /// - The live range affinity must be compatible with encoding constraints.
/// ///
/// We don't verify that live ranges are minimal. This would require recomputing live ranges for /// We don't verify that live ranges are minimal. This would require recomputing live ranges for

View File

@@ -15,7 +15,7 @@ use crate::verifier::{VerifierErrors, VerifierStepResult};
/// instruction encoding recipes. /// instruction encoding recipes.
/// ///
/// Values can be temporarily diverted to a different location by using the `regmove`, `regspill`, /// Values can be temporarily diverted to a different location by using the `regmove`, `regspill`,
/// and `regfill` instructions, but only inside an block. /// and `regfill` instructions, but only inside a block.
/// ///
/// If a liveness analysis is provided, it is used to verify that there are no active register /// If a liveness analysis is provided, it is used to verify that there are no active register
/// diversions across control flow edges. /// diversions across control flow edges.

View File

@@ -19,13 +19,13 @@
//! SSA form //! SSA form
//! //!
//! - Values must be defined by an instruction that exists and that is inserted in //! - Values must be defined by an instruction that exists and that is inserted in
//! an block, or be an argument of an existing block. //! a block, or be an argument of an existing block.
//! - Values used by an instruction must dominate the instruction. //! - Values used by an instruction must dominate the instruction.
//! //!
//! Control flow graph and dominator tree integrity: //! Control flow graph and dominator tree integrity:
//! //!
//! - All predecessors in the CFG must be branches to the block. //! - All predecessors in the CFG must be branches to the block.
//! - All branches to an block must be present in the CFG. //! - All branches to a block must be present in the CFG.
//! - A recomputed dominator tree is identical to the existing one. //! - A recomputed dominator tree is identical to the existing one.
//! //!
//! Type checking //! Type checking
@@ -961,7 +961,7 @@ impl<'a> Verifier<'a> {
format!("{} is defined by invalid instruction {}", v, def_inst), format!("{} is defined by invalid instruction {}", v, def_inst),
)); ));
} }
// Defining instruction is inserted in an block. // Defining instruction is inserted in a block.
if self.func.layout.inst_block(def_inst) == None { if self.func.layout.inst_block(def_inst) == None {
return errors.fatal(( return errors.fatal((
loc_inst, loc_inst,

View File

@@ -40,11 +40,11 @@ pub struct FunctionBuilder<'a> {
#[derive(Clone, Default)] #[derive(Clone, Default)]
struct BlockData { struct BlockData {
/// An Block is "pristine" iff no instructions have been added since the last /// A Block is "pristine" iff no instructions have been added since the last
/// call to `switch_to_block()`. /// call to `switch_to_block()`.
pristine: bool, pristine: bool,
/// An Block is "filled" iff a terminator instruction has been inserted since /// A Block is "filled" iff a terminator instruction has been inserted since
/// the last call to `switch_to_block()`. /// the last call to `switch_to_block()`.
/// ///
/// A filled block cannot be pristine. /// A filled block cannot be pristine.
@@ -832,7 +832,7 @@ impl<'a> FunctionBuilder<'a> {
); );
} }
/// An Block is 'filled' when a terminator instruction is present. /// A Block is 'filled' when a terminator instruction is present.
fn fill_current_block(&mut self) { fn fill_current_block(&mut self) {
self.func_ctx.blocks[self.position.block.unwrap()].filled = true; self.func_ctx.blocks[self.position.block.unwrap()].filled = true;
} }

View File

@@ -333,7 +333,7 @@ impl SSABuilder {
// Part 1: With a mutable borrow of self, update the DataFlowGraph if necessary. // Part 1: With a mutable borrow of self, update the DataFlowGraph if necessary.
let case = match self.ssa_blocks[ssa_block] { let case = match self.ssa_blocks[ssa_block] {
SSABlockData::BlockHeader(ref mut data) => { SSABlockData::BlockHeader(ref mut data) => {
// The block has multiple predecessors so we append an Block parameter that // The block has multiple predecessors so we append a Block parameter that
// will serve as a value. // will serve as a value.
if data.sealed { if data.sealed {
if data.predecessors.len() == 1 { if data.predecessors.len() == 1 {
@@ -408,7 +408,7 @@ impl SSABuilder {
self.block_headers[block] = ssa_block.into(); self.block_headers[block] = ssa_block.into();
ssa_block ssa_block
} }
/// Gets the header block corresponding to an Block, panics if the Block or the header block /// Gets the header block corresponding to a Block, panics if the Block or the header block
/// isn't declared. /// isn't declared.
pub fn header_block(&self, block: Block) -> SSABlock { pub fn header_block(&self, block: Block) -> SSABlock {
self.block_headers self.block_headers
@@ -491,7 +491,7 @@ impl SSABuilder {
} }
}; };
// For each undef var we look up values in the predecessors and create an block parameter // For each undef var we look up values in the predecessors and create a block parameter
// only if necessary. // only if necessary.
for (var, val) in undef_vars { for (var, val) in undef_vars {
let ty = func.dfg.value_type(val); let ty = func.dfg.value_type(val);
@@ -516,13 +516,13 @@ impl SSABuilder {
} }
} }
/// Given the local SSA Value of a Variable in an Block, perform a recursive lookup on /// Given the local SSA Value of a Variable in a Block, perform a recursive lookup on
/// predecessors to determine if it is redundant with another Value earlier in the CFG. /// predecessors to determine if it is redundant with another Value earlier in the CFG.
/// ///
/// If such a Value exists and is redundant, the local Value is replaced by the /// If such a Value exists and is redundant, the local Value is replaced by the
/// corresponding non-local Value. If the original Value was an Block parameter, /// corresponding non-local Value. If the original Value was a Block parameter,
/// the parameter may be removed if redundant. Parameters are placed eagerly by callers /// the parameter may be removed if redundant. Parameters are placed eagerly by callers
/// to avoid infinite loops when looking up a Value for an Block that is in a CFG loop. /// to avoid infinite loops when looking up a Value for a Block that is in a CFG loop.
/// ///
/// Doing this lookup for each Value in each Block preserves SSA form during construction. /// Doing this lookup for each Value in each Block preserves SSA form during construction.
/// ///
@@ -623,7 +623,7 @@ impl SSABuilder {
} }
ZeroOneOrMore::One(pred_val) => { ZeroOneOrMore::One(pred_val) => {
// Here all the predecessors use a single value to represent our variable // Here all the predecessors use a single value to represent our variable
// so we don't need to have it as an block argument. // so we don't need to have it as a block argument.
// We need to replace all the occurrences of val with pred_val but since // We need to replace all the occurrences of val with pred_val but since
// we can't afford a re-writing pass right now we just declare an alias. // we can't afford a re-writing pass right now we just declare an alias.
// Resolve aliases eagerly so that we can check for cyclic aliasing, // Resolve aliases eagerly so that we can check for cyclic aliasing,
@@ -692,7 +692,7 @@ impl SSABuilder {
) -> Option<(Block, SSABlock, Inst)> { ) -> Option<(Block, SSABlock, Inst)> {
match func.dfg.analyze_branch(jump_inst) { match func.dfg.analyze_branch(jump_inst) {
BranchInfo::NotABranch => { BranchInfo::NotABranch => {
panic!("you have declared a non-branch instruction as a predecessor to an block"); panic!("you have declared a non-branch instruction as a predecessor to a block");
} }
// For a single destination appending a jump argument to the instruction // For a single destination appending a jump argument to the instruction
// is sufficient. // is sufficient.

View File

@@ -558,7 +558,7 @@ impl<'a> Parser<'a> {
err!(self.loc, "expected jump table number: jt«n»") err!(self.loc, "expected jump table number: jt«n»")
} }
// Match and consume an block reference. // Match and consume a block reference.
fn match_block(&mut self, err_msg: &str) -> ParseResult<Block> { fn match_block(&mut self, err_msg: &str) -> ParseResult<Block> {
if let Some(Token::Block(block)) = self.token() { if let Some(Token::Block(block)) = self.token() {
self.consume(); self.consume();

View File

@@ -44,7 +44,7 @@ pub struct Details<'a> {
/// A comment in a parsed function. /// A comment in a parsed function.
/// ///
/// The comment belongs to the immediately preceding entity, whether that is an block header, and /// The comment belongs to the immediately preceding entity, whether that is a block header, and
/// instruction, or one of the preamble declarations. /// instruction, or one of the preamble declarations.
/// ///
/// Comments appearing inside the function but before the preamble, as well as comments appearing /// Comments appearing inside the function but before the preamble, as well as comments appearing

View File

@@ -274,7 +274,7 @@ impl Mutator for ReplaceInstWithTrap {
} }
} }
/// Try to remove an block. /// Try to remove a block.
struct RemoveBlock { struct RemoveBlock {
block: Block, block: Block,
} }

View File

@@ -185,10 +185,10 @@ pub fn translate_operator<FE: FuncEnvironment + ?Sized>(
let (params, results) = blocktype_params_results(module_translation_state, *ty)?; let (params, results) = blocktype_params_results(module_translation_state, *ty)?;
let (destination, else_data) = if params == results { let (destination, else_data) = if params == results {
// It is possible there is no `else` block, so we will only // It is possible there is no `else` block, so we will only
// allocate an block for it if/when we find the `else`. For now, // allocate a block for it if/when we find the `else`. For now,
// we if the condition isn't true, then we jump directly to the // we if the condition isn't true, then we jump directly to the
// destination block following the whole `if...end`. If we do end // destination block following the whole `if...end`. If we do end
// up discovering an `else`, then we will allocate an block for it // up discovering an `else`, then we will allocate a block for it
// and go back and patch the jump. // and go back and patch the jump.
let destination = block_with_params(builder, results, environ)?; let destination = block_with_params(builder, results, environ)?;
let branch_inst = builder let branch_inst = builder
@@ -212,7 +212,7 @@ pub fn translate_operator<FE: FuncEnvironment + ?Sized>(
builder.seal_block(next_block); // Only predecessor is the current block. builder.seal_block(next_block); // Only predecessor is the current block.
builder.switch_to_block(next_block); builder.switch_to_block(next_block);
// Here we append an argument to an Block targeted by an argumentless jump instruction // Here we append an argument to a Block targeted by an argumentless jump instruction
// But in fact there are two cases: // But in fact there are two cases:
// - either the If does not have a Else clause, in that case ty = EmptyBlock // - either the If does not have a Else clause, in that case ty = EmptyBlock
// and we add nothing; // and we add nothing;
@@ -241,7 +241,7 @@ pub fn translate_operator<FE: FuncEnvironment + ?Sized>(
// We have a branch from the head of the `if` to the `else`. // We have a branch from the head of the `if` to the `else`.
state.reachable = true; state.reachable = true;
// Ensure we have an block for the `else` block (it may have // Ensure we have a block for the `else` block (it may have
// already been pre-allocated, see `ElseData` for details). // already been pre-allocated, see `ElseData` for details).
let else_block = match *else_data { let else_block = match *else_data {
ElseData::NoElse { branch_inst } => { ElseData::NoElse { branch_inst } => {