forked from M-Labs/nac3
started expression checking
This commit is contained in:
parent
a9827da70b
commit
1990486cc2
66
nac3core/src/expression.rs
Normal file
66
nac3core/src/expression.rs
Normal file
@ -0,0 +1,66 @@
|
|||||||
|
use crate::inference::resolve_call;
|
||||||
|
use crate::primitives::*;
|
||||||
|
use crate::typedef::{GlobalContext, Type, Type::*};
|
||||||
|
use rustpython_parser::ast::{Expression, ExpressionType};
|
||||||
|
use std::collections::HashMap;
|
||||||
|
use std::convert::TryFrom;
|
||||||
|
use std::rc::Rc;
|
||||||
|
|
||||||
|
type SymTable<'a> = HashMap<&'a str, Rc<Type>>;
|
||||||
|
type ParserResult = Result<Rc<Type>, String>;
|
||||||
|
|
||||||
|
pub fn parse_expr(ctx: &GlobalContext, sym_table: &SymTable, expr: &Expression) -> ParserResult {
|
||||||
|
Err("not supported".to_string())
|
||||||
|
}
|
||||||
|
|
||||||
|
fn parse_constant(
|
||||||
|
ctx: &GlobalContext,
|
||||||
|
sym_table: &SymTable,
|
||||||
|
value: &rustpython_parser::ast::Number,
|
||||||
|
) -> ParserResult {
|
||||||
|
use rustpython_parser::ast::Number;
|
||||||
|
match value {
|
||||||
|
Number::Integer { value } => {
|
||||||
|
if i32::try_from(&value).is_ok() {
|
||||||
|
Ok(PrimitiveType(INT32_TYPE).into())
|
||||||
|
} else if i64::try_from(&value).is_ok() {
|
||||||
|
Ok(PrimitiveType(INT64_TYPE).into())
|
||||||
|
} else {
|
||||||
|
Err("integer out of range".to_string())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Number::Float { .. } => Ok(PrimitiveType(FLOAT_TYPE).into()),
|
||||||
|
_ => Err("not supported".to_string()),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn parse_identifier(ctx: &GlobalContext, sym_table: &SymTable, name: &str) -> ParserResult {
|
||||||
|
match sym_table.get(name) {
|
||||||
|
Some(v) => Ok(v.clone()),
|
||||||
|
None => Err("unbounded variable".to_string()),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn parse_list(
|
||||||
|
ctx: &GlobalContext,
|
||||||
|
sym_table: &SymTable,
|
||||||
|
elements: &[Expression],
|
||||||
|
) -> ParserResult {
|
||||||
|
if elements.len() == 0 {
|
||||||
|
return Ok(ParametricType(LIST_TYPE, vec![BotType.into()]).into());
|
||||||
|
}
|
||||||
|
|
||||||
|
let mut types = elements
|
||||||
|
.iter()
|
||||||
|
.map(|v| parse_expr(&ctx, sym_table, v));
|
||||||
|
|
||||||
|
let head = types.next().unwrap()?;
|
||||||
|
for v in types {
|
||||||
|
if v? != head {
|
||||||
|
return Err("inhomogeneous list is not allowed".to_string());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Ok(ParametricType(LIST_TYPE, vec![head]).into())
|
||||||
|
}
|
||||||
|
|
||||||
|
|
@ -5,6 +5,7 @@ extern crate rustpython_parser;
|
|||||||
pub mod inference;
|
pub mod inference;
|
||||||
pub mod primitives;
|
pub mod primitives;
|
||||||
pub mod typedef;
|
pub mod typedef;
|
||||||
|
pub mod expression;
|
||||||
|
|
||||||
use std::error::Error;
|
use std::error::Error;
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
|
Loading…
Reference in New Issue
Block a user