From ba5468cc5cb4ff071c746e34dcdd331b84f37b0f Mon Sep 17 00:00:00 2001 From: rarbore2 <rarbore2@illinois.edu> Date: Thu, 23 Jan 2025 11:55:47 -0600 Subject: [PATCH] Show basic blocks in Xdot --- hercules_cg/src/lib.rs | 12 ------------ hercules_ir/src/dot.rs | 23 +++++++++++++++++++++++ hercules_ir/src/ir.rs | 12 ++++++++++++ juno_scheduler/src/pm.rs | 13 +++++++++---- 4 files changed, 44 insertions(+), 16 deletions(-) diff --git a/hercules_cg/src/lib.rs b/hercules_cg/src/lib.rs index a70effb5..8aaab214 100644 --- a/hercules_cg/src/lib.rs +++ b/hercules_cg/src/lib.rs @@ -10,18 +10,6 @@ pub use crate::rt::*; use hercules_ir::*; -/* - * Basic block info consists of two things: - * - * 1. A map from node to block (named by control nodes). - * 2. For each node, which nodes are in its own block. - * - * Note that for #2, the structure is Vec<NodeID>, meaning the nodes are ordered - * inside the block. This order corresponds to the traversal order of the nodes - * in the block needed by the backend code generators. - */ -pub type BasicBlocks = (Vec<NodeID>, Vec<Vec<NodeID>>); - /* * The alignment of a type does not depend on dynamic constants. */ diff --git a/hercules_ir/src/dot.rs b/hercules_ir/src/dot.rs index 4d526366..9dd2cb1e 100644 --- a/hercules_ir/src/dot.rs +++ b/hercules_ir/src/dot.rs @@ -18,6 +18,7 @@ pub fn xdot_module( reverse_postorders: &Vec<Vec<NodeID>>, doms: Option<&Vec<DomTree>>, fork_join_maps: Option<&Vec<HashMap<NodeID, NodeID>>>, + bbs: Option<&Vec<BasicBlocks>>, ) { let mut tmp_path = temp_dir(); let mut rng = rand::thread_rng(); @@ -30,6 +31,7 @@ pub fn xdot_module( &reverse_postorders, doms, fork_join_maps, + bbs, &mut contents, ) .expect("PANIC: Unable to generate output file contents."); @@ -51,6 +53,7 @@ pub fn write_dot<W: Write>( reverse_postorders: &Vec<Vec<NodeID>>, doms: Option<&Vec<DomTree>>, fork_join_maps: Option<&Vec<HashMap<NodeID, NodeID>>>, + bbs: Option<&Vec<BasicBlocks>>, w: &mut W, ) -> std::fmt::Result { write_digraph_header(w)?; @@ -165,6 +168,26 @@ pub fn write_dot<W: Write>( } } + // Step 4: draw basic block edges in indigo. + if let Some(bbs) = bbs { + let bbs = &bbs[function_id.idx()].0; + for (idx, bb) in bbs.into_iter().enumerate() { + if idx != bb.idx() { + write_edge( + NodeID::new(idx), + function_id, + *bb, + function_id, + true, + "indigo", + "dotted", + &module, + w, + )?; + } + } + } + write_graph_footer(w)?; } diff --git a/hercules_ir/src/ir.rs b/hercules_ir/src/ir.rs index d1fdd225..46d35f25 100644 --- a/hercules_ir/src/ir.rs +++ b/hercules_ir/src/ir.rs @@ -351,6 +351,18 @@ pub type FunctionSchedules = Vec<Vec<Schedule>>; */ pub type FunctionLabels = Vec<HashSet<LabelID>>; +/* + * Basic block info consists of two things: + * + * 1. A map from node to block (named by control nodes). + * 2. For each node, which nodes are in its own block. + * + * Note that for #2, the structure is Vec<NodeID>, meaning the nodes are ordered + * inside the block. This order corresponds to the traversal order of the nodes + * in the block needed by the backend code generators. + */ +pub type BasicBlocks = (Vec<NodeID>, Vec<Vec<NodeID>>); + impl Module { /* * Printing out types, constants, and dynamic constants fully requires a diff --git a/juno_scheduler/src/pm.rs b/juno_scheduler/src/pm.rs index e93e7ecb..43fba4fd 100644 --- a/juno_scheduler/src/pm.rs +++ b/juno_scheduler/src/pm.rs @@ -1529,15 +1529,15 @@ fn run_pass( pm.fork_join_maps = Some(fork_join_maps); } Pass::Xdot => { - assert!(args.len() == 1); - let force_analyses = match args[0] { - Value::Boolean { val } => val, - _ => { + let force_analyses = match args.get(0) { + Some(Value::Boolean { val }) => *val, + Some(_) => { return Err(SchedulerError::PassError { pass: "xdot".to_string(), error: "expected boolean argument".to_string(), }); } + None => true, }; pm.make_reverse_postorders(); @@ -1549,14 +1549,19 @@ fn run_pass( let reverse_postorders = pm.reverse_postorders.take().unwrap(); let doms = pm.doms.take(); let fork_join_maps = pm.fork_join_maps.take(); + let bbs = pm.bbs.take(); pm.with_mod(|module| { xdot_module( module, &reverse_postorders, doms.as_ref(), fork_join_maps.as_ref(), + bbs.as_ref(), ) }); + + // Put BasicBlocks back, since it's needed for Codegen. + pm.bbs = bbs; } } -- GitLab