diff --git a/parser/src/ast.rs b/parser/src/ast.rs index e6f4106..eed2c93 100644 --- a/parser/src/ast.rs +++ b/parser/src/ast.rs @@ -74,6 +74,7 @@ pub enum TopLevelKind { ModAttribute, Import(Path), Mod(Identifier), + ImplDecl(ImplDecl), EnumDecl { visibility: Visibility, name: Identifier, @@ -192,6 +193,14 @@ pub enum Statement { Continue, } +#[derive(Debug, Clone, Serialize)] +pub struct ImplDecl { + pub generics: Generics, + pub target: TypeExpr, + pub trait_: Option, + pub methods: Vec, +} + #[derive(Debug, Clone, Serialize)] pub struct VarDecl { pub mutable: bool, diff --git a/src/codegen.rs b/src/codegen.rs index edc9fc6..af5c39b 100644 --- a/src/codegen.rs +++ b/src/codegen.rs @@ -1,8 +1,8 @@ use parser::ast::{ Attribute, BinaryOp, Block, EnumItem, Expression, FieldDecl, FunctionDecl, Generic, Generics, - Identifier, Literal, Path, Pattern, Postfix, Prefix, Statement, StatementBranch, TopLevel, - TopLevelKind, TypeExpr, TypeExprKind, TypePostfix, VarAssignStmt, VarDecl, VarDeclStmt, - Visibility, + Identifier, ImplDecl, Literal, Path, Pattern, Postfix, Prefix, Statement, StatementBranch, + TopLevel, TopLevelKind, TypeExpr, TypeExprKind, TypePostfix, VarAssignStmt, VarDecl, + VarDeclStmt, Visibility, }; // --------------------------------------------------------------------------- @@ -315,6 +315,7 @@ impl ToRust for TopLevelKind { Self::Import(path) => cg.addln(&format!("use {};", path.get_rust())), Self::Mod(id) => cg.addln(&format!("mod {};", id.get_rust())), Self::FunctionDecl(decl) => decl.to_rust(cg), + Self::ImplDecl(impl_) => impl_.to_rust(cg), Self::StructDecl { visibility, name, @@ -615,6 +616,33 @@ impl ToRust for FunctionDecl { } } +impl ToRust for ImplDecl { + fn to_rust(&self, cg: &mut RustCodegen) { + if let Some(trait_) = &self.trait_ { + cg.add_indentedln(&format!( + "impl{} {} for {} {{", + self.generics.get_rust(), + trait_.get_rust(), + self.target.get_rust() + )); + } else { + cg.add_indentedln(&format!( + "impl{} {} {{", + self.generics.get_rust(), + self.target.get_rust() + )); + } + cg.indent += 1; + + for method in &self.methods { + method.to_rust(cg); + } + + cg.indent -= 1; + cg.add_indentedln("}"); + } +} + impl GetRust for VarDecl { fn get_rust(&self) -> String { let ty = self