Skip to content

Commit

Permalink
.
Browse files Browse the repository at this point in the history
  • Loading branch information
TomAFrench committed Jan 6, 2025
1 parent d5a6c78 commit b9598bb
Show file tree
Hide file tree
Showing 5 changed files with 15 additions and 76 deletions.
11 changes: 5 additions & 6 deletions compiler/noirc_evaluator/src/ssa/function_builder/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -68,9 +68,9 @@ impl FunctionBuilder {
/// the FunctionBuilder. A function's default runtime type is `RuntimeType::Acir(InlineType::Inline)`.
/// This should only be used immediately following construction of a FunctionBuilder
/// and will panic if there are any already finished functions.
pub(crate) fn set_runtime(&mut self, runtime: RuntimeType, separated: bool) {
pub(crate) fn set_runtime(&mut self, runtime: RuntimeType) {
assert_eq!(self.finished_functions.len(), 0, "Attempted to set runtime on a FunctionBuilder with finished functions. A FunctionBuilder's runtime should only be set on its initial function");
self.current_function.set_runtime(runtime, separated);
self.current_function.set_runtime(runtime);
}

/// Finish the current function and create a new function.
Expand All @@ -83,11 +83,10 @@ impl FunctionBuilder {
name: String,
function_id: FunctionId,
runtime_type: RuntimeType,
separated: bool,
) {
let call_stack = self.current_function.dfg.get_call_stack(self.call_stack);
let mut new_function = Function::new(name, function_id);
new_function.set_runtime(runtime_type, separated);
new_function.set_runtime(runtime_type);
self.current_block = new_function.entry_block();
let old_function = std::mem::replace(&mut self.current_function, new_function);
// Copy the call stack to the new function
Expand All @@ -103,7 +102,7 @@ impl FunctionBuilder {
function_id: FunctionId,
inline_type: InlineType,
) {
self.new_function_with_type(name, function_id, RuntimeType::Acir(inline_type), false);
self.new_function_with_type(name, function_id, RuntimeType::Acir(inline_type));
}

/// Finish the current function and create a new unconstrained function.
Expand All @@ -113,7 +112,7 @@ impl FunctionBuilder {
function_id: FunctionId,
inline_type: InlineType,
) {
self.new_function_with_type(name, function_id, RuntimeType::Brillig(inline_type), false);
self.new_function_with_type(name, function_id, RuntimeType::Brillig(inline_type));
}

/// Consume the FunctionBuilder returning all the functions it has generated.
Expand Down
30 changes: 3 additions & 27 deletions compiler/noirc_evaluator/src/ssa/ir/dfg.rs
Original file line number Diff line number Diff line change
Expand Up @@ -33,16 +33,6 @@ pub(crate) struct DataFlowGraph {
/// ACIR functions are cloned as Brillig functions.
runtime: RuntimeType,

/// Indicate whether we are past the runtime separation step.
/// Before this step the DFG accepts any instruction, because
/// an ACIR function might be cloned as a Brillig function.
/// After the separation, we can instantly remove instructions
/// that would just be ignored by the runtime.
///
/// TODO(#6841): This would not be necessary if the SSA was
/// already generated for a specific runtime.
is_runtime_separated: bool,

/// All of the instructions in a function
instructions: DenseMap<Instruction>,

Expand Down Expand Up @@ -118,7 +108,6 @@ impl DataFlowGraph {
pub(crate) fn new(runtime: RuntimeType) -> Self {
Self {
runtime,
is_runtime_separated: false,
instructions: Default::default(),
results: Default::default(),
values: Default::default(),
Expand All @@ -139,22 +128,9 @@ impl DataFlowGraph {
self.runtime
}

/// Indicate whether the runtimes have been separated yet.
pub(crate) fn is_runtime_separated(&self) -> bool {
self.is_runtime_separated
}

/// Set runtime type of the function.
pub(crate) fn set_runtime(&mut self, runtime: RuntimeType, separated: bool) {
pub(crate) fn set_runtime(&mut self, runtime: RuntimeType) {
self.runtime = runtime;
self.is_runtime_separated = separated;
}

/// Mark the runtime as separated. After this we can drop
/// instructions that would be ignored by the runtime,
/// instead of inserting them and carrying them to the end.
pub(crate) fn set_runtime_separated(&mut self) {
self.is_runtime_separated = true;
}

/// Creates a new basic block with no parameters.
Expand Down Expand Up @@ -246,7 +222,7 @@ impl DataFlowGraph {
ctrl_typevars: Option<Vec<Type>>,
call_stack: CallStackId,
) -> InsertInstructionResult {
if self.is_runtime_separated && !self.is_handled_by_runtime(&instruction_data) {
if !self.is_handled_by_runtime(&instruction_data) {
return InsertInstructionResult::InstructionRemoved;
}

Expand All @@ -269,7 +245,7 @@ impl DataFlowGraph {
ctrl_typevars: Option<Vec<Type>>,
call_stack: CallStackId,
) -> InsertInstructionResult {
if self.is_runtime_separated && !self.is_handled_by_runtime(&instruction) {
if !self.is_handled_by_runtime(&instruction) {
return InsertInstructionResult::InstructionRemoved;
}
match instruction.simplify(self, block, ctrl_typevars.clone(), call_stack) {
Expand Down
46 changes: 5 additions & 41 deletions compiler/noirc_evaluator/src/ssa/ir/function.rs
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
use std::collections::{BTreeSet, HashSet};
use std::collections::BTreeSet;

use iter_extended::vecmap;
use noirc_frontend::monomorphization::ast::InlineType;
use serde::{Deserialize, Serialize};

use super::basic_block::BasicBlockId;
use super::dfg::DataFlowGraph;
use super::instruction::{Instruction, TerminatorInstruction};
use super::instruction::TerminatorInstruction;
use super::map::Id;
use super::types::Type;
use super::value::ValueId;
Expand Down Expand Up @@ -97,7 +97,7 @@ impl Function {
/// Takes the signature (function name & runtime) from a function but does not copy the body.
pub(crate) fn clone_signature(id: FunctionId, another: &Function) -> Self {
let mut new_function = Function::new(another.name.clone(), id);
new_function.set_runtime(another.runtime(), another.is_runtime_separated());
new_function.set_runtime(another.runtime());
new_function
}

Expand All @@ -117,14 +117,9 @@ impl Function {
self.dfg.runtime()
}

/// Indicate whether the runtimes have been separated yet.
pub(crate) fn is_runtime_separated(&self) -> bool {
self.dfg.is_runtime_separated()
}

/// Set runtime type of the function.
pub(crate) fn set_runtime(&mut self, runtime: RuntimeType, separated: bool) {
self.dfg.set_runtime(runtime, separated);
pub(crate) fn set_runtime(&mut self, runtime: RuntimeType) {
self.dfg.set_runtime(runtime);
}

pub(crate) fn is_no_predicates(&self) -> bool {
Expand Down Expand Up @@ -198,37 +193,6 @@ impl Function {

unreachable!("SSA Function {} has no reachable return instruction!", self.id())
}

/// Remove instructions from all the reachable blocks in a function based on a predicate,
/// keeping the ones where the predicate returns `true`.
pub(crate) fn retain_instructions(&mut self, pred: impl Fn(&Instruction) -> bool) {
for block_id in self.reachable_blocks() {
let mut to_remove = HashSet::new();
let block = &self.dfg[block_id];
for instruction_id in block.instructions() {
let instruction = &self.dfg[*instruction_id];
if !pred(instruction) {
to_remove.insert(*instruction_id);
}
}
if !to_remove.is_empty() {
let block = &mut self.dfg[block_id];
block.instructions_mut().retain(|id| !to_remove.contains(id));
}
}
}

/// Remove all instructions that aren't handled by the runtime, which is now
/// considered final. Seal the [DataFlowGraph] so it instantly simplifies
/// away instructions that the runtime would have to ignore.
///
/// TODO(#6841): Remove once the SSA generated is for a specific runtime already.
pub(crate) fn separate_runtime(&mut self) {
if self.runtime().is_acir() {
self.retain_instructions(|i| !i.is_brillig_only());
}
self.dfg.set_runtime_separated();
}
}

impl Clone for Function {
Expand Down
2 changes: 1 addition & 1 deletion compiler/noirc_evaluator/src/ssa/opt/inlining.rs
Original file line number Diff line number Diff line change
Expand Up @@ -361,7 +361,7 @@ impl InlineContext {
) -> InlineContext {
let source = &ssa.functions[&entry_point];
let mut builder = FunctionBuilder::new(source.name().to_owned(), entry_point);
builder.set_runtime(source.runtime(), source.is_runtime_separated());
builder.set_runtime(source.runtime());
Self {
builder,
recursion_level: 0,
Expand Down
2 changes: 1 addition & 1 deletion compiler/noirc_evaluator/src/ssa/ssa_gen/context.rs
Original file line number Diff line number Diff line change
Expand Up @@ -107,7 +107,7 @@ impl<'a> FunctionContext<'a> {
.1;

let mut builder = FunctionBuilder::new(function_name, function_id);
builder.set_runtime(runtime, false);
builder.set_runtime(runtime);
let definitions = HashMap::default();
let mut this = Self { definitions, builder, shared_context, loops: Vec::new() };
this.add_parameters_to_scope(parameters);
Expand Down

0 comments on commit b9598bb

Please sign in to comment.