dfir_lang/graph/ops/
difference_multiset.rs
1use quote::{quote_spanned, ToTokens};
2use syn::parse_quote;
3
4use super::{
5 DelayType, OperatorCategory, OperatorConstraints, OperatorInstance,
6 OperatorWriteOutput, PortIndexValue, WriteContextArgs, RANGE_0, RANGE_1,
7};
8
9pub const DIFFERENCE_MULTISET: OperatorConstraints = OperatorConstraints {
27 name: "difference_multiset",
28 categories: &[OperatorCategory::MultiIn],
29 hard_range_inn: &(2..=2),
30 soft_range_inn: &(2..=2),
31 hard_range_out: RANGE_1,
32 soft_range_out: RANGE_1,
33 num_args: 0,
34 persistence_args: &(0..=2),
35 type_args: RANGE_0,
36 is_external_input: false,
37 has_singleton_output: false,
38 flo_type: None,
39 ports_inn: Some(|| super::PortListSpec::Fixed(parse_quote! { pos, neg })),
40 ports_out: None,
41 input_delaytype_fn: |idx| match idx {
42 PortIndexValue::Path(path) if "neg" == path.to_token_stream().to_string() => {
43 Some(DelayType::Stratum)
44 }
45 _else => None,
46 },
47 write_fn: |wc @ &WriteContextArgs {
48 op_span,
49 ident,
50 inputs,
51 op_inst: OperatorInstance { .. },
52 ..
53 },
54 diagnostics| {
55 let OperatorWriteOutput {
56 write_prologue,
57 write_iterator,
58 write_iterator_after,
59 } = (super::anti_join_multiset::ANTI_JOIN_MULTISET.write_fn)(wc, diagnostics)?;
60
61 let pos = &inputs[1];
62 let write_iterator = quote_spanned! {op_span=>
63 let #pos = #pos.map(|k| (k, ()));
64 #write_iterator
65 let #ident = #ident.map(|(k, ())| k);
66 };
67
68 Ok(OperatorWriteOutput {
69 write_prologue,
70 write_iterator,
71 write_iterator_after,
72 })
73 },
74};