fix false positive error with same named methods in incomplete struct

master
Andrew Kelley 2016-02-02 20:06:51 -07:00
parent d3de73739f
commit a50474e7cf
2 changed files with 43 additions and 6 deletions

View File

@ -5062,12 +5062,20 @@ static void detect_top_level_decl_deps(CodeGen *g, ImportTableEntry *import, Ast
case NodeTypeFnProto:
{
// if the name is missing, we immediately announce an error
Buf *name = &node->data.fn_proto.name;
if (buf_len(name) == 0) {
Buf *fn_name = &node->data.fn_proto.name;
if (buf_len(fn_name) == 0) {
node->data.fn_proto.skip = true;
add_node_error(g, node, buf_sprintf("missing function name"));
break;
}
Buf *qualified_name;
AstNode *struct_node = node->data.fn_proto.struct_node;
if (struct_node) {
Buf *struct_name = &struct_node->data.struct_decl.name;
qualified_name = buf_sprintf("%s.%s", buf_ptr(struct_name), buf_ptr(fn_name));
} else {
qualified_name = fn_name;
}
// determine which other top level declarations this function prototype depends on.
@ -5076,14 +5084,14 @@ static void detect_top_level_decl_deps(CodeGen *g, ImportTableEntry *import, Ast
collect_expr_decl_deps(g, import, node, decl_node);
decl_node->name = name;
decl_node->name = qualified_name;
decl_node->import = import;
if (decl_node->deps.size() > 0) {
if (g->unresolved_top_level_decls.maybe_get(name)) {
if (g->unresolved_top_level_decls.maybe_get(qualified_name)) {
node->data.fn_proto.skip = true;
add_node_error(g, node, buf_sprintf("redefinition of '%s'", buf_ptr(name)));
add_node_error(g, node, buf_sprintf("redefinition of '%s'", buf_ptr(fn_name)));
} else {
g->unresolved_top_level_decls.put(name, node);
g->unresolved_top_level_decls.put(qualified_name, node);
}
} else {
resolve_top_level_decl(g, import, node);

View File

@ -1549,6 +1549,35 @@ pub fn main(args: [][]u8) -> %void {
}
)SOURCE", "OK\n");
add_simple_case("same named methods in incomplete struct", R"SOURCE(
import "std.zig";
struct Foo {
field1: Bar,
fn method(a: &Foo) -> bool { true }
}
struct Bar {
field2: i32,
fn method(b: &Bar) -> bool { true }
}
pub fn main(args: [][]u8) -> %void {
const bar = Bar {.field2 = 13,};
const foo = Foo {.field1 = bar,};
if (!foo.method()) {
%%stdout.printf("BAD\n");
}
if (!bar.method()) {
%%stdout.printf("BAD\n");
}
%%stdout.printf("OK\n");
}
)SOURCE", "OK\n");
}