From b6a5c5f5d2a466e867f59c463987ba8ee28664a5 Mon Sep 17 00:00:00 2001 From: gingerBill Date: Tue, 21 Feb 2023 17:24:22 +0000 Subject: Improve some error messages when casting a constant value which needs to be truncated/rounded --- src/check_expr.cpp | 31 +++++++++++++++++++++++-------- 1 file changed, 23 insertions(+), 8 deletions(-) (limited to 'src/check_expr.cpp') diff --git a/src/check_expr.cpp b/src/check_expr.cpp index 8a3bb2c1b..c4a29b04a 100644 --- a/src/check_expr.cpp +++ b/src/check_expr.cpp @@ -2915,17 +2915,32 @@ gb_internal void check_cast(CheckerContext *c, Operand *x, Type *type) { bool can_convert = check_cast_internal(c, x, type); if (!can_convert) { - gbString expr_str = expr_to_string(x->expr); - gbString to_type = type_to_string(type); - gbString from_type = type_to_string(x->type); - error(x->expr, "Cannot cast '%s' as '%s' from '%s'", expr_str, to_type, from_type); - gb_string_free(from_type); - gb_string_free(to_type); - gb_string_free(expr_str); + TEMPORARY_ALLOCATOR_GUARD(); + gbString expr_str = expr_to_string(x->expr, temporary_allocator()); + gbString to_type = type_to_string(type, temporary_allocator()); + gbString from_type = type_to_string(x->type, temporary_allocator()); + x->mode = Addressing_Invalid; + + begin_error_block(); + error(x->expr, "Cannot cast '%s' as '%s' from '%s'", expr_str, to_type, from_type); + if (is_const_expr) { + gbString val_str = exact_value_to_string(x->value); + if (is_type_float(x->type) && is_type_integer(type)) { + error_line("\t%s cannot be expressed without truncation/rounding as the type '%s'\n", val_str, to_type); + + // NOTE(bill): keep the mode and modify the type to minimize errors further on + x->mode = Addressing_Constant; + x->type = type; + } else { + error_line("\t%s cannot be expressed as the type '%s'\n", val_str, to_type); + } + gb_string_free(val_str); + } check_cast_error_suggestion(c, x, type); - x->mode = Addressing_Invalid; + end_error_block(); + return; } -- cgit v1.2.3