From 3ee9834197ddf0bece6b2f18f4ae958b4225743a Mon Sep 17 00:00:00 2001 From: whitequark Date: Sat, 26 Mar 2016 11:38:55 +0000 Subject: [PATCH] compiler: significantly increase readability of LLVM and ARTIQ IRs. --- artiq/compiler/ir.py | 6 +- .../compiler/transforms/artiq_ir_generator.py | 125 +++++++++--------- .../compiler/transforms/llvm_ir_generator.py | 111 +++++++++------- 3 files changed, 133 insertions(+), 109 deletions(-) diff --git a/artiq/compiler/ir.py b/artiq/compiler/ir.py index dd89fe3ec..18265eef9 100644 --- a/artiq/compiler/ir.py +++ b/artiq/compiler/ir.py @@ -437,7 +437,7 @@ class Function: def _add_name(self, base_name): if base_name == "": - name = "v.{}".format(self.next_name) + name = "UNN.{}".format(self.next_name) self.next_name += 1 elif base_name in self.names: name = "{}.{}".format(base_name, self.next_name) @@ -869,9 +869,11 @@ class Builtin(Instruction): """ :param op: (string) operation name """ - def __init__(self, op, operands, typ, name=""): + def __init__(self, op, operands, typ, name=None): assert isinstance(op, str) for operand in operands: assert isinstance(operand, Value) + if name is None: + name = "BLT.{}".format(op) super().__init__(operands, typ, name) self.op = op diff --git a/artiq/compiler/transforms/artiq_ir_generator.py b/artiq/compiler/transforms/artiq_ir_generator.py index 92f66f7ae..5030f0482 100644 --- a/artiq/compiler/transforms/artiq_ir_generator.py +++ b/artiq/compiler/transforms/artiq_ir_generator.py @@ -237,25 +237,25 @@ class ARTIQIRGenerator(algorithm.Visitor): for arg_name, default_node in zip(typ.optargs, node.args.defaults): default = self.visit(default_node) env_default_name = \ - self.current_env.type.add("default$" + arg_name, default.type) + self.current_env.type.add("$default." + arg_name, default.type) self.append(ir.SetLocal(self.current_env, env_default_name, default)) defaults.append(env_default_name) old_name, self.name = self.name, self.name + [name] - env_arg = ir.EnvironmentArgument(self.current_env.type, "outerenv") + env_arg = ir.EnvironmentArgument(self.current_env.type, "CLS") old_args, self.current_args = self.current_args, {} args = [] for arg_name in typ.args: - arg = ir.Argument(typ.args[arg_name], "arg." + arg_name) + arg = ir.Argument(typ.args[arg_name], "ARG." + arg_name) self.current_args[arg_name] = arg args.append(arg) optargs = [] for arg_name in typ.optargs: - arg = ir.Argument(ir.TOption(typ.optargs[arg_name]), "arg." + arg_name) + arg = ir.Argument(ir.TOption(typ.optargs[arg_name]), "ARG." + arg_name) self.current_args[arg_name] = arg optargs.append(arg) @@ -268,7 +268,7 @@ class ARTIQIRGenerator(algorithm.Visitor): if not is_lambda: self.function_map[node] = func - entry = self.add_block() + entry = self.add_block("entry") old_block, self.current_block = self.current_block, entry old_globals, self.current_globals = self.current_globals, node.globals_in_scope @@ -279,13 +279,13 @@ class ARTIQIRGenerator(algorithm.Visitor): if var not in node.globals_in_scope} env_type = ir.TEnvironment(name=func.name, vars=env_without_globals, outer=self.current_env.type) - env = self.append(ir.Alloc([], env_type, name="env")) + env = self.append(ir.Alloc([], env_type, name="ENV")) old_env, self.current_env = self.current_env, env if not is_lambda: - priv_env_type = ir.TEnvironment(name=func.name + ".priv", + priv_env_type = ir.TEnvironment(name="{}.private".format(func.name), vars={ "$return": typ.ret }) - priv_env = self.append(ir.Alloc([], priv_env_type, name="privenv")) + priv_env = self.append(ir.Alloc([], priv_env_type, name="PRV")) old_priv_env, self.current_private_env = self.current_private_env, priv_env self.append(ir.SetLocal(env, "$outer", env_arg)) @@ -401,18 +401,18 @@ class ARTIQIRGenerator(algorithm.Visitor): cond = self.coerce_to_bool(cond) head = self.current_block - if_true = self.add_block() + if_true = self.add_block("if.body") self.current_block = if_true self.visit(node.body) post_if_true = self.current_block if any(node.orelse): - if_false = self.add_block() + if_false = self.add_block("if.else") self.current_block = if_false self.visit(node.orelse) post_if_false = self.current_block - tail = self.add_block() + tail = self.add_block("if.tail") self.current_block = tail if not post_if_true.is_terminated(): post_if_true.append(ir.Branch(tail)) @@ -499,9 +499,9 @@ class ARTIQIRGenerator(algorithm.Visitor): head = self.add_block("for.head") self.append(ir.Branch(head)) self.current_block = head - phi = self.append(ir.Phi(length.type)) + phi = self.append(ir.Phi(length.type, name="IND")) phi.add_incoming(ir.Constant(0, phi.type), prehead) - cond = self.append(ir.Compare(ast.Lt(loc=None), phi, length)) + cond = self.append(ir.Compare(ast.Lt(loc=None), phi, length, name="CMP")) break_block = self.add_block("for.break") old_break, self.break_target = self.break_target, break_block @@ -510,7 +510,8 @@ class ARTIQIRGenerator(algorithm.Visitor): old_continue, self.continue_target = self.continue_target, continue_block self.current_block = continue_block - updated_index = self.append(ir.Arith(ast.Add(loc=None), phi, ir.Constant(1, phi.type))) + updated_index = self.append(ir.Arith(ast.Add(loc=None), phi, ir.Constant(1, phi.type), + name="IND.new")) phi.add_incoming(updated_index, continue_block) self.append(ir.Branch(head)) @@ -597,13 +598,13 @@ class ARTIQIRGenerator(algorithm.Visitor): # k for continuation final_suffix = ".try@{}:{}".format(node.loc.line(), node.loc.column()) final_env_type = ir.TEnvironment(name=self.current_function.name + final_suffix, - vars={ "$k": ir.TBasicBlock() }) + vars={ "$cont": ir.TBasicBlock() }) final_state = self.append(ir.Alloc([], final_env_type)) final_targets = [] final_paths = [] def final_branch(target, block): - block.append(ir.SetLocal(final_state, "$k", target)) + block.append(ir.SetLocal(final_state, "$cont", target)) final_targets.append(target) final_paths.append(block) @@ -696,19 +697,19 @@ class ARTIQIRGenerator(algorithm.Visitor): block.append(ir.Branch(finalizer)) if not body.is_terminated(): - body.append(ir.SetLocal(final_state, "$k", tail)) + body.append(ir.SetLocal(final_state, "$cont", tail)) body.append(ir.Branch(finalizer)) - cleanup.append(ir.SetLocal(final_state, "$k", reraise)) + cleanup.append(ir.SetLocal(final_state, "$cont", reraise)) cleanup.append(ir.Branch(finalizer)) for handler, post_handler in handlers: if not post_handler.is_terminated(): - post_handler.append(ir.SetLocal(final_state, "$k", tail)) + post_handler.append(ir.SetLocal(final_state, "$cont", tail)) post_handler.append(ir.Branch(finalizer)) if not post_finalizer.is_terminated(): - dest = post_finalizer.append(ir.GetLocal(final_state, "$k")) + dest = post_finalizer.append(ir.GetLocal(final_state, "$cont")) post_finalizer.append(ir.IndirectBranch(dest, final_targets)) else: if not body.is_terminated(): @@ -753,7 +754,7 @@ class ARTIQIRGenerator(algorithm.Visitor): heads, tails = [], [] for stmt in node.body: - self.current_block = self.add_block() + self.current_block = self.add_block("interleave.branch") heads.append(self.current_block) self.visit(stmt) tails.append(self.current_block) @@ -761,7 +762,7 @@ class ARTIQIRGenerator(algorithm.Visitor): for head in heads: interleave.add_destination(head) - self.current_block = self.add_block() + self.current_block = self.add_block("interleave.tail") for tail in tails: if not tail.is_terminated(): tail.append(ir.Branch(self.current_block)) @@ -773,7 +774,7 @@ class ARTIQIRGenerator(algorithm.Visitor): for stmt in node.body: self.append(ir.Builtin("at_mu", [start_mu], builtins.TNone())) - block = self.add_block() + block = self.add_block("parallel.branch") if self.current_block.is_terminated(): self.warn_unreachable(stmt[0]) else: @@ -837,17 +838,17 @@ class ARTIQIRGenerator(algorithm.Visitor): cond = self.visit(node.test) head = self.current_block - if_true = self.add_block() + if_true = self.add_block("ifexp.body") self.current_block = if_true true_result = self.visit(node.body) post_if_true = self.current_block - if_false = self.add_block() + if_false = self.add_block("ifexp.else") self.current_block = if_false false_result = self.visit(node.orelse) post_if_false = self.current_block - tail = self.add_block() + tail = self.add_block("ifexp.tail") self.current_block = tail if not post_if_true.is_terminated(): @@ -881,10 +882,10 @@ class ARTIQIRGenerator(algorithm.Visitor): if self.current_class is not None and \ name in self.current_class.type.attributes: return self.append(ir.GetAttr(self.current_class, name, - name="local." + name)) + name="FLD." + name)) return self.append(ir.GetLocal(self._env_for(name), name, - name="local." + name)) + name="LOC." + name)) def _set_local(self, name, value): if self.current_class is not None and \ @@ -910,7 +911,7 @@ class ARTIQIRGenerator(algorithm.Visitor): if self.current_assign is None: return self.append(ir.GetAttr(obj, node.attr, - name="{}.{}".format(_readable_name(obj), node.attr))) + name="{}.FLD.{}".format(_readable_name(obj), node.attr))) elif types.is_rpc_function(self.current_assign.type): # RPC functions are just type-level markers return self.append(ir.Builtin("nop", [], builtins.TNone())) @@ -930,47 +931,47 @@ class ARTIQIRGenerator(algorithm.Visitor): ir.Constant(False, builtins.TBool()))) head = self.current_block - self.current_block = out_of_bounds_block = self.add_block() + self.current_block = out_of_bounds_block = self.add_block("index.outofbounds") exn = self.alloc_exn(builtins.TException("IndexError"), ir.Constant("index {0} out of bounds 0:{1}", builtins.TStr()), index, length) self.raise_exn(exn, loc=loc) - self.current_block = in_bounds_block = self.add_block() + self.current_block = in_bounds_block = self.add_block("index.inbounds") head.append(ir.BranchIf(in_bounds, in_bounds_block, out_of_bounds_block)) return mapped_index - def _make_check(self, cond, exn_gen, loc=None): + def _make_check(self, cond, exn_gen, loc=None, name="check"): # cond: bool Value, condition # exn_gen: lambda()->exn Value, exception if condition not true cond_block = self.current_block - self.current_block = body_block = self.add_block() + self.current_block = body_block = self.add_block("{}.body".format(name)) self.raise_exn(exn_gen(), loc=loc) - self.current_block = tail_block = self.add_block() + self.current_block = tail_block = self.add_block("{}.tail".format(name)) cond_block.append(ir.BranchIf(cond, tail_block, body_block)) - def _make_loop(self, init, cond_gen, body_gen): + def _make_loop(self, init, cond_gen, body_gen, name="loop"): # init: 'iter Value, initial loop variable value # cond_gen: lambda('iter Value)->bool Value, loop condition # body_gen: lambda('iter Value)->'iter Value, loop body, # returns next loop variable value init_block = self.current_block - self.current_block = head_block = self.add_block() + self.current_block = head_block = self.add_block("{}.head".format(name)) init_block.append(ir.Branch(head_block)) phi = self.append(ir.Phi(init.type)) phi.add_incoming(init, init_block) cond = cond_gen(phi) - self.current_block = body_block = self.add_block() + self.current_block = body_block = self.add_block("{}.body".format(name)) body = body_gen(phi) self.append(ir.Branch(head_block)) phi.add_incoming(body, self.current_block) - self.current_block = tail_block = self.add_block() + self.current_block = tail_block = self.add_block("{}.tail".format(name)) head_block.append(ir.BranchIf(cond, body_block, tail_block)) return head_block, body_block, tail_block @@ -1072,7 +1073,7 @@ class ARTIQIRGenerator(algorithm.Visitor): prehead = self.current_block - head = self.current_block = self.add_block() + head = self.current_block = self.add_block("slice.head") prehead.append(ir.Branch(head)) index = self.append(ir.Phi(node.slice.type, @@ -1087,7 +1088,7 @@ class ARTIQIRGenerator(algorithm.Visitor): bounded_down = self.append(ir.Compare(ast.Gt(loc=None), index, mapped_stop_index)) within_bounds = self.append(ir.Select(counting_up, bounded_up, bounded_down)) - body = self.current_block = self.add_block() + body = self.current_block = self.add_block("slice.body") if self.current_assign is None: elem = self.iterable_get(value, index) @@ -1103,7 +1104,7 @@ class ARTIQIRGenerator(algorithm.Visitor): other_index.add_incoming(next_other_index, body) self.append(ir.Branch(head)) - tail = self.current_block = self.add_block() + tail = self.current_block = self.add_block("slice.tail") head.append(ir.BranchIf(within_bounds, body, tail)) if self.current_assign is None: @@ -1197,7 +1198,7 @@ class ARTIQIRGenerator(algorithm.Visitor): value_tail = self.current_block blocks.append((value, value_head, value_tail)) - self.current_block = self.add_block() + self.current_block = self.add_block("boolop.seq") tail = self.current_block phi = self.append(ir.Phi(node.type)) @@ -1366,26 +1367,26 @@ class ARTIQIRGenerator(algorithm.Visitor): # If the length is the same, compare element-by-element # and break when the comparison result is false - loop_head = self.add_block() + loop_head = self.add_block("compare.head") self.current_block = loop_head index_phi = self.append(ir.Phi(self._size_type)) index_phi.add_incoming(ir.Constant(0, self._size_type), head) loop_cond = self.append(ir.Compare(ast.Lt(loc=None), index_phi, lhs_length)) - loop_body = self.add_block() + loop_body = self.add_block("compare.body") self.current_block = loop_body lhs_elt = self.append(ir.GetElem(lhs, index_phi)) rhs_elt = self.append(ir.GetElem(rhs, index_phi)) body_result = self.polymorphic_compare_pair(op, lhs_elt, rhs_elt) - loop_body2 = self.add_block() + loop_body2 = self.add_block("compare.body2") self.current_block = loop_body2 index_next = self.append(ir.Arith(ast.Add(loc=None), index_phi, ir.Constant(1, self._size_type))) self.append(ir.Branch(loop_head)) index_phi.add_incoming(index_next, loop_body2) - tail = self.add_block() + tail = self.add_block("compare.tail") self.current_block = tail phi = self.append(ir.Phi(builtins.TBool())) head.append(ir.BranchIf(eq_length, loop_head, tail)) @@ -1431,14 +1432,14 @@ class ARTIQIRGenerator(algorithm.Visitor): elt = self.iterable_get(haystack, index) cmp_result = self.polymorphic_compare_pair(ast.Eq(loc=None), needle, elt) - loop_body2 = self.add_block() + loop_body2 = self.add_block("compare.body") self.current_block = loop_body2 return self.append(ir.Arith(ast.Add(loc=None), index, ir.Constant(1, length.type))) loop_head, loop_body, loop_tail = \ self._make_loop(ir.Constant(0, length.type), lambda index: self.append(ir.Compare(ast.Lt(loc=None), index, length)), - body_gen) + body_gen, name="compare") loop_body.append(ir.BranchIf(cmp_result, loop_tail, loop_body2)) phi = loop_tail.prepend(ir.Phi(builtins.TBool())) @@ -1479,7 +1480,7 @@ class ARTIQIRGenerator(algorithm.Visitor): result_tail = self.current_block blocks.append((result, result_head, result_tail)) - self.current_block = self.add_block() + self.current_block = self.add_block("compare.seq") lhs = rhs tail = self.current_block @@ -1674,8 +1675,10 @@ class ARTIQIRGenerator(algorithm.Visitor): fn_typ = callee.type offset = 0 elif types.is_method(callee.type): - func = self.append(ir.GetAttr(callee, "__func__")) - self_arg = self.append(ir.GetAttr(callee, "__self__")) + func = self.append(ir.GetAttr(callee, "__func__", + name="{}.CLS".format(callee.name))) + self_arg = self.append(ir.GetAttr(callee, "__self__", + name="{}.SLF".format(callee.name))) fn_typ = types.get_method_function(callee.type) offset = 1 else: @@ -1719,7 +1722,7 @@ class ARTIQIRGenerator(algorithm.Visitor): if self.unwind_target is None: insn = self.append(ir.Call(func, args, arg_exprs)) else: - after_invoke = self.add_block() + after_invoke = self.add_block("invoke") insn = self.append(ir.Invoke(func, args, arg_exprs, after_invoke, self.unwind_target)) self.current_block = after_invoke @@ -1734,7 +1737,7 @@ class ARTIQIRGenerator(algorithm.Visitor): if node.iodelay is not None and not iodelay.is_const(node.iodelay, 0): before_delay = self.current_block - during_delay = self.add_block() + during_delay = self.add_block("delay.head") before_delay.append(ir.Branch(during_delay)) self.current_block = during_delay @@ -1748,7 +1751,7 @@ class ARTIQIRGenerator(algorithm.Visitor): self.method_map[(attr_node.value.type.find(), attr_node.attr)].append(insn) if node.iodelay is not None and not iodelay.is_const(node.iodelay, 0): - after_delay = self.add_block() + after_delay = self.add_block("delay.tail") self.append(ir.Delay(node.iodelay, insn, after_delay)) self.current_block = after_delay @@ -1783,7 +1786,7 @@ class ARTIQIRGenerator(algorithm.Visitor): assert_subexprs = self.current_assert_subexprs = [] init = self.current_block - prehead = self.current_block = self.add_block() + prehead = self.current_block = self.add_block("assert.prehead") cond = self.visit(node.test) head = self.current_block finally: @@ -1795,7 +1798,7 @@ class ARTIQIRGenerator(algorithm.Visitor): init.append(ir.SetLocal(assert_env, subexpr_name, empty)) init.append(ir.Branch(prehead)) - if_failed = self.current_block = self.add_block() + if_failed = self.current_block = self.add_block("assert.fail") if node.msg: explanation = node.msg.s @@ -1813,7 +1816,7 @@ class ARTIQIRGenerator(algorithm.Visitor): subexpr_cond = self.append(ir.Builtin("is_some", [subexpr_value_opt], builtins.TBool())) - subexpr_body = self.current_block = self.add_block() + subexpr_body = self.current_block = self.add_block("assert.subexpr.body") self.append(ir.Builtin("printf", [ ir.Constant(" (%s) = ", builtins.TStr()), ir.Constant(subexpr_node.loc.source(), builtins.TStr()) @@ -1823,14 +1826,14 @@ class ARTIQIRGenerator(algorithm.Visitor): self.polymorphic_print([subexpr_value], separator="", suffix="\n") subexpr_postbody = self.current_block - subexpr_tail = self.current_block = self.add_block() + subexpr_tail = self.current_block = self.add_block("assert.subexpr.tail") self.append(ir.Branch(subexpr_tail), block=subexpr_postbody) self.append(ir.BranchIf(subexpr_cond, subexpr_body, subexpr_tail), block=subexpr_head) self.append(ir.Builtin("abort", [], builtins.TNone())) self.append(ir.Unreachable()) - tail = self.current_block = self.add_block() + tail = self.current_block = self.add_block("assert.tail") self.append(ir.BranchIf(cond, tail, if_failed), block=head) def polymorphic_print(self, values, separator, suffix="", as_repr=False, as_rtio=False): @@ -1904,10 +1907,10 @@ class ARTIQIRGenerator(algorithm.Visitor): is_last = self.append(ir.Compare(ast.Lt(loc=None), index, last)) head = self.current_block - if_last = self.current_block = self.add_block() + if_last = self.current_block = self.add_block("print.comma") printf(", ") - tail = self.current_block = self.add_block() + tail = self.current_block = self.add_block("print.tail") if_last.append(ir.Branch(tail)) head.append(ir.BranchIf(is_last, if_last, tail)) diff --git a/artiq/compiler/transforms/llvm_ir_generator.py b/artiq/compiler/transforms/llvm_ir_generator.py index 062742cd4..66113924d 100644 --- a/artiq/compiler/transforms/llvm_ir_generator.py +++ b/artiq/compiler/transforms/llvm_ir_generator.py @@ -269,11 +269,11 @@ class LLVMIRGenerator: return llty.as_pointer() else: # Catch-all for exceptions and custom classes if builtins.is_exception(typ): - name = "class.Exception" # they all share layout + name = "C.Exception" # they all share layout elif types.is_constructor(typ): - name = "class.{}".format(typ.name) + name = "C.{}".format(typ.name) else: - name = "instance.{}".format(typ.name) + name = "I.{}".format(typ.name) llty = self.llcontext.get_identified_type(name) if llty.elements is None: @@ -297,7 +297,7 @@ class LLVMIRGenerator: if name is None: sanitized_str = re.sub(rb"[^a-zA-Z0-9_.]", b"", as_bytes[:20]).decode('ascii') - name = self.llmodule.get_unique_name("str.{}".format(sanitized_str)) + name = self.llmodule.get_unique_name("S.{}".format(sanitized_str)) llstr = self.llmodule.get_global(name) if llstr is None: @@ -439,16 +439,16 @@ class LLVMIRGenerator: else: typ, _ = self.type_map[type(obj_ref)] - llobject = self.llmodule.get_global("object.{}".format(obj_id)) + llobject = self.llmodule.get_global("O.{}".format(obj_id)) if llobject is not None: llobjects[typ].append(llobject.bitcast(llptr)) lldatalayout = llvm.create_target_data(self.llmodule.data_layout) - llrpcattrty = self.llcontext.get_identified_type("attr_desc") + llrpcattrty = self.llcontext.get_identified_type("A") llrpcattrty.elements = [lli32, lli32, llptr, llptr] - lldescty = self.llcontext.get_identified_type("type_desc") + lldescty = self.llcontext.get_identified_type("D") lldescty.elements = [llrpcattrty.as_pointer().as_pointer(), llptr.as_pointer()] lldescs = [] @@ -457,9 +457,9 @@ class LLVMIRGenerator: continue if types.is_constructor(typ): - type_name = "class.{}".format(typ.name) + type_name = "C.{}".format(typ.name) else: - type_name = "instance.{}".format(typ.name) + type_name = "I.{}".format(typ.name) def llrpcattr_of_attr(name, typ): size = self.llty_of_type(typ). \ @@ -478,14 +478,19 @@ class LLVMIRGenerator: else: llrpctag = ll.Constant(llptr, None) - llrpcattr = ll.GlobalVariable(self.llmodule, llrpcattrty, - name="attr.{}.{}".format(type_name, name)) - llrpcattr.initializer = ll.Constant(llrpcattrty, [ + llrpcattrinit = ll.Constant(llrpcattrty, [ ll.Constant(lli32, size), ll.Constant(lli32, alignment), llrpctag, self.llstr_of_str(name) ]) + + if name == "__objectid__": + return self.get_or_define_global(name, llrpcattrty, llrpcattrinit) + + llrpcattr = ll.GlobalVariable(self.llmodule, llrpcattrty, + name="A.{}.{}".format(type_name, name)) + llrpcattr.initializer = llrpcattrinit llrpcattr.global_constant = True llrpcattr.unnamed_addr = True llrpcattr.linkage = 'private' @@ -497,7 +502,7 @@ class LLVMIRGenerator: llrpcattraryty = ll.ArrayType(llrpcattrty.as_pointer(), len(llrpcattrs) + 1) llrpcattrary = ll.GlobalVariable(self.llmodule, llrpcattraryty, - name="attrs.{}".format(type_name)) + name="Ax.{}".format(type_name)) llrpcattrary.initializer = ll.Constant(llrpcattraryty, llrpcattrs + [ll.Constant(llrpcattrty.as_pointer(), None)]) llrpcattrary.global_constant = True @@ -506,13 +511,13 @@ class LLVMIRGenerator: llobjectaryty = ll.ArrayType(llptr, len(llobjects[typ]) + 1) llobjectary = ll.GlobalVariable(self.llmodule, llobjectaryty, - name="objects.{}".format(type_name)) + name="Ox.{}".format(type_name)) llobjectary.initializer = ll.Constant(llobjectaryty, llobjects[typ] + [ll.Constant(llptr, None)]) llobjectary.linkage = 'private' lldesc = ll.GlobalVariable(self.llmodule, lldescty, - name="desc.{}".format(type_name)) + name="D.{}".format(type_name)) lldesc.initializer = ll.Constant(lldescty, [ llrpcattrary.bitcast(llrpcattrty.as_pointer().as_pointer()), llobjectary.bitcast(llptr.as_pointer()) @@ -548,6 +553,7 @@ class LLVMIRGenerator: llactualargs = self.llfunction.args for arg, llarg in zip(func.arguments, llactualargs): + llarg.name = arg.name self.llmap[arg] = llarg # Second, create all basic blocks. @@ -649,7 +655,8 @@ class LLVMIRGenerator: def process_GetLocal(self, insn): env = insn.environment() llptr = self.llptr_to_var(self.map(env), env.type, insn.var_name) - return self.llbuilder.load(llptr) + llptr.name = "ptr.{}.{}".format(env.name, insn.var_name) + return self.llbuilder.load(llptr, name="val.{}.{}".format(env.name, insn.var_name)) def process_SetLocal(self, insn): env = insn.environment() @@ -658,6 +665,7 @@ class LLVMIRGenerator: # We store NoneType as {} but return it as void. So, bail out here. return ll.Constant(ll.LiteralStructType([]), []) llptr = self.llptr_to_var(self.map(env), env.type, insn.var_name) + llptr.name = "ptr.{}.{}".format(env.name, insn.var_name) if isinstance(llvalue, ll.Block): llvalue = ll.BlockAddress(self.llfunction, llvalue) if llptr.type.pointee != llvalue.type: @@ -687,13 +695,13 @@ class LLVMIRGenerator: def get_class(self, typ): assert types.is_constructor(typ) llty = self.llty_of_type(typ).pointee - return self.get_or_define_global("class.{}".format(typ.name), llty) + return self.get_or_define_global("C.{}".format(typ.name), llty) def get_method(self, typ, attr): assert types.is_constructor(typ) assert types.is_function(typ.attributes[attr]) llty = self.llty_of_type(typ.attributes[attr]) - return self.get_or_define_global("method.{}.{}".format(typ.name, attr), llty) + return self.get_or_define_global("M.{}.{}".format(typ.name, attr), llty) def process_GetAttr(self, insn): typ, attr = insn.object().type, insn.attr @@ -715,7 +723,9 @@ class LLVMIRGenerator: assert False if types.is_method(insn.type) and attr not in typ.attributes: - llfun = self.llbuilder.load(self.get_method(typ.constructor, attr)) + llmethodptr = self.get_method(typ.constructor, attr) + llfun = self.llbuilder.load(llmethodptr) + llfun.name = "met.{}.{}".format(typ.constructor.name, attr) llself = self.map(insn.object()) llmethodty = self.llty_of_type(insn.type) @@ -727,11 +737,12 @@ class LLVMIRGenerator: return llmethod elif types.is_function(insn.type) and attr in typ.attributes and \ types.is_constructor(typ): - return self.llbuilder.load(self.get_method(typ, attr)) + llmethodptr = self.get_method(typ, attr) + return self.llbuilder.load(llmethodptr, name="cls.{}".format(llmethodptr.name)) else: llptr = self.llbuilder.gep(obj, [self.llindex(0), self.llindex(index)], - inbounds=True, name=insn.name) - return self.llbuilder.load(llptr) + inbounds=True, name="ptr.{}".format(insn.name)) + return self.llbuilder.load(llptr, name="val.{}".format(insn.name)) def process_SetAttr(self, insn): typ, attr = insn.object().type, insn.attr @@ -979,8 +990,8 @@ class LLVMIRGenerator: elif insn.op == "delay_mu": interval, = insn.operands llnowptr = self.llbuiltin("now") - llnow = self.llbuilder.load(llnowptr) - lladjusted = self.llbuilder.add(llnow, self.map(interval)) + llnow = self.llbuilder.load(llnowptr, name="now.old") + lladjusted = self.llbuilder.add(llnow, self.map(interval), name="now.new") return self.llbuilder.store(lladjusted, llnowptr) elif insn.op == "watchdog_set": interval, = insn.operands @@ -992,11 +1003,12 @@ class LLVMIRGenerator: assert False def process_Closure(self, insn): - llenv = self.llbuilder.bitcast(self.map(insn.environment()), llptr) + llenv = self.map(insn.environment()) + llenv = self.llbuilder.bitcast(llenv, llptr, name="ptr.{}".format(llenv.name)) if insn.target_function.name in self.function_map.values(): # If this closure belongs to a quoted function, we assume this is the only # time that the closure is created, and record the environment globally - llenvptr = self.get_or_define_global("env.{}".format(insn.target_function.name), + llenvptr = self.get_or_define_global("E.{}".format(insn.target_function.name), llptr) self.llbuilder.store(llenv, llenvptr) @@ -1009,9 +1021,10 @@ class LLVMIRGenerator: def _prepare_closure_call(self, insn): llargs = [self.map(arg) for arg in insn.arguments()] llclosure = self.map(insn.target_function()) - llenv = self.llbuilder.extract_value(llclosure, 0) + llenv = self.llbuilder.extract_value(llclosure, 0, name="env.call") if insn.static_target_function is None: - llfun = self.llbuilder.extract_value(llclosure, 1) + llfun = self.llbuilder.extract_value(llclosure, 1, + name="fun.{}".format(llclosure.name)) else: llfun = self.map(insn.static_target_function) return llfun, [llenv] + list(llargs) @@ -1119,15 +1132,18 @@ class LLVMIRGenerator: lltag = self.llstr_of_str(tag) - llstackptr = self.llbuilder.call(self.llbuiltin("llvm.stacksave"), []) + llstackptr = self.llbuilder.call(self.llbuiltin("llvm.stacksave"), [], + name="rpc.stack") llargs = [] - for arg in args: + for index, arg in enumerate(args): if builtins.is_none(arg.type): - llargslot = self.llbuilder.alloca(ll.LiteralStructType([])) + llargslot = self.llbuilder.alloca(ll.LiteralStructType([]), + name="rpc.arg{}".format(index)) else: llarg = self.map(arg) - llargslot = self.llbuilder.alloca(llarg.type) + llargslot = self.llbuilder.alloca(llarg.type, + name="rpc.arg{}".format(index)) self.llbuilder.store(llarg, llargslot) llargs.append(llargslot) @@ -1144,36 +1160,39 @@ class LLVMIRGenerator: # else *(T*)ptr # } llprehead = self.llbuilder.basic_block - llhead = self.llbuilder.append_basic_block(name=llprehead.name + ".rpc.head") + llhead = self.llbuilder.append_basic_block(name="rpc.head") if llunwindblock: - llheadu = self.llbuilder.append_basic_block(name=llprehead.name + ".rpc.head.unwind") - llalloc = self.llbuilder.append_basic_block(name=llprehead.name + ".rpc.alloc") - lltail = self.llbuilder.append_basic_block(name=llprehead.name + ".rpc.tail") + llheadu = self.llbuilder.append_basic_block(name="rpc.head.unwind") + llalloc = self.llbuilder.append_basic_block(name="rpc.continue") + lltail = self.llbuilder.append_basic_block(name="rpc.tail") llretty = self.llty_of_type(fun_type.ret) - llslot = self.llbuilder.alloca(llretty) - llslotgen = self.llbuilder.bitcast(llslot, llptr) + llslot = self.llbuilder.alloca(llretty, name="rpc.ret.alloc") + llslotgen = self.llbuilder.bitcast(llslot, llptr, name="rpc.ret.ptr") self.llbuilder.branch(llhead) self.llbuilder.position_at_end(llhead) - llphi = self.llbuilder.phi(llslotgen.type) + llphi = self.llbuilder.phi(llslotgen.type, name="rpc.size") llphi.add_incoming(llslotgen, llprehead) if llunwindblock: llsize = self.llbuilder.invoke(self.llbuiltin("recv_rpc"), [llphi], - llheadu, llunwindblock) + llheadu, llunwindblock, + name="rpc.size.next") self.llbuilder.position_at_end(llheadu) else: - llsize = self.llbuilder.call(self.llbuiltin("recv_rpc"), [llphi]) - lldone = self.llbuilder.icmp_unsigned('==', llsize, ll.Constant(llsize.type, 0)) + llsize = self.llbuilder.call(self.llbuiltin("recv_rpc"), [llphi], + name="rpc.size.next") + lldone = self.llbuilder.icmp_unsigned('==', llsize, ll.Constant(llsize.type, 0), + name="rpc.done") self.llbuilder.cbranch(lldone, lltail, llalloc) self.llbuilder.position_at_end(llalloc) - llalloca = self.llbuilder.alloca(lli8, llsize) + llalloca = self.llbuilder.alloca(lli8, llsize, name="rpc.alloc") llphi.add_incoming(llalloca, llalloc) self.llbuilder.branch(llhead) self.llbuilder.position_at_end(lltail) - llret = self.llbuilder.load(llslot) + llret = self.llbuilder.load(llslot, name="rpc.ret") if not builtins.is_allocated(fun_type.ret): # We didn't allocate anything except the slot for the value itself. # Don't waste stack space. @@ -1243,7 +1262,7 @@ class LLVMIRGenerator: llglobal = self.get_class(typ) else: llglobal = ll.GlobalVariable(self.llmodule, llty.pointee, - name="object.{}".format(objectid)) + name="O.{}".format(objectid)) self.llobject_map[value_id] = llglobal else: @@ -1297,7 +1316,7 @@ class LLVMIRGenerator: def process_Quote(self, insn): if insn.value in self.function_map: func_name = self.function_map[insn.value] - llenvptr = self.get_or_define_global("env.{}".format(func_name), llptr) + llenvptr = self.get_or_define_global("E.{}".format(func_name), llptr) llenv = self.llbuilder.load(llenvptr) llfun = self.get_function(insn.type.find(), func_name)