collect top level exprs
This commit is contained in:
parent
2f18cde64a
commit
355d132ba3
|
@ -10,6 +10,7 @@ struct AnalysisScope {
|
||||||
prev: Option<ScopeIdx>,
|
prev: Option<ScopeIdx>,
|
||||||
next: Vec<ScopeIdx>,
|
next: Vec<ScopeIdx>,
|
||||||
idents: Vec<(Ident, u16)>,
|
idents: Vec<(Ident, u16)>,
|
||||||
|
top_level_exprs: Vec<Expr>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl AnalysisScope {
|
impl AnalysisScope {
|
||||||
|
@ -102,7 +103,9 @@ impl Analyzer {
|
||||||
Expr::Block(a) => {
|
Expr::Block(a) => {
|
||||||
// blocks have their own scope
|
// blocks have their own scope
|
||||||
self.new_scope();
|
self.new_scope();
|
||||||
|
let sc = self.get_scope();
|
||||||
// analyze the contents in the new scope
|
// analyze the contents in the new scope
|
||||||
|
sc.top_level_exprs = a.exprs.clone();
|
||||||
for e in a.exprs {
|
for e in a.exprs {
|
||||||
self.analyze(e);
|
self.analyze(e);
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,7 +6,7 @@ use std::{
|
||||||
|
|
||||||
use crate::kinds;
|
use crate::kinds;
|
||||||
|
|
||||||
#[derive(Debug, PartialEq, Eq)]
|
#[derive(Debug, PartialEq, Eq, Clone)]
|
||||||
pub struct Ident(String);
|
pub struct Ident(String);
|
||||||
impl fmt::Display for Ident {
|
impl fmt::Display for Ident {
|
||||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||||
|
@ -14,7 +14,7 @@ impl fmt::Display for Ident {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug, Clone)]
|
||||||
pub enum Literal {
|
pub enum Literal {
|
||||||
String(String),
|
String(String),
|
||||||
Integer(i64),
|
Integer(i64),
|
||||||
|
|
|
@ -15,7 +15,7 @@ fn main() {
|
||||||
let block = parser.parse().unwrap();
|
let block = parser.parse().unwrap();
|
||||||
println!("Parse took {:?}", start.elapsed());
|
println!("Parse took {:?}", start.elapsed());
|
||||||
let e = parser::Expr::Block(block);
|
let e = parser::Expr::Block(block);
|
||||||
// parser::util::display(e);
|
parser::util::display(&e);
|
||||||
let start = Instant::now();
|
let start = Instant::now();
|
||||||
let mut analysis = compiler::Analyzer::new();
|
let mut analysis = compiler::Analyzer::new();
|
||||||
analysis.analyze(e);
|
analysis.analyze(e);
|
||||||
|
|
|
@ -7,7 +7,7 @@ use crate::{
|
||||||
|
|
||||||
pub mod util;
|
pub mod util;
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug, Clone)]
|
||||||
pub enum Expr {
|
pub enum Expr {
|
||||||
// Data and variables
|
// Data and variables
|
||||||
Assign(Box<Expr>, Box<Expr>),
|
Assign(Box<Expr>, Box<Expr>),
|
||||||
|
@ -46,7 +46,7 @@ pub enum Expr {
|
||||||
DivideAssign(Box<Expr>, Box<Expr>),
|
DivideAssign(Box<Expr>, Box<Expr>),
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Default)]
|
#[derive(Debug, Default, Clone)]
|
||||||
pub struct Block {
|
pub struct Block {
|
||||||
pub exprs: Vec<Expr>,
|
pub exprs: Vec<Expr>,
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,12 +2,12 @@ use std::fmt::Write;
|
||||||
|
|
||||||
use crate::parser::Expr;
|
use crate::parser::Expr;
|
||||||
|
|
||||||
pub fn display(e: Expr) {
|
pub fn display(e: &Expr) {
|
||||||
let result = fmt_expr(e, 0);
|
let result = fmt_expr(e, 0);
|
||||||
println!("{result}");
|
println!("{result}");
|
||||||
}
|
}
|
||||||
|
|
||||||
fn fmt_binop(left: Expr, right: Expr, op: &str, depth: usize) -> String {
|
fn fmt_binop(left: &Expr, right: &Expr, op: &str, depth: usize) -> String {
|
||||||
format!(
|
format!(
|
||||||
"({} {} {})",
|
"({} {} {})",
|
||||||
fmt_expr(left, depth),
|
fmt_expr(left, depth),
|
||||||
|
@ -16,16 +16,16 @@ fn fmt_binop(left: Expr, right: Expr, op: &str, depth: usize) -> String {
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn fmt_expr(e: Expr, depth: usize) -> String {
|
fn fmt_expr(e: &Expr, depth: usize) -> String {
|
||||||
match e {
|
match e {
|
||||||
Expr::Assign(l, r) => fmt_binop(*l, *r, "=", depth),
|
Expr::Assign(l, r) => fmt_binop(l, r, "=", depth),
|
||||||
Expr::AddAssign(l, r) => fmt_binop(*l, *r, "+=", depth),
|
Expr::AddAssign(l, r) => fmt_binop(l, r, "+=", depth),
|
||||||
Expr::SubtractAssign(l, r) => fmt_binop(*l, *r, "-=", depth),
|
Expr::SubtractAssign(l, r) => fmt_binop(l, r, "-=", depth),
|
||||||
Expr::MultiplyAssign(l, r) => fmt_binop(*l, *r, "*=", depth),
|
Expr::MultiplyAssign(l, r) => fmt_binop(l, r, "*=", depth),
|
||||||
Expr::DivideAssign(l, r) => fmt_binop(*l, *r, "/=", depth),
|
Expr::DivideAssign(l, r) => fmt_binop(l, r, "/=", depth),
|
||||||
Expr::Literal(l) => l.to_string(),
|
Expr::Literal(l) => l.to_string(),
|
||||||
Expr::Call(l, r) => {
|
Expr::Call(l, r) => {
|
||||||
let mut result = fmt_expr(*l, depth);
|
let mut result = fmt_expr(l, depth);
|
||||||
result.push('(');
|
result.push('(');
|
||||||
let len = r.len();
|
let len = r.len();
|
||||||
for (i, e) in r.into_iter().enumerate() {
|
for (i, e) in r.into_iter().enumerate() {
|
||||||
|
@ -38,17 +38,17 @@ fn fmt_expr(e: Expr, depth: usize) -> String {
|
||||||
result
|
result
|
||||||
}
|
}
|
||||||
Expr::If(c, t, f) => {
|
Expr::If(c, t, f) => {
|
||||||
let mut result = format!("if ({}) ({})", fmt_expr(*c, depth), fmt_expr(*t, depth));
|
let mut result = format!("if ({}) ({})", fmt_expr(c, depth), fmt_expr(t, depth));
|
||||||
if let Some(f) = f {
|
if let Some(f) = f {
|
||||||
let _ = write!(result, " else ({})", fmt_expr(*f, depth));
|
let _ = write!(result, " else ({})", fmt_expr(f, depth));
|
||||||
}
|
}
|
||||||
result
|
result
|
||||||
}
|
}
|
||||||
Expr::Return(l) => format!("return ({})", fmt_expr(*l, depth)),
|
Expr::Return(l) => format!("return ({})", fmt_expr(l, depth)),
|
||||||
Expr::Block(b) => {
|
Expr::Block(b) => {
|
||||||
let mut result = String::new();
|
let mut result = String::new();
|
||||||
let len = b.exprs.len();
|
let len = b.exprs.len();
|
||||||
for (i, expr) in b.exprs.into_iter().enumerate() {
|
for (i, expr) in b.exprs.iter().enumerate() {
|
||||||
result.push_str(&" ".repeat(depth));
|
result.push_str(&" ".repeat(depth));
|
||||||
result.push_str(&fmt_expr(expr, depth + 1));
|
result.push_str(&fmt_expr(expr, depth + 1));
|
||||||
if depth != 0 || i + 1 != len {
|
if depth != 0 || i + 1 != len {
|
||||||
|
@ -66,23 +66,23 @@ fn fmt_expr(e: Expr, depth: usize) -> String {
|
||||||
.map(|e| fmt_expr(e, depth))
|
.map(|e| fmt_expr(e, depth))
|
||||||
.collect::<Vec<_>>()
|
.collect::<Vec<_>>()
|
||||||
.join(", "),
|
.join(", "),
|
||||||
fmt_expr(*e, depth)
|
fmt_expr(e, depth)
|
||||||
),
|
),
|
||||||
Expr::Negate(l) => format!("(-{})", fmt_expr(*l, depth)),
|
Expr::Negate(l) => format!("(-{})", fmt_expr(l, depth)),
|
||||||
Expr::Not(l) => format!("(!{})", fmt_expr(*l, depth)),
|
Expr::Not(l) => format!("(!{})", fmt_expr(l, depth)),
|
||||||
Expr::EqualTo(l, r) => fmt_binop(*l, *r, "==", depth),
|
Expr::EqualTo(l, r) => fmt_binop(l, r, "==", depth),
|
||||||
Expr::NotEqualTo(l, r) => fmt_binop(*l, *r, "!=", depth),
|
Expr::NotEqualTo(l, r) => fmt_binop(l, r, "!=", depth),
|
||||||
Expr::And(l, r) => fmt_binop(*l, *r, "&&", depth),
|
Expr::And(l, r) => fmt_binop(l, r, "&&", depth),
|
||||||
Expr::Or(l, r) => fmt_binop(*l, *r, "||", depth),
|
Expr::Or(l, r) => fmt_binop(l, r, "||", depth),
|
||||||
Expr::LessThan(l, r) => fmt_binop(*l, *r, "<", depth),
|
Expr::LessThan(l, r) => fmt_binop(l, r, "<", depth),
|
||||||
Expr::LessThanOrEqualTo(l, r) => fmt_binop(*l, *r, "<=", depth),
|
Expr::LessThanOrEqualTo(l, r) => fmt_binop(l, r, "<=", depth),
|
||||||
Expr::GreaterThan(l, r) => fmt_binop(*l, *r, ">", depth),
|
Expr::GreaterThan(l, r) => fmt_binop(l, r, ">", depth),
|
||||||
Expr::GreaterThanOrEqualTo(l, r) => fmt_binop(*l, *r, ">=", depth),
|
Expr::GreaterThanOrEqualTo(l, r) => fmt_binop(l, r, ">=", depth),
|
||||||
Expr::Add(l, r) => fmt_binop(*l, *r, "+", depth),
|
Expr::Add(l, r) => fmt_binop(l, r, "+", depth),
|
||||||
Expr::Subtract(l, r) => fmt_binop(*l, *r, "-", depth),
|
Expr::Subtract(l, r) => fmt_binop(l, r, "-", depth),
|
||||||
Expr::Multiply(l, r) => fmt_binop(*l, *r, "*", depth),
|
Expr::Multiply(l, r) => fmt_binop(l, r, "*", depth),
|
||||||
Expr::Divide(l, r) => fmt_binop(*l, *r, "/", depth),
|
Expr::Divide(l, r) => fmt_binop(l, r, "/", depth),
|
||||||
Expr::Exponent(l, r) => fmt_binop(*l, *r, "**", depth),
|
Expr::Exponent(l, r) => fmt_binop(l, r, "**", depth),
|
||||||
Expr::Modulo(l, r) => fmt_binop(*l, *r, "%", depth),
|
Expr::Modulo(l, r) => fmt_binop(l, r, "%", depth),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue