From d2c929546fbda631e2c180c8bbff26a159ec4396 Mon Sep 17 00:00:00 2001 From: Russel Arbore <russel.jma@gmail.com> Date: Mon, 23 Dec 2024 16:41:08 -0800 Subject: [PATCH] Don't visit invalid dynamic constants --- hercules_cg/src/cpu.rs | 10 +++++++--- hercules_cg/src/rt.rs | 6 +++++- hercules_ir/src/ir.rs | 10 +++++++++- hercules_opt/src/inline.rs | 5 ++++- hercules_opt/src/pass.rs | 4 +++- juno_frontend/src/lib.rs | 4 ++-- 6 files changed, 30 insertions(+), 9 deletions(-) diff --git a/hercules_cg/src/cpu.rs b/hercules_cg/src/cpu.rs index eb76a47d..080c195a 100644 --- a/hercules_cg/src/cpu.rs +++ b/hercules_cg/src/cpu.rs @@ -114,8 +114,8 @@ impl<'a> CPUContext<'a> { .map(|idx| (NodeID::new(idx), LLVMBlock::default())) .collect(); - // Emit calculation of dynamic constants into the start block. Just - // calculate every dynamic constant, and let LLVM clean them up. + // Emit calculation of dynamic constants into the start block. Calculate + // every valid dynamic constant, and let LLVM clean them up. self.codegen_dynamic_constants( blocks.get_mut(&NodeID::new(0)).unwrap(), self.function.num_dynamic_constants, @@ -212,7 +212,11 @@ impl<'a> CPUContext<'a> { let term = &mut blocks.get_mut(&id).unwrap().term; write!(term, " ret {}\n", self.get_value(data, true))? } - _ => panic!("PANIC: Can't lower {:?}.", self.function.nodes[id.idx()]), + _ => panic!( + "PANIC: Can't lower {:?} in {}.", + self.function.nodes[id.idx()], + self.function.name + ), } Ok(()) } diff --git a/hercules_cg/src/rt.rs b/hercules_cg/src/rt.rs index ddbc8f53..47b739dc 100644 --- a/hercules_cg/src/rt.rs +++ b/hercules_cg/src/rt.rs @@ -455,7 +455,11 @@ impl<'a> RTContext<'a> { write!(block, " }}\n")?; } } - _ => panic!("PANIC: Can't lower {:?}.", func.nodes[id.idx()]), + _ => panic!( + "PANIC: Can't lower {:?} in {}.", + func.nodes[id.idx()], + func.name + ), } Ok(()) } diff --git a/hercules_ir/src/ir.rs b/hercules_ir/src/ir.rs index 4127d6c3..f6356dfd 100644 --- a/hercules_ir/src/ir.rs +++ b/hercules_ir/src/ir.rs @@ -596,7 +596,10 @@ pub fn constants_bottom_up(constants: &Vec<Constant>) -> impl Iterator<Item = Co /* * Create an iterator that traverses all the dynamic constants in the module * bottom up. This uses a coroutine to make iteratively traversing the dynamic - * constant DAGs easier. + * constant DAGs easier. This bottom-up visitor will ignore dynamic constants + * that reference non-sensical IDs. These are artifacts left over by the process + * of subsituting dynamic constants during some transformation passes, and + * shouldn't be used by any nodes. */ pub fn dynamic_constants_bottom_up( dynamic_constants: &Vec<DynamicConstant>, @@ -621,6 +624,11 @@ pub fn dynamic_constants_bottom_up( // We have to yield the children of this node before // this node itself. We keep track of which nodes have // yielded using visited. + if left.idx() >= visited.len() || right.idx() >= visited.len() { + // This is an invalid dynamic constant and should be + // skipped. + continue; + } let can_yield = visited[left.idx()] && visited[right.idx()]; if can_yield { visited.set(id.idx(), true); diff --git a/hercules_opt/src/inline.rs b/hercules_opt/src/inline.rs index 1c485ecc..9ab15874 100644 --- a/hercules_opt/src/inline.rs +++ b/hercules_opt/src/inline.rs @@ -45,6 +45,9 @@ pub fn inline(editors: &mut [FunctionEditor], callgraph: &CallGraph) { // Step 4: run inlining on each function individually. Iterate the functions // in topological order. for to_inline_id in topo { + if editors[to_inline_id.idx()].func().entry { + continue; + } // Since Rust cannot analyze the accesses into an array of mutable // references, we need to do some weirdness here to simultaneously get: // 1. A mutable reference to the function we're modifying. @@ -181,7 +184,7 @@ fn inline_func( // as the new references we just made in the first step. We // actually want to institute all the updates // *simultaneously*, hence the two step maneuver. - let first_dc = edit.num_dynamic_constants() + 1; + let first_dc = edit.num_dynamic_constants() + 100; for (dc_a, dc_n) in zip(dcs_a, first_dc..) { substitute_dynamic_constants_in_node( *dc_a, diff --git a/hercules_opt/src/pass.rs b/hercules_opt/src/pass.rs index 58251c42..ce53916b 100644 --- a/hercules_opt/src/pass.rs +++ b/hercules_opt/src/pass.rs @@ -867,7 +867,9 @@ impl PassManager { let mut rust_rt = String::new(); let mut llvm_ir = String::new(); for idx in 0..self.module.functions.len() { - if self.module.functions[idx].entry { + if self.module.functions[idx].entry + || callgraph.num_callees(FunctionID::new(idx)) != 0 + { rt_codegen( FunctionID::new(idx), &self.module, diff --git a/juno_frontend/src/lib.rs b/juno_frontend/src/lib.rs index 4ff5d9fc..b18b2979 100644 --- a/juno_frontend/src/lib.rs +++ b/juno_frontend/src/lib.rs @@ -184,8 +184,8 @@ pub fn compile_ir( if x_dot { pm.add_pass(hercules_opt::pass::Pass::Xdot(true)); } - add_pass!(pm, verify, Forkify); - add_pass!(pm, verify, ForkGuardElim); + //add_pass!(pm, verify, Forkify); + //add_pass!(pm, verify, ForkGuardElim); add_verified_pass!(pm, verify, DCE); add_pass!(pm, verify, Outline); add_pass!(pm, verify, InterproceduralSROA); -- GitLab