aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorKevin Watters <kevinwatters@gmail.com>2019-03-31 12:03:22 -0400
committerKevin Watters <kevinwatters@gmail.com>2019-03-31 12:03:22 -0400
commit381fbd3dafed820583c97f176d2694b21358d178 (patch)
tree071c9b572b655ca2ca5597a7252eebe228670a02 /src
parent76a2807b56a9c0a40c66915d5b77cf537ad376f2 (diff)
parentdd9113786c4e7b18e894bd3ceee94cdf08ac6037 (diff)
Merge branch 'master' of github.com:odin-lang/Odin
Diffstat (limited to 'src')
-rw-r--r--src/check_expr.cpp32
-rw-r--r--src/check_type.cpp6
-rw-r--r--src/ir.cpp8
-rw-r--r--src/parser.cpp5
4 files changed, 44 insertions, 7 deletions
diff --git a/src/check_expr.cpp b/src/check_expr.cpp
index af3ef01b4..d10dd33c7 100644
--- a/src/check_expr.cpp
+++ b/src/check_expr.cpp
@@ -5,6 +5,7 @@ enum CallArgumentError {
CallArgumentError_NonVariadicExpand,
CallArgumentError_VariadicTuple,
CallArgumentError_MultipleVariadicExpand,
+ CallArgumentError_AmbiguousPolymorphicVariadic,
CallArgumentError_ArgumentCount,
CallArgumentError_TooFewArguments,
CallArgumentError_TooManyArguments,
@@ -4492,6 +4493,15 @@ CALL_ARGUMENT_CHECKER(check_call_arguments_internal) {
err = CallArgumentError_NonVariadicExpand;
} else if (operands.count == 0 && param_count_excluding_defaults == 0) {
err = CallArgumentError_None;
+
+ if (variadic) {
+ GB_ASSERT(param_tuple != nullptr && param_tuple->variables.count > 0);
+ Type *t = param_tuple->variables[0]->type;
+ if (is_type_polymorphic(t)) {
+ error(call, "Ambiguous call to a polymorphic variadic procedure with no variadic input");
+ err = CallArgumentError_AmbiguousPolymorphicVariadic;
+ }
+ }
} else {
i32 error_code = 0;
if (operands.count < param_count_excluding_defaults) {
@@ -4583,6 +4593,12 @@ CALL_ARGUMENT_CHECKER(check_call_arguments_internal) {
GB_ASSERT(is_type_slice(slice));
Type *elem = base_type(slice)->Slice.elem;
Type *t = elem;
+
+ if (is_type_polymorphic(t)) {
+ error(call, "Ambiguous call to a polymorphic variadic procedure with no variadic input");
+ err = CallArgumentError_AmbiguousPolymorphicVariadic;
+ }
+
for (; operand_index < operands.count; operand_index++) {
Operand o = operands[operand_index];
if (vari_expand) {
@@ -4761,11 +4777,24 @@ CALL_ARGUMENT_CHECKER(check_named_call_arguments) {
for (isize i = 0; i < param_count; i++) {
+ Entity *e = pt->params->Tuple.variables[i];
Operand *o = &ordered_operands[i];
+ bool param_is_variadic = pt->variadic && pt->variadic_index == i;
+
+
if (o->mode == Addressing_Invalid) {
+ if (param_is_variadic) {
+ Type *slice = e->type;
+ GB_ASSERT(is_type_slice(slice));
+ Type *elem = base_type(slice)->Slice.elem;
+ if (is_type_polymorphic(elem)) {
+ error(call, "Ambiguous call to a polymorphic variadic procedure with no variadic input");
+ err = CallArgumentError_AmbiguousPolymorphicVariadic;
+ return err;
+ }
+ }
continue;
}
- Entity *e = pt->params->Tuple.variables[i];
if (e->kind == Entity_TypeName) {
GB_ASSERT(pt->is_polymorphic);
@@ -4782,7 +4811,6 @@ CALL_ARGUMENT_CHECKER(check_named_call_arguments) {
}
} else {
i64 s = 0;
- bool param_is_variadic = pt->variadic && pt->variadic_index == i;
if (!check_is_assignable_to_with_score(c, o, e->type, &s, param_is_variadic)) {
bool ok = false;
if (e->flags & EntityFlag_AutoCast) {
diff --git a/src/check_type.cpp b/src/check_type.cpp
index 1721ed881..22cd409ee 100644
--- a/src/check_type.cpp
+++ b/src/check_type.cpp
@@ -1570,6 +1570,12 @@ Type *check_get_params(CheckerContext *ctx, Scope *scope, Ast *_params, bool *is
if (operands != nullptr && variables.count < operands->count) {
Operand op = (*operands)[variables.count];
+ if (op.expr == nullptr) {
+ // NOTE(bill): 2019-03-30
+ // This is just to add the error message to determine_type_from_polymorphic which
+ // depends on valid position information
+ op.expr = _params;
+ }
if (is_type_polymorphic_type) {
type = determine_type_from_polymorphic(ctx, type, op);
if (type == t_invalid) {
diff --git a/src/ir.cpp b/src/ir.cpp
index b5ff56b93..b486a6309 100644
--- a/src/ir.cpp
+++ b/src/ir.cpp
@@ -1433,11 +1433,13 @@ irValue *ir_value_procedure(irModule *m, Entity *entity, Type *type, Ast *type_e
irValue *ir_generate_array(irModule *m, Type *elem_type, i64 count, String prefix, i64 id) {
gbAllocator a = ir_allocator();
Token token = {Token_Ident};
- isize name_len = prefix.len + 10;
+ isize name_len = prefix.len + 1 + 20;
- char *text = gb_alloc_array(a, char, name_len);
+ auto suffix_id = cast(unsigned long long)id;
+ char *text = gb_alloc_array(a, char, name_len+1);
gb_snprintf(text, name_len,
- "%.*s-%llx", LIT(prefix), cast(unsigned long long)id);
+ "%.*s-%llu", LIT(prefix), suffix_id);
+ text[name_len] = 0;
String s = make_string_c(text);
diff --git a/src/parser.cpp b/src/parser.cpp
index 2eee82e22..12b7edb01 100644
--- a/src/parser.cpp
+++ b/src/parser.cpp
@@ -3024,6 +3024,7 @@ Ast *parse_field_list(AstFile *f, isize *name_count_, u32 allowed_flags, TokenKi
isize total_name_count = 0;
bool allow_ellipsis = allowed_flags&FieldFlag_ellipsis;
bool seen_ellipsis = false;
+ bool is_signature = (allowed_flags & FieldFlag_Signature) == FieldFlag_Signature;
while (f->curr_token.kind != follow &&
f->curr_token.kind != Token_Colon &&
@@ -3064,7 +3065,7 @@ Ast *parse_field_list(AstFile *f, isize *name_count_, u32 allowed_flags, TokenKi
if (f->curr_token.kind != Token_Eq) {
type = parse_var_type(f, allow_ellipsis, allow_typeid_token);
Ast *tt = unparen_expr(type);
- if (!any_polymorphic_names && tt->kind == Ast_TypeidType && tt->TypeidType.specialization != nullptr) {
+ if (is_signature && !any_polymorphic_names && tt->kind == Ast_TypeidType && tt->TypeidType.specialization != nullptr) {
syntax_error(type, "Specialization of typeid is not allowed without polymorphic names");
}
}
@@ -3121,7 +3122,7 @@ Ast *parse_field_list(AstFile *f, isize *name_count_, u32 allowed_flags, TokenKi
if (f->curr_token.kind != Token_Eq) {
type = parse_var_type(f, allow_ellipsis, allow_typeid_token);
Ast *tt = unparen_expr(type);
- if (!any_polymorphic_names && tt->kind == Ast_TypeidType && tt->TypeidType.specialization != nullptr) {
+ if (is_signature && !any_polymorphic_names && tt->kind == Ast_TypeidType && tt->TypeidType.specialization != nullptr) {
syntax_error(type, "Specialization of typeid is not allowed without polymorphic names");
}
}