diff --git a/src/ops.rs b/src/ops.rs index e7162f65a..e33359063 100644 --- a/src/ops.rs +++ b/src/ops.rs @@ -86,9 +86,9 @@ impl OpType { signature.get(port).cloned().map(EdgeKind::Value) } else if port.index() == port_count && dir == Direction::Incoming - && self.static_input().is_some() + && OpTag::StaticInput.is_superset(self.tag()) { - self.static_input().map(EdgeKind::Static) + Some(EdgeKind::Static(static_in_type(self))) } else { self.other_port(dir) } @@ -103,7 +103,7 @@ impl OpType { if self.other_port(dir).is_some() && non_df_count == 1 { // if there is a static input it comes before the non_df_ports let static_input = - (dir == Direction::Incoming && self.static_input().is_some()) as usize; + (dir == Direction::Incoming && OpTag::StaticInput.is_superset(self.tag())) as usize; Some(Port::new( dir, @@ -122,7 +122,8 @@ impl OpType { .non_df_port_count(dir) .unwrap_or(has_other_ports as usize); // if there is a static input it comes before the non_df_ports - let static_input = (dir == Direction::Incoming && self.static_input().is_some()) as usize; + let static_input = + (dir == Direction::Incoming && OpTag::StaticInput.is_superset(self.tag())) as usize; signature.port_count(dir) + non_df_count + static_input } @@ -142,6 +143,14 @@ impl OpType { } } +fn static_in_type(op: &OpType) -> Type { + match op { + OpType::Call(call) => Type::new_function(call.called_function_type().clone()), + OpType::LoadConstant(load) => load.constant_type().clone(), + _ => panic!("this function should not be called if the optype is not known to be Call or LoadConst.") + } +} + /// Macro used by operations that want their /// name to be the same as their type name macro_rules! impl_op_name { @@ -188,14 +197,6 @@ pub trait OpTrait { fn signature(&self) -> FunctionType { Default::default() } - - /// Get the static input type of this operation if it has one (only Some for - /// [`LoadConstant`] and [`Call`]) - #[inline] - fn static_input(&self) -> Option { - None - } - /// The edge kind for the non-dataflow or constant inputs of the operation, /// not described by the signature. /// diff --git a/src/ops/dataflow.rs b/src/ops/dataflow.rs index 5b63b706f..4ab06d5cf 100644 --- a/src/ops/dataflow.rs +++ b/src/ops/dataflow.rs @@ -11,10 +11,6 @@ pub(super) trait DataflowOpTrait { fn description(&self) -> &str; fn signature(&self) -> FunctionType; - /// Get the static input type of this operation if it has one. - fn static_input(&self) -> Option { - None - } /// The edge kind for the non-dataflow or constant inputs of the operation, /// not described by the signature. /// @@ -125,10 +121,6 @@ impl OpTrait for T { fn other_output(&self) -> Option { DataflowOpTrait::other_output(self) } - - fn static_input(&self) -> Option { - DataflowOpTrait::static_input(self) - } } impl StaticTag for T { const TAG: OpTag = T::TAG; @@ -156,10 +148,12 @@ impl DataflowOpTrait for Call { fn signature(&self) -> FunctionType { self.signature.clone() } - +} +impl Call { #[inline] - fn static_input(&self) -> Option { - Some(Type::new_function(self.signature.clone())) + /// Return the signature of the function called by this op. + pub fn called_function_type(&self) -> &FunctionType { + &self.signature } } @@ -204,10 +198,12 @@ impl DataflowOpTrait for LoadConstant { fn signature(&self) -> FunctionType { FunctionType::new(TypeRow::new(), vec![self.datatype.clone()]) } - +} +impl LoadConstant { #[inline] - fn static_input(&self) -> Option { - Some(self.datatype.clone()) + /// The type of the constant loaded by this op. + pub fn constant_type(&self) -> &Type { + &self.datatype } } diff --git a/src/ops/tag.rs b/src/ops/tag.rs index e45014977..049f383e1 100644 --- a/src/ops/tag.rs +++ b/src/ops/tag.rs @@ -46,6 +46,8 @@ pub enum OpTag { Input, /// A dataflow output. Output, + /// Dataflow node that has a static input + StaticInput, /// A function call. FnCall, /// A constant load operation. @@ -121,8 +123,9 @@ impl OpTag { ], OpTag::TailLoop => &[OpTag::DataflowChild, OpTag::DataflowParent], OpTag::Conditional => &[OpTag::DataflowChild], - OpTag::FnCall => &[OpTag::DataflowChild], - OpTag::LoadConst => &[OpTag::DataflowChild], + OpTag::StaticInput => &[OpTag::DataflowChild], + OpTag::FnCall => &[OpTag::StaticInput], + OpTag::LoadConst => &[OpTag::StaticInput], OpTag::Leaf => &[OpTag::DataflowChild], OpTag::DataflowParent => &[OpTag::Any], } @@ -150,6 +153,7 @@ impl OpTag { OpTag::Cfg => "Nested control-flow operation", OpTag::TailLoop => "Tail-recursive loop", OpTag::Conditional => "Conditional operation", + OpTag::StaticInput => "Dataflow child with static input (LoadConst or FnCall)", OpTag::FnCall => "Function call", OpTag::LoadConst => "Constant load operation", OpTag::Leaf => "Leaf operation",