From 7fea40208d52340c2404758ff7ffa0b79170bc52 Mon Sep 17 00:00:00 2001 From: NotAFile Date: Mon, 24 Jan 2022 00:10:09 +0100 Subject: [PATCH] start reworking syntax for stdlib --- lib/builtins/main.hyd | 7 +++++++ src/frontend.rs | 13 +++++++------ src/package.rs | 2 +- src/parser.rs | 38 +++++++++++++++++++++++++++++--------- src/parser/module.rs | 34 ++++++++++++++++------------------ 5 files changed, 60 insertions(+), 34 deletions(-) create mode 100644 lib/builtins/main.hyd diff --git a/lib/builtins/main.hyd b/lib/builtins/main.hyd new file mode 100644 index 0000000..3b23c26 --- /dev/null +++ b/lib/builtins/main.hyd @@ -0,0 +1,7 @@ + + +module reduce_or ( + a: Logic + ) + -> Logic<1> { +} diff --git a/src/frontend.rs b/src/frontend.rs index 22d9a2d..d7f012e 100644 --- a/src/frontend.rs +++ b/src/frontend.rs @@ -285,7 +285,7 @@ fn lower_assignment( pub fn lower_module(pa_module: parser::Module) -> Result { let mut writer = rtlil::ILWriter::new(); - let mut ir_module = rtlil::Module::new(make_pubid(pa_module.name)); + let mut ir_module = rtlil::Module::new(make_pubid(pa_module.name.fragment())); let mut context = Context { callables: get_builtins() .into_iter() @@ -297,17 +297,18 @@ pub fn lower_module(pa_module: parser::Module) -> Result { writer.write_line("autoidx 1"); for (idx, port) in pa_module.ports.iter().enumerate() { - let sigtype = TypeStruct::logic_width(port.net.width.unwrap_or(1) as u32); + // FIXME: Actually resolve types + let sigtype = TypeStruct::logic_width(TODO_WIDTH); // FIXME: CRIMES CRIMES CRIMES let sigtype = Box::leak(Box::new(sigtype)); let sig = Signal { - name: port.net.name.to_owned(), - il_id: make_pubid(port.net.name), + name: port.net.name.fragment().to_string(), + il_id: make_pubid(port.net.name.fragment()), typ: sigtype, }; let sig = context .signals - .entry(port.net.name.to_owned()) + .entry(port.net.name.fragment().to_string()) .or_insert(sig); let dir_option = match port.direction { @@ -316,7 +317,7 @@ pub fn lower_module(pa_module: parser::Module) -> Result { }; let wire = rtlil::Wire::new( sig.il_id.to_owned(), - port.net.width.unwrap_or(1) as u32, + TODO_WIDTH, Some(dir_option), ); ir_module.add_wire(wire); diff --git a/src/package.rs b/src/package.rs index b7ae510..126abe0 100644 --- a/src/package.rs +++ b/src/package.rs @@ -9,7 +9,7 @@ pub struct Package { impl Package { pub fn open(&self) -> Result { - let filepath = self.path.with_file_name("main.hyd"); + let filepath = self.path.join("main.hyd"); File::open(filepath) } } diff --git a/src/parser.rs b/src/parser.rs index 10090a9..57d8dcf 100644 --- a/src/parser.rs +++ b/src/parser.rs @@ -38,6 +38,22 @@ fn identifier(input: Span) -> IResult { ))(input) } +// TODO: allow recursive generics +fn typename(input: Span) -> IResult { + map( + tuple(( + identifier, + opt(delimited(char('<'), ws0(expression), char('>'))) + )), + |(ident, _)| { + TypeName { + name: ident, + generics: () + } + } + )(input) +} + fn widthspec(input: Span) -> IResult { delimited(char('['), ws0(decimal), char(']'))(input) } @@ -46,10 +62,16 @@ fn intliteral(input: Span) -> IResult { tuple((terminated(decimal, char('\'')), alt((decimal, hexadecimal))))(input) } +#[derive(Debug)] +pub struct TypeName<'a> { + name: Span<'a>, + generics: (), +} + #[derive(Debug)] pub struct NetDecl<'a> { - pub name: &'a str, - pub width: Option, + pub name: Span<'a>, + pub typ: TypeName<'a>, pub value: Option<(u64, u64)>, } @@ -93,14 +115,12 @@ pub enum Expression<'a> { fn declaration(i: Span) -> IResult { map( tuple(( - ws0(alt((tag("reg"), tag("wire")))), - opt(ws0(widthspec)), - identifier, + separated_pair(identifier, ws0(char(':')), typename), opt(preceded(ws0(char('=')), intliteral)), )), - |(_, width, ident, value)| NetDecl { - name: ident.fragment(), - width, + |((ident, typ), value)| NetDecl { + name: ident, + typ, value, }, )(i) @@ -172,7 +192,7 @@ fn assign_statement(input: Span) -> IResult { } pub fn parse(input: Span) -> IResult { - module(input) + ws0(module)(input) } #[cfg(test)] diff --git a/src/parser/module.rs b/src/parser/module.rs index 3418514..5648602 100644 --- a/src/parser/module.rs +++ b/src/parser/module.rs @@ -4,14 +4,14 @@ use nom::{ character::complete::{char, multispace1}, combinator::{consumed, map}, error::context, - multi::{many1, separated_list0}, - sequence::{delimited, terminated, tuple}, + multi::{many0, separated_list0}, + sequence::{delimited, terminated, tuple, preceded}, }; use crate::parser::{ assign_statement, declaration, identifier, proc::{proc_block, ProcBlock}, - ws0, Assign, IResult, NetDecl, Span, + ws0, Assign, IResult, NetDecl, Span, typename }; #[derive(Debug)] @@ -29,7 +29,7 @@ pub struct PortDecl<'a> { #[derive(Debug)] pub struct Module<'a> { - pub name: &'a str, + pub name: Span<'a>, pub ports: Vec>, pub items: Vec>, } @@ -42,22 +42,18 @@ pub enum ModuleItem<'a> { fn port_decl(i: Span) -> IResult { map( - consumed(tuple(( - alt(( - map(tag("input"), |_| PortDirection::Input), - map(tag("output"), |_| PortDirection::Output), - )), + consumed( declaration, - ))), - |(pos, (direction, net))| PortDecl { + ), + |(pos, net)| PortDecl { pos, - direction, + direction: PortDirection::Input, net, }, )(i) } -fn ports_list(input: Span) -> IResult> { +fn inputs_list(input: Span) -> IResult> { separated_list0(ws0(char(',')), ws0(port_decl))(input) } @@ -87,12 +83,14 @@ pub fn module(input: Span) -> IResult { tuple(( tag("module"), ws0(identifier), - ws0(delimited(char('('), ws0(ports_list), char(')'))), - ws0(delimited(char('{'), many1(ws0(module_item)), char('}'))), + ws0(delimited(char('('), ws0(inputs_list), char(')'))), + ws0(preceded(tag("->"), ws0(typename))), + ws0(delimited(char('{'), ws0(many0(ws0(module_item))), char('}'))), )), - |(_, name, ports, items)| Module { - name: (*name.fragment()), - ports, + |(_, name, inputs, ret, items)| Module { + name, + // TODO: add back in returns + ports: inputs, items, }, ),