| ... | ... | @@ -6206,7 +6206,9 @@ static bool const_val_fits_in_num_lit(ConstExprValue *const_val, TypeTableEntry |
| 6206 | 6206 | (const_val->type->id == TypeTableEntryIdInt || const_val->type->id == TypeTableEntryIdNumLitInt))); |
| 6207 | 6207 | } |
| 6208 | 6208 | |
| 6209 | | static bool ir_num_lit_fits_in_other_type(IrAnalyze *ira, IrInstruction *instruction, TypeTableEntry *other_type) { |
| 6209 | static bool ir_num_lit_fits_in_other_type(IrAnalyze *ira, IrInstruction *instruction, TypeTableEntry *other_type, |
| 6210 | bool explicit_cast) |
| 6211 | { |
| 6210 | 6212 | if (type_is_invalid(other_type)) { |
| 6211 | 6213 | return false; |
| 6212 | 6214 | } |
| ... | ... | @@ -6243,6 +6245,32 @@ static bool ir_num_lit_fits_in_other_type(IrAnalyze *ira, IrInstruction *instruc |
| 6243 | 6245 | return true; |
| 6244 | 6246 | } |
| 6245 | 6247 | } |
| 6248 | if (explicit_cast && (other_type->id == TypeTableEntryIdInt || other_type->id == TypeTableEntryIdNumLitInt) && |
| 6249 | const_val_is_float) |
| 6250 | { |
| 6251 | if (bigfloat_has_fraction(&const_val->data.x_bigfloat)) { |
| 6252 | Buf *val_buf = buf_alloc(); |
| 6253 | bigfloat_write_buf(val_buf, &const_val->data.x_bigfloat); |
| 6254 | |
| 6255 | ir_add_error(ira, instruction, |
| 6256 | buf_sprintf("fractional component prevents float value %s from being casted to type '%s'", |
| 6257 | buf_ptr(val_buf), |
| 6258 | buf_ptr(&other_type->name))); |
| 6259 | return false; |
| 6260 | } else { |
| 6261 | BigInt bigint; |
| 6262 | bigint_init_bigfloat(&bigint, &const_val->data.x_bigfloat); |
| 6263 | if (other_type->id == TypeTableEntryIdNumLitInt) { |
| 6264 | return true; |
| 6265 | } else { |
| 6266 | if (bigint_fits_in_bits(&bigint, other_type->data.integral.bit_count, |
| 6267 | other_type->data.integral.is_signed)) |
| 6268 | { |
| 6269 | return true; |
| 6270 | } |
| 6271 | } |
| 6272 | } |
| 6273 | } |
| 6246 | 6274 | |
| 6247 | 6275 | const char *num_lit_str; |
| 6248 | 6276 | Buf *val_buf = buf_alloc(); |
| ... | ... | @@ -6425,12 +6453,12 @@ static ImplicitCastMatchResult ir_types_match_with_implicit_cast(IrAnalyze *ira, |
| 6425 | 6453 | if (expected_type->id == TypeTableEntryIdPointer && |
| 6426 | 6454 | expected_type->data.pointer.is_const) |
| 6427 | 6455 | { |
| 6428 | | if (ir_num_lit_fits_in_other_type(ira, value, expected_type->data.pointer.child_type)) { |
| 6456 | if (ir_num_lit_fits_in_other_type(ira, value, expected_type->data.pointer.child_type, false)) { |
| 6429 | 6457 | return ImplicitCastMatchResultYes; |
| 6430 | 6458 | } else { |
| 6431 | 6459 | return ImplicitCastMatchResultReportedError; |
| 6432 | 6460 | } |
| 6433 | | } else if (ir_num_lit_fits_in_other_type(ira, value, expected_type)) { |
| 6461 | } else if (ir_num_lit_fits_in_other_type(ira, value, expected_type, false)) { |
| 6434 | 6462 | return ImplicitCastMatchResultYes; |
| 6435 | 6463 | } else { |
| 6436 | 6464 | return ImplicitCastMatchResultReportedError; |
| ... | ... | @@ -6542,7 +6570,7 @@ static TypeTableEntry *ir_resolve_peer_types(IrAnalyze *ira, AstNode *source_nod |
| 6542 | 6570 | } else if (prev_type->id == TypeTableEntryIdNumLitInt || |
| 6543 | 6571 | prev_type->id == TypeTableEntryIdNumLitFloat) |
| 6544 | 6572 | { |
| 6545 | | if (ir_num_lit_fits_in_other_type(ira, prev_inst, cur_type)) { |
| 6573 | if (ir_num_lit_fits_in_other_type(ira, prev_inst, cur_type, false)) { |
| 6546 | 6574 | prev_inst = cur_inst; |
| 6547 | 6575 | continue; |
| 6548 | 6576 | } else { |
| ... | ... | @@ -6551,7 +6579,7 @@ static TypeTableEntry *ir_resolve_peer_types(IrAnalyze *ira, AstNode *source_nod |
| 6551 | 6579 | } else if (cur_type->id == TypeTableEntryIdNumLitInt || |
| 6552 | 6580 | cur_type->id == TypeTableEntryIdNumLitFloat) |
| 6553 | 6581 | { |
| 6554 | | if (ir_num_lit_fits_in_other_type(ira, cur_inst, prev_type)) { |
| 6582 | if (ir_num_lit_fits_in_other_type(ira, cur_inst, prev_type, false)) { |
| 6555 | 6583 | continue; |
| 6556 | 6584 | } else { |
| 6557 | 6585 | return ira->codegen->builtin_types.entry_invalid; |
| ... | ... | @@ -7636,7 +7664,7 @@ static IrInstruction *ir_analyze_cast(IrAnalyze *ira, IrInstruction *source_inst |
| 7636 | 7664 | } else if (actual_type->id == TypeTableEntryIdNumLitInt || |
| 7637 | 7665 | actual_type->id == TypeTableEntryIdNumLitFloat) |
| 7638 | 7666 | { |
| 7639 | | if (ir_num_lit_fits_in_other_type(ira, value, wanted_type->data.maybe.child_type)) { |
| 7667 | if (ir_num_lit_fits_in_other_type(ira, value, wanted_type->data.maybe.child_type, true)) { |
| 7640 | 7668 | return ir_analyze_maybe_wrap(ira, source_instr, value, wanted_type); |
| 7641 | 7669 | } else { |
| 7642 | 7670 | return ira->codegen->invalid_instruction; |
| ... | ... | @@ -7658,7 +7686,7 @@ static IrInstruction *ir_analyze_cast(IrAnalyze *ira, IrInstruction *source_inst |
| 7658 | 7686 | } else if (actual_type->id == TypeTableEntryIdNumLitInt || |
| 7659 | 7687 | actual_type->id == TypeTableEntryIdNumLitFloat) |
| 7660 | 7688 | { |
| 7661 | | if (ir_num_lit_fits_in_other_type(ira, value, wanted_type->data.error.child_type)) { |
| 7689 | if (ir_num_lit_fits_in_other_type(ira, value, wanted_type->data.error.child_type, true)) { |
| 7662 | 7690 | return ir_analyze_err_wrap_payload(ira, source_instr, value, wanted_type); |
| 7663 | 7691 | } else { |
| 7664 | 7692 | return ira->codegen->invalid_instruction; |
| ... | ... | @@ -7736,7 +7764,7 @@ static IrInstruction *ir_analyze_cast(IrAnalyze *ira, IrInstruction *source_inst |
| 7736 | 7764 | return ira->codegen->invalid_instruction; |
| 7737 | 7765 | |
| 7738 | 7766 | return cast2; |
| 7739 | | } else if (ir_num_lit_fits_in_other_type(ira, value, wanted_type)) { |
| 7767 | } else if (ir_num_lit_fits_in_other_type(ira, value, wanted_type, true)) { |
| 7740 | 7768 | CastOp op; |
| 7741 | 7769 | if ((actual_type->id == TypeTableEntryIdNumLitFloat && |
| 7742 | 7770 | wanted_type->id == TypeTableEntryIdFloat) || |
| ... | ... | @@ -8630,7 +8658,7 @@ static TypeTableEntry *ir_analyze_bin_op_math(IrAnalyze *ira, IrInstructionBinOp |
| 8630 | 8658 | return ira->codegen->builtin_types.entry_invalid; |
| 8631 | 8659 | } |
| 8632 | 8660 | |
| 8633 | | ir_num_lit_fits_in_other_type(ira, &bin_op_instruction->base, resolved_type); |
| 8661 | ir_num_lit_fits_in_other_type(ira, &bin_op_instruction->base, resolved_type, false); |
| 8634 | 8662 | return resolved_type; |
| 8635 | 8663 | } |
| 8636 | 8664 | |