@@ -242,7 +242,9 @@ pub fn dominators<G: ControlFlowGraph>(graph: G) -> Dominators<G::Node> {
242
242
immediate_dominators[ * node] = Some ( pre_order_to_real[ idom[ idx] ] ) ;
243
243
}
244
244
245
- Dominators { post_order_rank, immediate_dominators }
245
+ let start_node = graph. start_node ( ) ;
246
+ immediate_dominators[ start_node] = None ;
247
+ Dominators { start_node, post_order_rank, immediate_dominators }
246
248
}
247
249
248
250
/// Evaluate the link-eval virtual forest, providing the currently minimum semi
@@ -308,6 +310,7 @@ fn compress(
308
310
/// Tracks the list of dominators for each node.
309
311
#[ derive( Clone , Debug ) ]
310
312
pub struct Dominators < N : Idx > {
313
+ start_node : N ,
311
314
post_order_rank : IndexVec < N , usize > ,
312
315
// Even though we track only the immediate dominator of each node, it's
313
316
// possible to get its full list of dominators by looking up the dominator
@@ -316,14 +319,14 @@ pub struct Dominators<N: Idx> {
316
319
}
317
320
318
321
impl < Node : Idx > Dominators < Node > {
319
- /// Whether the given Node has an immediate dominator .
322
+ /// Returns true if node is reachable from the start node .
320
323
pub fn is_reachable ( & self , node : Node ) -> bool {
321
- self . immediate_dominators [ node] . is_some ( )
324
+ node == self . start_node || self . immediate_dominators [ node] . is_some ( )
322
325
}
323
326
324
- pub fn immediate_dominator ( & self , node : Node ) -> Node {
325
- assert ! ( self . is_reachable ( node ) , " node {node:?} is not reachable" ) ;
326
- self . immediate_dominators [ node] . unwrap ( )
327
+ /// Returns the immediate dominator of node, if any.
328
+ pub fn immediate_dominator ( & self , node : Node ) -> Option < Node > {
329
+ self . immediate_dominators [ node]
327
330
}
328
331
329
332
/// Provides an iterator over each dominator up the CFG, for the given Node.
@@ -357,12 +360,7 @@ impl<'dom, Node: Idx> Iterator for Iter<'dom, Node> {
357
360
358
361
fn next ( & mut self ) -> Option < Self :: Item > {
359
362
if let Some ( node) = self . node {
360
- let dom = self . dominators . immediate_dominator ( node) ;
361
- if dom == node {
362
- self . node = None ; // reached the root
363
- } else {
364
- self . node = Some ( dom) ;
365
- }
363
+ self . node = self . dominators . immediate_dominator ( node) ;
366
364
Some ( node)
367
365
} else {
368
366
None
0 commit comments