fixing quite a few bugs
This commit is contained in:
@@ -52,11 +52,11 @@ class Generator:
|
||||
|
||||
def add_constant(self, value: Any, no_string: bool = False):
|
||||
existing_constant_name = self.constants_reverse.get(value, None)
|
||||
if existing_constant_name != None: return f"[.{existing_constant_name}]"
|
||||
if existing_constant_name != None: return f"[{existing_constant_name}]"
|
||||
self.constants["LC" + str(self.constant_counter)] = {"value": value, "no_string": no_string}
|
||||
self.constants_reverse[value] = "LC" + str(self.constant_counter)
|
||||
self.constant_counter += 1
|
||||
return "[.LC" + str(self.constant_counter-1) + "]"
|
||||
return "[LC" + str(self.constant_counter-1) + "]"
|
||||
|
||||
def add_function(self, node: FunctionNode):
|
||||
self.functions[node.name] = {
|
||||
|
@@ -32,6 +32,14 @@ class X86_64Generator(Generator):
|
||||
var_pos = self.get_var_pos(var_name, scope)
|
||||
|
||||
if isinstance(var_pos, str): # in a reg, not on the stack
|
||||
waste = {
|
||||
"rax": "eax",
|
||||
"rdi": "edi",
|
||||
"rsi": "esi"
|
||||
}
|
||||
if waste[var_pos] == reg: # literally useless
|
||||
return
|
||||
|
||||
if offset == 0:
|
||||
lines.append(f"mov {reg}, {var_pos}\n\t")
|
||||
elif offset == -8:
|
||||
@@ -248,7 +256,9 @@ class X86_64Generator(Generator):
|
||||
|
||||
for inst in node.statements:
|
||||
#self.function_lines.append(f"; {inst}\n\t")
|
||||
self.generate_InstructionNode(inst, self.function_lines)
|
||||
node_type = str(type(inst))[19:-2]
|
||||
getattr(self, f"generate_{node_type}")(inst, self.function_lines)
|
||||
#self.generate_InstructionNode(inst, self.function_lines)
|
||||
|
||||
def generate_InstructionNode(self, node: InstructionNode, lines = None):
|
||||
lines = lines or self.lines
|
||||
@@ -438,6 +448,7 @@ class X86_64Generator(Generator):
|
||||
if node.arguments[0].value != 0:
|
||||
lines.append(f"jmp .{node.arguments[1].name}\n\t")
|
||||
elif isinstance(node.arguments[0], VarRefNode):
|
||||
self.current_var_scope.table[node.arguments[0].var_name]["used"] = True # putting a variable in an if statement means we're accessing it
|
||||
self.get_variable(lines, node.arguments[0].var_name, "eax")
|
||||
lines.append(f"test eax, eax\n\t")
|
||||
lines.append(f"jnz .{node.arguments[1].name}\n\t")
|
||||
@@ -491,7 +502,7 @@ class X86_64Generator(Generator):
|
||||
"lesser": "setl"
|
||||
}
|
||||
lines.append(f"{instructions[node.instruction]} al\n\t")
|
||||
lines.append("movzx rax, al\n\t")
|
||||
lines.append("movzx eax, al\n\t")
|
||||
|
||||
|
||||
var_name = node.arguments[2].var_name
|
||||
@@ -513,7 +524,7 @@ class X86_64Generator(Generator):
|
||||
if isinstance(node.arguments[0], IntNode):
|
||||
lines.append(f"mov rax, {node.arguments[0].value}")
|
||||
elif isinstance(node.arguments[0], BoolNode):
|
||||
lines.append(f"mov rax, {int(node.arguments[0].value)}")
|
||||
lines.append(f"mov eax, {int(node.arguments[0].value)}")
|
||||
elif isinstance(node.arguments[0], FloatNode):
|
||||
lines.append(f"mov xmm0, {node.arguments[0].value}")
|
||||
#self.get_variable(lines, node.arguments[0].var_name, "rax")
|
||||
@@ -526,10 +537,11 @@ class X86_64Generator(Generator):
|
||||
#self.push("rax", lines)
|
||||
elif isinstance(node.arguments[0], VarRefNode):
|
||||
var = func_scope.lookup(node.arguments[0].var_name)
|
||||
|
||||
if var["type"] == StringNode:
|
||||
self.get_variable(self.function_lines, node.arguments[0].var_name, "rax", offset=0, scope=func["scope"])
|
||||
self.get_variable(self.function_lines, node.arguments[0].var_name, "rdx", offset=-8, scope=func["scope"])
|
||||
elif var["type"] == BoolNode:
|
||||
self.get_variable(self.function_lines, node.arguments[0].var_name, "eax", scope=func["scope"])
|
||||
else:
|
||||
self.get_variable(self.function_lines, node.arguments[0].var_name, "rax", scope=func["scope"])
|
||||
else:
|
||||
@@ -644,7 +656,7 @@ class X86_64Generator(Generator):
|
||||
f.write("section .data\n")
|
||||
for name, const in self.constants.items():
|
||||
value = const["value"]
|
||||
f.write("." + name + ": ")
|
||||
f.write(name + ": ")
|
||||
value_type = type(value)
|
||||
if value_type == str:
|
||||
if not const["no_string"]:
|
||||
|
Reference in New Issue
Block a user