Almost fix function overloading. Return var issues.
This commit is contained in:
@@ -154,6 +154,7 @@ emit_function :: (state : *Codegen_State, node : *AST_Node, indentation : int, e
|
|||||||
if function_variable.return_var {
|
if function_variable.return_var {
|
||||||
return_variable := h2tv(state.type_variables, function_variable.return_var);
|
return_variable := h2tv(state.type_variables, function_variable.return_var);
|
||||||
print_to_builder(*state.builder, "% ", type_to_string(return_variable));
|
print_to_builder(*state.builder, "% ", type_to_string(return_variable));
|
||||||
|
print("shiet: %\n", return_variable.*);
|
||||||
} else {
|
} else {
|
||||||
append(*state.builder, "void ");
|
append(*state.builder, "void ");
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -284,9 +284,6 @@ Use of undeclard symbol '%'.
|
|||||||
record_error(checker, message, node.source_location, false);
|
record_error(checker, message, node.source_location, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
foo :: (i : int, p : int) {}
|
|
||||||
foo :: (i : int, p : int, t : int) {}
|
|
||||||
|
|
||||||
no_matching_overload_found :: (checker : *Semantic_Checker, call : *AST_Node, overloads : *Defined_Symbol, arg_node : *AST_Node = null) {
|
no_matching_overload_found :: (checker : *Semantic_Checker, call : *AST_Node, overloads : *Defined_Symbol, arg_node : *AST_Node = null) {
|
||||||
builder : String_Builder;
|
builder : String_Builder;
|
||||||
init_string_builder(*builder,, temp);
|
init_string_builder(*builder,, temp);
|
||||||
@@ -339,6 +336,8 @@ no_matching_overload_found :: (checker : *Semantic_Checker, call : *AST_Node, ov
|
|||||||
// foo :: (f : float) {} (file_path:line_num)
|
// foo :: (f : float) {} (file_path:line_num)
|
||||||
func_location := func_var.source_node.source_location;
|
func_location := func_var.source_node.source_location;
|
||||||
indent(*builder, 2);
|
indent(*builder, 2);
|
||||||
|
|
||||||
|
// @Incomplete(niels): We need a way to properly save the path of the declaration
|
||||||
print_to_builder(*builder, "% (%:%)\n", print_from_source_location(func_location), checker.path,
|
print_to_builder(*builder, "% (%:%)\n", print_from_source_location(func_location), checker.path,
|
||||||
func_location.main_token.line);
|
func_location.main_token.line);
|
||||||
|
|
||||||
@@ -573,7 +572,8 @@ type_mismatch :: (checker : *Semantic_Checker, usage_site : *AST_Node, expect_no
|
|||||||
print_to_builder(*builder, "got:\n");
|
print_to_builder(*builder, "got:\n");
|
||||||
|
|
||||||
indent(*builder, 2);
|
indent(*builder, 2);
|
||||||
print_to_builder(*builder, "%\n", print_from_source_location(got_var.source_node.parent.source_location));
|
|
||||||
|
print_to_builder(*builder, "%\n", print_from_source_location(got_var.source_node.source_location));
|
||||||
|
|
||||||
message := builder_to_string(*builder);
|
message := builder_to_string(*builder);
|
||||||
|
|
||||||
@@ -1097,18 +1097,6 @@ create_function_constraint :: (checker : *Semantic_Checker, node : *AST_Node) {
|
|||||||
assert(false, "Compiler error. Functions should all be declared at this point in time.");
|
assert(false, "Compiler error. Functions should all be declared at this point in time.");
|
||||||
}
|
}
|
||||||
|
|
||||||
//@Note(niels): Constraint should be:
|
|
||||||
// X(X1, ..., Xn) { return E; }: [[X]] = ([[X1]], ..., [[Xn]]) -> [[E]]
|
|
||||||
// We return the type variable handle for X (the function name)
|
|
||||||
|
|
||||||
// @Incomplete(niels): In this case we will have a list of function overloads
|
|
||||||
// The list is most often of size 1, but in the case it is > 1
|
|
||||||
// we have overloads that we have to match against.
|
|
||||||
// This means our constraint gets slightly more complicated.
|
|
||||||
// At this point we could consider cheating and already matching the types
|
|
||||||
// at this point and finding the correct function variable.
|
|
||||||
// We can do this because technically we have already declared all functions at this point.
|
|
||||||
// So we don't have any unresolved types as of this point.
|
|
||||||
handle := find_result.type_variable;
|
handle := find_result.type_variable;
|
||||||
if node.foreign_declaration {
|
if node.foreign_declaration {
|
||||||
return;
|
return;
|
||||||
@@ -1309,12 +1297,6 @@ create_call_constraint :: (checker : *Semantic_Checker, node : *AST_Node, type_v
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// @Incomplete(niels): Fix overload resolution.
|
|
||||||
// Currently we don't have proper resolution. We don't even pick a proper function.
|
|
||||||
// We need to run through all functions in this find result, and match the arguments.
|
|
||||||
// If no overload is found, we have to print out all overloads and post mismatched arguments.
|
|
||||||
// If an overload is found we proceed as usual.
|
|
||||||
|
|
||||||
overload_found := false;
|
overload_found := false;
|
||||||
arg_node : *AST_Node = null;
|
arg_node : *AST_Node = null;
|
||||||
|
|
||||||
@@ -1346,6 +1328,14 @@ create_call_constraint :: (checker : *Semantic_Checker, node : *AST_Node, type_v
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Type_Mismatch_Data :: struct {
|
||||||
|
lhs : Result;
|
||||||
|
rhs : Result;
|
||||||
|
}
|
||||||
|
|
||||||
|
mismatches : [..]Type_Mismatch_Data;
|
||||||
|
mismatches.allocator = temp;
|
||||||
|
|
||||||
for *func : find_result.functions {
|
for *func : find_result.functions {
|
||||||
if overload_found {
|
if overload_found {
|
||||||
break;
|
break;
|
||||||
@@ -1357,13 +1347,6 @@ create_call_constraint :: (checker : *Semantic_Checker, node : *AST_Node, type_v
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
if function.return_var > 0 {
|
|
||||||
return_var := h2tv(checker, function.return_var);
|
|
||||||
constrained_var := h2tv(checker, type_var);
|
|
||||||
constrained_var.type = return_var.type;
|
|
||||||
constrained_var.typename = return_var.typename;
|
|
||||||
}
|
|
||||||
|
|
||||||
if node.children.count == 0 && function.child_count == 0 {
|
if node.children.count == 0 && function.child_count == 0 {
|
||||||
overload_found = true;
|
overload_found = true;
|
||||||
break;
|
break;
|
||||||
@@ -1374,30 +1357,39 @@ create_call_constraint :: (checker : *Semantic_Checker, node : *AST_Node, type_v
|
|||||||
for arg : arg_vars {
|
for arg : arg_vars {
|
||||||
function_param := function.children[it_index];
|
function_param := function.children[it_index];
|
||||||
|
|
||||||
// @Incomplete(nb): Improve the error handling of this constraint.
|
|
||||||
// The usage site might be the call, but really the usage site
|
|
||||||
// is the variable, with the call around it.
|
|
||||||
// We could probably expand source locations to always include the whole line
|
|
||||||
// That is unlikely to be annoying now that I think about it.
|
|
||||||
// So maybe we just always do that? Then we always have the complete information
|
|
||||||
// and the actual token we want to focus on is just the one we have?
|
|
||||||
// @Update(nb): We actually do this now for a bunch of places, but not all.
|
|
||||||
// Error reporting in this case is still not great, since it doesn't properly mark the
|
|
||||||
// faulty variable.
|
|
||||||
create_equivalence_constraint(checker, arg.var, function_param, arg.node);
|
|
||||||
if !types_compatible(checker, arg.var, function_param) {
|
if !types_compatible(checker, arg.var, function_param) {
|
||||||
if all_args_match {
|
if all_args_match {
|
||||||
arg_node = arg.node;
|
arg_node = arg.node;
|
||||||
}
|
}
|
||||||
|
fun_param := h2tv(checker, function_param);
|
||||||
|
mismatch : Type_Mismatch_Data;
|
||||||
|
mismatch.lhs = arg;
|
||||||
|
mismatch.rhs = .{ function_param, fun_param.source_node };
|
||||||
|
array_add(*mismatches, mismatch);
|
||||||
|
|
||||||
all_args_match = false;
|
all_args_match = false;
|
||||||
} else {
|
} else {
|
||||||
overload_found = all_args_match;
|
overload_found = all_args_match;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if overload_found {
|
||||||
|
if function.return_var > 0 {
|
||||||
|
return_var := h2tv(checker, function.return_var);
|
||||||
|
constrained_var := h2tv(checker, type_var);
|
||||||
|
constrained_var.type = return_var.type;
|
||||||
|
constrained_var.typename = return_var.typename;
|
||||||
|
print("%\n", constrained_var.typename);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if !overload_found {
|
if !overload_found {
|
||||||
no_matching_overload_found(checker, node, find_result, arg_node);
|
no_matching_overload_found(checker, node, find_result, arg_node);
|
||||||
|
|
||||||
|
for mismatch : mismatches {
|
||||||
|
type_mismatch(checker, mismatch.lhs.node, mismatch.rhs.node, mismatch.rhs.var, mismatch.lhs.var);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1610,11 +1602,7 @@ union_terms :: (checker : *Semantic_Checker, lhs_handle : Type_Variable_Handle,
|
|||||||
} else {
|
} else {
|
||||||
type_mismatch(checker, lhs_var.source_node.parent, rhs_var.source_node.parent, rhs_handle, lhs_handle);
|
type_mismatch(checker, lhs_var.source_node.parent, rhs_var.source_node.parent, rhs_handle, lhs_handle);
|
||||||
}
|
}
|
||||||
|
} else if lhs_handle != rhs_handle {
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if lhs_handle != rhs_handle {
|
|
||||||
lhs := h2tv(checker, lhs_handle);
|
lhs := h2tv(checker, lhs_handle);
|
||||||
lhs.uf_parent = rhs_handle;
|
lhs.uf_parent = rhs_handle;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,7 +4,9 @@ camera :: constant_buffer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
vertex main :: (pos : float4 @position) -> float4 @position {
|
vertex main :: (pos : float4 @position) -> float4 @position {
|
||||||
return mul(camera.projection, mul(camera.view, pos));
|
mv : float4 = mul(camera.view, pos);
|
||||||
|
mvp : float4 = mul(camera.projection, mv);
|
||||||
|
return mvp;
|
||||||
}
|
}
|
||||||
|
|
||||||
pixel main :: () -> float4 @target {
|
pixel main :: () -> float4 @target {
|
||||||
|
|||||||
@@ -1,16 +1,4 @@
|
|||||||
[1;37mtest/unknown_overload.shd:6,0: [31merror: [37mProcedure call did not match any of the possible overloads for 'foo'
|
[1;37mtest/unknown_overload.shd:6,4: [31merror: [37mType mismatch. Expected float3 got float
|
||||||
[96m found:
|
|
||||||
foo(v, v);
|
|
||||||
^^^
|
|
||||||
|
|
||||||
[97m While matching argument 1 in function call.
|
|
||||||
[96m foo(v, v);
|
|
||||||
^
|
|
||||||
[97m Possible overloads:
|
|
||||||
[96m foo :: (v1 : float3, v2 : float3) { (test/unknown_overload.shd:1)
|
|
||||||
[96m foo :: (v1 : float2, v2 : float2, v3 : float2) { (test/unknown_overload.shd:2)
|
|
||||||
|
|
||||||
[36m[37m[1;37mtest/unknown_overload.shd:6,4: [31merror: [37mType mismatch. Expected float3 got float
|
|
||||||
[96m found:
|
[96m found:
|
||||||
foo(v, v);
|
foo(v, v);
|
||||||
^
|
^
|
||||||
@@ -30,4 +18,16 @@
|
|||||||
got:
|
got:
|
||||||
v : float = 2.0
|
v : float = 2.0
|
||||||
|
|
||||||
|
[36m[37m[1;37mtest/unknown_overload.shd:6,0: [31merror: [37mProcedure call did not match any of the possible overloads for 'foo'
|
||||||
|
[96m found:
|
||||||
|
foo(v, v);
|
||||||
|
^^^
|
||||||
|
|
||||||
|
[97m While matching argument 1 in function call.
|
||||||
|
[96m foo(v, v);
|
||||||
|
^
|
||||||
|
[97m Possible overloads:
|
||||||
|
[96m foo :: (v1 : float3, v2 : float3) { (test/unknown_overload.shd:1)
|
||||||
|
[96m foo :: (v1 : float2, v2 : float2, v3 : float2) { (test/unknown_overload.shd:2)
|
||||||
|
|
||||||
[36m[37m
|
[36m[37m
|
||||||
@@ -6,6 +6,6 @@
|
|||||||
float
|
float
|
||||||
|
|
||||||
got:
|
got:
|
||||||
res : float2 = float2(2.0, 2.0)
|
res : float2 = float2(2.0, 2.0);
|
||||||
|
|
||||||
[36m[37m
|
[36m[37m
|
||||||
@@ -1,4 +1,14 @@
|
|||||||
[1;37mtest/wrong_type_for_function.shd:11,17: [31merror: [37mProcedure call did not match any of the possible overloads for 'float4'
|
[1;37mtest/wrong_type_for_function.shd:11,24: [31merror: [37mType mismatch. Expected float got float2
|
||||||
|
[96m found:
|
||||||
|
color : float4 = float4(y, 1.0, 1.0, 1.0);
|
||||||
|
^
|
||||||
|
expected:
|
||||||
|
float
|
||||||
|
|
||||||
|
got:
|
||||||
|
y : float2 = foo()
|
||||||
|
|
||||||
|
[36m[37m[1;37mtest/wrong_type_for_function.shd:11,17: [31merror: [37mProcedure call did not match any of the possible overloads for 'float4'
|
||||||
[96m found:
|
[96m found:
|
||||||
color : float4 = float4(y, 1.0, 1.0, 1.0);
|
color : float4 = float4(y, 1.0, 1.0, 1.0);
|
||||||
^^^^^^
|
^^^^^^
|
||||||
@@ -9,14 +19,4 @@
|
|||||||
[97m Possible overloads:
|
[97m Possible overloads:
|
||||||
[96m foreign float4 :: (float, float, float, float) -> float4; (test/wrong_type_for_function.shd:79)
|
[96m foreign float4 :: (float, float, float, float) -> float4; (test/wrong_type_for_function.shd:79)
|
||||||
|
|
||||||
[36m[37m[1;37mtest/wrong_type_for_function.shd:11,24: [31merror: [37mType mismatch. Expected float got float2
|
|
||||||
[96m found:
|
|
||||||
color : float4 = float4(y, 1.0, 1.0, 1.0);
|
|
||||||
^
|
|
||||||
expected:
|
|
||||||
float
|
|
||||||
|
|
||||||
got:
|
|
||||||
y : float2 = foo()
|
|
||||||
|
|
||||||
[36m[37m
|
[36m[37m
|
||||||
Reference in New Issue
Block a user