authorgravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2016-12-17 20:47:35-05:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2016-12-17 20:47:35-05:00
log0f047337ac0bf65b5f6d92248adc1452047f2622
treea15cc9d6f7250f056771d5ff18f9ec1862964d58
parenta07d7ee53d7695b7ca56ced0a4ba25de2532ccbc

IR: fix `this` expression

Previously it returned a block instead of a function when a function had any arguments.

4 files changed, 47 insertions(+), 18 deletions(-)

src/analyze.cpp+28-5
......@@ -145,12 +145,12 @@ ScopeDecls *create_decls_scope(AstNode *node, Scope *parent, TypeTableEntry *con
145145 return scope;
146146}
147147
148Scope *create_block_scope(AstNode *node, Scope *parent) {
148ScopeBlock *create_block_scope(AstNode *node, Scope *parent) {
149149 assert(node->type == NodeTypeBlock);
150150 ScopeBlock *scope = allocate<ScopeBlock>(1);
151151 init_scope(&scope->base, ScopeIdBlock, node, parent);
152152 scope->label_table.init(1);
153 return &scope->base;
153 return scope;
154154}
155155
156156ScopeDefer *create_defer_scope(AstNode *node, Scope *parent) {
......@@ -1446,7 +1446,7 @@ static void resolve_decl_fn(CodeGen *g, TldFn *tld_fn) {
14461446 if (is_main_fn)
14471447 g->main_fn = fn_table_entry;
14481448
1449 if (is_main_fn && !g->link_libc) {
1449 if (is_main_fn && !g->link_libc && tld_fn->base.visib_mod != VisibModExport) {
14501450 TypeTableEntry *err_void = get_error_type(g, g->builtin_types.entry_void);
14511451 TypeTableEntry *actual_return_type = fn_table_entry->type_entry->data.fn.fn_type_id.return_type;
14521452 if (actual_return_type != err_void) {
......@@ -2049,6 +2049,29 @@ FnTableEntry *scope_fn_entry(Scope *scope) {
20492049 return nullptr;
20502050}
20512051
2052FnTableEntry *scope_get_fn_if_root(Scope *scope) {
2053 assert(scope);
2054 scope = scope->parent;
2055 while (scope) {
2056 switch (scope->id) {
2057 case ScopeIdBlock:
2058 return nullptr;
2059 case ScopeIdDecls:
2060 case ScopeIdDefer:
2061 case ScopeIdVarDecl:
2062 case ScopeIdCImport:
2063 case ScopeIdLoop:
2064 scope = scope->parent;
2065 continue;
2066 case ScopeIdFnDef:
2067 ScopeFnDef *fn_scope = (ScopeFnDef *)scope;
2068 return fn_scope->fn_entry;
2069 }
2070 zig_unreachable();
2071 }
2072 return nullptr;
2073}
2074
20522075TypeEnumField *find_enum_type_field(TypeTableEntry *enum_type, Buf *name) {
20532076 for (uint32_t i = 0; i < enum_type->data.enumeration.src_field_count; i += 1) {
20542077 TypeEnumField *type_enum_field = &enum_type->data.enumeration.fields[i];
......@@ -2392,9 +2415,9 @@ ImportTableEntry *add_source_file(CodeGen *g, PackageTableEntry *package,
23922415 assert(proto_node->type == NodeTypeFnProto);
23932416 Buf *proto_name = proto_node->data.fn_proto.name;
23942417
2395 bool is_private = (proto_node->data.fn_proto.visib_mod == VisibModPrivate);
2418 bool is_pub = (proto_node->data.fn_proto.visib_mod == VisibModPub);
23962419
2397 if (buf_eql_str(proto_name, "main") && !is_private) {
2420 if (buf_eql_str(proto_name, "main") && is_pub) {
23982421 g->have_exported_main = true;
23992422 }
24002423 }
src/analyze.hpp+2-1
......@@ -74,8 +74,9 @@ FnTableEntry *create_fn(AstNode *proto_node);
7474FnTableEntry *create_fn_raw(FnInline inline_value, bool internal_linkage);
7575void init_fn_type_id(FnTypeId *fn_type_id, AstNode *proto_node);
7676AstNode *get_param_decl_node(FnTableEntry *fn_entry, size_t index);
77FnTableEntry *scope_get_fn_if_root(Scope *scope);
7778
78Scope *create_block_scope(AstNode *node, Scope *parent);
79ScopeBlock *create_block_scope(AstNode *node, Scope *parent);
7980ScopeDefer *create_defer_scope(AstNode *node, Scope *parent);
8081Scope *create_var_scope(AstNode *node, Scope *parent, VariableTableEntry *var);
8182ScopeCImport *create_cimport_scope(AstNode *node, Scope *parent);
src/ir.cpp+15-10
......@@ -2051,9 +2051,15 @@ static VariableTableEntry *ir_create_var(IrBuilder *irb, AstNode *node, Scope *s
20512051static IrInstruction *ir_gen_block(IrBuilder *irb, Scope *parent_scope, AstNode *block_node) {
20522052 assert(block_node->type == NodeTypeBlock);
20532053
2054 Scope *outer_block_scope = create_block_scope(block_node, parent_scope);
2054 ScopeBlock *scope_block = create_block_scope(block_node, parent_scope);
2055 Scope *outer_block_scope = &scope_block->base;
20552056 Scope *child_scope = outer_block_scope;
20562057
2058 FnTableEntry *fn_entry = scope_fn_entry(parent_scope);
2059 if (fn_entry && fn_entry->child_scope == parent_scope) {
2060 fn_entry->def_scope = scope_block;
2061 }
2062
20572063 IrInstruction *return_value = nullptr;
20582064 for (size_t i = 0; i < block_node->data.block.statements.length; i += 1) {
20592065 AstNode *statement_node = block_node->data.block.statements.at(i);
......@@ -3270,12 +3276,9 @@ static IrInstruction *ir_gen_this_literal(IrBuilder *irb, Scope *scope, AstNode
32703276 if (!scope->parent)
32713277 return ir_build_const_import(irb, scope, node, node->owner);
32723278
3273 FnTableEntry *fn_entry = exec_fn_entry(irb->exec);
3274 if (fn_entry && scope->parent && scope->parent->parent &&
3275 !scope_fn_entry(scope->parent->parent))
3276 {
3279 FnTableEntry *fn_entry = scope_get_fn_if_root(scope);
3280 if (fn_entry)
32773281 return ir_build_const_fn(irb, scope, node, fn_entry);
3278 }
32793282
32803283 if (scope->id == ScopeIdDecls) {
32813284 ScopeDecls *decls_scope = (ScopeDecls *)scope;
......@@ -4379,6 +4382,7 @@ static bool is_u8(TypeTableEntry *type) {
43794382static IrBasicBlock *ir_get_new_bb(IrAnalyze *ira, IrBasicBlock *old_bb) {
43804383 if (old_bb->other)
43814384 return old_bb->other;
4385
43824386 IrBasicBlock *new_bb = ir_build_bb_from(&ira->new_irb, old_bb);
43834387
43844388 // We are about to enqueue old_bb for analysis. Before we do so, check old_bb
......@@ -4391,7 +4395,8 @@ static IrBasicBlock *ir_get_new_bb(IrAnalyze *ira, IrBasicBlock *old_bb) {
43914395 IrInstructionPhi *phi_instruction = (IrInstructionPhi *)instruction;
43924396 for (size_t incoming_i = 0; incoming_i < phi_instruction->incoming_count; incoming_i += 1) {
43934397 IrBasicBlock *predecessor = phi_instruction->incoming_blocks[incoming_i];
4394 ir_get_new_bb(ira, predecessor);
4398 IrBasicBlock *new_predecessor = ir_get_new_bb(ira, predecessor);
4399 ir_ref_bb(new_predecessor);
43954400 }
43964401 }
43974402 ira->old_bb_queue.append(old_bb);
......@@ -4404,7 +4409,7 @@ static void ir_start_bb(IrAnalyze *ira, IrBasicBlock *old_bb, IrBasicBlock *cons
44044409 ira->old_irb.current_basic_block = old_bb;
44054410 ira->const_predecessor_bb = const_predecessor_bb;
44064411
4407 if (old_bb->other)
4412 if (!const_predecessor_bb && old_bb->other)
44084413 ira->new_irb.exec->basic_block_list.append(old_bb->other);
44094414}
44104415
......@@ -6478,7 +6483,7 @@ static TypeTableEntry *ir_analyze_instruction_phi(IrAnalyze *ira, IrInstructionP
64786483 IrInstruction *old_value = phi_instruction->incoming_values[i];
64796484 assert(old_value);
64806485 IrInstruction *new_value = old_value->other;
6481 if (new_value->type_entry->id == TypeTableEntryIdInvalid)
6486 if (!new_value || new_value->type_entry->id == TypeTableEntryIdInvalid)
64826487 return ira->codegen->builtin_types.entry_invalid;
64836488 new_incoming_values.append(new_value);
64846489 }
......@@ -7704,7 +7709,7 @@ static TypeTableEntry *ir_analyze_instruction_switch_br(IrAnalyze *ira,
77047709
77057710 IrBasicBlock *new_else_block = ir_get_new_bb(ira, switch_br_instruction->else_block);
77067711 ir_build_switch_br_from(&ira->new_irb, &switch_br_instruction->base,
7707 target_value, new_else_block, case_count, cases, is_inline);
7712 target_value, new_else_block, case_count, cases, false);
77087713 return ir_finish_anal(ira, ira->codegen->builtin_types.entry_unreachable);
77097714}
77107715
std/bootstrap.zig+2-2
......@@ -16,7 +16,7 @@ var argv: &&u8 = undefined;
1616export nakedcc fn _start() -> unreachable {
1717 @setFnVisible(this, want_start_symbol);
1818
19 switch (@compileVar("arch")) {
19 inline switch (@compileVar("arch")) {
2020 Arch.x86_64 => {
2121 argc = asm("mov (%%rsp), %[argc]": [argc] "=r" (-> usize));
2222 argv = asm("lea 0x8(%%rsp), %[argv]": [argv] "=r" (-> &&u8));
......@@ -32,7 +32,7 @@ export nakedcc fn _start() -> unreachable {
3232
3333fn callMain() -> %void {
3434 const args = @alloca([]u8, argc);
35 for (args) |arg, i| {
35 for (args) |_, i| {
3636 const ptr = argv[i];
3737 args[i] = ptr[0...cstr.len(ptr)];
3838 }