graphix_compiler/node/
genn.rs

1use super::{callsite::CallSite, Constant, Nop, Ref, NOP};
2use crate::{
3    expr::{ExprId, ModPath},
4    typ::{FnType, Type},
5    BindId, ExecCtx, Node, Rt, UserEvent, KNOWN,
6};
7use netidx::publisher::{Typ, Value};
8use std::collections::HashMap;
9
10/// generate a no op with the specific type
11pub fn nop<R: Rt, E: UserEvent>(typ: Type) -> Node<R, E> {
12    Nop::new(typ)
13}
14
15/// bind a variable and return a node referencing it
16pub fn bind<R: Rt, E: UserEvent>(
17    ctx: &mut ExecCtx<R, E>,
18    scope: &ModPath,
19    name: &str,
20    typ: Type,
21    top_id: ExprId,
22) -> (BindId, Node<R, E>) {
23    let id = ctx.env.bind_variable(scope, name, typ.clone()).id;
24    ctx.rt.ref_var(id, top_id);
25    (id, Box::new(Ref { spec: NOP.clone(), typ, id, top_id }))
26}
27
28/// generate a reference to a bind id
29pub fn reference<R: Rt, E: UserEvent>(
30    ctx: &mut ExecCtx<R, E>,
31    id: BindId,
32    typ: Type,
33    top_id: ExprId,
34) -> Node<R, E> {
35    ctx.rt.ref_var(id, top_id);
36    Box::new(Ref { spec: NOP.clone(), typ, id, top_id })
37}
38
39pub fn constant<R: Rt, E: UserEvent>(v: Value) -> Node<R, E> {
40    Box::new(Constant {
41        spec: NOP.clone(),
42        typ: Type::Primitive(Typ::get(&v).into()),
43        value: v,
44    })
45}
46
47/// generate and return an apply node for the given lambda
48pub fn apply<R: Rt, E: UserEvent>(
49    fnode: Node<R, E>,
50    args: Vec<Node<R, E>>,
51    typ: &FnType,
52    top_id: ExprId,
53) -> Node<R, E> {
54    let ftype = typ.reset_tvars();
55    KNOWN.with_borrow_mut(|known| {
56        known.clear();
57        ftype.alias_tvars(known);
58    });
59    Box::new(CallSite {
60        spec: NOP.clone(),
61        ftype,
62        args,
63        arg_spec: HashMap::default(),
64        fnode,
65        function: None,
66        top_id,
67    })
68}