function calls not working entirely >:(

This commit is contained in:
2025-10-15 15:32:40 +11:00
parent e0dd9ee541
commit a75dcb933e
7 changed files with 52 additions and 27 deletions

View File

@@ -28,6 +28,8 @@ class Compiler:
self.environment: Environment = Environment()
self.errors: list[str] = []
self.counter = 0
self.__initialize_builtins()
def __initialize_builtins(self) -> None:
@@ -58,6 +60,10 @@ class Compiler:
self.environment.define("true", true_var, true_var.type)
self.environment.define("false", false_var, false_var.type)
def __increment_counter(self) -> int:
self.counter += 1
return self.counter
def compile(self, node: Node) -> None:
match node.type():
case NodeType.Program:
@@ -300,6 +306,9 @@ class Compiler:
types.append(p_type)
match name:
case "print":
ret = self.builtin_print(params=args, return_type=types[0])
ret_type = self.type_map["Int"]
case _:
func, ret_type = self.environment.lookup(name)
ret = self.builder.call(func, args)
@@ -343,4 +352,31 @@ class Compiler:
fmt: str = f"{string}\0"
c_fmt: ir.Constant = ir.Constant(ir.ArrayType(ir.IntType(8), len(fmt)), bytearray(fmt.encode("utf-8")))
global_fmt = ir.GlobalVariable(self.module, c_fmt.type, name=f"__str_{self.__increment_counter()}")
global_fmt.linkage = "internal"
global_fmt.global_constant = True
global_fmt.initializer = c_fmt
return global_fmt, global_fmt.type
def builtin_print(self, params: list[ir.Instruction], return_type: ir.Type) -> None:
func, _ = self.environment.lookup("print")
c_str = self.builder.alloca(return_type)
self.builder.store(params[0], c_str)
rest_params = params[1:]
if isinstance(params[0], ir.LoadInstr):
# printing from a variable load instruction
c_fmt: ir.LoadInstr = params[0]
g_var_ptr = c_fmt.operands[0]
string_val = self.builder.load(g_var_ptr)
fmt_arg = self.builder.bitcast(string_val, ir.IntType(8).as_pointer())
return self.builder.call(func, [fmt_arg, *rest_params])
else:
# printing from a normal string
fmt_arg = self.builder.bitcast(self.module.get_global(f"__str_{self.counter}"), ir.IntType(8).as_pointer())
return self.builder.call(func, [fmt_arg, *rest_params])
# endregion