package main import "core:fmt" NodeKind :: enum { Integer, Float, Character, String, Identifier, Block, BinaryExpression, UnaryExpression, FieldAccess, IndexAccess, FunctionCall, Function, Struct, Enum, Union, } Node :: struct { kind: NodeKind, range: TextRange, children: [dynamic]^Node, value: TokenValue, value_token_kind: TokenKind, } node_create_value :: proc(kind: NodeKind, range: TextRange, value: TokenValue) -> (ret: ^Node) { ret = new(Node) ret^ = { kind = kind, range = range, value = value, } return } node_create_block :: proc(range: TextRange, children: [dynamic]^Node) -> (ret: ^Node) { ret = new(Node) ret^ = { kind = .Block, range = range, children = children, } return } node_create_binary :: proc(kind: TokenKind, range: TextRange, left: ^Node, right: ^Node) -> (ret: ^Node) { ret = new(Node) ret^ = { kind = .BinaryExpression, range = range, children = { left, right }, value_token_kind = kind, } return } node_create_unary :: proc(kind: TokenKind, range: TextRange, operand: ^Node) -> (ret: ^Node) { ret = new(Node) ret^ = { kind = .UnaryExpression, range = range, children = { operand }, value_token_kind = kind, } return } node_create_field_access :: proc(range: TextRange, left: ^Node, right: ^Node) -> (ret: ^Node) { ret = new(Node) ret^ = { kind = .FieldAccess, range = range, children = { left, right }, } return } node_create_index_access :: proc(range: TextRange, left: ^Node, right: ^Node) -> (ret: ^Node) { ret = new(Node) ret^ = { kind = .IndexAccess, range = range, children = { left, right }, } return } node_create_function_call :: proc(range: TextRange, name: ^Node, args: [dynamic]^Node) -> (ret: ^Node) { ret = new(Node) ret^ = { kind = .FunctionCall, range = range, children = { name }, } for arg in args { append(&ret.children, arg) } return } node_print :: proc(node: ^Node, indent := 0) { for i in 0..