xenon_codegen/
function.rs1use core::fmt;
2
3use crate::{Visibility, attribute::Attribute, statement::Statement, r#type::Type};
4
5#[derive(Debug, Clone, Default)]
6pub struct Function {
7 pub r#async: bool,
8 pub attrs: Vec<Attribute>,
9 pub visibility: Visibility,
10 pub name: String,
11 pub arguments: Vec<Argument>,
12 pub returns: Type,
13 pub body: Statement,
14}
15impl Function {
16 pub fn new(name: String, returns: Type, body: Statement) -> Function {
17 Function {
18 r#async: false,
19 attrs: vec![],
20 visibility: Visibility::Private,
21 name,
22 arguments: vec![],
23 returns,
24 body,
25 }
26 }
27
28 pub fn is_valid(&self) -> bool {
29 for i in 0..self.attrs.len() {
30 if !self.attrs[i].is_valid() {
31 return false;
32 }
33 }
34 if self.name.is_empty() {
35 return false;
36 }
37 for i in 0..self.arguments.len() {
38 if !self.arguments[i].is_valid() {
39 return false;
40 }
41 }
42 if !self.returns.is_valid() {
43 return false;
44 }
45 if !self.body.is_valid() {
46 return false;
47 }
48
49 true
50 }
51}
52
53impl fmt::Display for Function {
54 fn fmt(&self, fmt: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
55 for i in 0..self.attrs.len() {
56 match writeln!(fmt, "{}", self.attrs[i]) {
57 Ok(_) => (),
58 Err(e) => return Err(e),
59 }
60 }
61 if self.r#async {
62 match write!(fmt, "async") {
63 Ok(_) => (),
64 Err(e) => return Err(e),
65 }
66 }
67 match write!(fmt, "{} fn {}(", self.visibility, self.name) {
68 Ok(_) => (),
69 Err(e) => return Err(e),
70 }
71 if !self.arguments.is_empty() {
72 match write!(fmt, "{}", self.arguments[0]) {
73 Ok(_) => (),
74 Err(e) => return Err(e),
75 }
76 for i in 1..self.arguments.len() {
77 match write!(fmt, ", {}", self.arguments[i]) {
78 Ok(_) => (),
79 Err(e) => return Err(e),
80 }
81 }
82 }
83 match write!(fmt, ") -> {}", self.returns) {
84 Ok(_) => (),
85 Err(e) => return Err(e),
86 }
87 match write!(fmt, " {}", self.body) {
88 Ok(_) => (),
89 Err(e) => return Err(e),
90 }
91
92 Ok(())
93 }
94}
95
96#[derive(Debug, Clone, Default)]
97pub struct Argument {
98 pub name: String,
99 pub r#type: Type,
100}
101impl Argument {
102 pub fn new(nm: String, ty: Type) -> Argument {
103 Argument {
104 name: nm,
105 r#type: ty,
106 }
107 }
108
109 pub fn is_valid(&self) -> bool {
110 !self.name.is_empty() && self.r#type.is_valid()
111 }
112}
113impl fmt::Display for Argument {
114 fn fmt(&self, fmt: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
115 match write!(fmt, "{}: {}", self.name, self.r#type) {
116 Ok(_) => (),
117 Err(e) => return Err(e),
118 }
119 Ok(())
120 }
121}