From c2f501bf364cfb93e0d6a8a83946e2e0bb60827c Mon Sep 17 00:00:00 2001 From: Krzosa Karol Date: Fri, 3 Jun 2022 14:13:45 +0200 Subject: [PATCH] More work on conversions and constant evaluation --- new_types.kl | 2 ++ typecheck.cpp | 77 +++++++++++++++++++++++---------------------------- 2 files changed, 36 insertions(+), 43 deletions(-) diff --git a/new_types.kl b/new_types.kl index fb0f549..7cde920 100644 --- a/new_types.kl +++ b/new_types.kl @@ -1,11 +1,13 @@ unary_test :: () int_val :: 1251525 + uns: U64 = -int_val float_val :: 124.42 conversion: F64 = -+int_val float2 := -float_val unsigned: Int = -+-+-int_val + // int_float: S64 = float_val // string :: -"Thing" // boolean :: -true diff --git a/typecheck.cpp b/typecheck.cpp index eb62c9f..6f17265 100644 --- a/typecheck.cpp +++ b/typecheck.cpp @@ -151,52 +151,40 @@ eval_binary(Token *pos, Token_Kind op, Value a, Value b){ } function Value -eval_unary(Token *pos, Token_Kind op, Value v){ +eval_unary(Token *pos, Token_Kind op, Value a){ + if(!is_numeric(a.type)) parsing_error(pos, "Constant application of binary %s on values of type %s is not allowed", token_kind_string(op).str, docname(a.type)); + + S64 left_int = value_get_int(a); + F64 left_float = value_get_float(a); + switch(op){ case TK_Sub:{ - switch(v.type->kind){ - // @todo: Bounds checking for conversion from negative to positive - // it's, positive is 2147483647 negative is -2147483648 - case TYPE_UNTYPED_INT: v.int_val = -v.int_val;break; - case TYPE_UNTYPED_FLOAT: v.f64_val = -v.f64_val;break; - case TYPE_INT: v.s64_val = -v.int_val;break; - case TYPE_S64: v.s64_val = -v.s64_val;break; - case TYPE_S32: v.s32_val = -v.s32_val;break; - case TYPE_S16: v.s16_val = -v.s16_val;break; - case TYPE_S8: v.s8_val = -v.s8_val; break; - case TYPE_F32: v.f32_val = -v.f32_val;break; - case TYPE_F64: v.f64_val = -v.f64_val;break; - case TYPE_U64: - case TYPE_U32: - case TYPE_U16: - case TYPE_U8: - case TYPE_UINT: parsing_error(pos, "Application of unary [-] on type %s results in overflow", docname(v.type));break; - default: parsing_error(pos, "Constant application of unary [-] on type of %s is unsupported", docname(v.type));break; - } + left_int = -left_int; + left_float = -left_float; }break; case TK_Add:{ - switch(v.type->kind){ - case TYPE_UNTYPED_INT: v.int_val = +v.int_val;break; - case TYPE_UNTYPED_FLOAT: v.f64_val = +v.f64_val;break; - case TYPE_INT: v.s64_val = +v.int_val;break; - case TYPE_S64: v.s64_val = +v.int_val;break; - case TYPE_S32: v.s32_val = +v.int_val;break; - case TYPE_S16: v.s16_val = +v.int_val;break; - case TYPE_S8: v.s8_val = +v.int_val;break; - case TYPE_F32: v.f32_val = +v.f32_val;break; - case TYPE_F64: v.f64_val = +v.f64_val;break; - case TYPE_U64: v.u64_val = +v.u64_val;break; - case TYPE_U32: v.u32_val = +v.u32_val;break; - case TYPE_U16: v.u16_val = +v.u16_val;break; - case TYPE_U8: v.u8_val = +v.u8_val;break; - case TYPE_UINT: v.u64_val = +v.u64_val;break; - default: parsing_error(pos, "Constant application of unary [+] on type of %s is unsupported", docname(v.type));break; - } + left_int = +left_int; + left_float = +left_float; }break; - default: invalid_codepath; + invalid_default_case; + } + // case TYPE_UINT: parsing_error(pos, "Application of unary [-] on type %s results in overflow", docname(v.type));break; + // default: parsing_error(pos, "Constant application of unary [-] on type of %s is unsupported", docname(v.type));break; + // default: parsing_error(pos, "Constant application of unary [+] on type of %s is unsupported", docname(v.type));break; + + Value before_conversion; + if(is_int(a.type)){ + before_conversion.type = untyped_int; + before_conversion.int_val = left_int; + } + else{ + assert(is_float(a.type)); + before_conversion.type = untyped_float; + before_conversion.f64_val = left_float; } - return v; + Value result = convert_untyped(pos, before_conversion, a.type); + return result; } #define rewrite_into_const(ast,T,s) _rewrite_into_const(ast,sizeof(T),s) @@ -578,8 +566,9 @@ resolve_expr(Ast_Expr *ast, Ast_Resolved_Type *expected_type, Sym *lambda_to_res Operand op = resolve_expr(node->expr); if(!is_numeric(op.type)) parsing_error(node->pos, "Unary [-] cant be applied to value of type %s", docname(op.type)); if(op.is_const){ - rewrite_into_const(node, Ast_Unary, eval_unary(node->pos, node->op, op.value)); - return operand_const_rvalue(op.value); + Value value = eval_unary(node->pos, node->op, op.value); + rewrite_into_const(node, Ast_Unary, value); + return operand_const_rvalue(value); } return operand_rvalue(op.value.type); }break; @@ -587,8 +576,10 @@ resolve_expr(Ast_Expr *ast, Ast_Resolved_Type *expected_type, Sym *lambda_to_res Operand op = resolve_expr(node->expr); if(!is_numeric(op.type)) parsing_error(node->pos, "Unary [+] cant be applied to value of type %s", docname(op.type)); if(op.is_const){ - rewrite_into_const(node, Ast_Unary, eval_unary(node->pos, node->op, op.value)); - return operand_const_rvalue(op.value); + Value value = eval_unary(node->pos, node->op, op.value); + rewrite_into_const(node, Ast_Unary, value); + return operand_const_rvalue(value); + } return operand_rvalue(op.type); }break;