| ... | @@ -788,8 +788,10 @@ static LLVMValueRef gen_fn_call_expr(CodeGen *g, AstNode *node) { | ... | @@ -788,8 +788,10 @@ static LLVMValueRef gen_fn_call_expr(CodeGen *g, AstNode *node) { |
| 788 | | 788 | |
| 789 | TypeTableEntry *src_return_type = fn_type->data.fn.fn_type_id.return_type; | 789 | TypeTableEntry *src_return_type = fn_type->data.fn.fn_type_id.return_type; |
| 790 | | 790 | |
| | 791 | bool ret_has_bits = type_has_bits(src_return_type); |
| | 792 | |
| 791 | int fn_call_param_count = node->data.fn_call_expr.params.length; | 793 | int fn_call_param_count = node->data.fn_call_expr.params.length; |
| 792 | bool first_arg_ret = handle_is_ptr(src_return_type); | 794 | bool first_arg_ret = ret_has_bits && handle_is_ptr(src_return_type); |
| 793 | int actual_param_count = fn_call_param_count + (struct_type ? 1 : 0) + (first_arg_ret ? 1 : 0); | 795 | int actual_param_count = fn_call_param_count + (struct_type ? 1 : 0) + (first_arg_ret ? 1 : 0); |
| 794 | bool is_var_args = fn_type->data.fn.fn_type_id.is_var_args; | 796 | bool is_var_args = fn_type->data.fn.fn_type_id.is_var_args; |
| 795 | | 797 | |
| ... | @@ -824,10 +826,10 @@ static LLVMValueRef gen_fn_call_expr(CodeGen *g, AstNode *node) { | ... | @@ -824,10 +826,10 @@ static LLVMValueRef gen_fn_call_expr(CodeGen *g, AstNode *node) { |
| 824 | | 826 | |
| 825 | if (src_return_type->id == TypeTableEntryIdUnreachable) { | 827 | if (src_return_type->id == TypeTableEntryIdUnreachable) { |
| 826 | return LLVMBuildUnreachable(g->builder); | 828 | return LLVMBuildUnreachable(g->builder); |
| | 829 | } else if (!ret_has_bits) { |
| | 830 | return nullptr; |
| 827 | } else if (first_arg_ret) { | 831 | } else if (first_arg_ret) { |
| 828 | return node->data.fn_call_expr.tmp_ptr; | 832 | return node->data.fn_call_expr.tmp_ptr; |
| 829 | } else if (!type_has_bits(src_return_type)) { | | |
| 830 | return nullptr; | | |
| 831 | } else { | 833 | } else { |
| 832 | return result; | 834 | return result; |
| 833 | } | 835 | } |
| ... | @@ -1568,6 +1570,9 @@ static LLVMValueRef gen_assign_raw(CodeGen *g, AstNode *source_node, BinOpType b | ... | @@ -1568,6 +1570,9 @@ static LLVMValueRef gen_assign_raw(CodeGen *g, AstNode *source_node, BinOpType b |
| 1568 | LLVMValueRef target_ref, LLVMValueRef value, | 1570 | LLVMValueRef target_ref, LLVMValueRef value, |
| 1569 | TypeTableEntry *op1_type, TypeTableEntry *op2_type) | 1571 | TypeTableEntry *op1_type, TypeTableEntry *op2_type) |
| 1570 | { | 1572 | { |
| | 1573 | if (!type_has_bits(op1_type)) { |
| | 1574 | return nullptr; |
| | 1575 | } |
| 1571 | if (handle_is_ptr(op1_type)) { | 1576 | if (handle_is_ptr(op1_type)) { |
| 1572 | assert(op1_type == op2_type); | 1577 | assert(op1_type == op2_type); |
| 1573 | assert(bin_op == BinOpTypeAssign); | 1578 | assert(bin_op == BinOpTypeAssign); |
| ... | @@ -1584,7 +1589,8 @@ static LLVMValueRef gen_assign_raw(CodeGen *g, AstNode *source_node, BinOpType b | ... | @@ -1584,7 +1589,8 @@ static LLVMValueRef gen_assign_raw(CodeGen *g, AstNode *source_node, BinOpType b |
| 1584 | } | 1589 | } |
| 1585 | | 1590 | |
| 1586 | add_debug_source_node(g, source_node); | 1591 | add_debug_source_node(g, source_node); |
| 1587 | return LLVMBuildStore(g->builder, value, target_ref); | 1592 | LLVMBuildStore(g->builder, value, target_ref); |
| | 1593 | return nullptr; |
| 1588 | } | 1594 | } |
| 1589 | | 1595 | |
| 1590 | static LLVMValueRef gen_assign_expr(CodeGen *g, AstNode *node) { | 1596 | static LLVMValueRef gen_assign_expr(CodeGen *g, AstNode *node) { |
| ... | @@ -1600,11 +1606,8 @@ static LLVMValueRef gen_assign_expr(CodeGen *g, AstNode *node) { | ... | @@ -1600,11 +1606,8 @@ static LLVMValueRef gen_assign_expr(CodeGen *g, AstNode *node) { |
| 1600 | | 1606 | |
| 1601 | LLVMValueRef value = gen_expr(g, node->data.bin_op_expr.op2); | 1607 | LLVMValueRef value = gen_expr(g, node->data.bin_op_expr.op2); |
| 1602 | | 1608 | |
| 1603 | if (!type_has_bits(op1_type)) { | 1609 | gen_assign_raw(g, node, node->data.bin_op_expr.bin_op, target_ref, value, op1_type, op2_type); |
| 1604 | return nullptr; | 1610 | return nullptr; |
| 1605 | } | | |
| 1606 | | | |
| 1607 | return gen_assign_raw(g, node, node->data.bin_op_expr.bin_op, target_ref, value, op1_type, op2_type); | | |
| 1608 | } | 1611 | } |
| 1609 | | 1612 | |
| 1610 | static LLVMValueRef gen_unwrap_maybe(CodeGen *g, AstNode *node, LLVMValueRef maybe_struct_ref) { | 1613 | static LLVMValueRef gen_unwrap_maybe(CodeGen *g, AstNode *node, LLVMValueRef maybe_struct_ref) { |
| ... | @@ -1846,11 +1849,12 @@ static LLVMValueRef gen_return(CodeGen *g, AstNode *source_node, LLVMValueRef va | ... | @@ -1846,11 +1849,12 @@ static LLVMValueRef gen_return(CodeGen *g, AstNode *source_node, LLVMValueRef va |
| 1846 | assert(g->cur_ret_ptr); | 1849 | assert(g->cur_ret_ptr); |
| 1847 | gen_assign_raw(g, source_node, BinOpTypeAssign, g->cur_ret_ptr, value, return_type, return_type); | 1850 | gen_assign_raw(g, source_node, BinOpTypeAssign, g->cur_ret_ptr, value, return_type, return_type); |
| 1848 | add_debug_source_node(g, source_node); | 1851 | add_debug_source_node(g, source_node); |
| 1849 | return LLVMBuildRetVoid(g->builder); | 1852 | LLVMBuildRetVoid(g->builder); |
| 1850 | } else { | 1853 | } else { |
| 1851 | add_debug_source_node(g, source_node); | 1854 | add_debug_source_node(g, source_node); |
| 1852 | return LLVMBuildRet(g->builder, value); | 1855 | LLVMBuildRet(g->builder, value); |
| 1853 | } | 1856 | } |
| | 1857 | return nullptr; |
| 1854 | } | 1858 | } |
| 1855 | | 1859 | |
| 1856 | static LLVMValueRef gen_return_expr(CodeGen *g, AstNode *node) { | 1860 | static LLVMValueRef gen_return_expr(CodeGen *g, AstNode *node) { |