get basic when conditions to work
This commit is contained in:
parent
6950b66b55
commit
6c6aefd1c4
|
@ -88,7 +88,7 @@ pub struct CodeGenerator<'a> {
|
||||||
uplc_function_holder: Vec<(String, Term<Name>)>,
|
uplc_function_holder: Vec<(String, Term<Name>)>,
|
||||||
uplc_function_holder_lookup: IndexMap<(String, String), (ScopeLevels, TypedExpr)>,
|
uplc_function_holder_lookup: IndexMap<(String, String), (ScopeLevels, TypedExpr)>,
|
||||||
uplc_data_holder_lookup: IndexMap<(String, String, String), (ScopeLevels, TypedExpr)>,
|
uplc_data_holder_lookup: IndexMap<(String, String, String), (ScopeLevels, TypedExpr)>,
|
||||||
uplc_when_lookup: IndexMap<(String, String, String), ScopeLevels>,
|
uplc_data_constr_lookup: IndexMap<(String, String), ScopeLevels>,
|
||||||
uplc_data_usage_holder_lookup: IndexMap<(String, String), ScopeLevels>,
|
uplc_data_usage_holder_lookup: IndexMap<(String, String), ScopeLevels>,
|
||||||
functions: &'a HashMap<(String, String), &'a Function<Arc<tipo::Type>, TypedExpr>>,
|
functions: &'a HashMap<(String, String), &'a Function<Arc<tipo::Type>, TypedExpr>>,
|
||||||
type_aliases: &'a HashMap<(String, String), &'a TypeAlias<Arc<tipo::Type>>>,
|
type_aliases: &'a HashMap<(String, String), &'a TypeAlias<Arc<tipo::Type>>>,
|
||||||
|
@ -109,7 +109,7 @@ impl<'a> CodeGenerator<'a> {
|
||||||
uplc_function_holder: Vec::new(),
|
uplc_function_holder: Vec::new(),
|
||||||
uplc_function_holder_lookup: IndexMap::new(),
|
uplc_function_holder_lookup: IndexMap::new(),
|
||||||
uplc_data_holder_lookup: IndexMap::new(),
|
uplc_data_holder_lookup: IndexMap::new(),
|
||||||
uplc_when_lookup: IndexMap::new(),
|
uplc_data_constr_lookup: IndexMap::new(),
|
||||||
uplc_data_usage_holder_lookup: IndexMap::new(),
|
uplc_data_usage_holder_lookup: IndexMap::new(),
|
||||||
functions,
|
functions,
|
||||||
type_aliases,
|
type_aliases,
|
||||||
|
@ -160,202 +160,7 @@ impl<'a> CodeGenerator<'a> {
|
||||||
.into(),
|
.into(),
|
||||||
};
|
};
|
||||||
|
|
||||||
//Apply constr arg getter to top level.
|
term = self.add_arg_getter(term);
|
||||||
|
|
||||||
term = Term::Apply {
|
|
||||||
function: Term::Lambda {
|
|
||||||
parameter_name: Name {
|
|
||||||
text: "constr_field_get_arg".to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
},
|
|
||||||
body: term.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
argument: Term::Lambda {
|
|
||||||
parameter_name: Name {
|
|
||||||
text: "constr_list".to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
},
|
|
||||||
body: Term::Lambda {
|
|
||||||
parameter_name: Name {
|
|
||||||
text: "arg_number".to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
},
|
|
||||||
body: Term::Apply {
|
|
||||||
function: Term::Lambda {
|
|
||||||
parameter_name: Name {
|
|
||||||
text: "recurse".to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
},
|
|
||||||
body: Term::Apply {
|
|
||||||
function: Term::Apply {
|
|
||||||
function: Term::Apply {
|
|
||||||
function: Term::Var(Name {
|
|
||||||
text: "recurse".to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
})
|
|
||||||
.into(),
|
|
||||||
argument: Term::Var(Name {
|
|
||||||
text: "recurse".to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
})
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
|
|
||||||
// Start recursive with index 0 of list
|
|
||||||
argument: Term::Constant(Constant::Integer(0.into())).into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
argument: Term::Var(Name {
|
|
||||||
text: "constr_list".to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
})
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
|
|
||||||
argument: Term::Lambda {
|
|
||||||
parameter_name: Name {
|
|
||||||
text: "self_recursor".to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
},
|
|
||||||
body: Term::Lambda {
|
|
||||||
parameter_name: Name {
|
|
||||||
text: "current_arg_number".to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
},
|
|
||||||
body: Term::Lambda {
|
|
||||||
parameter_name: Name {
|
|
||||||
text: "list_of_constr_args".to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
},
|
|
||||||
body: Term::Apply {
|
|
||||||
function: Term::Apply {
|
|
||||||
function: Term::Apply {
|
|
||||||
function: Term::Apply {
|
|
||||||
function: Term::Force(
|
|
||||||
Term::Builtin(DefaultFunction::IfThenElse)
|
|
||||||
.into(),
|
|
||||||
)
|
|
||||||
.into(),
|
|
||||||
argument: Term::Apply {
|
|
||||||
function: Term::Apply {
|
|
||||||
function: Term::Builtin(
|
|
||||||
DefaultFunction::EqualsInteger,
|
|
||||||
)
|
|
||||||
.into(),
|
|
||||||
argument: Term::Var(Name {
|
|
||||||
text: "arg_number".to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
})
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
argument: Term::Var(Name {
|
|
||||||
text: "current_arg_number".to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
})
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
argument: Term::Force(
|
|
||||||
Term::Builtin(DefaultFunction::HeadList).into(),
|
|
||||||
)
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
argument: Term::Lambda {
|
|
||||||
parameter_name: Name {
|
|
||||||
text: "current_list_of_constr_args".to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
},
|
|
||||||
body: Term::Apply {
|
|
||||||
function: Term::Apply {
|
|
||||||
function: Term::Apply {
|
|
||||||
function: Term::Var(Name {
|
|
||||||
text: "self_recursor".to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
})
|
|
||||||
.into(),
|
|
||||||
argument: Term::Var(Name {
|
|
||||||
text: "self_recursor".to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
})
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
|
|
||||||
argument: Term::Apply {
|
|
||||||
function: Term::Apply {
|
|
||||||
function: Term::Builtin(
|
|
||||||
DefaultFunction::AddInteger,
|
|
||||||
)
|
|
||||||
.into(),
|
|
||||||
argument: Term::Var(Name {
|
|
||||||
text: "current_arg_number"
|
|
||||||
.to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
})
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
argument: Term::Constant(
|
|
||||||
Constant::Integer(1.into()),
|
|
||||||
)
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
|
|
||||||
argument: Term::Apply {
|
|
||||||
function: Term::Force(
|
|
||||||
Term::Builtin(
|
|
||||||
DefaultFunction::TailList,
|
|
||||||
)
|
|
||||||
.into(),
|
|
||||||
)
|
|
||||||
.into(),
|
|
||||||
|
|
||||||
argument: Term::Var(Name {
|
|
||||||
text: "current_list_of_constr_args"
|
|
||||||
.to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
})
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
argument: Term::Var(Name {
|
|
||||||
text: "list_of_constr_args".to_string(),
|
|
||||||
unique: 0.into(),
|
|
||||||
})
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
}
|
|
||||||
.into(),
|
|
||||||
};
|
|
||||||
|
|
||||||
for arg in arguments.iter().rev() {
|
for arg in arguments.iter().rev() {
|
||||||
term = Term::Lambda {
|
term = Term::Lambda {
|
||||||
|
@ -628,7 +433,7 @@ impl<'a> CodeGenerator<'a> {
|
||||||
) {
|
) {
|
||||||
match dbg!(pattern) {
|
match dbg!(pattern) {
|
||||||
Pattern::Int { .. } | Pattern::String { .. } | Pattern::Var { .. } => {
|
Pattern::Int { .. } | Pattern::String { .. } | Pattern::Var { .. } => {
|
||||||
self.recurse_scope_level(value, scope_level.scope_increment_sequence(1));
|
self.recurse_scope_level(value, scope_level.clone());
|
||||||
}
|
}
|
||||||
|
|
||||||
Pattern::VarUsage {
|
Pattern::VarUsage {
|
||||||
|
@ -659,22 +464,17 @@ impl<'a> CodeGenerator<'a> {
|
||||||
|
|
||||||
match &**tipo {
|
match &**tipo {
|
||||||
Type::App { module, name, .. } => {
|
Type::App { module, name, .. } => {
|
||||||
if let Some(val) = self.uplc_when_lookup.get(&(
|
if let Some(val) = self
|
||||||
module.to_string(),
|
.uplc_data_constr_lookup
|
||||||
name.clone(),
|
.get(&(module.to_string(), name.clone()))
|
||||||
constructor_name.clone(),
|
{
|
||||||
)) {
|
if scope_level.is_less_than(val, false) {
|
||||||
if scope_level.is_less_than(&val, false) {
|
self.uplc_data_constr_lookup
|
||||||
self.uplc_when_lookup.insert(
|
.insert((module.to_string(), name.clone()), scope_level);
|
||||||
(module.to_string(), name.clone(), constructor_name.clone()),
|
|
||||||
scope_level,
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
self.uplc_when_lookup.insert(
|
self.uplc_data_constr_lookup
|
||||||
(module.to_string(), name.clone(), constructor_name.clone()),
|
.insert((module.to_string(), name.clone()), scope_level);
|
||||||
scope_level,
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Type::Fn { .. } => {
|
Type::Fn { .. } => {
|
||||||
|
@ -826,7 +626,6 @@ impl<'a> CodeGenerator<'a> {
|
||||||
let left_term = self.recurse_code_gen(left, scope_level.clone());
|
let left_term = self.recurse_code_gen(left, scope_level.clone());
|
||||||
|
|
||||||
let right_term = self.recurse_code_gen(right, scope_level);
|
let right_term = self.recurse_code_gen(right, scope_level);
|
||||||
println!("NAME IS {name:#?}");
|
|
||||||
match name {
|
match name {
|
||||||
BinOp::Eq => match &*left.tipo() {
|
BinOp::Eq => match &*left.tipo() {
|
||||||
Type::App { name, .. } => match name.as_str() {
|
Type::App { name, .. } => match name.as_str() {
|
||||||
|
@ -918,61 +717,163 @@ impl<'a> CodeGenerator<'a> {
|
||||||
pattern,
|
pattern,
|
||||||
} => todo!(),
|
} => todo!(),
|
||||||
TypedExpr::When {
|
TypedExpr::When {
|
||||||
location,
|
subjects, clauses, ..
|
||||||
tipo,
|
|
||||||
subjects,
|
|
||||||
clauses,
|
|
||||||
} => {
|
} => {
|
||||||
let mut current_clauses = clauses.clone();
|
let current_clauses = clauses.clone();
|
||||||
let mut new_current_clauses: Vec<(Vec<usize>, TypedExpr)> = current_clauses
|
let mut data_type = "".to_string();
|
||||||
|
let mut current_module = "".to_string();
|
||||||
|
let mut total_constr_length = 0;
|
||||||
|
let mut new_current_clauses: Vec<(usize, TypedExpr)> = current_clauses
|
||||||
.iter()
|
.iter()
|
||||||
.map(|clause| {
|
.map(|clause| {
|
||||||
let mut final_keys = Vec::new();
|
let pattern = &clause.pattern[0];
|
||||||
for pattern in clause.pattern.clone() {
|
let index = match pattern {
|
||||||
let key = match pattern {
|
Pattern::Constructor {
|
||||||
Pattern::Constructor { name, tipo, .. } => {
|
name, tipo, module, ..
|
||||||
let key = match &*tipo {
|
} => {
|
||||||
|
let key = match &**tipo {
|
||||||
Type::App { module, name, .. } => {
|
Type::App { module, name, .. } => {
|
||||||
(module.clone(), name.clone())
|
(module.clone(), name.clone())
|
||||||
}
|
}
|
||||||
Type::Fn { args, ret } => todo!(),
|
Type::Fn { .. } => todo!(),
|
||||||
Type::Var { tipo } => todo!(),
|
Type::Var { .. } => todo!(),
|
||||||
};
|
};
|
||||||
|
|
||||||
let dt = self.data_types.get(&key).unwrap();
|
let dt = self.data_types.get(&key).unwrap();
|
||||||
|
|
||||||
let index = dt.constructors.iter().position(|c| name == c.name);
|
let index =
|
||||||
|
dt.constructors.iter().position(|c| name.clone() == c.name);
|
||||||
|
data_type = dt.name.clone();
|
||||||
|
current_module = module.clone().unwrap_or_else(|| "".to_string());
|
||||||
|
total_constr_length = dt.constructors.len();
|
||||||
|
|
||||||
// index.unwrap()
|
index.unwrap_or(dt.constructors.len())
|
||||||
index.unwrap()
|
|
||||||
}
|
}
|
||||||
_ => todo!(),
|
_ => todo!(),
|
||||||
};
|
};
|
||||||
final_keys.push(key);
|
(index, clause.then.clone())
|
||||||
}
|
|
||||||
(final_keys, clause.then.clone())
|
|
||||||
})
|
})
|
||||||
.collect();
|
.collect();
|
||||||
let mut term = self.recurse_code_gen(
|
|
||||||
&new_current_clauses.remove(new_current_clauses.len() - 1).1,
|
|
||||||
scope_level.scope_increment_sequence(1),
|
|
||||||
);
|
|
||||||
|
|
||||||
for subject in subjects {}
|
new_current_clauses.sort_by(|a, b| a.0.cmp(&b.0));
|
||||||
|
|
||||||
// for clause in new_current_clauses.iter().rev() {
|
let subject = &subjects[0];
|
||||||
// let branch_term =
|
let mut is_var = false;
|
||||||
// self.recurse_code_gen(&clause.1, scope_level.scope_increment_sequence(1));
|
let mut current_var_name = "".to_string();
|
||||||
|
let mut current_subject = subject.clone();
|
||||||
|
|
||||||
// for index in clause.0 {
|
while !is_var {
|
||||||
// term = Term::Apply {
|
match current_subject.clone() {
|
||||||
// function: Term::Var { text: "co" },
|
TypedExpr::Var {
|
||||||
// argument: (),
|
constructor, name, ..
|
||||||
// }
|
} => match (
|
||||||
// }
|
constructor.clone().variant.clone(),
|
||||||
// }
|
(*constructor.tipo).clone(),
|
||||||
|
) {
|
||||||
|
(ValueConstructorVariant::LocalVariable { .. }, Type::App { .. }) => {
|
||||||
|
current_var_name = if current_var_name.is_empty() {
|
||||||
|
name
|
||||||
|
} else {
|
||||||
|
format!("{name}_field_{current_var_name}")
|
||||||
|
};
|
||||||
|
is_var = true;
|
||||||
|
}
|
||||||
|
_ => todo!(),
|
||||||
|
},
|
||||||
|
TypedExpr::RecordAccess { label, record, .. } => {
|
||||||
|
current_var_name = if current_var_name.is_empty() {
|
||||||
|
label.to_string()
|
||||||
|
} else {
|
||||||
|
format!("{label}_field_{current_var_name}")
|
||||||
|
};
|
||||||
|
current_subject = *record.clone();
|
||||||
|
}
|
||||||
|
_ => {}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
todo!();
|
let mut term = Term::Apply {
|
||||||
|
function: Term::Var(Name {
|
||||||
|
text: format!("choose_{current_module}_{data_type}_constr"),
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
argument: Term::Var(Name {
|
||||||
|
text: current_var_name,
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
};
|
||||||
|
let need_lam = total_constr_length - new_current_clauses.len() > 0;
|
||||||
|
|
||||||
|
let (last, new_current_clauses) = new_current_clauses.split_last().unwrap();
|
||||||
|
let mut new_current_clauses = new_current_clauses.to_vec();
|
||||||
|
let last_term =
|
||||||
|
self.recurse_code_gen(&last.1, scope_level.scope_increment_sequence(1));
|
||||||
|
|
||||||
|
let mut current: Option<(usize, TypedExpr)> = None;
|
||||||
|
for index in 0..total_constr_length - 1 {
|
||||||
|
if current.is_none() {
|
||||||
|
current = new_current_clauses.pop();
|
||||||
|
}
|
||||||
|
if let Some(val) = current.clone() {
|
||||||
|
if val.0 == index {
|
||||||
|
let branch_term = self
|
||||||
|
.recurse_code_gen(&val.1, scope_level.scope_increment_sequence(1));
|
||||||
|
|
||||||
|
term = Term::Apply {
|
||||||
|
function: term.into(),
|
||||||
|
argument: Term::Delay(branch_term.into()).into(),
|
||||||
|
};
|
||||||
|
} else {
|
||||||
|
term = Term::Apply {
|
||||||
|
function: term.into(),
|
||||||
|
argument: Term::Var(Name {
|
||||||
|
text: "last_constr_then".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
term = Term::Apply {
|
||||||
|
function: term.into(),
|
||||||
|
argument: Term::Var(Name {
|
||||||
|
text: "last_constr_then".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if need_lam {
|
||||||
|
term = Term::Apply {
|
||||||
|
function: Term::Lambda {
|
||||||
|
parameter_name: Name {
|
||||||
|
text: "last_constr_then".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
},
|
||||||
|
body: Term::Apply {
|
||||||
|
function: term.into(),
|
||||||
|
argument: Term::Var(Name {
|
||||||
|
text: "last_constr_then".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
argument: Term::Delay(last_term.into()).into(),
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
term = Term::Apply {
|
||||||
|
function: term.into(),
|
||||||
|
argument: Term::Delay(last_term.into()).into(),
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
term
|
||||||
}
|
}
|
||||||
//if statements increase scope due to branching.
|
//if statements increase scope due to branching.
|
||||||
TypedExpr::If {
|
TypedExpr::If {
|
||||||
|
@ -1076,12 +977,7 @@ impl<'a> CodeGenerator<'a> {
|
||||||
constructor.clone().variant.clone(),
|
constructor.clone().variant.clone(),
|
||||||
(*constructor.tipo).clone(),
|
(*constructor.tipo).clone(),
|
||||||
) {
|
) {
|
||||||
(
|
(ValueConstructorVariant::LocalVariable { .. }, Type::App { .. }) => {
|
||||||
ValueConstructorVariant::LocalVariable { .. },
|
|
||||||
Type::App {
|
|
||||||
module: app_module, ..
|
|
||||||
},
|
|
||||||
) => {
|
|
||||||
current_var_name = if current_var_name.is_empty() {
|
current_var_name = if current_var_name.is_empty() {
|
||||||
name
|
name
|
||||||
} else {
|
} else {
|
||||||
|
@ -1198,11 +1094,123 @@ impl<'a> CodeGenerator<'a> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Pull out all uplc data holder and data usage, Sort By Scope Level, Then
|
for (key, scope) in self.uplc_data_constr_lookup.clone().iter() {
|
||||||
|
if scope_level.is_less_than(scope, false) {
|
||||||
|
let data_constrs = *self.data_types.get(key).unwrap();
|
||||||
|
let mut constr_term = Term::Var(Name {
|
||||||
|
text: "last_constructor_result".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
});
|
||||||
|
|
||||||
|
let length = data_constrs.constructors.len();
|
||||||
|
|
||||||
|
for index in (0..length - 1).rev() {
|
||||||
|
constr_term = Term::Apply {
|
||||||
|
function: Term::Apply {
|
||||||
|
function: Term::Apply {
|
||||||
|
function: Term::Force(
|
||||||
|
Term::Builtin(DefaultFunction::IfThenElse).into(),
|
||||||
|
)
|
||||||
|
.into(),
|
||||||
|
argument: Term::Apply {
|
||||||
|
function: Term::Apply {
|
||||||
|
function: Term::Builtin(DefaultFunction::EqualsInteger)
|
||||||
|
.into(),
|
||||||
|
argument: Term::Constant(Constant::Integer(index as i128))
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
argument: Term::Var(Name {
|
||||||
|
text: "constr_index".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
argument: Term::Var(Name {
|
||||||
|
text: format!("constr_{index}_result"),
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
argument: constr_term.into(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
constr_term = Term::Lambda {
|
||||||
|
parameter_name: Name {
|
||||||
|
text: "last_constructor_result".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
},
|
||||||
|
body: Term::Force(constr_term.into()).into(),
|
||||||
|
};
|
||||||
|
|
||||||
|
for index in 0..length - 1 {
|
||||||
|
constr_term = Term::Lambda {
|
||||||
|
parameter_name: Name {
|
||||||
|
text: format!("constr_{index}_result"),
|
||||||
|
unique: 0.into(),
|
||||||
|
},
|
||||||
|
body: constr_term.into(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
let data_type_name = data_constrs.name.clone();
|
||||||
|
|
||||||
|
constr_term = Term::Lambda {
|
||||||
|
parameter_name: Name {
|
||||||
|
text: "constr_data".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
},
|
||||||
|
body: Term::Apply {
|
||||||
|
function: Term::Lambda {
|
||||||
|
parameter_name: Name {
|
||||||
|
text: "constr_index".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
},
|
||||||
|
body: constr_term.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
argument: Term::Apply {
|
||||||
|
function: Term::Builtin(DefaultFunction::FstPair).into(),
|
||||||
|
argument: Term::Apply {
|
||||||
|
function: Term::Builtin(DefaultFunction::UnConstrData).into(),
|
||||||
|
argument: Term::Var(Name {
|
||||||
|
text: "constr_data".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
};
|
||||||
|
let module = &key.0;
|
||||||
|
|
||||||
|
term = Term::Apply {
|
||||||
|
function: Term::Lambda {
|
||||||
|
parameter_name: Name {
|
||||||
|
text: format!("choose_{module}_{data_type_name}_constr"),
|
||||||
|
unique: 0.into(),
|
||||||
|
},
|
||||||
|
body: term.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
argument: constr_term.into(),
|
||||||
|
};
|
||||||
|
self.uplc_data_constr_lookup.shift_remove(key);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Pull out all uplc data holder and data usage, filter by Scope Level, Sort By Scope Depth, Then Apply
|
||||||
let mut data_holder: Vec<((String, String, String), (bool, ScopeLevels, u64))> = self
|
let mut data_holder: Vec<((String, String, String), (bool, ScopeLevels, u64))> = self
|
||||||
.uplc_data_usage_holder_lookup
|
.uplc_data_usage_holder_lookup
|
||||||
.iter()
|
.iter()
|
||||||
.filter(|record_scope| scope_level.is_less_than(&record_scope.1, false))
|
.filter(|record_scope| scope_level.is_less_than(record_scope.1, false))
|
||||||
.map(|((module, name), scope)| {
|
.map(|((module, name), scope)| {
|
||||||
(
|
(
|
||||||
(module.to_string(), name.to_string(), "".to_string()),
|
(module.to_string(), name.to_string(), "".to_string()),
|
||||||
|
@ -1304,4 +1312,203 @@ impl<'a> CodeGenerator<'a> {
|
||||||
|
|
||||||
term
|
term
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn add_arg_getter(&self, term: Term<Name>) -> Term<Name> {
|
||||||
|
//Apply constr arg getter to top level.
|
||||||
|
|
||||||
|
Term::Apply {
|
||||||
|
function: Term::Lambda {
|
||||||
|
parameter_name: Name {
|
||||||
|
text: "constr_field_get_arg".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
},
|
||||||
|
body: term.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
argument: Term::Lambda {
|
||||||
|
parameter_name: Name {
|
||||||
|
text: "constr_list".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
},
|
||||||
|
body: Term::Lambda {
|
||||||
|
parameter_name: Name {
|
||||||
|
text: "arg_number".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
},
|
||||||
|
body: Term::Apply {
|
||||||
|
function: Term::Lambda {
|
||||||
|
parameter_name: Name {
|
||||||
|
text: "recurse".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
},
|
||||||
|
body: Term::Apply {
|
||||||
|
function: Term::Apply {
|
||||||
|
function: Term::Apply {
|
||||||
|
function: Term::Var(Name {
|
||||||
|
text: "recurse".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
argument: Term::Var(Name {
|
||||||
|
text: "recurse".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
|
||||||
|
// Start recursive with index 0 of list
|
||||||
|
argument: Term::Constant(Constant::Integer(0.into())).into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
argument: Term::Var(Name {
|
||||||
|
text: "constr_list".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
|
||||||
|
argument: Term::Lambda {
|
||||||
|
parameter_name: Name {
|
||||||
|
text: "self_recursor".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
},
|
||||||
|
body: Term::Lambda {
|
||||||
|
parameter_name: Name {
|
||||||
|
text: "current_arg_number".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
},
|
||||||
|
body: Term::Lambda {
|
||||||
|
parameter_name: Name {
|
||||||
|
text: "list_of_constr_args".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
},
|
||||||
|
body: Term::Apply {
|
||||||
|
function: Term::Apply {
|
||||||
|
function: Term::Apply {
|
||||||
|
function: Term::Apply {
|
||||||
|
function: Term::Force(
|
||||||
|
Term::Builtin(DefaultFunction::IfThenElse)
|
||||||
|
.into(),
|
||||||
|
)
|
||||||
|
.into(),
|
||||||
|
argument: Term::Apply {
|
||||||
|
function: Term::Apply {
|
||||||
|
function: Term::Builtin(
|
||||||
|
DefaultFunction::EqualsInteger,
|
||||||
|
)
|
||||||
|
.into(),
|
||||||
|
argument: Term::Var(Name {
|
||||||
|
text: "arg_number".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
argument: Term::Var(Name {
|
||||||
|
text: "current_arg_number".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
argument: Term::Force(
|
||||||
|
Term::Builtin(DefaultFunction::HeadList).into(),
|
||||||
|
)
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
argument: Term::Lambda {
|
||||||
|
parameter_name: Name {
|
||||||
|
text: "current_list_of_constr_args".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
},
|
||||||
|
body: Term::Apply {
|
||||||
|
function: Term::Apply {
|
||||||
|
function: Term::Apply {
|
||||||
|
function: Term::Var(Name {
|
||||||
|
text: "self_recursor".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
argument: Term::Var(Name {
|
||||||
|
text: "self_recursor".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
|
||||||
|
argument: Term::Apply {
|
||||||
|
function: Term::Apply {
|
||||||
|
function: Term::Builtin(
|
||||||
|
DefaultFunction::AddInteger,
|
||||||
|
)
|
||||||
|
.into(),
|
||||||
|
argument: Term::Var(Name {
|
||||||
|
text: "current_arg_number"
|
||||||
|
.to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
argument: Term::Constant(
|
||||||
|
Constant::Integer(1.into()),
|
||||||
|
)
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
|
||||||
|
argument: Term::Apply {
|
||||||
|
function: Term::Force(
|
||||||
|
Term::Builtin(
|
||||||
|
DefaultFunction::TailList,
|
||||||
|
)
|
||||||
|
.into(),
|
||||||
|
)
|
||||||
|
.into(),
|
||||||
|
|
||||||
|
argument: Term::Var(Name {
|
||||||
|
text: "current_list_of_constr_args"
|
||||||
|
.to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
argument: Term::Var(Name {
|
||||||
|
text: "list_of_constr_args".to_string(),
|
||||||
|
unique: 0.into(),
|
||||||
|
})
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
.into(),
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -11,8 +11,8 @@ struct Level(usize);
|
||||||
|
|
||||||
#[derive(Error, Debug)]
|
#[derive(Error, Debug)]
|
||||||
pub enum Error {
|
pub enum Error {
|
||||||
#[error("Free Unique `{0}`")]
|
#[error("Free Unique {} with name {}", .0.unique, .0.text)]
|
||||||
FreeUnique(Unique),
|
FreeUnique(Name),
|
||||||
#[error("Free Index `{0}`")]
|
#[error("Free Index `{0}`")]
|
||||||
FreeIndex(DeBruijn),
|
FreeIndex(DeBruijn),
|
||||||
}
|
}
|
||||||
|
@ -37,9 +37,9 @@ impl Converter {
|
||||||
term: &Term<Name>,
|
term: &Term<Name>,
|
||||||
) -> Result<Term<NamedDeBruijn>, Error> {
|
) -> Result<Term<NamedDeBruijn>, Error> {
|
||||||
let converted_term = match term {
|
let converted_term = match term {
|
||||||
Term::Var(Name { text, unique }) => Term::Var(NamedDeBruijn {
|
Term::Var(name) => Term::Var(NamedDeBruijn {
|
||||||
text: text.to_string(),
|
text: name.text.to_string(),
|
||||||
index: self.get_index(*unique)?,
|
index: self.get_index(name)?,
|
||||||
}),
|
}),
|
||||||
Term::Delay(term) => Term::Delay(Rc::new(self.name_to_named_debruijn(term)?)),
|
Term::Delay(term) => Term::Delay(Rc::new(self.name_to_named_debruijn(term)?)),
|
||||||
Term::Lambda {
|
Term::Lambda {
|
||||||
|
@ -48,7 +48,7 @@ impl Converter {
|
||||||
} => {
|
} => {
|
||||||
self.declare_unique(parameter_name.unique);
|
self.declare_unique(parameter_name.unique);
|
||||||
|
|
||||||
let index = self.get_index(parameter_name.unique)?;
|
let index = self.get_index(parameter_name)?;
|
||||||
|
|
||||||
let name = NamedDeBruijn {
|
let name = NamedDeBruijn {
|
||||||
text: parameter_name.text.to_string(),
|
text: parameter_name.text.to_string(),
|
||||||
|
@ -83,7 +83,7 @@ impl Converter {
|
||||||
|
|
||||||
pub fn name_to_debruijn(&mut self, term: &Term<Name>) -> Result<Term<DeBruijn>, Error> {
|
pub fn name_to_debruijn(&mut self, term: &Term<Name>) -> Result<Term<DeBruijn>, Error> {
|
||||||
let converted_term = match term {
|
let converted_term = match term {
|
||||||
Term::Var(Name { unique, .. }) => Term::Var(self.get_index(*unique)?),
|
Term::Var(name) => Term::Var(self.get_index(name)?),
|
||||||
Term::Delay(term) => Term::Delay(Rc::new(self.name_to_debruijn(term)?)),
|
Term::Delay(term) => Term::Delay(Rc::new(self.name_to_debruijn(term)?)),
|
||||||
Term::Lambda {
|
Term::Lambda {
|
||||||
parameter_name,
|
parameter_name,
|
||||||
|
@ -91,7 +91,7 @@ impl Converter {
|
||||||
} => {
|
} => {
|
||||||
self.declare_unique(parameter_name.unique);
|
self.declare_unique(parameter_name.unique);
|
||||||
|
|
||||||
let name = self.get_index(parameter_name.unique)?;
|
let name = self.get_index(parameter_name)?;
|
||||||
|
|
||||||
self.start_scope();
|
self.start_scope();
|
||||||
|
|
||||||
|
@ -316,16 +316,16 @@ impl Converter {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_index(&mut self, unique: Unique) -> Result<DeBruijn, Error> {
|
fn get_index(&mut self, name: &Name) -> Result<DeBruijn, Error> {
|
||||||
for scope in self.levels.iter().rev() {
|
for scope in self.levels.iter().rev() {
|
||||||
if let Some(found_level) = scope.get(&unique) {
|
if let Some(found_level) = scope.get(&name.unique) {
|
||||||
let index = self.current_level.0 - found_level.0;
|
let index = self.current_level.0 - found_level.0;
|
||||||
|
|
||||||
return Ok(index.into());
|
return Ok(index.into());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Err(Error::FreeUnique(unique))
|
Err(Error::FreeUnique(name.clone()))
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_unique(&mut self, index: DeBruijn) -> Result<Unique, Error> {
|
fn get_unique(&mut self, index: DeBruijn) -> Result<Unique, Error> {
|
||||||
|
|
|
@ -27,3 +27,12 @@ pub fn eqString(a: ByteArray, b: ByteArray) {
|
||||||
a == b
|
a == b
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub type Thing {
|
||||||
|
Some
|
||||||
|
None
|
||||||
|
}
|
||||||
|
|
||||||
|
pub type Other {
|
||||||
|
Wow
|
||||||
|
Yes
|
||||||
|
}
|
||||||
|
|
|
@ -16,8 +16,7 @@ pub fn spend(datum: sample.Datum, rdmr: Redeemer, ctx: spend.ScriptContext) -> B
|
||||||
let b = datum.rdmr
|
let b = datum.rdmr
|
||||||
|
|
||||||
when b is {
|
when b is {
|
||||||
sample.Buy | sample.Sell -> 1 == 1
|
sample.Buy -> 1 == 1
|
||||||
sample.Sell -> 5 == 1
|
sample.Sell -> 5 == 1
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue