expr: replace old builder functions with direct constructors; add more region tags

This commit is contained in:
Michael Sippel 2024-10-04 02:19:24 +02:00
parent 1a152670d3
commit 2ac69a7b12
Signed by: senvas
GPG key ID: F96CF119C34B64A6
3 changed files with 38 additions and 36 deletions

View file

@ -16,6 +16,7 @@ pub enum Statement {
val_expr: LTExpr,
},
LetAssign {
name_region: InputRegionTag,
typ: Option<TypeTag>,
var_id: String,
val_expr: LTExpr,
@ -109,34 +110,5 @@ impl LTExpr {
LTExpr::ExportBlock{ region, statements } => region
}.clone()
}
pub fn lit_uint(val: u64) -> Self {
LTExpr::WordLiteral {
region: InputRegionTag::default(),
val: val as tisc::VM_Word,
}
}
pub fn application(head: LTExpr, body: Vec<LTExpr>) -> Self {
LTExpr::Application {
region: InputRegionTag::default(),
typ: None,
head: Box::new(head),
body: body,
}
}
pub fn block(body: Vec<Statement>) -> Self {
LTExpr::Block { region: InputRegionTag::default(), statements: body }
}
}
impl Statement {
pub fn while_loop(cond: LTExpr, body: Vec<Statement>) -> Self {
Statement::WhileLoop {
condition: cond,
body,
}
}
}

View file

@ -214,6 +214,7 @@ where It: Iterator<Item = (InputRegionTag, Result<LTIRToken, LexError>)>
let _ = parse_expect(tokens, LTIRToken::StatementSep)?;
Ok(Statement::LetAssign {
name_region,
typ: match typ {
Some((r,t)) => Some(Ok(t)),
None => None
@ -292,8 +293,19 @@ where It: Iterator<Item = (InputRegionTag, Result<LTIRToken, LexError>)>
{
match tokens.next() {
Some((region, Ok(LTIRToken::Symbol(sym)))) => Ok(LTExpr::Symbol{ region, symbol: sym, typ: None }),
Some((region, Ok(LTIRToken::Char(c)))) => Ok(LTExpr::lit_uint(c as u64)),
Some((region, Ok(LTIRToken::Num(n)))) => Ok(LTExpr::lit_uint(n as u64)),
Some((region, Ok(LTIRToken::Char(c)))) => Ok(
LTExpr::Ascend {
region: region.clone(),
typ: match typectx.parse("Char ~ Unicode ~ _2^32") {
Ok(t) => Ok(t),
Err(e) => Err(TypeError::ParseError(e))
},
expr: Box::new(
LTExpr::WordLiteral{ region, val: c as tisc::VM_Word }
)
}
),
Some((region, Ok(LTIRToken::Num(n)))) => Ok(LTExpr::WordLiteral{ region, val: n as tisc::VM_Word }),
Some((region, Ok(_))) => Err((region, ParseError::UnexpectedToken)),
Some((region, Err(err))) => Err((region, ParseError::LexError(err))),
None => Err((InputRegionTag::default(), ParseError::UnexpectedEnd)),
@ -345,7 +357,13 @@ where It: Iterator<Item = (InputRegionTag, Result<LTIRToken, LexError>)>
break;
}
Ok(LTIRToken::BlockOpen) => {
children.push(LTExpr::block(parse_statement_block(typectx, tokens)?));
let region = region.clone();
let statements = parse_statement_block(typectx, tokens)?;
children.push(
LTExpr::Block {
region,
statements
});
}
Ok(LTIRToken::BlockClose) => {
break;
@ -368,6 +386,7 @@ where It: Iterator<Item = (InputRegionTag, Result<LTIRToken, LexError>)>
};
if let Some(expr) = children.pop() {
region.begin = expr.get_region().begin;
children.push(LTExpr::Ascend {
region: region.clone(),
typ,
@ -402,8 +421,10 @@ where It: Iterator<Item = (InputRegionTag, Result<LTIRToken, LexError>)>
let _ = parse_expect(tokens, LTIRToken::ExprOpen)?;
let cond = parse_expr(typectx, tokens)?;
let _ = parse_expect(tokens, LTIRToken::ExprClose)?;
let if_expr = LTExpr::block(parse_statement_block(typectx, tokens)?);
let mut else_expr = LTExpr::block(vec![]);
let if_statements = parse_statement_block(typectx, tokens)?;
let if_expr = LTExpr::Block{ region: region.clone(), statements: if_statements };
let mut else_expr = LTExpr::Block{ region: InputRegionTag::default(), statements: vec![] };
if let Some((region, peektok)) = tokens.peek() {
if let Ok(LTIRToken::Symbol(name)) = peektok {
@ -445,8 +466,16 @@ where It: Iterator<Item = (InputRegionTag, Result<LTIRToken, LexError>)>
if children.len() > 1 {
let head = children.remove(0);
let mut region = head.get_region();
for c in children.iter() {
let cr = c.get_region();
region.begin = usize::min( region.begin, cr.begin );
region.end = usize::max( region.end, cr.end );
}
Ok(LTExpr::Application {
region: InputRegionTag::default(),
region,
typ: None,
head: Box::new(head),
body: children,

View file

@ -138,6 +138,7 @@ impl ProcedureCompiler {
}
}
Statement::LetAssign {
name_region,
typ,
var_id,
val_expr,
@ -170,7 +171,7 @@ impl ProcedureCompiler {
.declare_var(var_id.clone(), laddertypes::TypeTerm::unit());
self = self.compile_statement(&Statement::Assignment {
name_region: InputRegionTag::default(),
name_region: *name_region,
var_id: var_id.clone(),
val_expr: val_expr.clone(),
}, false);