reference strings, first error reporting

main
NotAFile 2022-01-05 00:13:56 +01:00
parent 5b4f378526
commit 33149eb5aa
3 changed files with 56 additions and 26 deletions

View File

@ -31,7 +31,36 @@ fn make_pubid(id: &str) -> String {
} }
#[derive(Debug)] #[derive(Debug)]
pub struct CompileError; pub enum CompileErrorKind {
UndefinedReference(String)
}
#[derive(Debug)]
pub struct CompileError {
kind: CompileErrorKind,
}
impl CompileError {
fn new(kind: CompileErrorKind) -> Self {
Self {
kind
}
}
}
pub enum GenericParam<T> {
Unsolved,
Solved(T),
}
pub enum Type {
/// a wire of some width
Wire(GenericParam<u32>)
}
// module that can be instantiated like a function
pub struct Callable {
}
fn lower_expression(module: &mut rtlil::Module, expr: &parser::Expression) -> Result<String, CompileError> { fn lower_expression(module: &mut rtlil::Module, expr: &parser::Expression) -> Result<String, CompileError> {
match expr { match expr {
@ -43,7 +72,7 @@ fn lower_expression(module: &mut rtlil::Module, expr: &parser::Expression) -> Re
let mut args_resolved = call.args.iter().map(|expr| lower_expression(module, expr)); let mut args_resolved = call.args.iter().map(|expr| lower_expression(module, expr));
// TODO: make this sensible // TODO: make this sensible
let cell = match call.name.as_str() { let cell = match *call.name.fragment() {
"and" => { "and" => {
let arg_a = args_resolved.next().unwrap()?; let arg_a = args_resolved.next().unwrap()?;
let arg_b = args_resolved.next().unwrap()?; let arg_b = args_resolved.next().unwrap()?;
@ -66,12 +95,12 @@ fn lower_expression(module: &mut rtlil::Module, expr: &parser::Expression) -> Re
let cell_id = module.make_genid("reduce_or"); let cell_id = module.make_genid("reduce_or");
builtin_unop_cell("$reduce_or", &cell_id, &arg_a, &output_gen_id) builtin_unop_cell("$reduce_or", &cell_id, &arg_a, &output_gen_id)
} }
_ => return Err(CompileError {}), name => return Err(CompileError::new(CompileErrorKind::UndefinedReference(name.to_owned()))),
}; };
module.add_cell(cell); module.add_cell(cell);
Ok(output_gen_id) Ok(output_gen_id)
} }
parser::Expression::Operation(op) => todo!(), parser::Expression::Operation(_op) => todo!(),
} }
} }

View File

@ -2,6 +2,7 @@ mod literals;
mod parser; mod parser;
mod rtlil; mod rtlil;
mod frontend; mod frontend;
mod builtin_cells;
use nom::error::convert_error; use nom::error::convert_error;
use std::fs::File; use std::fs::File;

View File

@ -43,8 +43,8 @@ fn intliteral(input: Span) -> IResult<Span, (u64, u64)> {
} }
#[derive(Debug)] #[derive(Debug)]
pub struct NetDecl { pub struct NetDecl<'a> {
pub name: String, pub name: &'a str,
pub width: Option<u64>, pub width: Option<u64>,
pub value: Option<(u64, u64)>, pub value: Option<(u64, u64)>,
} }
@ -59,44 +59,44 @@ pub enum PortDirection {
pub struct PortDecl<'a> { pub struct PortDecl<'a> {
pub pos: Span<'a>, pub pos: Span<'a>,
pub direction: PortDirection, pub direction: PortDirection,
pub net: NetDecl, pub net: NetDecl<'a>,
} }
#[derive(Debug)] #[derive(Debug)]
pub struct Module<'a> { pub struct Module<'a> {
pub name: String, pub name: &'a str,
pub ports: Vec<PortDecl<'a>>, pub ports: Vec<PortDecl<'a>>,
pub statements: Vec<Statement>, pub statements: Vec<Statement<'a>>,
} }
#[derive(Debug)] #[derive(Debug)]
pub enum Statement { pub enum Statement<'a> {
Assign(Assign), Assign(Assign<'a>),
} }
#[derive(Debug)] #[derive(Debug)]
pub struct Assign { pub struct Assign<'a> {
pub lhs: String, pub lhs: &'a str,
pub expr: Expression, pub expr: Expression<'a>,
} }
#[derive(Debug)] #[derive(Debug)]
pub enum Operation { pub enum Operation<'a> {
And { a: String, b: Expression }, And { a: String, b: Expression<'a> },
Or { a: String, b: Expression }, Or { a: String, b: Expression<'a> },
} }
#[derive(Debug)] #[derive(Debug)]
pub struct Call { pub struct Call<'a> {
pub name: String, pub name: Span<'a>,
pub args: Vec<Expression>, pub args: Vec<Expression<'a>>,
} }
#[derive(Debug)] #[derive(Debug)]
pub enum Expression { pub enum Expression<'a> {
Ident(String), Ident(&'a str),
Call(Box<Call>), Call(Box<Call<'a>>),
Operation(Box<Operation>), Operation(Box<Operation<'a>>),
} }
fn declaration(i: Span) -> IResult<Span, NetDecl> { fn declaration(i: Span) -> IResult<Span, NetDecl> {
@ -108,7 +108,7 @@ fn declaration(i: Span) -> IResult<Span, NetDecl> {
opt(preceded(ws0(char('=')), intliteral)), opt(preceded(ws0(char('=')), intliteral)),
)), )),
|(_, width, ident, value)| NetDecl { |(_, width, ident, value)| NetDecl {
name: (*ident.fragment()).into(), name: ident.fragment(),
width, width,
value, value,
}, },
@ -167,7 +167,7 @@ fn call_item(input: Span) -> IResult<Span, Call> {
), ),
)), )),
|(name, args)| Call { |(name, args)| Call {
name: (*name.fragment()).into(), name: name,
args, args,
}, },
)(input) )(input)