way better prints yay
This commit is contained in:
98
generator.v
98
generator.v
@@ -5,6 +5,7 @@ import os
|
||||
|
||||
struct Generator {
|
||||
mut:
|
||||
symbols SymbolTable
|
||||
out strings.Builder
|
||||
}
|
||||
|
||||
@@ -21,9 +22,23 @@ fn mangle_struct(name string) string {
|
||||
return 'one_class_${name}_'
|
||||
}
|
||||
|
||||
fn mangle_if_struct_type(name string) string {
|
||||
if name.len < 7 || name[0..6] != 'struct' {return name}
|
||||
return 'struct ${mangle_struct(name[7..])}'
|
||||
|
||||
fn get_type_format(type string) string {
|
||||
return match type {
|
||||
'int', 'bool' {'d'}
|
||||
'real' {'f'}
|
||||
else {panic("invalid type to print")}
|
||||
}
|
||||
}
|
||||
|
||||
fn (mut g Generator) get_print_label(expr Expr) string {
|
||||
return match expr {
|
||||
Variable { expr.name }
|
||||
MemberAccess {
|
||||
"${g.get_print_label(expr.from)}.${expr.member}"
|
||||
}
|
||||
else { "" }
|
||||
}
|
||||
}
|
||||
|
||||
fn (mut g Generator) get_c_type(typ string) string {
|
||||
@@ -34,10 +49,43 @@ fn (mut g Generator) get_c_type(typ string) string {
|
||||
}
|
||||
}
|
||||
|
||||
fn (mut g Generator) mangle_if_class(name string) string {
|
||||
if g.symbols.lookup_class(name) != none {
|
||||
return 'struct ${mangle_struct(name)}'
|
||||
}
|
||||
return name
|
||||
}
|
||||
|
||||
// thank google gemini for this one, I genuinely did not have the mental strength to
|
||||
// think this at 9pm
|
||||
fn (mut g Generator) gen_class_print_func(stmt ClassDecl) {
|
||||
struct_name := mangle_struct(stmt.name)
|
||||
g.out.writeln('void print_${struct_name}(struct ${struct_name} s, int indent) {')
|
||||
|
||||
g.out.writeln('printf("${stmt.name} {\\n");')
|
||||
|
||||
for member in stmt.members {
|
||||
g.out.writeln('for(int i=0; i<indent + 1; i++) printf(" ");')
|
||||
g.out.write_string('printf("${member.name}: ");')
|
||||
|
||||
if g.symbols.lookup_class(member.type) != none {
|
||||
inner_struct_name := mangle_struct(member.type)
|
||||
g.out.writeln('print_${inner_struct_name}(s.${member.name}, indent + 1);')
|
||||
} else {
|
||||
format := get_type_format(member.type)
|
||||
g.out.writeln('printf("%${format}\\n", s.${member.name});')
|
||||
}
|
||||
}
|
||||
|
||||
g.out.writeln('for(int i=0; i<indent; i++) printf(" ");')
|
||||
g.out.writeln('printf("}\\n");')
|
||||
g.out.writeln('}')
|
||||
}
|
||||
|
||||
fn (mut g Generator) gen_stmt(stmt Stmt) {
|
||||
match stmt {
|
||||
VarDecl {
|
||||
c_type := mangle_if_struct_type(g.get_c_type(stmt.type))
|
||||
c_type := g.mangle_if_class(g.get_c_type(stmt.type))
|
||||
if stmt.const {
|
||||
g.out.write_string('const ')
|
||||
}
|
||||
@@ -63,7 +111,7 @@ fn (mut g Generator) gen_stmt(stmt Stmt) {
|
||||
}
|
||||
FuncDecl {
|
||||
dump(stmt.ret_type)
|
||||
c_type := mangle_if_struct_type(g.get_c_type(stmt.ret_type))
|
||||
c_type := g.mangle_if_class(g.get_c_type(stmt.ret_type))
|
||||
g.out.write_string('${c_type} ${mangle_func(stmt.name)}(')
|
||||
for param in stmt.params {
|
||||
g.gen_stmt(param)
|
||||
@@ -75,7 +123,7 @@ fn (mut g Generator) gen_stmt(stmt Stmt) {
|
||||
g.gen_stmt(stmt.block)
|
||||
}
|
||||
Param {
|
||||
c_type := mangle_if_struct_type(g.get_c_type(stmt.type))
|
||||
c_type := g.mangle_if_class(g.get_c_type(stmt.type))
|
||||
g.out.write_string('${c_type} ${mangle_var(stmt.name)}')
|
||||
}
|
||||
ClassDecl {
|
||||
@@ -85,6 +133,8 @@ fn (mut g Generator) gen_stmt(stmt Stmt) {
|
||||
g.out.writeln(';')
|
||||
}
|
||||
g.out.writeln('};')
|
||||
|
||||
g.gen_class_print_func(stmt)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -114,18 +164,28 @@ fn (mut g Generator) gen_expr(expr Expr) {
|
||||
g.out.write_string(')')
|
||||
}
|
||||
PrintExpr {
|
||||
g.out.write_string('printf(\"%')
|
||||
format := match expr.type {
|
||||
'int', 'bool' {'d'}
|
||||
'real' {'lf'}
|
||||
else {panic("Tried printing illegal type")}
|
||||
}
|
||||
g.out.write_string('${format}\\n\", ')
|
||||
g.gen_expr(expr.expr)
|
||||
g.out.write_string(')')
|
||||
label := g.get_print_label(expr.expr)
|
||||
if g.symbols.lookup_class(expr.type) != none {
|
||||
class_name := mangle_struct(expr.type)
|
||||
if label != "" {
|
||||
g.out.write_string('printf("${label}: ");')
|
||||
}
|
||||
g.out.write_string('print_${class_name}(')
|
||||
g.gen_expr(expr.expr)
|
||||
g.out.write_string(', 0)')
|
||||
} else {
|
||||
g.out.write_string('printf(\"')
|
||||
if label != "" {
|
||||
g.out.write_string('${label}: ')
|
||||
}
|
||||
format := get_type_format(expr.type)
|
||||
g.out.write_string('%${format}\\n\", ')
|
||||
g.gen_expr(expr.expr)
|
||||
g.out.write_string(')')
|
||||
}
|
||||
}
|
||||
TypeCast {
|
||||
c_type := mangle_if_struct_type(g.get_c_type(expr.type))
|
||||
c_type := g.mangle_if_class(g.get_c_type(expr.type))
|
||||
g.out.write_string('((${c_type})')
|
||||
g.gen_expr(expr.expr)
|
||||
g.out.write_string(')')
|
||||
@@ -146,7 +206,7 @@ fn (mut g Generator) gen_expr(expr Expr) {
|
||||
g.out.write_string(')')
|
||||
}
|
||||
ClassMember {
|
||||
c_type := mangle_if_struct_type(g.get_c_type(expr.type))
|
||||
c_type := g.mangle_if_class(g.get_c_type(expr.type))
|
||||
g.out.write_string('${c_type} ${expr.name}')
|
||||
}
|
||||
ClassInstantiation {
|
||||
@@ -159,6 +219,10 @@ fn (mut g Generator) gen_expr(expr Expr) {
|
||||
}
|
||||
g.out.write_string('}')
|
||||
}
|
||||
MemberAccess {
|
||||
g.gen_expr(expr.from)
|
||||
g.out.write_string('.${expr.member}')
|
||||
}
|
||||
else {panic("Unimplemented expression")}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user