diff --git a/lib/std/core/builtin.c3 b/lib/std/core/builtin.c3 index 36df39607..6868c8877 100644 --- a/lib/std/core/builtin.c3 +++ b/lib/std/core/builtin.c3 @@ -44,12 +44,13 @@ macro void @scope(&variable; @body) @builtin /** * Swap two variables + * @checked *a = *b, *b = *a **/ macro void @swap(&a, &b) @builtin { - var temp = a; - a = b; - b = temp; + var temp = *a; + *a = *b; + *b = temp; } /** diff --git a/lib/std/core/mem.c3 b/lib/std/core/mem.c3 index ec00764db..e04839b9b 100644 --- a/lib/std/core/mem.c3 +++ b/lib/std/core/mem.c3 @@ -9,12 +9,15 @@ const DEFAULT_MEM_ALIGNMENT = (void*.alignof) * 2; macro @volatile_load(&x) @builtin { - return $$volatile_load(&x); + return $$volatile_load(x); } +/** + * @checked *x == y : "The value doesn't match the variable" + **/ macro @volatile_store(&x, y) @builtin { - return $$volatile_store(&x, ($typeof(x))y); + return $$volatile_store(x, ($typeof(*x))y); } enum AtomicOrdering : int @@ -37,10 +40,11 @@ enum AtomicOrdering : int * @require $ordering != AtomicOrdering.RELEASE "Release ordering is not valid for load." * @require $ordering != AtomicOrdering.ACQUIRE_RELEASE "Acquire release is not valid for load." * @require types::may_load_atomic($typeof(x)) "Only integer, float and pointers may be used." + * @require @typekind(x) == POINTER "You can only load from a pointer" **/ macro @atomic_load(&x, AtomicOrdering $ordering = SEQ_CONSISTENT, $volatile = false) @builtin { - return $$atomic_load(&x, $volatile, (int)$ordering); + return $$atomic_load(x, $volatile, (int)$ordering); } /** @@ -55,7 +59,7 @@ macro @atomic_load(&x, AtomicOrdering $ordering = SEQ_CONSISTENT, $volatile = fa **/ macro void @atomic_store(&x, value, AtomicOrdering $ordering = SEQ_CONSISTENT, $volatile = false) @builtin { - $$atomic_store(&x, value, $volatile, (int)$ordering); + $$atomic_store(x, value, $volatile, (int)$ordering); } macro compare_exchange(ptr, compare, value, AtomicOrdering $success = SEQ_CONSISTENT, AtomicOrdering $failure = SEQ_CONSISTENT, bool $volatile = true, bool $weak = false, usz $alignment = 0) diff --git a/lib/std/core/mem_allocator.c3 b/lib/std/core/mem_allocator.c3 index 2cf5c08a6..e8386ae85 100644 --- a/lib/std/core/mem_allocator.c3 +++ b/lib/std/core/mem_allocator.c3 @@ -64,7 +64,7 @@ fault AllocationFailure macro void*! Allocator.alloc(&allocator, usz size) { - return allocator.function(&allocator, size, 0, 0, null, ALLOC); + return allocator.function(allocator, size, 0, 0, null, ALLOC); } /** @@ -72,12 +72,12 @@ macro void*! Allocator.alloc(&allocator, usz size) */ macro void*! Allocator.alloc_aligned(&allocator, usz size, usz alignment, usz offset = 0) { - return allocator.function(&allocator, size, alignment, offset, null, ALIGNED_ALLOC); + return allocator.function(allocator, size, alignment, offset, null, ALIGNED_ALLOC); } macro void*! Allocator.realloc(&allocator, void* old_pointer, usz size) { - return allocator.function(&allocator, size, 0, 0, old_pointer, REALLOC); + return allocator.function(allocator, size, 0, 0, old_pointer, REALLOC); } /** @@ -85,18 +85,18 @@ macro void*! Allocator.realloc(&allocator, void* old_pointer, usz size) */ macro void*! Allocator.realloc_aligned(&allocator, void* old_pointer, usz size, usz alignment, usz offset = 0) { - return allocator.function(&allocator, size, alignment, offset, old_pointer, ALIGNED_REALLOC); + return allocator.function(allocator, size, alignment, offset, old_pointer, ALIGNED_REALLOC); } macro usz Allocator.mark(&allocator) { - return (usz)(uptr)allocator.function(&allocator, 0, 0, 0, null, MARK) ?? 0; + return (usz)(uptr)allocator.function(allocator, 0, 0, 0, null, MARK) ?? 0; } macro void*! Allocator.calloc(&allocator, usz size) { - return allocator.function(&allocator, size, 0, 0, null, CALLOC); + return allocator.function(allocator, size, 0, 0, null, CALLOC); } /** @@ -104,22 +104,22 @@ macro void*! Allocator.calloc(&allocator, usz size) */ macro void*! Allocator.calloc_aligned(&allocator, usz size, usz alignment, usz offset = 0) { - return allocator.function(&allocator, size, alignment, offset, null, ALIGNED_CALLOC); + return allocator.function(allocator, size, alignment, offset, null, ALIGNED_CALLOC); } macro void! Allocator.free(&allocator, void* old_pointer) { - allocator.function(&allocator, 0, 0, 0, old_pointer, FREE)!; + allocator.function(allocator, 0, 0, 0, old_pointer, FREE)!; } macro void! Allocator.free_aligned(&allocator, void* old_pointer) { - allocator.function(&allocator, 0, 0, 0, old_pointer, ALIGNED_FREE)!; + allocator.function(allocator, 0, 0, 0, old_pointer, ALIGNED_FREE)!; } macro void Allocator.reset(&allocator, usz mark = 0) { - (void)allocator.function(&allocator, mark, 0, 0, null, RESET); + (void)allocator.function(allocator, mark, 0, 0, null, RESET); } fn usz alignment_for_allocation(usz alignment) @inline @private diff --git a/lib/std/hash/fnv32a.c3 b/lib/std/hash/fnv32a.c3 index f200180f0..8e853ec4b 100644 --- a/lib/std/hash/fnv32a.c3 +++ b/lib/std/hash/fnv32a.c3 @@ -8,7 +8,7 @@ def Fnv32a = distinct uint; const FNV32A_START @private = 0x811c9dc5; const FNV32A_MUL @private = 0x01000193; -macro void @update(uint &h, char x) @private => h = (h * FNV32A_MUL) ^ x; +macro void @update(uint* &h, char x) @private => *h = (*h * FNV32A_MUL) ^ x; fn void Fnv32a.init(&self) { diff --git a/lib/std/hash/fnv64a.c3 b/lib/std/hash/fnv64a.c3 index 40207b6dc..c27924688 100644 --- a/lib/std/hash/fnv64a.c3 +++ b/lib/std/hash/fnv64a.c3 @@ -8,7 +8,7 @@ def Fnv64a = distinct ulong; const FNV64A_START @private = 0xcbf29ce484222325; const FNV64A_MUL @private = 0x00000100000001b3; -macro void @update(ulong &h, char x) @private => h = (h * FNV64A_MUL) ^ x; +macro void @update(ulong* &h, char x) @private => *h = (*h * FNV64A_MUL) ^ x; fn void Fnv64a.init(&self) { diff --git a/lib/std/hash/sha1.c3 b/lib/std/hash/sha1.c3 index 1e5332d39..433b2e199 100644 --- a/lib/std/hash/sha1.c3 +++ b/lib/std/hash/sha1.c3 @@ -103,34 +103,39 @@ macro @blk0(&block, i) @local $endif } -macro @r0(&block, v, &w, x, y, &z, i) @local +macro @r0(&block, v, &wref, x, y, &z, i) @local { - z += ((w & (x ^ y)) ^ y) + @blk0(block, i) + 0x5A827999 + v.rotl(5); - w = w.rotl(30); + var w = *wref; + *z += ((w & (x ^ y)) ^ y) + @blk0(*block, i) + 0x5A827999 + v.rotl(5); + *wref = w.rotl(30); } -macro @r1(&block, v, &w, x, y, &z, i) @local +macro @r1(&block, v, &wref, x, y, &z, i) @local { - z += ((w & (x ^ y)) ^ y) + @blk(block, i) + 0x5A827999 + v.rotl(5); - w = w.rotl(30); + var w = *wref; + *z += ((w & (x ^ y)) ^ y) + @blk(*block, i) + 0x5A827999 + v.rotl(5); + *wref = w.rotl(30); } -macro @r2(&block, v, &w, x, y, &z, i) @local +macro @r2(&block, v, &wref, x, y, &z, i) @local { - z += (w ^ x ^ y) + @blk(block, i) + 0x6ED9EBA1 + v.rotl(5); - w = w.rotl(30); + var w = *wref; + *z += (w ^ x ^ y) + @blk(*block, i) + 0x6ED9EBA1 + v.rotl(5); + *wref = w.rotl(30); } -macro @r3(&block, v, &w, x, y, &z, i) @local +macro @r3(&block, v, &wref, x, y, &z, i) @local { - z += (((w | x) &y) | (w & x)) + @blk(block, i) + 0x8F1BBCDC + v.rotl(5); - w = w.rotl(30); + var w = *wref; + *z += (((w | x) & y) | (w & x)) + @blk(*block, i) + 0x8F1BBCDC + v.rotl(5); + *wref = w.rotl(30); } -macro @r4(&block, v, &w, x, y, &z, i) @local +macro @r4(&block, v, &wref, x, y, &z, i) @local { - z += (w ^ x ^ y) + @blk(block, i) + 0xCA62C1D6 + v.rotl(5); - w = w.rotl(30); + var w = *wref; + *z += (w ^ x ^ y) + @blk(*block, i) + 0xCA62C1D6 + v.rotl(5); + *wref = w.rotl(30); } /** diff --git a/lib/std/io/io_printf.c3 b/lib/std/io/io_printf.c3 index 8867efb6b..063f48ccd 100644 --- a/lib/std/io/io_printf.c3 +++ b/lib/std/io/io_printf.c3 @@ -121,7 +121,7 @@ macro bool! Formatter.print_with_function(&self, any arg) self.width = old_width; self.prec = old_prec; } - arg.to_format(&self)!; + arg.to_format(self)!; return true; } if (&arg.to_string) diff --git a/lib/std/math/math_vector.c3 b/lib/std/math/math_vector.c3 index 7e0c3fe64..cac87c541 100644 --- a/lib/std/math/math_vector.c3 +++ b/lib/std/math/math_vector.c3 @@ -9,10 +9,10 @@ def Vec2 = double[<2>]; def Vec3 = double[<3>]; def Vec4 = double[<4>]; -macro Vec2f.length_sq(&self) => self.dot(self); -macro Vec3f.length_sq(&self) => self.dot(self); -macro Vec4f.length_sq(&self) => self.dot(self); -macro Vec2.length_sq(&self) => self.dot(self); +macro Vec2f.length_sq(self) => self.dot(self); +macro Vec3f.length_sq(self) => self.dot(self); +macro Vec4f.length_sq(self) => self.dot(self); +macro Vec2.length_sq(self) => self.dot(self); macro Vec3.length_sq(self) => self.dot(self); macro Vec4.length_sq(self) => self.dot(self); diff --git a/releasenotes.md b/releasenotes.md index 381499cad..fe6bfc20e 100644 --- a/releasenotes.md +++ b/releasenotes.md @@ -6,6 +6,7 @@ - Exhaustive switches with enums has better analysis. - Globals may now be initialized with optional values. - New generic syntax. +- Macro ref parameters are now of pointer type and ref parameters are not assignable. - Added `nextcase default`. - Added `$embed` to embed binary data. - Ad hoc generics are now allowed. @@ -46,6 +47,7 @@ - Addition of `@local` for file local visibility. - Addition of `@public` for overriding default visibility. - Default visibility can be overridden per module compile unit. Eg `module foo @private`. +- Optimized macro codegen for -O0. - Addition of unary `+`. - Remove the `:` and `;` used in $if, $switch etc. - Faults have an ordinal. @@ -144,6 +146,9 @@ - Added posix socket functions. ### Fixes +- Fixes missing checks to body arguments. +- Do not create debug declaration for value-only parameter. +- Bug in alignment for atomics. - Fix to bug when comparing nested arrays. - Fix to bug when a macro is using rethrow. - Fixes bug initializing a const struct with a const struct value. diff --git a/resources/examples/swap.c3 b/resources/examples/swap.c3 index 54366aaca..1d304fbf5 100644 --- a/resources/examples/swap.c3 +++ b/resources/examples/swap.c3 @@ -2,13 +2,13 @@ module test; import libc; /** - * @checked a = b, b = a + * @checked *a = *b, *b = *a */ macro void @swap(&a, &b) { - $typeof(a) temp = a; - a = b; - b = temp; + var temp = *a; + *a = *b; + *b = temp; } fn void main() diff --git a/src/compiler/compiler_internal.h b/src/compiler/compiler_internal.h index af7be401e..9267be9e7 100644 --- a/src/compiler/compiler_internal.h +++ b/src/compiler/compiler_internal.h @@ -676,7 +676,11 @@ typedef struct Decl_ void *tb_symbol; }; AlignSize alignment; - const char *section; + union + { + const char *section; + ExprId varef_id; + }; AlignSize offset : 32; AlignSize padding : 32; /* bool is_exported : 1; @@ -2974,6 +2978,24 @@ INLINE bool expr_is_deref(Expr *expr) return expr->expr_kind == EXPR_UNARY && expr->unary_expr.operator == UNARYOP_DEREF; } +INLINE bool expr_is_addr(Expr *expr) +{ + return expr->expr_kind == EXPR_UNARY && expr->unary_expr.operator == UNARYOP_ADDR; +} + +INLINE bool expr_is_any_addr(Expr *expr) +{ + if (expr->expr_kind != EXPR_UNARY) return false; + switch (expr->unary_expr.operator) + { + case UNARYOP_ADDR: + case UNARYOP_TADDR: + return true; + default: + return false; + } +} + INLINE bool expr_is_mult(Expr *expr) { return expr->expr_kind == EXPR_BINARY && expr->binary_expr.operator == BINARYOP_MULT; diff --git a/src/compiler/llvm_codegen.c b/src/compiler/llvm_codegen.c index 3256ce0b5..88626ec73 100644 --- a/src/compiler/llvm_codegen.c +++ b/src/compiler/llvm_codegen.c @@ -325,8 +325,8 @@ void llvm_emit_ptr_from_array(GenContext *c, BEValue *value) switch (value->type->type_kind) { case TYPE_POINTER: - llvm_value_rvalue(c, value); - value->kind = BE_ADDRESS; + llvm_value_rvalue(c, value); + value->kind = BE_ADDRESS; return; case TYPE_ARRAY: case TYPE_VECTOR: @@ -585,6 +585,7 @@ void llvm_emit_and_set_decl_alloca(GenContext *c, Decl *decl) { Type *type = type_lowering(decl->type); if (type == type_void) return; + assert(!decl->backend_ref && !decl->is_value); decl->backend_ref = llvm_emit_alloca(c, llvm_get_type(c, type), decl->alignment, decl->name ? decl->name : ".anon"); } @@ -1023,6 +1024,7 @@ void llvm_append_function_attributes(GenContext *c, Decl *decl) } LLVMValueRef llvm_get_ref(GenContext *c, Decl *decl) { + assert(!decl->is_value); LLVMValueRef backend_ref = decl->backend_ref; if (backend_ref) { diff --git a/src/compiler/llvm_codegen_builtins.c b/src/compiler/llvm_codegen_builtins.c index ed655b677..f60b0cb4e 100644 --- a/src/compiler/llvm_codegen_builtins.c +++ b/src/compiler/llvm_codegen_builtins.c @@ -140,8 +140,7 @@ INLINE void llvm_emit_volatile_store(GenContext *c, BEValue *result_value, Expr BEValue value; llvm_emit_expr(c, &value, expr->call_expr.arguments[0]); llvm_emit_expr(c, result_value, expr->call_expr.arguments[1]); - llvm_value_rvalue(c, &value); - value.kind = BE_ADDRESS; + llvm_value_deref(c, &value); BEValue store_value = *result_value; LLVMValueRef store = llvm_store(c, &value, &store_value); if (store) LLVMSetVolatile(store, true); @@ -150,9 +149,7 @@ INLINE void llvm_emit_volatile_store(GenContext *c, BEValue *result_value, Expr INLINE void llvm_emit_volatile_load(GenContext *c, BEValue *result_value, Expr *expr) { llvm_emit_expr(c, result_value, expr->call_expr.arguments[0]); - llvm_value_rvalue(c, result_value); - result_value->kind = BE_ADDRESS; - result_value->type = type_lowering(result_value->type->pointer); + llvm_value_deref(c, result_value); llvm_value_rvalue(c, result_value); LLVMSetVolatile(result_value->value, true); } @@ -162,8 +159,7 @@ INLINE void llvm_emit_atomic_store(GenContext *c, BEValue *result_value, Expr *e BEValue value; llvm_emit_expr(c, &value, expr->call_expr.arguments[0]); llvm_emit_expr(c, result_value, expr->call_expr.arguments[1]); - llvm_value_rvalue(c, &value); - value.kind = BE_ADDRESS; + llvm_value_deref(c, &value); BEValue store_value = *result_value; LLVMValueRef store = llvm_store(c, &value, &store_value); if (store) @@ -176,9 +172,7 @@ INLINE void llvm_emit_atomic_store(GenContext *c, BEValue *result_value, Expr *e INLINE void llvm_emit_atomic_load(GenContext *c, BEValue *result_value, Expr *expr) { llvm_emit_expr(c, result_value, expr->call_expr.arguments[0]); - llvm_value_rvalue(c, result_value); - result_value->kind = BE_ADDRESS; - result_value->type = type_lowering(result_value->type->pointer); + llvm_value_deref(c, result_value); llvm_value_rvalue(c, result_value); if (expr->call_expr.arguments[1]->const_expr.b) LLVMSetVolatile(result_value->value, true); LLVMSetOrdering(result_value->value, llvm_atomic_ordering(expr->call_expr.arguments[2]->const_expr.ixx.i.low)); diff --git a/src/compiler/llvm_codegen_debug_info.c b/src/compiler/llvm_codegen_debug_info.c index 2759423e0..ea9c7f7c2 100644 --- a/src/compiler/llvm_codegen_debug_info.c +++ b/src/compiler/llvm_codegen_debug_info.c @@ -161,6 +161,7 @@ void llvm_emit_debug_local_var(GenContext *c, Decl *decl) decl->var.backend_debug_ref = var; LLVMMetadataRef inline_at = NULL; + assert(!decl->is_value); LLVMDIBuilderInsertDeclareAtEnd(c->debug.builder, decl->backend_ref, var, LLVMDIBuilderCreateExpression(c->debug.builder, NULL, 0), @@ -186,7 +187,7 @@ void llvm_emit_debug_parameter(GenContext *c, Decl *parameter, unsigned index) unsigned col = parameter->span.col; if (col == 0) col = 1; - parameter->var.backend_debug_ref = LLVMDIBuilderCreateParameterVariable( + parameter->var.backend_debug_ref = LLVMDIBuilderCreateParameterVariable( c->debug.builder, c->debug.function, name, @@ -199,8 +200,9 @@ void llvm_emit_debug_parameter(GenContext *c, Decl *parameter, unsigned index) LLVMDIFlagZero); LLVMMetadataRef inline_at = NULL; + if (parameter->is_value) return; LLVMDIBuilderInsertDeclareAtEnd(c->debug.builder, - parameter->backend_ref, + parameter->is_value ? NULL : parameter->backend_ref, parameter->var.backend_debug_ref, LLVMDIBuilderCreateExpression(c->debug.builder, NULL, 0), LLVMDIBuilderCreateDebugLocation(c->context, row, col, c->debug.function, diff --git a/src/compiler/llvm_codegen_expr.c b/src/compiler/llvm_codegen_expr.c index 81c874b63..749ce53ef 100644 --- a/src/compiler/llvm_codegen_expr.c +++ b/src/compiler/llvm_codegen_expr.c @@ -26,7 +26,7 @@ static inline void llvm_emit_initialize_reference_bitstruct(GenContext *c, BEVal static inline void llvm_emit_initialize_reference_list(GenContext *c, BEValue *ref, Expr *expr); static inline void llvm_emit_initialize_reference_vector(GenContext *c, BEValue *ref, Type *real_type, Expr **elements); static inline void llvm_emit_initializer_list_expr(GenContext *c, BEValue *value, Expr *expr); -static inline void llvm_emit_macro_block(GenContext *context, BEValue *be_value, Expr *expr); +static inline void llvm_emit_macro_block(GenContext *c, BEValue *be_value, Expr *expr); static inline void llvm_emit_post_inc_dec(GenContext *c, BEValue *value, Expr *expr, int diff); static inline void llvm_emit_pre_inc_dec(GenContext *c, BEValue *value, Expr *expr, int diff); static inline void llvm_emit_return_block(GenContext *c, BEValue *be_value, Type *type, AstId current, BlockExit **block_exit); @@ -2471,6 +2471,21 @@ static inline void llvm_emit_pre_inc_dec(GenContext *c, BEValue *value, Expr *ex static inline void llvm_emit_deref(GenContext *c, BEValue *value, Expr *inner, Type *type) { + if (inner->expr_kind == EXPR_UNARY) + { + switch (inner->unary_expr.operator) + { + case UNARYOP_ADDR: + llvm_emit_expr(c, value, inner->unary_expr.expr); + return; + case UNARYOP_TADDR: + llvm_emit_expr(c, value, inner->unary_expr.expr); + llvm_value_addr(c, value); + return; + default: + break; + } + } llvm_emit_expr(c, value, inner); llvm_value_rvalue(c, value); if (active_target.feature.safe_mode) @@ -2482,8 +2497,6 @@ static inline void llvm_emit_deref(GenContext *c, BEValue *value, Expr *inner, T scratch_buffer_append("' was null."); llvm_emit_panic_on_true(c, check, scratch_buffer_to_string(), inner->span, NULL, NULL, NULL); } - // Load the pointer value. - llvm_value_rvalue(c, value); // Convert pointer to address value->kind = BE_ADDRESS; value->type = type; @@ -5894,7 +5907,7 @@ static inline void llvm_emit_expr_block(GenContext *context, BEValue *be_value, llvm_emit_return_block(context, be_value, expr->type, expr->expr_block.first_stmt, expr->expr_block.block_exit_ref); } -static inline void llvm_emit_macro_block(GenContext *context, BEValue *be_value, Expr *expr) +static inline void llvm_emit_macro_block(GenContext *c, BEValue *be_value, Expr *expr) { FOREACH_BEGIN(Decl *val, expr->macro_block.params) // Skip vararg @@ -5913,39 +5926,40 @@ static inline void llvm_emit_macro_block(GenContext *context, BEValue *be_value, case VARDECL_ERASE: case VARDECL_BITMEMBER: UNREACHABLE - case VARDECL_PARAM_REF: - { - BEValue addr; - llvm_emit_expr(context, &addr, val->var.init_expr); - val->backend_ref = addr.value; - continue; - } case VARDECL_PARAM_CT: case VARDECL_PARAM_CT_TYPE: case VARDECL_PARAM_EXPR: continue; + case VARDECL_PARAM_REF: case VARDECL_PARAM: break; } - llvm_emit_and_set_decl_alloca(context, val); - BEValue value; - llvm_emit_expr(context, &value, val->var.init_expr); - llvm_store_decl(context, val, &value); + Expr *init_expr = val->var.init_expr; + BEValue value; + llvm_emit_expr(c, &value, init_expr); + if (type_is_abi_aggregate(value.type) || llvm_value_is_addr(&value) || val->var.is_written || val->var.is_addr) + { + llvm_emit_and_set_decl_alloca(c, val); + llvm_store_decl(c, val, &value); + continue; + } + val->is_value = true; + val->backend_value = value.value; FOREACH_END(); - if (llvm_use_debug(context)) + if (llvm_use_debug(c)) { - llvm_debug_push_lexical_scope(context, astptr(expr->macro_block.first_stmt)->span); + llvm_debug_push_lexical_scope(c, astptr(expr->macro_block.first_stmt)->span); } - llvm_emit_return_block(context, be_value, expr->type, expr->macro_block.first_stmt, expr->macro_block.block_exit); - if (expr->macro_block.is_noreturn && context->current_block && context->current_block_is_target) + llvm_emit_return_block(c, be_value, expr->type, expr->macro_block.first_stmt, expr->macro_block.block_exit); + if (expr->macro_block.is_noreturn && c->current_block && c->current_block_is_target) { - llvm_emit_unreachable(context); + llvm_emit_unreachable(c); } - if (llvm_use_debug(context)) + if (llvm_use_debug(c)) { - llvm_debug_scope_pop(context); + llvm_debug_scope_pop(c); } } diff --git a/src/compiler/llvm_codegen_internal.h b/src/compiler/llvm_codegen_internal.h index a0b56fe6e..ccb94fbaa 100644 --- a/src/compiler/llvm_codegen_internal.h +++ b/src/compiler/llvm_codegen_internal.h @@ -285,6 +285,7 @@ static inline bool llvm_value_is_addr(BEValue *value) { return value->kind == BE static inline bool llvm_value_is_bool(BEValue *value) { return value->kind == BE_BOOLEAN; } bool llvm_value_is_const(BEValue *value); void llvm_value_rvalue(GenContext *context, BEValue *value); +void llvm_value_deref(GenContext *c, BEValue *value); void llvm_value_set(BEValue *value, LLVMValueRef llvm_value, Type *type); void llvm_value_set_int(GenContext *c, BEValue *value, Type *type, uint64_t i); void llvm_value_set_address(BEValue *value, LLVMValueRef llvm_value, Type *type, AlignSize alignment); diff --git a/src/compiler/llvm_codegen_value.c b/src/compiler/llvm_codegen_value.c index d95efd806..c3d67b795 100644 --- a/src/compiler/llvm_codegen_value.c +++ b/src/compiler/llvm_codegen_value.c @@ -1,5 +1,13 @@ #include "llvm_codegen_internal.h" +void llvm_value_deref(GenContext *c, BEValue *value) +{ + llvm_value_rvalue(c, value); + value->kind = BE_ADDRESS; + Type *type = value->type = type_lowering(type_get_indexed_type(value->type)); + value->alignment = type_abi_alignment(type); +} + void llvm_value_set(BEValue *value, LLVMValueRef llvm_value, Type *type) { type = type_lowering(type); @@ -151,6 +159,7 @@ void llvm_value_fold_optional(GenContext *c, BEValue *value) void llvm_value_set_decl_address(GenContext *c, BEValue *value, Decl *decl) { + assert(!decl->is_value); LLVMValueRef backend_ref = llvm_get_ref(c, decl); llvm_value_set_address(value, backend_ref, decl->type, decl->alignment); diff --git a/src/compiler/sema_decls.c b/src/compiler/sema_decls.c index b0e153b8b..857fef03b 100644 --- a/src/compiler/sema_decls.c +++ b/src/compiler/sema_decls.c @@ -734,7 +734,6 @@ static inline bool sema_analyse_signature(SemaContext *context, Signature *sig, return false; } SEMA_ERROR(params[MAX_PARAMS], "The number of params exceeded the max of %d. To accept more arguments, consider using varargs.", MAX_PARAMS); - return false; } // Fill in the type if the first parameter is lacking a type. @@ -747,13 +746,9 @@ static inline bool sema_analyse_signature(SemaContext *context, Signature *sig, switch (param->var.kind) { case VARDECL_PARAM_REF: - if (!is_macro) - { - inferred_type = type_get_ptr(method_parent->type); - param->var.kind = VARDECL_PARAM; - break; - } - FALLTHROUGH; + inferred_type = type_get_ptr(method_parent->type); + if (!is_macro) param->var.kind = VARDECL_PARAM; + break; case VARDECL_PARAM: inferred_type = method_parent->type; break; @@ -797,10 +792,22 @@ static inline bool sema_analyse_signature(SemaContext *context, Signature *sig, param->unit = context->unit; assert(param->decl_kind == DECL_VAR); VarDeclKind var_kind = param->var.kind; + if (param->var.type_info) + { + if (!sema_resolve_type_info_maybe_inferred(context, param->var.type_info, is_macro)) return decl_poison(param); + param->type = param->var.type_info->type; + } switch (var_kind) { - case VARDECL_PARAM_EXPR: case VARDECL_PARAM_REF: + if (param->var.type_info && !type_is_pointer(param->type)) + { + SEMA_ERROR(param->var.type_info, "A pointer type was expected for a ref argument, did you mean %s?", + type_quoted_error_string(type_get_ptr(param->type))); + return decl_poison(param); + } + FALLTHROUGH; + case VARDECL_PARAM_EXPR: if (!is_macro) { SEMA_ERROR(param, "Only regular parameters are allowed for functions."); @@ -808,7 +815,6 @@ static inline bool sema_analyse_signature(SemaContext *context, Signature *sig, } if (!is_macro_at_name && (!type_parent || i != 0 || var_kind != VARDECL_PARAM_REF)) { - SEMA_ERROR(param, "Ref and expression parameters are not allowed in function-like macros. Prefix the macro name with '@'."); return decl_poison(param); } @@ -821,29 +827,23 @@ static inline bool sema_analyse_signature(SemaContext *context, Signature *sig, } FALLTHROUGH; case VARDECL_PARAM: - if (param->var.type_info) + if (!param->type && !is_macro) { - if (!sema_resolve_type_info_maybe_inferred(context, param->var.type_info, is_macro)) return decl_poison(param); - param->type = param->var.type_info->type; - } - else if (!is_macro) - { - SEMA_ERROR(param, "Only typed parameters are allowed for functions."); - return false; + RETURN_SEMA_ERROR(param, "Only typed parameters are allowed for functions."); } bool erase_decl = false; if (!sema_analyse_attributes_for_var(context, param, &erase_decl)) return false; assert(!erase_decl); break; case VARDECL_PARAM_CT_TYPE: - if (!is_macro) + if (param->var.type_info) { - SEMA_ERROR(param, "Only regular parameters are allowed for functions."); + SEMA_ERROR(param->var.type_info, "A compile time type parameter cannot have a type itself."); return decl_poison(param); } - if (param->var.type_info) + if (!is_macro) { - SEMA_ERROR(param->var.type_info, "A compile time type parameter cannot have a type itself."); + SEMA_ERROR(param, "Only regular parameters are allowed for functions."); return decl_poison(param); } break; diff --git a/src/compiler/sema_expr.c b/src/compiler/sema_expr.c index 97089df64..3d57d293f 100644 --- a/src/compiler/sema_expr.c +++ b/src/compiler/sema_expr.c @@ -414,12 +414,14 @@ static bool sema_binary_is_expr_lvalue(Expr *top_expr, Expr *expr) decl = decl_raw(decl); switch (decl->var.kind) { + case VARDECL_PARAM_REF: + SEMA_ERROR(top_expr, "You cannot assign to a ref parameter."); + return false; case VARDECL_LOCAL_CT: case VARDECL_LOCAL_CT_TYPE: case VARDECL_LOCAL: case VARDECL_GLOBAL: case VARDECL_PARAM: - case VARDECL_PARAM_REF: case VARDECL_PARAM_CT: case VARDECL_PARAM_CT_TYPE: return true; @@ -543,10 +545,10 @@ static bool expr_may_ref(Expr *expr) case VARDECL_LOCAL: case VARDECL_GLOBAL: case VARDECL_PARAM: - case VARDECL_PARAM_REF: case VARDECL_PARAM_CT: case VARDECL_PARAM_CT_TYPE: return true; + case VARDECL_PARAM_REF: case VARDECL_CONST: case VARDECL_PARAM_EXPR: case VARDECL_MEMBER: @@ -740,12 +742,6 @@ static inline bool sema_cast_ident_rvalue(SemaContext *context, Expr *expr) // Impossible to reach this, they are already unfolded UNREACHABLE case VARDECL_PARAM_REF: - expr_replace(expr, copy_expr_single(decl->var.init_expr)); - if (expr->expr_kind == EXPR_IDENTIFIER) - { - expr->identifier_expr.was_ref = true; - } - return sema_cast_rvalue(context, expr); case VARDECL_PARAM: case VARDECL_GLOBAL: case VARDECL_LOCAL: @@ -1537,6 +1533,7 @@ static inline bool sema_call_analyse_invocation(SemaContext *context, Expr *call // &foo if (!sema_analyse_expr_lvalue(context, arg)) return false; if (!sema_expr_check_assign(context, arg)) return false; + expr_insert_addr(arg); *optional |= IS_OPTIONAL(arg); if (!sema_call_check_contract_param_match(context, param, arg)) return false; if (type_is_invalid_storage_type(type) || type == type_void) @@ -1549,7 +1546,7 @@ static inline bool sema_call_analyse_invocation(SemaContext *context, Expr *call SEMA_ERROR(arg, "'%s' cannot be implicitly cast to '%s'.", type_to_error_string(arg->type), type_to_error_string(type)); return false; } - if (param && !param->alignment) + if (!param->alignment) { if (arg->expr_kind == EXPR_IDENTIFIER) { @@ -2100,17 +2097,17 @@ static bool sema_call_analyse_body_expansion(SemaContext *macro_context, Expr *c } Expr **args = call_expr->arguments; + Decl **params = macro_context->yield_params; // Evaluate the expressions. TODO hash expressions for (unsigned i = 0; i < expressions; i++) { Expr *expr = args[i]; - if (!sema_analyse_expr(macro_context, expr)) return false; + if (!sema_analyse_expr_rhs(macro_context, params[i]->type, expr, false)) return false; } AstId macro_defer = macro_context->active_scope.defer_last; Ast *first_defer = NULL; SemaContext *context = macro_context->yield_context; - Decl **params = macro_context->yield_params; Expr *func_expr = exprptr(call_expr->function); assert(func_expr->expr_kind == EXPR_MACRO_BODY_EXPANSION); expr_replace(call, func_expr); @@ -2212,6 +2209,13 @@ static inline bool sema_expr_analyse_call(SemaContext *context, Expr *expr) switch (decl->decl_kind) { case DECL_MACRO: + struct_var = func_expr->access_expr.parent; + if (decl->func_decl.signature.params[0]->var.kind == VARDECL_PARAM_REF) break; + if (decl->func_decl.signature.params[0]->type->type_kind == TYPE_POINTER) + { + expr_insert_addr(struct_var); + } + break; case DECL_FUNC: struct_var = func_expr->access_expr.parent; if (decl->func_decl.signature.params[0]->type->type_kind == TYPE_POINTER) @@ -5582,8 +5586,9 @@ static inline const char *sema_addr_may_take_of_var(Expr *expr, Decl *decl) case VARDECL_LOCAL: if (is_void) return "You cannot take the address of a variable of type 'void'"; return NULL; - case VARDECL_PARAM: case VARDECL_PARAM_REF: + return "You may not take the address of a ref parameter"; + case VARDECL_PARAM: if (is_void) return "You cannot take the address of a parameter of type 'void'"; return NULL; case VARDECL_CONST: @@ -5694,11 +5699,7 @@ static inline bool sema_expr_analyse_addr(SemaContext *context, Expr *expr) { Expr *parent = inner->access_expr.parent; if (parent->expr_kind == EXPR_TYPEINFO) break; - Expr *parent_copy = expr_copy(parent); - parent->expr_kind = EXPR_UNARY; - parent->unary_expr = (ExprUnary){ .expr = parent_copy, .operator = UNARYOP_ADDR }; - if (!sema_analyse_expr_lvalue_fold_const(context, parent)) return false; - expr_rewrite_insert_deref(parent); + if (!sema_analyse_expr_lvalue_fold_const(context, parent)) return false; break; } default: @@ -7343,22 +7344,25 @@ static inline bool sema_expr_analyse_ct_arg(SemaContext *context, Expr *expr) if (!sema_binary_is_expr_lvalue(arg_expr, arg_expr)) return false; + ExprId va_ref_id = exprid(arg_expr); Decl *decl = NULL; // Try to find the original param. FOREACH_BEGIN(Decl *val, context->macro_params) if (!val) continue; - if (val->var.init_expr == arg_expr) + if (val->var.kind == VARDECL_PARAM_REF && val->varef_id == va_ref_id) { decl = val; - decl->var.kind = VARDECL_PARAM_REF; break; } FOREACH_END(); // Not found, so generate a new. if (!decl) { - decl = decl_new_generated_var(arg_expr->type, VARDECL_PARAM_REF, arg_expr->span); - decl->var.init_expr = arg_expr; + arg_expr = copy_expr_single(arg_expr); + expr_insert_addr(arg_expr); + decl = decl_new_generated_var(arg_expr->type, VARDECL_PARAM_REF, arg_expr->span); + decl->var.init_expr = arg_expr; + decl->varef_id = va_ref_id; vec_add(context->macro_params, decl); } // Replace with the identifier. @@ -8038,6 +8042,11 @@ bool sema_insert_method_call(SemaContext *context, Expr *method_call, Decl *meth Decl *first_param = method_decl->func_decl.signature.params[0]; Type *first = first_param->type; // Deref / addr as needed. + if (first_param->var.kind == VARDECL_PARAM_REF) + { + assert(first->type_kind == TYPE_POINTER); + first = first->pointer; + } if (type != first) { if (first->type_kind == TYPE_POINTER && first->pointer == type) diff --git a/src/compiler/sema_liveness.c b/src/compiler/sema_liveness.c index 3a181e15d..11106d042 100644 --- a/src/compiler/sema_liveness.c +++ b/src/compiler/sema_liveness.c @@ -398,8 +398,16 @@ static void sema_trace_expr_liveness(Expr *expr) return; } case EXPR_MACRO_BODY_EXPANSION: + { + FOREACH_BEGIN(Decl *arg, expr->body_expansion_expr.declarations) + sema_trace_decl_liveness(arg); + FOREACH_END(); + FOREACH_BEGIN(Expr *arg, expr->body_expansion_expr.values) + sema_trace_expr_liveness(arg); + FOREACH_END(); sema_trace_stmt_liveness(astptrzero(expr->body_expansion_expr.first_stmt)); return; + } case EXPR_NOP: return; case EXPR_POINTER_OFFSET: diff --git a/src/version.h b/src/version.h index b460084a7..b43b05c05 100644 --- a/src/version.h +++ b/src/version.h @@ -1 +1 @@ -#define COMPILER_VERSION "0.4.566" \ No newline at end of file +#define COMPILER_VERSION "0.4.567" \ No newline at end of file diff --git a/test/test_suite/builtins/prefetch.c3t b/test/test_suite/builtins/prefetch.c3t index 24bac0177..b2efdfc42 100644 --- a/test/test_suite/builtins/prefetch.c3t +++ b/test/test_suite/builtins/prefetch.c3t @@ -13,10 +13,7 @@ fn void main() /* #expect: test.ll %a = alloca i32, align 4 - %ptr = alloca ptr, align 8 store i32 0, ptr %a, align 4 call void @llvm.prefetch.p0(ptr %a, i32 1, i32 3, i32 1) call void @llvm.prefetch.p0(ptr %a, i32 0, i32 1, i32 1) - store ptr %a, ptr %ptr, align 8 - %0 = load ptr, ptr %ptr, align 8 - call void @llvm.prefetch.p0(ptr %0, i32 0, i32 3, i32 1) + call void @llvm.prefetch.p0(ptr %a, i32 0, i32 3, i32 1) diff --git a/test/test_suite/cast/implicit_infer_len_cast.c3t b/test/test_suite/cast/implicit_infer_len_cast.c3t index e8614113e..c2d3a651e 100644 --- a/test/test_suite/cast/implicit_infer_len_cast.c3t +++ b/test/test_suite/cast/implicit_infer_len_cast.c3t @@ -26,8 +26,7 @@ fn void main() %literal = alloca [1 x <2 x i32>], align 8 %bb = alloca [1 x %"int[]"], align 16 %literal1 = alloca [2 x i32], align 4 - %y2 = alloca ptr, align 8 - %z3 = alloca [2 x [2 x i32]], align 16 + %z2 = alloca [2 x [2 x i32]], align 16 call void @llvm.memcpy.p0.p0.i32(ptr align 16 %x, ptr align 16 @.__const, i32 16, i1 false) call void @llvm.memcpy.p0.p0.i32(ptr align 8 %y, ptr align 8 @.__const.1, i32 8, i1 false) call void @llvm.memcpy.p0.p0.i32(ptr align 8 %z, ptr align 8 %y, i32 8, i1 false) @@ -48,9 +47,7 @@ fn void main() %8 = insertvalue %"int[]" undef, ptr %literal1, 0 %9 = insertvalue %"int[]" %8, i64 2, 1 store %"int[]" %9, ptr %5, align 16 - store ptr %x, ptr %y2, align 8 - %10 = load ptr, ptr %y2, align 8 - call void @llvm.memcpy.p0.p0.i32(ptr align 16 %z3, ptr align 4 %10, i32 16, i1 false) - %11 = getelementptr inbounds [2 x [2 x i32]], ptr %z3, i64 0, i64 1 - %12 = getelementptr inbounds [2 x i32], ptr %11, i64 0, i64 1 + call void @llvm.memcpy.p0.p0.i32(ptr align 16 %z2, ptr align 4 %x, i32 16, i1 false) + %10 = getelementptr inbounds [2 x [2 x i32]], ptr %z2, i64 0, i64 1 + %11 = getelementptr inbounds [2 x i32], ptr %10, i64 0, i64 1 ret void diff --git a/test/test_suite/concurrency/atomic_load_store.c3t b/test/test_suite/concurrency/atomic_load_store.c3t index 0d4015b50..8f684099c 100644 --- a/test/test_suite/concurrency/atomic_load_store.c3t +++ b/test/test_suite/concurrency/atomic_load_store.c3t @@ -20,7 +20,28 @@ fn void main() /* #expect: test.ll +define void @test.main() #0 { +entry: + %a = alloca i32, align 4 + %x = alloca i32, align 4 + %y = alloca i32, align 4 + %retparam = alloca i64, align 8 + %varargslots = alloca [1 x %any], align 16 + store i32 111, ptr %a, align 4 %0 = load atomic i32, ptr %a seq_cst, align 4 + store i32 %0, ptr %x, align 4 %1 = load atomic volatile i32, ptr %a monotonic, align 4 - store atomic i32 %3, ptr %a seq_cst, align 4 - store atomic volatile i32 %5, ptr %a monotonic, align 4 + store i32 %1, ptr %y, align 4 + %2 = load i32, ptr %x, align 4 + %add = add i32 123, %2 + store atomic i32 %add, ptr %a seq_cst, align 4 + %3 = load i32, ptr %y, align 4 + %add1 = add i32 33, %3 + store atomic volatile i32 %add1, ptr %a monotonic, align 4 + %4 = insertvalue %any undef, ptr %a, 0 + %5 = insertvalue %any %4, i64 ptrtoint (ptr @"$ct.int" to i64), 1 + %6 = getelementptr inbounds [1 x %any], ptr %varargslots, i64 0, i64 0 + store %any %5, ptr %6, align 16 + %7 = call i64 @std.io.printfn(ptr %retparam, ptr @.str, i64 2, ptr %varargslots, i64 1) + ret void +} diff --git a/test/test_suite/defer/defer_static_var.c3t b/test/test_suite/defer/defer_static_var.c3t index 8328429da..50f15e5bb 100644 --- a/test/test_suite/defer/defer_static_var.c3t +++ b/test/test_suite/defer/defer_static_var.c3t @@ -51,7 +51,6 @@ define i32 @foo.foo(i32 %0) #0 { entry: %gt = icmp sgt i32 %0, 0 br i1 %gt, label %if.then, label %if.exit - if.then: ; preds = %entry %1 = load i32, ptr @foo.y, align 4 %add = add i32 %1, 1 @@ -59,7 +58,6 @@ if.then: ; preds = %entry %2 = load i32, ptr @foo.y, align 4 call void (ptr, ...) @printf(ptr @.str, i32 %2) ret i32 2 - if.exit: ; preds = %entry %3 = load i32, ptr @foo.y, align 4 %add1 = add i32 %3, 1 @@ -68,137 +66,110 @@ if.exit: ; preds = %entry call void (ptr, ...) @printf(ptr @.str.1, i32 %4) ret i32 %0 } - +; Function Attrs: nounwind define void @foo.main() #0 { entry: - %x = alloca i32, align 4 %i = alloca i32, align 4 - %x3 = alloca i32, align 4 - %i4 = alloca i32, align 4 - %x15 = alloca i32, align 4 - %i16 = alloca i32, align 4 + %i3 = alloca i32, align 4 + %i14 = alloca i32, align 4 %0 = call i32 @foo.foo(i32 1) %1 = call i32 @foo.foo(i32 2) %2 = call i32 @foo.foo(i32 -2) - store i32 0, ptr %x, align 4 - %3 = load i32, ptr %x, align 4 - call void (ptr, ...) @printf(ptr @.str.2, i32 %3) + call void (ptr, ...) @printf(ptr @.str.2, i32 0) store i32 0, ptr %i, align 4 br label %loop.cond - loop.cond: ; preds = %if.exit, %entry - %4 = load i32, ptr %i, align 4 - %lt = icmp slt i32 %4, 100 + %3 = load i32, ptr %i, align 4 + %lt = icmp slt i32 %3, 100 br i1 %lt, label %loop.body, label %loop.exit - loop.body: ; preds = %loop.cond - %5 = load i32, ptr %i, align 4 - %6 = load i32, ptr %x, align 4 - %eq = icmp eq i32 %5, %6 + %4 = load i32, ptr %i, align 4 + %eq = icmp eq i32 %4, 0 br i1 %eq, label %if.then, label %if.exit - if.then: ; preds = %loop.body - %7 = load i32, ptr @main.y, align 4 - %add = add i32 %7, 1 + %5 = load i32, ptr @main.y, align 4 + %add = add i32 %5, 1 store i32 %add, ptr @main.y, align 4 - %8 = load i32, ptr %i, align 4 - %9 = load i32, ptr @main.y, align 4 - call void (ptr, ...) @printf(ptr @.str.3, i32 %8, i32 %9) + %6 = load i32, ptr %i, align 4 + %7 = load i32, ptr @main.y, align 4 + call void (ptr, ...) @printf(ptr @.str.3, i32 %6, i32 %7) br label %loop.exit - if.exit: ; preds = %loop.body call void (ptr, ...) @printf(ptr @.str.4) - %10 = load i32, ptr @main.y, align 4 - %add1 = add i32 %10, 1 + %8 = load i32, ptr @main.y, align 4 + %add1 = add i32 %8, 1 store i32 %add1, ptr @main.y, align 4 + %9 = load i32, ptr %i, align 4 + %10 = load i32, ptr @main.y, align 4 + call void (ptr, ...) @printf(ptr @.str.5, i32 %9, i32 %10) %11 = load i32, ptr %i, align 4 - %12 = load i32, ptr @main.y, align 4 - call void (ptr, ...) @printf(ptr @.str.5, i32 %11, i32 %12) - %13 = load i32, ptr %i, align 4 - %add2 = add i32 %13, 1 + %add2 = add i32 %11, 1 store i32 %add2, ptr %i, align 4 br label %loop.cond - loop.exit: ; preds = %if.then, %loop.cond - store i32 1, ptr %x3, align 4 - %14 = load i32, ptr %x3, align 4 - call void (ptr, ...) @printf(ptr @.str.6, i32 %14) - store i32 0, ptr %i4, align 4 - br label %loop.cond5 - -loop.cond5: ; preds = %if.exit11, %loop.exit - %15 = load i32, ptr %i4, align 4 - %lt6 = icmp slt i32 %15, 100 - br i1 %lt6, label %loop.body7, label %loop.exit14 - -loop.body7: ; preds = %loop.cond5 - %16 = load i32, ptr %i4, align 4 - %17 = load i32, ptr %x3, align 4 - %eq8 = icmp eq i32 %16, %17 - br i1 %eq8, label %if.then9, label %if.exit11 - -if.then9: ; preds = %loop.body7 - %18 = load i32, ptr @main.y.7, align 4 - %add10 = add i32 %18, 1 - store i32 %add10, ptr @main.y.7, align 4 - %19 = load i32, ptr %i4, align 4 - %20 = load i32, ptr @main.y.7, align 4 - call void (ptr, ...) @printf(ptr @.str.8, i32 %19, i32 %20) - br label %loop.exit14 - -if.exit11: ; preds = %loop.body7 + call void (ptr, ...) @printf(ptr @.str.6, i32 1) + store i32 0, ptr %i3, align 4 + br label %loop.cond4 +loop.cond4: ; preds = %if.exit10, %loop.exit + %12 = load i32, ptr %i3, align 4 + %lt5 = icmp slt i32 %12, 100 + br i1 %lt5, label %loop.body6, label %loop.exit13 +loop.body6: ; preds = %loop.cond4 + %13 = load i32, ptr %i3, align 4 + %eq7 = icmp eq i32 %13, 1 + br i1 %eq7, label %if.then8, label %if.exit10 +if.then8: ; preds = %loop.body6 + %14 = load i32, ptr @main.y.7, align 4 + %add9 = add i32 %14, 1 + store i32 %add9, ptr @main.y.7, align 4 + %15 = load i32, ptr %i3, align 4 + %16 = load i32, ptr @main.y.7, align 4 + call void (ptr, ...) @printf(ptr @.str.8, i32 %15, i32 %16) + br label %loop.exit13 +if.exit10: ; preds = %loop.body6 call void (ptr, ...) @printf(ptr @.str.9) - %21 = load i32, ptr @main.y.7, align 4 - %add12 = add i32 %21, 1 - store i32 %add12, ptr @main.y.7, align 4 - %22 = load i32, ptr %i4, align 4 - %23 = load i32, ptr @main.y.7, align 4 - call void (ptr, ...) @printf(ptr @.str.10, i32 %22, i32 %23) - %24 = load i32, ptr %i4, align 4 - %add13 = add i32 %24, 1 - store i32 %add13, ptr %i4, align 4 - br label %loop.cond5 - -loop.exit14: ; preds = %if.then9, %loop.cond5 - store i32 2, ptr %x15, align 4 - %25 = load i32, ptr %x15, align 4 - call void (ptr, ...) @printf(ptr @.str.11, i32 %25) - store i32 0, ptr %i16, align 4 - br label %loop.cond17 - -loop.cond17: ; preds = %if.exit23, %loop.exit14 - %26 = load i32, ptr %i16, align 4 - %lt18 = icmp slt i32 %26, 100 - br i1 %lt18, label %loop.body19, label %loop.exit26 - -loop.body19: ; preds = %loop.cond17 - %27 = load i32, ptr %i16, align 4 - %28 = load i32, ptr %x15, align 4 - %eq20 = icmp eq i32 %27, %28 - br i1 %eq20, label %if.then21, label %if.exit23 - -if.then21: ; preds = %loop.body19 - %29 = load i32, ptr @main.y.12, align 4 - %add22 = add i32 %29, 1 - store i32 %add22, ptr @main.y.12, align 4 - %30 = load i32, ptr %i16, align 4 - %31 = load i32, ptr @main.y.12, align 4 - call void (ptr, ...) @printf(ptr @.str.13, i32 %30, i32 %31) - br label %loop.exit26 - -if.exit23: ; preds = %loop.body19 + %17 = load i32, ptr @main.y.7, align 4 + %add11 = add i32 %17, 1 + store i32 %add11, ptr @main.y.7, align 4 + %18 = load i32, ptr %i3, align 4 + %19 = load i32, ptr @main.y.7, align 4 + call void (ptr, ...) @printf(ptr @.str.10, i32 %18, i32 %19) + %20 = load i32, ptr %i3, align 4 + %add12 = add i32 %20, 1 + store i32 %add12, ptr %i3, align 4 + br label %loop.cond4 +loop.exit13: ; preds = %if.then8, %loop.cond4 + call void (ptr, ...) @printf(ptr @.str.11, i32 2) + store i32 0, ptr %i14, align 4 + br label %loop.cond15 +loop.cond15: ; preds = %if.exit21, %loop.exit13 + %21 = load i32, ptr %i14, align 4 + %lt16 = icmp slt i32 %21, 100 + br i1 %lt16, label %loop.body17, label %loop.exit24 +loop.body17: ; preds = %loop.cond15 + %22 = load i32, ptr %i14, align 4 + %eq18 = icmp eq i32 %22, 2 + br i1 %eq18, label %if.then19, label %if.exit21 +if.then19: ; preds = %loop.body17 + %23 = load i32, ptr @main.y.12, align 4 + %add20 = add i32 %23, 1 + store i32 %add20, ptr @main.y.12, align 4 + %24 = load i32, ptr %i14, align 4 + %25 = load i32, ptr @main.y.12, align 4 + call void (ptr, ...) @printf(ptr @.str.13, i32 %24, i32 %25) + br label %loop.exit24 +if.exit21: ; preds = %loop.body17 call void (ptr, ...) @printf(ptr @.str.14) - %32 = load i32, ptr @main.y.12, align 4 - %add24 = add i32 %32, 1 - store i32 %add24, ptr @main.y.12, align 4 - %33 = load i32, ptr %i16, align 4 - %34 = load i32, ptr @main.y.12, align 4 - call void (ptr, ...) @printf(ptr @.str.15, i32 %33, i32 %34) - %35 = load i32, ptr %i16, align 4 - %add25 = add i32 %35, 1 - store i32 %add25, ptr %i16, align 4 - br label %loop.cond17 - -loop.exit26: ; preds = %if.then21, %loop.cond17 + %26 = load i32, ptr @main.y.12, align 4 + %add22 = add i32 %26, 1 + store i32 %add22, ptr @main.y.12, align 4 + %27 = load i32, ptr %i14, align 4 + %28 = load i32, ptr @main.y.12, align 4 + call void (ptr, ...) @printf(ptr @.str.15, i32 %27, i32 %28) + %29 = load i32, ptr %i14, align 4 + %add23 = add i32 %29, 1 + store i32 %add23, ptr %i14, align 4 + br label %loop.cond15 +loop.exit24: ; preds = %if.then19, %loop.cond15 ret void } \ No newline at end of file diff --git a/test/test_suite/errors/error_regression_2.c3t b/test/test_suite/errors/error_regression_2.c3t index da0981b5a..70356c8e5 100644 --- a/test/test_suite/errors/error_regression_2.c3t +++ b/test/test_suite/errors/error_regression_2.c3t @@ -268,89 +268,71 @@ entry: %reterr8 = alloca i64, align 8 %literal9 = alloca %Doc, align 8 %error_var = alloca i64, align 8 - %value = alloca %Head, align 8 %literal10 = alloca %Head, align 8 + %value = alloca %Head, align 8 %temp = alloca ptr, align 8 %using = alloca ptr, align 8 - %end_padding = alloca i64, align 8 %error_var11 = alloca i64, align 8 %using12 = alloca ptr, align 8 - %end_padding13 = alloca i64, align 8 - %.anon = alloca i64, align 8 - %size = alloca i64, align 8 + %allocator = alloca ptr, align 8 %retparam = alloca ptr, align 8 %varargslots = alloca [1 x %any], align 16 %indirectarg = alloca %"any[]", align 8 - %reterr23 = alloca i64, align 8 - %literal24 = alloca %Doc, align 8 - %error_var25 = alloca i64, align 8 - %value26 = alloca %Head, align 8 - %literal27 = alloca %Head, align 8 - %error_var28 = alloca i64, align 8 - %value29 = alloca %"char[]", align 8 - %temp30 = alloca ptr, align 8 + %reterr22 = alloca i64, align 8 + %literal23 = alloca %Doc, align 8 + %error_var24 = alloca i64, align 8 + %literal25 = alloca %Head, align 8 + %error_var26 = alloca i64, align 8 + %value27 = alloca %"char[]", align 8 + %temp28 = alloca ptr, align 8 + %using29 = alloca ptr, align 8 + %error_var30 = alloca i64, align 8 %using31 = alloca ptr, align 8 - %end_padding32 = alloca i64, align 8 - %error_var33 = alloca i64, align 8 - %using34 = alloca ptr, align 8 - %end_padding35 = alloca i64, align 8 - %.anon36 = alloca i64, align 8 - %size38 = alloca i64, align 8 - %retparam41 = alloca ptr, align 8 - %varargslots46 = alloca [1 x %any], align 16 - %indirectarg47 = alloca %"any[]", align 8 - %temp54 = alloca ptr, align 8 - %using55 = alloca ptr, align 8 - %end_padding56 = alloca i64, align 8 - %error_var57 = alloca i64, align 8 - %using58 = alloca ptr, align 8 - %end_padding59 = alloca i64, align 8 - %.anon60 = alloca i64, align 8 - %size62 = alloca i64, align 8 - %retparam65 = alloca ptr, align 8 - %varargslots70 = alloca [1 x %any], align 16 - %indirectarg71 = alloca %"any[]", align 8 + %allocator33 = alloca ptr, align 8 + %retparam35 = alloca ptr, align 8 + %varargslots40 = alloca [1 x %any], align 16 + %indirectarg41 = alloca %"any[]", align 8 + %value48 = alloca %Head, align 8 + %temp49 = alloca ptr, align 8 + %using50 = alloca ptr, align 8 + %error_var51 = alloca i64, align 8 + %using52 = alloca ptr, align 8 + %allocator54 = alloca ptr, align 8 + %retparam56 = alloca ptr, align 8 + %varargslots61 = alloca [1 x %any], align 16 + %indirectarg62 = alloca %"any[]", align 8 %len = alloca i32, align 4 %str = alloca ptr, align 8 - %using79 = alloca ptr, align 8 - %end_padding80 = alloca i64, align 8 - %error_var81 = alloca i64, align 8 - %using82 = alloca ptr, align 8 - %end_padding83 = alloca i64, align 8 - %.anon84 = alloca i32, align 4 - %size86 = alloca i64, align 8 - %retparam88 = alloca ptr, align 8 - %varargslots93 = alloca [1 x %any], align 16 - %indirectarg94 = alloca %"any[]", align 8 - %reterr102 = alloca i64, align 8 - %literal103 = alloca %Doc, align 8 - %error_var104 = alloca i64, align 8 - %value105 = alloca %Head, align 8 - %literal106 = alloca %Head, align 8 - %error_var107 = alloca i64, align 8 - %value108 = alloca %"char[]", align 8 - %temp112 = alloca ptr, align 8 - %using113 = alloca ptr, align 8 - %end_padding114 = alloca i64, align 8 - %error_var115 = alloca i64, align 8 - %using116 = alloca ptr, align 8 - %end_padding117 = alloca i64, align 8 - %.anon118 = alloca i64, align 8 - %size120 = alloca i64, align 8 - %retparam123 = alloca ptr, align 8 - %varargslots128 = alloca [1 x %any], align 16 - %indirectarg129 = alloca %"any[]", align 8 - %temp136 = alloca ptr, align 8 - %using137 = alloca ptr, align 8 - %end_padding138 = alloca i64, align 8 - %error_var139 = alloca i64, align 8 - %using140 = alloca ptr, align 8 - %end_padding141 = alloca i64, align 8 - %.anon142 = alloca i64, align 8 - %size144 = alloca i64, align 8 - %retparam147 = alloca ptr, align 8 - %varargslots152 = alloca [1 x %any], align 16 - %indirectarg153 = alloca %"any[]", align 8 + %using70 = alloca ptr, align 8 + %error_var71 = alloca i64, align 8 + %using72 = alloca ptr, align 8 + %allocator73 = alloca ptr, align 8 + %retparam75 = alloca ptr, align 8 + %varargslots80 = alloca [1 x %any], align 16 + %indirectarg81 = alloca %"any[]", align 8 + %reterr89 = alloca i64, align 8 + %literal90 = alloca %Doc, align 8 + %error_var91 = alloca i64, align 8 + %literal92 = alloca %Head, align 8 + %error_var93 = alloca i64, align 8 + %value96 = alloca %"char[]", align 8 + %temp97 = alloca ptr, align 8 + %using98 = alloca ptr, align 8 + %error_var99 = alloca i64, align 8 + %using100 = alloca ptr, align 8 + %allocator102 = alloca ptr, align 8 + %retparam104 = alloca ptr, align 8 + %varargslots109 = alloca [1 x %any], align 16 + %indirectarg110 = alloca %"any[]", align 8 + %value117 = alloca %Head, align 8 + %temp118 = alloca ptr, align 8 + %using119 = alloca ptr, align 8 + %error_var120 = alloca i64, align 8 + %using121 = alloca ptr, align 8 + %allocator123 = alloca ptr, align 8 + %retparam125 = alloca ptr, align 8 + %varargslots130 = alloca [1 x %any], align 16 + %indirectarg131 = alloca %"any[]", align 8 store ptr %1, ptr %url, align 8 %ptroffset = getelementptr inbounds i64, ptr %url, i64 1 store i64 %2, ptr %ptroffset, align 8 @@ -387,7 +369,7 @@ if.exit4: ; preds = %if.exit %hi6 = load i64, ptr %13, align 8 %14 = call i8 @test.contains(ptr %lo5, i64 %hi6, ptr @.str.4, i64 13) %15 = trunc i8 %14 to i1 - br i1 %15, label %if.then7, label %if.exit19 + br i1 %15, label %if.then7, label %if.exit18 if.then7: ; preds = %if.exit4 %16 = getelementptr inbounds %Doc, ptr %literal9, i32 0, i32 0 @@ -396,421 +378,386 @@ if.then7: ; preds = %if.exit4 call void @llvm.memcpy.p0.p0.i32(ptr align 8 %value, ptr align 8 %literal10, i32 8, i1 false) %18 = load ptr, ptr @std.core.mem.thread_allocator, align 8 store ptr %18, ptr %using, align 8 - store i64 0, ptr %end_padding, align 8 %19 = load ptr, ptr %using, align 8 store ptr %19, ptr %using12, align 8 - %20 = load i64, ptr %end_padding, align 8 - store i64 %20, ptr %end_padding13, align 8 - store i64 8, ptr %.anon, align 8 - %21 = load ptr, ptr %using12, align 8 - %22 = load i64, ptr %.anon, align 8 - %23 = load i64, ptr %end_padding13, align 8 - %add = add i64 %22, %23 - store i64 %add, ptr %size, align 8 - %24 = getelementptr inbounds %Allocator, ptr %21, i32 0, i32 0 - %25 = load ptr, ptr %24, align 8 - %26 = load i64, ptr %size, align 8 - %27 = call i64 %25(ptr %retparam, ptr %21, i64 %26, i64 0, i64 0, ptr null, i32 0) - %not_err = icmp eq i64 %27, 0 - %28 = call i1 @llvm.expect.i1(i1 %not_err, i1 true) - br i1 %28, label %after_check, label %assign_optional + %20 = load ptr, ptr %using12, align 8 + store ptr %20, ptr %allocator, align 8 + %21 = load ptr, ptr %allocator, align 8 + %22 = getelementptr inbounds %Allocator, ptr %21, i32 0, i32 0 + %23 = load ptr, ptr %22, align 8 + %24 = load ptr, ptr %allocator, align 8 + %25 = call i64 %23(ptr %retparam, ptr %24, i64 8, i64 0, i64 0, ptr null, i32 0) + %not_err = icmp eq i64 %25, 0 + %26 = call i1 @llvm.expect.i1(i1 %not_err, i1 true) + br i1 %26, label %after_check, label %assign_optional assign_optional: ; preds = %if.then7 - store i64 %27, ptr %error_var11, align 8 + store i64 %25, ptr %error_var11, align 8 br label %panic_block after_check: ; preds = %if.then7 - %29 = load ptr, ptr %retparam, align 8 + %27 = load ptr, ptr %retparam, align 8 br label %noerr_block panic_block: ; preds = %assign_optional - %30 = insertvalue %any undef, ptr %error_var11, 0 - %31 = insertvalue %any %30, i64 ptrtoint (ptr @"$ct.anyfault" to i64), 1 - %32 = getelementptr inbounds [1 x %any], ptr %varargslots, i64 0, i64 0 - store %any %31, ptr %32, align 16 - %33 = insertvalue %"any[]" undef, ptr %varargslots, 0 - %34 = insertvalue %"any[]" %33, i64 1, 1 - store %"any[]" %34, ptr %indirectarg, align 8 - call void @std.core.builtin.panicf(ptr @.panic_msg, i64 36, ptr @.file, i64 6, ptr @.func, i64 7, i32 200, ptr byval(%"any[]") align 8 %indirectarg) + %28 = insertvalue %any undef, ptr %error_var11, 0 + %29 = insertvalue %any %28, i64 ptrtoint (ptr @"$ct.anyfault" to i64), 1 + %30 = getelementptr inbounds [1 x %any], ptr %varargslots, i64 0, i64 0 + store %any %29, ptr %30, align 16 + %31 = insertvalue %"any[]" undef, ptr %varargslots, 0 + %32 = insertvalue %"any[]" %31, i64 1, 1 + store %"any[]" %32, ptr %indirectarg, align 8 + call void @std.core.builtin.panicf(ptr @.panic_msg, i64 36, ptr @.file, i64 6, ptr @.func, i64 7, i32 204, ptr byval(%"any[]") align 8 %indirectarg) unreachable noerr_block: ; preds = %after_check - store ptr %29, ptr %temp, align 8 - %35 = load ptr, ptr %temp, align 8 - %not = icmp eq ptr %35, null - br i1 %not, label %if.then16, label %if.exit17 + store ptr %27, ptr %temp, align 8 + %33 = load ptr, ptr %temp, align 8 + %not = icmp eq ptr %33, null + br i1 %not, label %if.then15, label %if.exit16 -if.then16: ; preds = %noerr_block +if.then15: ; preds = %noerr_block store i64 ptrtoint (ptr @"test.ReadError$OUT_OF_MEMORY" to i64), ptr %error_var, align 8 br label %guard_block -if.exit17: ; preds = %noerr_block - %36 = load ptr, ptr %temp, align 8 - call void @llvm.memcpy.p0.p0.i32(ptr align 8 %36, ptr align 8 %value, i32 8, i1 false) - br label %noerr_block18 +if.exit16: ; preds = %noerr_block + %34 = load ptr, ptr %temp, align 8 + call void @llvm.memcpy.p0.p0.i32(ptr align 8 %34, ptr align 8 %value, i32 8, i1 false) + br label %noerr_block17 -guard_block: ; preds = %if.then16 - %37 = load i64, ptr %error_var, align 8 - ret i64 %37 +guard_block: ; preds = %if.then15 + %35 = load i64, ptr %error_var, align 8 + ret i64 %35 -noerr_block18: ; preds = %if.exit17 - %38 = load ptr, ptr %temp, align 8 - store ptr %38, ptr %16, align 8 +noerr_block17: ; preds = %if.exit16 + %36 = load ptr, ptr %temp, align 8 + store ptr %36, ptr %16, align 8 call void @llvm.memcpy.p0.p0.i32(ptr align 8 %0, ptr align 8 %literal9, i32 8, i1 false) ret i64 0 -if.exit19: ; preds = %if.exit4 - %39 = getelementptr inbounds %"char[]", ptr %url, i32 0, i32 0 - %lo20 = load ptr, ptr %39, align 8 - %40 = getelementptr inbounds %"char[]", ptr %url, i32 0, i32 1 - %hi21 = load i64, ptr %40, align 8 - %41 = call i8 @test.contains(ptr %lo20, i64 %hi21, ptr @.str.5, i64 11) - %42 = trunc i8 %41 to i1 - br i1 %42, label %if.then22, label %if.exit78 - -if.then22: ; preds = %if.exit19 - %43 = getelementptr inbounds %Doc, ptr %literal24, i32 0, i32 0 - store ptr null, ptr %literal27, align 8 - %44 = getelementptr inbounds %Head, ptr %literal27, i32 0, i32 0 - store %"char[]" zeroinitializer, ptr %value29, align 8 - %45 = load ptr, ptr @std.core.mem.thread_allocator, align 8 - store ptr %45, ptr %using31, align 8 - store i64 0, ptr %end_padding32, align 8 - %46 = load ptr, ptr %using31, align 8 - store ptr %46, ptr %using34, align 8 - %47 = load i64, ptr %end_padding32, align 8 - store i64 %47, ptr %end_padding35, align 8 - store i64 16, ptr %.anon36, align 8 - %48 = load ptr, ptr %using34, align 8 - %49 = load i64, ptr %.anon36, align 8 - %50 = load i64, ptr %end_padding35, align 8 - %add39 = add i64 %49, %50 - store i64 %add39, ptr %size38, align 8 - %51 = getelementptr inbounds %Allocator, ptr %48, i32 0, i32 0 - %52 = load ptr, ptr %51, align 8 - %53 = load i64, ptr %size38, align 8 - %54 = call i64 %52(ptr %retparam41, ptr %48, i64 %53, i64 0, i64 0, ptr null, i32 0) - %not_err42 = icmp eq i64 %54, 0 - %55 = call i1 @llvm.expect.i1(i1 %not_err42, i1 true) - br i1 %55, label %after_check44, label %assign_optional43 - -assign_optional43: ; preds = %if.then22 - store i64 %54, ptr %error_var33, align 8 - br label %panic_block45 - -after_check44: ; preds = %if.then22 - %56 = load ptr, ptr %retparam41, align 8 - br label %noerr_block48 - -panic_block45: ; preds = %assign_optional43 - %57 = insertvalue %any undef, ptr %error_var33, 0 - %58 = insertvalue %any %57, i64 ptrtoint (ptr @"$ct.anyfault" to i64), 1 - %59 = getelementptr inbounds [1 x %any], ptr %varargslots46, i64 0, i64 0 - store %any %58, ptr %59, align 16 - %60 = insertvalue %"any[]" undef, ptr %varargslots46, 0 - %61 = insertvalue %"any[]" %60, i64 1, 1 - store %"any[]" %61, ptr %indirectarg47, align 8 - call void @std.core.builtin.panicf(ptr @.panic_msg, i64 36, ptr @.file, i64 6, ptr @.func, i64 7, i32 200, ptr byval(%"any[]") align 8 %indirectarg47) +if.exit18: ; preds = %if.exit4 + %37 = getelementptr inbounds %"char[]", ptr %url, i32 0, i32 0 + %lo19 = load ptr, ptr %37, align 8 + %38 = getelementptr inbounds %"char[]", ptr %url, i32 0, i32 1 + %hi20 = load i64, ptr %38, align 8 + %39 = call i8 @test.contains(ptr %lo19, i64 %hi20, ptr @.str.5, i64 11) + %40 = trunc i8 %39 to i1 + br i1 %40, label %if.then21, label %if.exit69 + +if.then21: ; preds = %if.exit18 + %41 = getelementptr inbounds %Doc, ptr %literal23, i32 0, i32 0 + store ptr null, ptr %literal25, align 8 + %42 = getelementptr inbounds %Head, ptr %literal25, i32 0, i32 0 + store %"char[]" zeroinitializer, ptr %value27, align 8 + %43 = load ptr, ptr @std.core.mem.thread_allocator, align 8 + store ptr %43, ptr %using29, align 8 + %44 = load ptr, ptr %using29, align 8 + store ptr %44, ptr %using31, align 8 + %45 = load ptr, ptr %using31, align 8 + store ptr %45, ptr %allocator33, align 8 + %46 = load ptr, ptr %allocator33, align 8 + %47 = getelementptr inbounds %Allocator, ptr %46, i32 0, i32 0 + %48 = load ptr, ptr %47, align 8 + %49 = load ptr, ptr %allocator33, align 8 + %50 = call i64 %48(ptr %retparam35, ptr %49, i64 16, i64 0, i64 0, ptr null, i32 0) + %not_err36 = icmp eq i64 %50, 0 + %51 = call i1 @llvm.expect.i1(i1 %not_err36, i1 true) + br i1 %51, label %after_check38, label %assign_optional37 + +assign_optional37: ; preds = %if.then21 + store i64 %50, ptr %error_var30, align 8 + br label %panic_block39 + +after_check38: ; preds = %if.then21 + %52 = load ptr, ptr %retparam35, align 8 + br label %noerr_block42 + +panic_block39: ; preds = %assign_optional37 + %53 = insertvalue %any undef, ptr %error_var30, 0 + %54 = insertvalue %any %53, i64 ptrtoint (ptr @"$ct.anyfault" to i64), 1 + %55 = getelementptr inbounds [1 x %any], ptr %varargslots40, i64 0, i64 0 + store %any %54, ptr %55, align 16 + %56 = insertvalue %"any[]" undef, ptr %varargslots40, 0 + %57 = insertvalue %"any[]" %56, i64 1, 1 + store %"any[]" %57, ptr %indirectarg41, align 8 + call void @std.core.builtin.panicf(ptr @.panic_msg, i64 36, ptr @.file, i64 6, ptr @.func, i64 7, i32 204, ptr byval(%"any[]") align 8 %indirectarg41) unreachable -noerr_block48: ; preds = %after_check44 - store ptr %56, ptr %temp30, align 8 - %62 = load ptr, ptr %temp30, align 8 - %not49 = icmp eq ptr %62, null - br i1 %not49, label %if.then50, label %if.exit51 - -if.then50: ; preds = %noerr_block48 - store i64 ptrtoint (ptr @"test.ReadError$OUT_OF_MEMORY" to i64), ptr %error_var28, align 8 - br label %guard_block52 - -if.exit51: ; preds = %noerr_block48 - %63 = load ptr, ptr %temp30, align 8 - call void @llvm.memcpy.p0.p0.i32(ptr align 8 %63, ptr align 8 %value29, i32 16, i1 false) - br label %noerr_block53 - -guard_block52: ; preds = %if.then50 - %64 = load i64, ptr %error_var28, align 8 - ret i64 %64 - -noerr_block53: ; preds = %if.exit51 - %65 = load ptr, ptr %temp30, align 8 - store ptr %65, ptr %44, align 8 - call void @llvm.memcpy.p0.p0.i32(ptr align 8 %value26, ptr align 8 %literal27, i32 8, i1 false) - %66 = load ptr, ptr @std.core.mem.thread_allocator, align 8 - store ptr %66, ptr %using55, align 8 - store i64 0, ptr %end_padding56, align 8 - %67 = load ptr, ptr %using55, align 8 - store ptr %67, ptr %using58, align 8 - %68 = load i64, ptr %end_padding56, align 8 - store i64 %68, ptr %end_padding59, align 8 - store i64 8, ptr %.anon60, align 8 - %69 = load ptr, ptr %using58, align 8 - %70 = load i64, ptr %.anon60, align 8 - %71 = load i64, ptr %end_padding59, align 8 - %add63 = add i64 %70, %71 - store i64 %add63, ptr %size62, align 8 - %72 = getelementptr inbounds %Allocator, ptr %69, i32 0, i32 0 - %73 = load ptr, ptr %72, align 8 - %74 = load i64, ptr %size62, align 8 - %75 = call i64 %73(ptr %retparam65, ptr %69, i64 %74, i64 0, i64 0, ptr null, i32 0) - %not_err66 = icmp eq i64 %75, 0 - %76 = call i1 @llvm.expect.i1(i1 %not_err66, i1 true) - br i1 %76, label %after_check68, label %assign_optional67 - -assign_optional67: ; preds = %noerr_block53 - store i64 %75, ptr %error_var57, align 8 - br label %panic_block69 - -after_check68: ; preds = %noerr_block53 - %77 = load ptr, ptr %retparam65, align 8 - br label %noerr_block72 - -panic_block69: ; preds = %assign_optional67 - %78 = insertvalue %any undef, ptr %error_var57, 0 - %79 = insertvalue %any %78, i64 ptrtoint (ptr @"$ct.anyfault" to i64), 1 - %80 = getelementptr inbounds [1 x %any], ptr %varargslots70, i64 0, i64 0 - store %any %79, ptr %80, align 16 - %81 = insertvalue %"any[]" undef, ptr %varargslots70, 0 - %82 = insertvalue %"any[]" %81, i64 1, 1 - store %"any[]" %82, ptr %indirectarg71, align 8 - call void @std.core.builtin.panicf(ptr @.panic_msg, i64 36, ptr @.file, i64 6, ptr @.func, i64 7, i32 200, ptr byval(%"any[]") align 8 %indirectarg71) +noerr_block42: ; preds = %after_check38 + store ptr %52, ptr %temp28, align 8 + %58 = load ptr, ptr %temp28, align 8 + %not43 = icmp eq ptr %58, null + br i1 %not43, label %if.then44, label %if.exit45 + +if.then44: ; preds = %noerr_block42 + store i64 ptrtoint (ptr @"test.ReadError$OUT_OF_MEMORY" to i64), ptr %error_var26, align 8 + br label %guard_block46 + +if.exit45: ; preds = %noerr_block42 + %59 = load ptr, ptr %temp28, align 8 + call void @llvm.memcpy.p0.p0.i32(ptr align 8 %59, ptr align 8 %value27, i32 16, i1 false) + br label %noerr_block47 + +guard_block46: ; preds = %if.then44 + %60 = load i64, ptr %error_var26, align 8 + ret i64 %60 + +noerr_block47: ; preds = %if.exit45 + %61 = load ptr, ptr %temp28, align 8 + store ptr %61, ptr %42, align 8 + call void @llvm.memcpy.p0.p0.i32(ptr align 8 %value48, ptr align 8 %literal25, i32 8, i1 false) + %62 = load ptr, ptr @std.core.mem.thread_allocator, align 8 + store ptr %62, ptr %using50, align 8 + %63 = load ptr, ptr %using50, align 8 + store ptr %63, ptr %using52, align 8 + %64 = load ptr, ptr %using52, align 8 + store ptr %64, ptr %allocator54, align 8 + %65 = load ptr, ptr %allocator54, align 8 + %66 = getelementptr inbounds %Allocator, ptr %65, i32 0, i32 0 + %67 = load ptr, ptr %66, align 8 + %68 = load ptr, ptr %allocator54, align 8 + %69 = call i64 %67(ptr %retparam56, ptr %68, i64 8, i64 0, i64 0, ptr null, i32 0) + %not_err57 = icmp eq i64 %69, 0 + %70 = call i1 @llvm.expect.i1(i1 %not_err57, i1 true) + br i1 %70, label %after_check59, label %assign_optional58 + +assign_optional58: ; preds = %noerr_block47 + store i64 %69, ptr %error_var51, align 8 + br label %panic_block60 + +after_check59: ; preds = %noerr_block47 + %71 = load ptr, ptr %retparam56, align 8 + br label %noerr_block63 + +panic_block60: ; preds = %assign_optional58 + %72 = insertvalue %any undef, ptr %error_var51, 0 + %73 = insertvalue %any %72, i64 ptrtoint (ptr @"$ct.anyfault" to i64), 1 + %74 = getelementptr inbounds [1 x %any], ptr %varargslots61, i64 0, i64 0 + store %any %73, ptr %74, align 16 + %75 = insertvalue %"any[]" undef, ptr %varargslots61, 0 + %76 = insertvalue %"any[]" %75, i64 1, 1 + store %"any[]" %76, ptr %indirectarg62, align 8 + call void @std.core.builtin.panicf(ptr @.panic_msg, i64 36, ptr @.file, i64 6, ptr @.func, i64 7, i32 204, ptr byval(%"any[]") align 8 %indirectarg62) unreachable -noerr_block72: ; preds = %after_check68 - store ptr %77, ptr %temp54, align 8 - %83 = load ptr, ptr %temp54, align 8 - %not73 = icmp eq ptr %83, null - br i1 %not73, label %if.then74, label %if.exit75 - -if.then74: ; preds = %noerr_block72 - store i64 ptrtoint (ptr @"test.ReadError$OUT_OF_MEMORY" to i64), ptr %error_var25, align 8 - br label %guard_block76 - -if.exit75: ; preds = %noerr_block72 - %84 = load ptr, ptr %temp54, align 8 - call void @llvm.memcpy.p0.p0.i32(ptr align 8 %84, ptr align 8 %value26, i32 8, i1 false) - br label %noerr_block77 - -guard_block76: ; preds = %if.then74 - %85 = load i64, ptr %error_var25, align 8 - ret i64 %85 - -noerr_block77: ; preds = %if.exit75 - %86 = load ptr, ptr %temp54, align 8 - store ptr %86, ptr %43, align 8 - call void @llvm.memcpy.p0.p0.i32(ptr align 8 %0, ptr align 8 %literal24, i32 8, i1 false) +noerr_block63: ; preds = %after_check59 + store ptr %71, ptr %temp49, align 8 + %77 = load ptr, ptr %temp49, align 8 + %not64 = icmp eq ptr %77, null + br i1 %not64, label %if.then65, label %if.exit66 + +if.then65: ; preds = %noerr_block63 + store i64 ptrtoint (ptr @"test.ReadError$OUT_OF_MEMORY" to i64), ptr %error_var24, align 8 + br label %guard_block67 + +if.exit66: ; preds = %noerr_block63 + %78 = load ptr, ptr %temp49, align 8 + call void @llvm.memcpy.p0.p0.i32(ptr align 8 %78, ptr align 8 %value48, i32 8, i1 false) + br label %noerr_block68 + +guard_block67: ; preds = %if.then65 + %79 = load i64, ptr %error_var24, align 8 + ret i64 %79 + +noerr_block68: ; preds = %if.exit66 + %80 = load ptr, ptr %temp49, align 8 + store ptr %80, ptr %41, align 8 + call void @llvm.memcpy.p0.p0.i32(ptr align 8 %0, ptr align 8 %literal23, i32 8, i1 false) ret i64 0 -if.exit78: ; preds = %if.exit19 - %87 = getelementptr inbounds %"char[]", ptr %url, i32 0, i32 1 - %88 = load i64, ptr %87, align 8 - %trunc = trunc i64 %88 to i32 - %89 = getelementptr inbounds %"char[]", ptr %url, i32 0, i32 0 - %90 = load ptr, ptr %89, align 8 - %91 = call i32 (ptr, i64, ptr, ...) @snprintf(ptr null, i64 0, ptr @.str.6, i32 %trunc, ptr %90) - store i32 %91, ptr %len, align 4 - %92 = load ptr, ptr @std.core.mem.thread_allocator, align 8 - store ptr %92, ptr %using79, align 8 - store i64 0, ptr %end_padding80, align 8 - %93 = load ptr, ptr %using79, align 8 - store ptr %93, ptr %using82, align 8 - %94 = load i64, ptr %end_padding80, align 8 - store i64 %94, ptr %end_padding83, align 8 - %95 = load i32, ptr %len, align 4 - %add85 = add i32 %95, 1 - store i32 %add85, ptr %.anon84, align 4 - %96 = load ptr, ptr %using82, align 8 - %97 = load i32, ptr %.anon84, align 4 - %sext = sext i32 %97 to i64 - %98 = load i64, ptr %end_padding83, align 8 - %add87 = add i64 %sext, %98 - store i64 %add87, ptr %size86, align 8 - %99 = getelementptr inbounds %Allocator, ptr %96, i32 0, i32 0 - %100 = load ptr, ptr %99, align 8 - %101 = load i64, ptr %size86, align 8 - %102 = call i64 %100(ptr %retparam88, ptr %96, i64 %101, i64 0, i64 0, ptr null, i32 0) - %not_err89 = icmp eq i64 %102, 0 - %103 = call i1 @llvm.expect.i1(i1 %not_err89, i1 true) - br i1 %103, label %after_check91, label %assign_optional90 - -assign_optional90: ; preds = %if.exit78 - store i64 %102, ptr %error_var81, align 8 - br label %panic_block92 - -after_check91: ; preds = %if.exit78 - %104 = load ptr, ptr %retparam88, align 8 - br label %noerr_block95 - -panic_block92: ; preds = %assign_optional90 - %105 = insertvalue %any undef, ptr %error_var81, 0 - %106 = insertvalue %any %105, i64 ptrtoint (ptr @"$ct.anyfault" to i64), 1 - %107 = getelementptr inbounds [1 x %any], ptr %varargslots93, i64 0, i64 0 - store %any %106, ptr %107, align 16 - %108 = insertvalue %"any[]" undef, ptr %varargslots93, 0 - %109 = insertvalue %"any[]" %108, i64 1, 1 - store %"any[]" %109, ptr %indirectarg94, align 8 - call void @std.core.builtin.panicf(ptr @.panic_msg, i64 36, ptr @.file, i64 6, ptr @.func, i64 7, i32 200, ptr byval(%"any[]") align 8 %indirectarg94) +if.exit69: ; preds = %if.exit18 + %81 = getelementptr inbounds %"char[]", ptr %url, i32 0, i32 1 + %82 = load i64, ptr %81, align 8 + %trunc = trunc i64 %82 to i32 + %83 = getelementptr inbounds %"char[]", ptr %url, i32 0, i32 0 + %84 = load ptr, ptr %83, align 8 + %85 = call i32 (ptr, i64, ptr, ...) @snprintf(ptr null, i64 0, ptr @.str.6, i32 %trunc, ptr %84) + store i32 %85, ptr %len, align 4 + %86 = load ptr, ptr @std.core.mem.thread_allocator, align 8 + store ptr %86, ptr %using70, align 8 + %87 = load ptr, ptr %using70, align 8 + store ptr %87, ptr %using72, align 8 + %88 = load i32, ptr %len, align 4 + %add = add i32 %88, 1 + %89 = load ptr, ptr %using72, align 8 + store ptr %89, ptr %allocator73, align 8 + %sext = sext i32 %add to i64 + %add74 = add i64 %sext, 0 + %90 = load ptr, ptr %allocator73, align 8 + %91 = getelementptr inbounds %Allocator, ptr %90, i32 0, i32 0 + %92 = load ptr, ptr %91, align 8 + %93 = load ptr, ptr %allocator73, align 8 + %94 = call i64 %92(ptr %retparam75, ptr %93, i64 %add74, i64 0, i64 0, ptr null, i32 0) + %not_err76 = icmp eq i64 %94, 0 + %95 = call i1 @llvm.expect.i1(i1 %not_err76, i1 true) + br i1 %95, label %after_check78, label %assign_optional77 + +assign_optional77: ; preds = %if.exit69 + store i64 %94, ptr %error_var71, align 8 + br label %panic_block79 + +after_check78: ; preds = %if.exit69 + %96 = load ptr, ptr %retparam75, align 8 + br label %noerr_block82 + +panic_block79: ; preds = %assign_optional77 + %97 = insertvalue %any undef, ptr %error_var71, 0 + %98 = insertvalue %any %97, i64 ptrtoint (ptr @"$ct.anyfault" to i64), 1 + %99 = getelementptr inbounds [1 x %any], ptr %varargslots80, i64 0, i64 0 + store %any %98, ptr %99, align 16 + %100 = insertvalue %"any[]" undef, ptr %varargslots80, 0 + %101 = insertvalue %"any[]" %100, i64 1, 1 + store %"any[]" %101, ptr %indirectarg81, align 8 + call void @std.core.builtin.panicf(ptr @.panic_msg, i64 36, ptr @.file, i64 6, ptr @.func, i64 7, i32 204, ptr byval(%"any[]") align 8 %indirectarg81) unreachable -noerr_block95: ; preds = %after_check91 - store ptr %104, ptr %str, align 8 - %110 = load ptr, ptr %str, align 8 - %not96 = icmp eq ptr %110, null - br i1 %not96, label %if.then97, label %if.exit98 +noerr_block82: ; preds = %after_check78 + store ptr %96, ptr %str, align 8 + %102 = load ptr, ptr %str, align 8 + %not83 = icmp eq ptr %102, null + br i1 %not83, label %if.then84, label %if.exit85 -if.then97: ; preds = %noerr_block95 +if.then84: ; preds = %noerr_block82 ret i64 ptrtoint (ptr @"test.ReadError$OUT_OF_MEMORY" to i64) -if.exit98: ; preds = %noerr_block95 - %111 = load ptr, ptr %str, align 8 - %112 = load i32, ptr %len, align 4 - %sext99 = sext i32 %112 to i64 - %add100 = add i64 %sext99, 1 - %113 = getelementptr inbounds %"char[]", ptr %url, i32 0, i32 1 - %114 = load i64, ptr %113, align 8 - %trunc101 = trunc i64 %114 to i32 - %115 = getelementptr inbounds %"char[]", ptr %url, i32 0, i32 0 - %116 = load ptr, ptr %115, align 8 - %117 = call i32 (ptr, i64, ptr, ...) @snprintf(ptr %111, i64 %add100, ptr @.str.7, i32 %trunc101, ptr %116) - %118 = getelementptr inbounds %Doc, ptr %literal103, i32 0, i32 0 - store ptr null, ptr %literal106, align 8 - %119 = getelementptr inbounds %Head, ptr %literal106, i32 0, i32 0 - %120 = load ptr, ptr %str, align 8 - %121 = load i32, ptr %len, align 4 - %sub = sub i32 %121, 1 - %sext109 = sext i32 %sub to i64 - %122 = add i64 %sext109, 1 - %size110 = sub i64 %122, 0 - %ptroffset111 = getelementptr inbounds i8, ptr %120, i64 0 - %123 = insertvalue %"char[]" undef, ptr %ptroffset111, 0 - %124 = insertvalue %"char[]" %123, i64 %size110, 1 - store %"char[]" %124, ptr %value108, align 8 - %125 = load ptr, ptr @std.core.mem.thread_allocator, align 8 - store ptr %125, ptr %using113, align 8 - store i64 0, ptr %end_padding114, align 8 - %126 = load ptr, ptr %using113, align 8 - store ptr %126, ptr %using116, align 8 - %127 = load i64, ptr %end_padding114, align 8 - store i64 %127, ptr %end_padding117, align 8 - store i64 16, ptr %.anon118, align 8 - %128 = load ptr, ptr %using116, align 8 - %129 = load i64, ptr %.anon118, align 8 - %130 = load i64, ptr %end_padding117, align 8 - %add121 = add i64 %129, %130 - store i64 %add121, ptr %size120, align 8 - %131 = getelementptr inbounds %Allocator, ptr %128, i32 0, i32 0 - %132 = load ptr, ptr %131, align 8 - %133 = load i64, ptr %size120, align 8 - %134 = call i64 %132(ptr %retparam123, ptr %128, i64 %133, i64 0, i64 0, ptr null, i32 0) - %not_err124 = icmp eq i64 %134, 0 - %135 = call i1 @llvm.expect.i1(i1 %not_err124, i1 true) - br i1 %135, label %after_check126, label %assign_optional125 - -assign_optional125: ; preds = %if.exit98 - store i64 %134, ptr %error_var115, align 8 - br label %panic_block127 - -after_check126: ; preds = %if.exit98 - %136 = load ptr, ptr %retparam123, align 8 - br label %noerr_block130 - -panic_block127: ; preds = %assign_optional125 - %137 = insertvalue %any undef, ptr %error_var115, 0 - %138 = insertvalue %any %137, i64 ptrtoint (ptr @"$ct.anyfault" to i64), 1 - %139 = getelementptr inbounds [1 x %any], ptr %varargslots128, i64 0, i64 0 - store %any %138, ptr %139, align 16 - %140 = insertvalue %"any[]" undef, ptr %varargslots128, 0 - %141 = insertvalue %"any[]" %140, i64 1, 1 - store %"any[]" %141, ptr %indirectarg129, align 8 - call void @std.core.builtin.panicf(ptr @.panic_msg, i64 36, ptr @.file, i64 6, ptr @.func, i64 7, i32 200, ptr byval(%"any[]") align 8 %indirectarg129) +if.exit85: ; preds = %noerr_block82 + %103 = load ptr, ptr %str, align 8 + %104 = load i32, ptr %len, align 4 + %sext86 = sext i32 %104 to i64 + %add87 = add i64 %sext86, 1 + %105 = getelementptr inbounds %"char[]", ptr %url, i32 0, i32 1 + %106 = load i64, ptr %105, align 8 + %trunc88 = trunc i64 %106 to i32 + %107 = getelementptr inbounds %"char[]", ptr %url, i32 0, i32 0 + %108 = load ptr, ptr %107, align 8 + %109 = call i32 (ptr, i64, ptr, ...) @snprintf(ptr %103, i64 %add87, ptr @.str.7, i32 %trunc88, ptr %108) + %110 = getelementptr inbounds %Doc, ptr %literal90, i32 0, i32 0 + store ptr null, ptr %literal92, align 8 + %111 = getelementptr inbounds %Head, ptr %literal92, i32 0, i32 0 + %112 = load ptr, ptr %str, align 8 + %113 = load i32, ptr %len, align 4 + %sub = sub i32 %113, 1 + %sext94 = sext i32 %sub to i64 + %114 = add i64 %sext94, 1 + %size = sub i64 %114, 0 + %ptroffset95 = getelementptr inbounds i8, ptr %112, i64 0 + %115 = insertvalue %"char[]" undef, ptr %ptroffset95, 0 + %116 = insertvalue %"char[]" %115, i64 %size, 1 + store %"char[]" %116, ptr %value96, align 8 + %117 = load ptr, ptr @std.core.mem.thread_allocator, align 8 + store ptr %117, ptr %using98, align 8 + %118 = load ptr, ptr %using98, align 8 + store ptr %118, ptr %using100, align 8 + %119 = load ptr, ptr %using100, align 8 + store ptr %119, ptr %allocator102, align 8 + %120 = load ptr, ptr %allocator102, align 8 + %121 = getelementptr inbounds %Allocator, ptr %120, i32 0, i32 0 + %122 = load ptr, ptr %121, align 8 + %123 = load ptr, ptr %allocator102, align 8 + %124 = call i64 %122(ptr %retparam104, ptr %123, i64 16, i64 0, i64 0, ptr null, i32 0) + %not_err105 = icmp eq i64 %124, 0 + %125 = call i1 @llvm.expect.i1(i1 %not_err105, i1 true) + br i1 %125, label %after_check107, label %assign_optional106 + +assign_optional106: ; preds = %if.exit85 + store i64 %124, ptr %error_var99, align 8 + br label %panic_block108 + +after_check107: ; preds = %if.exit85 + %126 = load ptr, ptr %retparam104, align 8 + br label %noerr_block111 + +panic_block108: ; preds = %assign_optional106 + %127 = insertvalue %any undef, ptr %error_var99, 0 + %128 = insertvalue %any %127, i64 ptrtoint (ptr @"$ct.anyfault" to i64), 1 + %129 = getelementptr inbounds [1 x %any], ptr %varargslots109, i64 0, i64 0 + store %any %128, ptr %129, align 16 + %130 = insertvalue %"any[]" undef, ptr %varargslots109, 0 + %131 = insertvalue %"any[]" %130, i64 1, 1 + store %"any[]" %131, ptr %indirectarg110, align 8 + call void @std.core.builtin.panicf(ptr @.panic_msg, i64 36, ptr @.file, i64 6, ptr @.func, i64 7, i32 204, ptr byval(%"any[]") align 8 %indirectarg110) unreachable -noerr_block130: ; preds = %after_check126 - store ptr %136, ptr %temp112, align 8 - %142 = load ptr, ptr %temp112, align 8 - %not131 = icmp eq ptr %142, null - br i1 %not131, label %if.then132, label %if.exit133 - -if.then132: ; preds = %noerr_block130 - store i64 ptrtoint (ptr @"test.ReadError$OUT_OF_MEMORY" to i64), ptr %error_var107, align 8 - br label %guard_block134 - -if.exit133: ; preds = %noerr_block130 - %143 = load ptr, ptr %temp112, align 8 - call void @llvm.memcpy.p0.p0.i32(ptr align 8 %143, ptr align 8 %value108, i32 16, i1 false) - br label %noerr_block135 - -guard_block134: ; preds = %if.then132 - %144 = load i64, ptr %error_var107, align 8 - ret i64 %144 - -noerr_block135: ; preds = %if.exit133 - %145 = load ptr, ptr %temp112, align 8 - store ptr %145, ptr %119, align 8 - call void @llvm.memcpy.p0.p0.i32(ptr align 8 %value105, ptr align 8 %literal106, i32 8, i1 false) - %146 = load ptr, ptr @std.core.mem.thread_allocator, align 8 - store ptr %146, ptr %using137, align 8 - store i64 0, ptr %end_padding138, align 8 - %147 = load ptr, ptr %using137, align 8 - store ptr %147, ptr %using140, align 8 - %148 = load i64, ptr %end_padding138, align 8 - store i64 %148, ptr %end_padding141, align 8 - store i64 8, ptr %.anon142, align 8 - %149 = load ptr, ptr %using140, align 8 - %150 = load i64, ptr %.anon142, align 8 - %151 = load i64, ptr %end_padding141, align 8 - %add145 = add i64 %150, %151 - store i64 %add145, ptr %size144, align 8 - %152 = getelementptr inbounds %Allocator, ptr %149, i32 0, i32 0 - %153 = load ptr, ptr %152, align 8 - %154 = load i64, ptr %size144, align 8 - %155 = call i64 %153(ptr %retparam147, ptr %149, i64 %154, i64 0, i64 0, ptr null, i32 0) - %not_err148 = icmp eq i64 %155, 0 - %156 = call i1 @llvm.expect.i1(i1 %not_err148, i1 true) - br i1 %156, label %after_check150, label %assign_optional149 - -assign_optional149: ; preds = %noerr_block135 - store i64 %155, ptr %error_var139, align 8 - br label %panic_block151 - -after_check150: ; preds = %noerr_block135 - %157 = load ptr, ptr %retparam147, align 8 - br label %noerr_block154 - -panic_block151: ; preds = %assign_optional149 - %158 = insertvalue %any undef, ptr %error_var139, 0 - %159 = insertvalue %any %158, i64 ptrtoint (ptr @"$ct.anyfault" to i64), 1 - %160 = getelementptr inbounds [1 x %any], ptr %varargslots152, i64 0, i64 0 - store %any %159, ptr %160, align 16 - %161 = insertvalue %"any[]" undef, ptr %varargslots152, 0 - %162 = insertvalue %"any[]" %161, i64 1, 1 - store %"any[]" %162, ptr %indirectarg153, align 8 - call void @std.core.builtin.panicf(ptr @.panic_msg, i64 36, ptr @.file, i64 6, ptr @.func, i64 7, i32 200, ptr byval(%"any[]") align 8 %indirectarg153) +noerr_block111: ; preds = %after_check107 + store ptr %126, ptr %temp97, align 8 + %132 = load ptr, ptr %temp97, align 8 + %not112 = icmp eq ptr %132, null + br i1 %not112, label %if.then113, label %if.exit114 + +if.then113: ; preds = %noerr_block111 + store i64 ptrtoint (ptr @"test.ReadError$OUT_OF_MEMORY" to i64), ptr %error_var93, align 8 + br label %guard_block115 + +if.exit114: ; preds = %noerr_block111 + %133 = load ptr, ptr %temp97, align 8 + call void @llvm.memcpy.p0.p0.i32(ptr align 8 %133, ptr align 8 %value96, i32 16, i1 false) + br label %noerr_block116 + +guard_block115: ; preds = %if.then113 + %134 = load i64, ptr %error_var93, align 8 + ret i64 %134 + +noerr_block116: ; preds = %if.exit114 + %135 = load ptr, ptr %temp97, align 8 + store ptr %135, ptr %111, align 8 + call void @llvm.memcpy.p0.p0.i32(ptr align 8 %value117, ptr align 8 %literal92, i32 8, i1 false) + %136 = load ptr, ptr @std.core.mem.thread_allocator, align 8 + store ptr %136, ptr %using119, align 8 + %137 = load ptr, ptr %using119, align 8 + store ptr %137, ptr %using121, align 8 + %138 = load ptr, ptr %using121, align 8 + store ptr %138, ptr %allocator123, align 8 + %139 = load ptr, ptr %allocator123, align 8 + %140 = getelementptr inbounds %Allocator, ptr %139, i32 0, i32 0 + %141 = load ptr, ptr %140, align 8 + %142 = load ptr, ptr %allocator123, align 8 + %143 = call i64 %141(ptr %retparam125, ptr %142, i64 8, i64 0, i64 0, ptr null, i32 0) + %not_err126 = icmp eq i64 %143, 0 + %144 = call i1 @llvm.expect.i1(i1 %not_err126, i1 true) + br i1 %144, label %after_check128, label %assign_optional127 + +assign_optional127: ; preds = %noerr_block116 + store i64 %143, ptr %error_var120, align 8 + br label %panic_block129 + +after_check128: ; preds = %noerr_block116 + %145 = load ptr, ptr %retparam125, align 8 + br label %noerr_block132 + +panic_block129: ; preds = %assign_optional127 + %146 = insertvalue %any undef, ptr %error_var120, 0 + %147 = insertvalue %any %146, i64 ptrtoint (ptr @"$ct.anyfault" to i64), 1 + %148 = getelementptr inbounds [1 x %any], ptr %varargslots130, i64 0, i64 0 + store %any %147, ptr %148, align 16 + %149 = insertvalue %"any[]" undef, ptr %varargslots130, 0 + %150 = insertvalue %"any[]" %149, i64 1, 1 + store %"any[]" %150, ptr %indirectarg131, align 8 + call void @std.core.builtin.panicf(ptr @.panic_msg, i64 36, ptr @.file, i64 6, ptr @.func, i64 7, i32 204, ptr byval(%"any[]") align 8 %indirectarg131) unreachable -noerr_block154: ; preds = %after_check150 - store ptr %157, ptr %temp136, align 8 - %163 = load ptr, ptr %temp136, align 8 - %not155 = icmp eq ptr %163, null - br i1 %not155, label %if.then156, label %if.exit157 - -if.then156: ; preds = %noerr_block154 - store i64 ptrtoint (ptr @"test.ReadError$OUT_OF_MEMORY" to i64), ptr %error_var104, align 8 - br label %guard_block158 - -if.exit157: ; preds = %noerr_block154 - %164 = load ptr, ptr %temp136, align 8 - call void @llvm.memcpy.p0.p0.i32(ptr align 8 %164, ptr align 8 %value105, i32 8, i1 false) - br label %noerr_block159 - -guard_block158: ; preds = %if.then156 - %165 = load i64, ptr %error_var104, align 8 - ret i64 %165 - -noerr_block159: ; preds = %if.exit157 - %166 = load ptr, ptr %temp136, align 8 - store ptr %166, ptr %118, align 8 - call void @llvm.memcpy.p0.p0.i32(ptr align 8 %0, ptr align 8 %literal103, i32 8, i1 false) +noerr_block132: ; preds = %after_check128 + store ptr %145, ptr %temp118, align 8 + %151 = load ptr, ptr %temp118, align 8 + %not133 = icmp eq ptr %151, null + br i1 %not133, label %if.then134, label %if.exit135 + +if.then134: ; preds = %noerr_block132 + store i64 ptrtoint (ptr @"test.ReadError$OUT_OF_MEMORY" to i64), ptr %error_var91, align 8 + br label %guard_block136 + +if.exit135: ; preds = %noerr_block132 + %152 = load ptr, ptr %temp118, align 8 + call void @llvm.memcpy.p0.p0.i32(ptr align 8 %152, ptr align 8 %value117, i32 8, i1 false) + br label %noerr_block137 + +guard_block136: ; preds = %if.then134 + %153 = load i64, ptr %error_var91, align 8 + ret i64 %153 + +noerr_block137: ; preds = %if.exit135 + %154 = load ptr, ptr %temp118, align 8 + store ptr %154, ptr %110, align 8 + call void @llvm.memcpy.p0.p0.i32(ptr align 8 %0, ptr align 8 %literal90, i32 8, i1 false) ret i64 0 } diff --git a/test/test_suite/errors/failable_catch.c3t b/test/test_suite/errors/failable_catch.c3t index 99cac82ac..60c2f431b 100644 --- a/test/test_suite/errors/failable_catch.c3t +++ b/test/test_suite/errors/failable_catch.c3t @@ -34,47 +34,35 @@ define i32 @main() #0 { entry: %a = alloca i32, align 4 %a.f = alloca i64, align 8 - %x = alloca i32, align 4 %blockret = alloca i32, align 4 %b = alloca i32, align 4 %b.f = alloca i64, align 8 - %x1 = alloca i32, align 4 - %blockret2 = alloca i32, align 4 + %blockret1 = alloca i32, align 4 %c = alloca i32, align 4 %c.f = alloca i64, align 8 - %x8 = alloca i32, align 4 - %blockret9 = alloca i32, align 4 - %blockret26 = alloca i64, align 8 + %blockret19 = alloca i64, align 8 %f = alloca i64, align 8 - store i32 1, ptr %x, align 4 - %0 = load i32, ptr %x, align 4 - %intbool = icmp ne i32 %0, 0 - br i1 %intbool, label %if.then, label %if.exit + br label %if.then if.then: ; preds = %entry - %1 = load i32, ptr %x, align 4 - store i32 %1, ptr %blockret, align 4 + store i32 1, ptr %blockret, align 4 br label %expr_block.exit -if.exit: ; preds = %entry - store i64 ptrtoint (ptr @"failable_catch.MyErr$TEST" to i64), ptr %a.f, align 8 - br label %after_assign - expr_block.exit: ; preds = %if.then - %2 = load i32, ptr %blockret, align 4 - store i32 %2, ptr %a, align 4 + %0 = load i32, ptr %blockret, align 4 + store i32 %0, ptr %a, align 4 store i64 0, ptr %a.f, align 8 br label %after_assign -after_assign: ; preds = %expr_block.exit, %if.exit +after_assign: ; preds = %expr_block.exit %optval = load i64, ptr %a.f, align 8 %not_err = icmp eq i64 %optval, 0 - %3 = call i1 @llvm.expect.i1(i1 %not_err, i1 true) - br i1 %3, label %after_check, label %else_block + %1 = call i1 @llvm.expect.i1(i1 %not_err, i1 true) + br i1 %1, label %after_check, label %else_block after_check: ; preds = %after_assign - %4 = load i32, ptr %a, align 4 - %add = add i32 %4, 3 + %2 = load i32, ptr %a, align 4 + %add = add i32 %2, 3 br label %phi_block else_block: ; preds = %after_assign @@ -82,133 +70,116 @@ else_block: ; preds = %after_assign phi_block: ; preds = %else_block, %after_check %val = phi i32 [ %add, %after_check ], [ 2, %else_block ] - store i32 %val, ptr %x1, align 4 - %5 = load i32, ptr %x1, align 4 - %intbool3 = icmp ne i32 %5, 0 - br i1 %intbool3, label %if.then4, label %if.exit5 + %intbool = icmp ne i32 %val, 0 + br i1 %intbool, label %if.then2, label %if.exit -if.then4: ; preds = %phi_block - %6 = load i32, ptr %x1, align 4 - store i32 %6, ptr %blockret2, align 4 - br label %expr_block.exit6 +if.then2: ; preds = %phi_block + store i32 %val, ptr %blockret1, align 4 + br label %expr_block.exit3 -if.exit5: ; preds = %phi_block +if.exit: ; preds = %phi_block store i64 ptrtoint (ptr @"failable_catch.MyErr$TEST" to i64), ptr %b.f, align 8 - br label %after_assign7 + br label %after_assign4 -expr_block.exit6: ; preds = %if.then4 - %7 = load i32, ptr %blockret2, align 4 - store i32 %7, ptr %b, align 4 +expr_block.exit3: ; preds = %if.then2 + %3 = load i32, ptr %blockret1, align 4 + store i32 %3, ptr %b, align 4 store i64 0, ptr %b.f, align 8 + br label %after_assign4 + +after_assign4: ; preds = %expr_block.exit3, %if.exit + br label %if.exit6 + +if.exit6: ; preds = %after_assign4 + store i64 ptrtoint (ptr @"failable_catch.MyErr$TEST" to i64), ptr %c.f, align 8 br label %after_assign7 -after_assign7: ; preds = %expr_block.exit6, %if.exit5 - store i32 0, ptr %x8, align 4 - %8 = load i32, ptr %x8, align 4 - %intbool10 = icmp ne i32 %8, 0 - br i1 %intbool10, label %if.then11, label %if.exit12 +after_assign7: ; preds = %if.exit6 + %optval8 = load i64, ptr %a.f, align 8 + %not_err9 = icmp eq i64 %optval8, 0 + %4 = call i1 @llvm.expect.i1(i1 %not_err9, i1 true) + br i1 %4, label %after_check10, label %voiderr -if.then11: ; preds = %after_assign7 - %9 = load i32, ptr %x8, align 4 - store i32 %9, ptr %blockret9, align 4 - br label %expr_block.exit13 +after_check10: ; preds = %after_assign7 + %5 = load i32, ptr %a, align 4 + call void (ptr, ...) @printf(ptr @.str, i32 %5) + br label %voiderr -if.exit12: ; preds = %after_assign7 - store i64 ptrtoint (ptr @"failable_catch.MyErr$TEST" to i64), ptr %c.f, align 8 - br label %after_assign14 +voiderr: ; preds = %after_check10, %after_assign7 + %optval11 = load i64, ptr %b.f, align 8 + %not_err12 = icmp eq i64 %optval11, 0 + %6 = call i1 @llvm.expect.i1(i1 %not_err12, i1 true) + br i1 %6, label %after_check13, label %voiderr14 -expr_block.exit13: ; preds = %if.then11 - %10 = load i32, ptr %blockret9, align 4 - store i32 %10, ptr %c, align 4 - store i64 0, ptr %c.f, align 8 - br label %after_assign14 +after_check13: ; preds = %voiderr + %7 = load i32, ptr %b, align 4 + call void (ptr, ...) @printf(ptr @.str.1, i32 %7) + br label %voiderr14 -after_assign14: ; preds = %expr_block.exit13, %if.exit12 - %optval15 = load i64, ptr %a.f, align 8 +voiderr14: ; preds = %after_check13, %voiderr + %optval15 = load i64, ptr %c.f, align 8 %not_err16 = icmp eq i64 %optval15, 0 - %11 = call i1 @llvm.expect.i1(i1 %not_err16, i1 true) - br i1 %11, label %after_check17, label %voiderr + %8 = call i1 @llvm.expect.i1(i1 %not_err16, i1 true) + br i1 %8, label %after_check17, label %voiderr18 -after_check17: ; preds = %after_assign14 - %12 = load i32, ptr %a, align 4 - call void (ptr, ...) @printf(ptr @.str, i32 %12) - br label %voiderr +after_check17: ; preds = %voiderr14 + %9 = load i32, ptr %c, align 4 + call void (ptr, ...) @printf(ptr @.str.2, i32 %9) + br label %voiderr18 -voiderr: ; preds = %after_check17, %after_assign14 - %optval18 = load i64, ptr %b.f, align 8 - %not_err19 = icmp eq i64 %optval18, 0 - %13 = call i1 @llvm.expect.i1(i1 %not_err19, i1 true) - br i1 %13, label %after_check20, label %voiderr21 - -after_check20: ; preds = %voiderr - %14 = load i32, ptr %b, align 4 - call void (ptr, ...) @printf(ptr @.str.1, i32 %14) - br label %voiderr21 - -voiderr21: ; preds = %after_check20, %voiderr - %optval22 = load i64, ptr %c.f, align 8 - %not_err23 = icmp eq i64 %optval22, 0 - %15 = call i1 @llvm.expect.i1(i1 %not_err23, i1 true) - br i1 %15, label %after_check24, label %voiderr25 - -after_check24: ; preds = %voiderr21 - %16 = load i32, ptr %c, align 4 - call void (ptr, ...) @printf(ptr @.str.2, i32 %16) - br label %voiderr25 - -voiderr25: ; preds = %after_check24, %voiderr21 +voiderr18: ; preds = %after_check17, %voiderr14 br label %testblock -testblock: ; preds = %voiderr25 - %optval27 = load i64, ptr %c.f, align 8 - %not_err28 = icmp eq i64 %optval27, 0 - %17 = call i1 @llvm.expect.i1(i1 %not_err28, i1 true) - br i1 %17, label %after_check29, label %assign_optional +testblock: ; preds = %voiderr18 + %optval20 = load i64, ptr %c.f, align 8 + %not_err21 = icmp eq i64 %optval20, 0 + %10 = call i1 @llvm.expect.i1(i1 %not_err21, i1 true) + br i1 %10, label %after_check22, label %assign_optional assign_optional: ; preds = %testblock - store i64 %optval27, ptr %f, align 8 + store i64 %optval20, ptr %f, align 8 br label %end_block -after_check29: ; preds = %testblock +after_check22: ; preds = %testblock store i64 0, ptr %f, align 8 br label %end_block -end_block: ; preds = %after_check29, %assign_optional - %18 = load i64, ptr %f, align 8 - %neq = icmp ne i64 %18, 0 - br i1 %neq, label %if.then30, label %if.exit31 +end_block: ; preds = %after_check22, %assign_optional + %11 = load i64, ptr %f, align 8 + %neq = icmp ne i64 %11, 0 + br i1 %neq, label %if.then23, label %if.exit24 -if.then30: ; preds = %end_block - %19 = load i64, ptr %f, align 8 - store i64 %19, ptr %blockret26, align 8 - br label %expr_block.exit32 +if.then23: ; preds = %end_block + %12 = load i64, ptr %f, align 8 + store i64 %12, ptr %blockret19, align 8 + br label %expr_block.exit25 -if.exit31: ; preds = %end_block - store i64 0, ptr %blockret26, align 8 - br label %expr_block.exit32 +if.exit24: ; preds = %end_block + store i64 0, ptr %blockret19, align 8 + br label %expr_block.exit25 -expr_block.exit32: ; preds = %if.exit31, %if.then30 - %20 = load i64, ptr %blockret26, align 8 - %neq33 = icmp ne i64 %20, 0 - br i1 %neq33, label %if.then34, label %if.exit35 +expr_block.exit25: ; preds = %if.exit24, %if.then23 + %13 = load i64, ptr %blockret19, align 8 + %neq26 = icmp ne i64 %13, 0 + br i1 %neq26, label %if.then27, label %if.exit28 -if.then34: ; preds = %expr_block.exit32 +if.then27: ; preds = %expr_block.exit25 call void (ptr, ...) @printf(ptr @.str.3) - br label %if.exit35 + br label %if.exit28 -if.exit35: ; preds = %if.then34, %expr_block.exit32 +if.exit28: ; preds = %if.then27, %expr_block.exit25 store i32 3, ptr %c, align 4 store i64 0, ptr %c.f, align 8 - %optval36 = load i64, ptr %c.f, align 8 - %not_err37 = icmp eq i64 %optval36, 0 - %21 = call i1 @llvm.expect.i1(i1 %not_err37, i1 true) - br i1 %21, label %after_check38, label %voiderr39 + %optval29 = load i64, ptr %c.f, align 8 + %not_err30 = icmp eq i64 %optval29, 0 + %14 = call i1 @llvm.expect.i1(i1 %not_err30, i1 true) + br i1 %14, label %after_check31, label %voiderr32 -after_check38: ; preds = %if.exit35 - %22 = load i32, ptr %c, align 4 - call void (ptr, ...) @printf(ptr @.str.4, i32 %22) - br label %voiderr39 +after_check31: ; preds = %if.exit28 + %15 = load i32, ptr %c, align 4 + call void (ptr, ...) @printf(ptr @.str.4, i32 %15) + br label %voiderr32 -voiderr39: ; preds = %after_check38, %if.exit35 +voiderr32: ; preds = %after_check31, %if.exit28 ret i32 0 } diff --git a/test/test_suite/errors/or_and_rethrow.c3t b/test/test_suite/errors/or_and_rethrow.c3t index 288a32e9d..909513725 100644 --- a/test/test_suite/errors/or_and_rethrow.c3t +++ b/test/test_suite/errors/or_and_rethrow.c3t @@ -285,10 +285,6 @@ noerr_block15: ; preds = %after_check14, %ass ; Function Attrs: nounwind define i32 @main(i32 %0, ptr %1) #0 { entry: - %.anon = alloca i32, align 4 - %.anon1 = alloca ptr, align 8 - store i32 %0, ptr %.anon, align 4 - store ptr %1, ptr %.anon1, align 8 call void @foo.main() ret i32 0 } diff --git a/test/test_suite/errors/printing_errors.c3t b/test/test_suite/errors/printing_errors.c3t index 354843208..60e69a80e 100644 --- a/test/test_suite/errors/printing_errors.c3t +++ b/test/test_suite/errors/printing_errors.c3t @@ -54,10 +54,6 @@ faultname_exit: ; preds = %faultname_ok, %faul ; Function Attrs: nounwind define i32 @main(i32 %0, ptr %1) #0 { entry: - %.anon = alloca i32, align 4 - %.anon1 = alloca ptr, align 8 - store i32 %0, ptr %.anon, align 4 - store ptr %1, ptr %.anon1, align 8 call void @test.main() ret i32 0 } diff --git a/test/test_suite/from_docs/examples_macro_function.c3t b/test/test_suite/from_docs/examples_macro_function.c3t index 860ed506b..70202ea71 100644 --- a/test/test_suite/from_docs/examples_macro_function.c3t +++ b/test/test_suite/from_docs/examples_macro_function.c3t @@ -33,18 +33,12 @@ define i32 @example.test() #0 { entry: %a = alloca i32, align 4 %b = alloca i32, align 4 - %a1 = alloca ptr, align 8 - %b2 = alloca i32, align 4 store i32 2, ptr %a, align 4 store i32 3, ptr %b, align 4 - store ptr @example.square, ptr %a1, align 8 - store i32 2, ptr %b2, align 4 - %0 = load ptr, ptr %a1, align 8 - %1 = load i32, ptr %b2, align 4 - %2 = call i32 %0(i32 %1) - %3 = load i32, ptr %a, align 4 - %add = add i32 %2, %3 - %4 = load i32, ptr %b, align 4 - %add3 = add i32 %add, %4 - ret i32 %add3 + %0 = call i32 @example.square(i32 2) + %1 = load i32, ptr %a, align 4 + %add = add i32 %0, %1 + %2 = load i32, ptr %b, align 4 + %add1 = add i32 %add, %2 + ret i32 %add1 } \ No newline at end of file diff --git a/test/test_suite/functions/macro_arguments.c3 b/test/test_suite/functions/macro_arguments.c3 index bc8667311..a2bc5b87d 100644 --- a/test/test_suite/functions/macro_arguments.c3 +++ b/test/test_suite/functions/macro_arguments.c3 @@ -7,6 +7,6 @@ fn void foo3(bar) { } // #error: Only typed parameters are allowed for functions fn void foo4($Type) { } // #error: Only regular parameters are allowed for functions. -fn void foo8(int &foo) {} // #error: Only regular parameters are allowed for functions. +fn void foo8(int* &foo) {} // #error: Only regular parameters are allowed for functions. fn void foo9(int x, int x) {} // #error: Duplicate parameter name 'x'. diff --git a/test/test_suite/generic/generic_over_fn.c3t b/test/test_suite/generic/generic_over_fn.c3t index 620566e2e..f0abd2994 100644 --- a/test/test_suite/generic/generic_over_fn.c3t +++ b/test/test_suite/generic/generic_over_fn.c3t @@ -70,7 +70,6 @@ entry: %.anon5 = alloca i64, align 8 %tc = alloca %"int[]", align 8 %list = alloca %"int[]", align 8 - %cmp = alloca ptr, align 8 %len = alloca i64, align 8 %0 = getelementptr inbounds [5 x %"int[]"], ptr %literal, i64 0, i64 0 store %"int[]" zeroinitializer, ptr %0, align 8 @@ -134,7 +133,6 @@ loop.body: ; preds = %loop.cond %ptroffset = getelementptr inbounds %"int[]", ptr %31, i64 %32 call void @llvm.memcpy.p0.p0.i32(ptr align 8 %tc, ptr align 8 %ptroffset, i32 16, i1 false) call void @llvm.memcpy.p0.p0.i32(ptr align 8 %list, ptr align 8 %tc, i32 16, i1 false) - store ptr @sort_test.cmp_int_value, ptr %cmp, align 8 %33 = getelementptr inbounds %"int[]", ptr %list, i32 0, i32 1 %34 = load i64, ptr %33, align 8 store i64 %34, ptr %len, align 8 @@ -144,10 +142,9 @@ loop.body: ; preds = %loop.cond %hi = load i64, ptr %36, align 8 %37 = load i64, ptr %len, align 8 %sub = sub i64 %37, 1 - %38 = load ptr, ptr %cmp, align 8 - call void @"test_generic$sa$int$p$fn$int$int$$int$$.sort"(ptr %lo, i64 %hi, i64 0, i64 %sub, ptr %38) - %39 = load i64, ptr %.anon5, align 8 - %add = add i64 %39, 1 + call void @"test_generic$sa$int$p$fn$int$int$$int$$.sort"(ptr %lo, i64 %hi, i64 0, i64 %sub, ptr @sort_test.cmp_int_value) + %38 = load i64, ptr %.anon5, align 8 + %add = add i64 %38, 1 store i64 %add, ptr %.anon5, align 8 br label %loop.cond @@ -168,7 +165,6 @@ entry: %.anon5 = alloca i64, align 8 %tc = alloca %"int[]", align 8 %list = alloca %"int[]", align 8 - %cmp = alloca ptr, align 8 %len = alloca i64, align 8 %0 = getelementptr inbounds [5 x %"int[]"], ptr %literal, i64 0, i64 0 store %"int[]" zeroinitializer, ptr %0, align 8 @@ -232,7 +228,6 @@ loop.body: ; preds = %loop.cond %ptroffset = getelementptr inbounds %"int[]", ptr %31, i64 %32 call void @llvm.memcpy.p0.p0.i32(ptr align 8 %tc, ptr align 8 %ptroffset, i32 16, i1 false) call void @llvm.memcpy.p0.p0.i32(ptr align 8 %list, ptr align 8 %tc, i32 16, i1 false) - store ptr @sort_test.cmp_int_value2, ptr %cmp, align 8 %33 = getelementptr inbounds %"int[]", ptr %list, i32 0, i32 1 %34 = load i64, ptr %33, align 8 store i64 %34, ptr %len, align 8 @@ -242,10 +237,9 @@ loop.body: ; preds = %loop.cond %hi = load i64, ptr %36, align 8 %37 = load i64, ptr %len, align 8 %sub = sub i64 %37, 1 - %38 = load ptr, ptr %cmp, align 8 - call void @"test_generic$sa$int$p$fn$int$int$$int$$.sort"(ptr %lo, i64 %hi, i64 0, i64 %sub, ptr %38) - %39 = load i64, ptr %.anon5, align 8 - %add = add i64 %39, 1 + call void @"test_generic$sa$int$p$fn$int$int$$int$$.sort"(ptr %lo, i64 %hi, i64 0, i64 %sub, ptr @sort_test.cmp_int_value2) + %38 = load i64, ptr %.anon5, align 8 + %add = add i64 %38, 1 store i64 %add, ptr %.anon5, align 8 br label %loop.cond diff --git a/test/test_suite/literals/bin_literal.c3t b/test/test_suite/literals/bin_literal.c3t index 4312dc5e8..cbaea43dc 100644 --- a/test/test_suite/literals/bin_literal.c3t +++ b/test/test_suite/literals/bin_literal.c3t @@ -27,11 +27,9 @@ entry: %retparam1 = alloca i64, align 8 %varargslots2 = alloca [3 x %any], align 16 %i = alloca i8, align 1 - %shift = alloca i8, align 1 %taddr = alloca i8, align 1 %i3 = alloca i8, align 1 - %shift4 = alloca i8, align 1 - %taddr5 = alloca i8, align 1 + %taddr4 = alloca i8, align 1 store i32 123, ptr %a, align 4 store i32 -23, ptr %b, align 4 %0 = load i32, ptr %a, align 4 @@ -58,28 +56,24 @@ entry: store %any %14, ptr %15, align 16 %16 = load i8, ptr %z, align 1 store i8 %16, ptr %i, align 1 - store i8 1, ptr %shift, align 1 %17 = load i8, ptr %i, align 1 %18 = load i8, ptr %i, align 1 - %19 = load i8, ptr %shift, align 1 - %20 = call i8 @llvm.fshr.i8(i8 %17, i8 %18, i8 %19) - store i8 %20, ptr %taddr, align 1 - %21 = insertvalue %any undef, ptr %taddr, 0 - %22 = insertvalue %any %21, i64 ptrtoint (ptr @"$ct.char" to i64), 1 - %23 = getelementptr inbounds [3 x %any], ptr %varargslots2, i64 0, i64 1 - store %any %22, ptr %23, align 16 - %24 = load i8, ptr %z, align 1 - store i8 %24, ptr %i3, align 1 - store i8 1, ptr %shift4, align 1 + %19 = call i8 @llvm.fshr.i8(i8 %17, i8 %18, i8 1) + store i8 %19, ptr %taddr, align 1 + %20 = insertvalue %any undef, ptr %taddr, 0 + %21 = insertvalue %any %20, i64 ptrtoint (ptr @"$ct.char" to i64), 1 + %22 = getelementptr inbounds [3 x %any], ptr %varargslots2, i64 0, i64 1 + store %any %21, ptr %22, align 16 + %23 = load i8, ptr %z, align 1 + store i8 %23, ptr %i3, align 1 + %24 = load i8, ptr %i3, align 1 %25 = load i8, ptr %i3, align 1 - %26 = load i8, ptr %i3, align 1 - %27 = load i8, ptr %shift4, align 1 - %28 = call i8 @llvm.fshl.i8(i8 %25, i8 %26, i8 %27) - store i8 %28, ptr %taddr5, align 1 - %29 = insertvalue %any undef, ptr %taddr5, 0 - %30 = insertvalue %any %29, i64 ptrtoint (ptr @"$ct.char" to i64), 1 - %31 = getelementptr inbounds [3 x %any], ptr %varargslots2, i64 0, i64 2 - store %any %30, ptr %31, align 16 - %32 = call i64 @std.io.printfn(ptr %retparam1, ptr @.str.1, i64 8, ptr %varargslots2, i64 3) + %26 = call i8 @llvm.fshl.i8(i8 %24, i8 %25, i8 1) + store i8 %26, ptr %taddr4, align 1 + %27 = insertvalue %any undef, ptr %taddr4, 0 + %28 = insertvalue %any %27, i64 ptrtoint (ptr @"$ct.char" to i64), 1 + %29 = getelementptr inbounds [3 x %any], ptr %varargslots2, i64 0, i64 2 + store %any %28, ptr %29, align 16 + %30 = call i64 @std.io.printfn(ptr %retparam1, ptr @.str.1, i64 8, ptr %varargslots2, i64 3) ret void } diff --git a/test/test_suite/macro_methods/access.c3 b/test/test_suite/macro_methods/access.c3 index 153445d93..91a5fc184 100644 --- a/test/test_suite/macro_methods/access.c3 +++ b/test/test_suite/macro_methods/access.c3 @@ -15,7 +15,7 @@ struct An2 extern fn void printf(char *string); -macro void An2.@helloWorld(An2 &an2) +macro void An2.@helloWorld(An2* &an2) { printf("An2 hello\n"); } diff --git a/test/test_suite/macro_methods/macro_method_different_args.c3t b/test/test_suite/macro_methods/macro_method_different_args.c3t index 330eea7a1..5c1ce8f03 100644 --- a/test/test_suite/macro_methods/macro_method_different_args.c3t +++ b/test/test_suite/macro_methods/macro_method_different_args.c3t @@ -7,7 +7,7 @@ struct Foo int x; } -macro void Foo.@hello(Foo &this) { this.x = 3; printf("-%d\n", this.x); } +macro void Foo.@hello(Foo* &this) { this.x = 3; printf("-%d\n", this.x); } macro void Foo.hello(Foo* this) { this.x = 4; printf("-%d\n", this.x); } macro void Foo.hello2(Foo this) { this.x = 5; printf("-%d\n", this.x); } @@ -27,8 +27,7 @@ fn void main() define void @foo.main() #0 { entry: %a = alloca %Foo, align 4 - %this = alloca ptr, align 8 - %this1 = alloca %Foo, align 4 + %this = alloca %Foo, align 4 store i32 0, ptr %a, align 4 %0 = getelementptr inbounds %Foo, ptr %a, i32 0, i32 0 store i32 3, ptr %0, align 4 @@ -38,25 +37,22 @@ entry: %3 = getelementptr inbounds %Foo, ptr %a, i32 0, i32 0 %4 = load i32, ptr %3, align 4 call void (ptr, ...) @printf(ptr @.str.1, i32 %4) - store ptr %a, ptr %this, align 8 - %5 = load ptr, ptr %this, align 8 - %6 = getelementptr inbounds %Foo, ptr %5, i32 0, i32 0 - store i32 4, ptr %6, align 4 - %7 = load ptr, ptr %this, align 8 - %8 = getelementptr inbounds %Foo, ptr %7, i32 0, i32 0 + %5 = getelementptr inbounds %Foo, ptr %a, i32 0, i32 0 + store i32 4, ptr %5, align 4 + %6 = getelementptr inbounds %Foo, ptr %a, i32 0, i32 0 + %7 = load i32, ptr %6, align 4 + call void (ptr, ...) @printf(ptr @.str.2, i32 %7) + %8 = getelementptr inbounds %Foo, ptr %a, i32 0, i32 0 %9 = load i32, ptr %8, align 4 - call void (ptr, ...) @printf(ptr @.str.2, i32 %9) - %10 = getelementptr inbounds %Foo, ptr %a, i32 0, i32 0 - %11 = load i32, ptr %10, align 4 - call void (ptr, ...) @printf(ptr @.str.3, i32 %11) - call void @llvm.memcpy.p0.p0.i32(ptr align 4 %this1, ptr align 4 %a, i32 4, i1 false) - %12 = getelementptr inbounds %Foo, ptr %this1, i32 0, i32 0 - store i32 5, ptr %12, align 4 - %13 = getelementptr inbounds %Foo, ptr %this1, i32 0, i32 0 + call void (ptr, ...) @printf(ptr @.str.3, i32 %9) + call void @llvm.memcpy.p0.p0.i32(ptr align 4 %this, ptr align 4 %a, i32 4, i1 false) + %10 = getelementptr inbounds %Foo, ptr %this, i32 0, i32 0 + store i32 5, ptr %10, align 4 + %11 = getelementptr inbounds %Foo, ptr %this, i32 0, i32 0 + %12 = load i32, ptr %11, align 4 + call void (ptr, ...) @printf(ptr @.str.4, i32 %12) + %13 = getelementptr inbounds %Foo, ptr %a, i32 0, i32 0 %14 = load i32, ptr %13, align 4 - call void (ptr, ...) @printf(ptr @.str.4, i32 %14) - %15 = getelementptr inbounds %Foo, ptr %a, i32 0, i32 0 - %16 = load i32, ptr %15, align 4 - call void (ptr, ...) @printf(ptr @.str.5, i32 %16) + call void (ptr, ...) @printf(ptr @.str.5, i32 %14) ret void } \ No newline at end of file diff --git a/test/test_suite/macro_methods/macro_method_fails.c3 b/test/test_suite/macro_methods/macro_method_fails.c3 index 780b4f24f..367e7fa5a 100644 --- a/test/test_suite/macro_methods/macro_method_fails.c3 +++ b/test/test_suite/macro_methods/macro_method_fails.c3 @@ -15,7 +15,7 @@ struct An2 extern fn void printf(char* string); -macro void An2.@helloWorld(An2 &an2) +macro void An2.@helloWorld(An2* &an2) { printf("An2 hello\n"); } diff --git a/test/test_suite/macro_methods/macro_methods_defined_twice.c3 b/test/test_suite/macro_methods/macro_methods_defined_twice.c3 index e98a0a558..01f70ed04 100644 --- a/test/test_suite/macro_methods/macro_methods_defined_twice.c3 +++ b/test/test_suite/macro_methods/macro_methods_defined_twice.c3 @@ -9,14 +9,14 @@ module baz; import foo; import std::io; -macro void foo::Bar.@test(Bar &bar) +macro void foo::Bar.@test(Bar* &bar) { io::printn("Inside of baz::Bar.test"); } module bad; import foo; -macro void Bar.@test(Bar &bar) // #error: This macro method is already defined for 'Bar'. +macro void Bar.@test(Bar* &bar) // #error: This macro method is already defined for 'Bar'. { io::printn("Inside of baz::Bar.test"); } diff --git a/test/test_suite/macros/deref_macro_pointer.c3 b/test/test_suite/macros/deref_macro_pointer.c3 index 56bc0aa4b..14741fd54 100644 --- a/test/test_suite/macros/deref_macro_pointer.c3 +++ b/test/test_suite/macros/deref_macro_pointer.c3 @@ -3,7 +3,7 @@ module test; fn void test(int* a) {} macro @abc(&self) { - test(self); // #error: is a dereferenced pointer + test(self); // #error: Implicitly casting 'int**' to 'int*' } fn void! test1() diff --git a/test/test_suite/macros/macro_body_defer.c3t b/test/test_suite/macros/macro_body_defer.c3t index 7f8030983..99dedbb0a 100644 --- a/test/test_suite/macros/macro_body_defer.c3t +++ b/test/test_suite/macros/macro_body_defer.c3t @@ -57,71 +57,68 @@ entry: define i64 @foo.main() #0 { entry: - %i = alloca i32, align 4 - %i1 = alloca i32, align 4 - %i3 = alloca i32, align 4 %reterr = alloca i64, align 8 call void (ptr, ...) @printf(ptr @.str) call void (ptr, ...) @printf(ptr @.str.1) call void (ptr, ...) @printf(ptr @.str.2) - store i32 34, ptr %i, align 4 call void (ptr, ...) @printf(ptr @.str.3) - %0 = load i32, ptr %i, align 4 - call void (ptr, ...) @printf(ptr @.str.4, i32 %0) - %1 = load i32, ptr %i, align 4 - call void (ptr, ...) @printf(ptr @.str.5, i32 %1) + call void (ptr, ...) @printf(ptr @.str.4, i32 34) + call void (ptr, ...) @printf(ptr @.str.5, i32 34) br label %loop.body + loop.body: ; preds = %entry - store i32 3, ptr %i1, align 4 call void (ptr, ...) @printf(ptr @.str.6) call void (ptr, ...) @printf(ptr @.str.7) - %2 = load i32, ptr %i1, align 4 - call void (ptr, ...) @printf(ptr @.str.8, i32 %2) + call void (ptr, ...) @printf(ptr @.str.8, i32 3) call void (ptr, ...) @printf(ptr @.str.9) br label %loop.exit + loop.exit: ; preds = %loop.body - br label %loop.body2 -loop.body2: ; preds = %loop.exit + br label %loop.body1 + +loop.body1: ; preds = %loop.exit call void (ptr, ...) @printf(ptr @.str.10) - store i32 3, ptr %i3, align 4 call void (ptr, ...) @printf(ptr @.str.11) call void (ptr, ...) @printf(ptr @.str.12) - %3 = load i32, ptr %i3, align 4 - call void (ptr, ...) @printf(ptr @.str.13, i32 %3) + call void (ptr, ...) @printf(ptr @.str.13, i32 3) call void (ptr, ...) @printf(ptr @.str.14) ret i64 0 } + ; Function Attrs: nounwind define i32 @main(i32 %0, ptr %1) #0 { entry: - %.anon = alloca i32, align 4 - %.anon1 = alloca ptr, align 8 %blockret = alloca i32, align 4 %temp_err = alloca i64, align 8 - store i32 %0, ptr %.anon, align 4 - store ptr %1, ptr %.anon1, align 8 br label %testblock + testblock: ; preds = %entry %2 = call i64 @foo.main() %not_err = icmp eq i64 %2, 0 %3 = call i1 @llvm.expect.i1(i1 %not_err, i1 true) br i1 %3, label %after_check, label %assign_optional + assign_optional: ; preds = %testblock store i64 %2, ptr %temp_err, align 8 br label %end_block + after_check: ; preds = %testblock store i64 0, ptr %temp_err, align 8 br label %end_block + end_block: ; preds = %after_check, %assign_optional %4 = load i64, ptr %temp_err, align 8 %neq = icmp ne i64 %4, 0 br i1 %neq, label %if.then, label %if.exit + if.then: ; preds = %end_block store i32 1, ptr %blockret, align 4 br label %expr_block.exit + if.exit: ; preds = %end_block store i32 0, ptr %blockret, align 4 br label %expr_block.exit + expr_block.exit: ; preds = %if.exit, %if.then %5 = load i32, ptr %blockret, align 4 ret i32 %5 diff --git a/test/test_suite/macros/macro_common.c3t b/test/test_suite/macros/macro_common.c3t index 925b08013..ea3a756d2 100644 --- a/test/test_suite/macros/macro_common.c3t +++ b/test/test_suite/macros/macro_common.c3t @@ -16,37 +16,16 @@ fn void test2() define void @test.test2() #0 { entry: - %x = alloca i32, align 4 %blockret = alloca double, align 8 - %x1 = alloca i32, align 4 - %blockret2 = alloca double, align 8 - store i32 1, ptr %x, align 4 - %0 = load i32, ptr %x, align 4 - %not = icmp eq i32 %0, 0 - br i1 %not, label %if.then, label %if.exit - -if.then: ; preds = %entry - store double 0.000000e+00, ptr %blockret, align 8 - br label %expr_block.exit + br label %if.exit if.exit: ; preds = %entry + br label %if.then + +if.then: ; preds = %if.exit store double 0.000000e+00, ptr %blockret, align 8 br label %expr_block.exit -expr_block.exit: ; preds = %if.exit, %if.then - store i32 0, ptr %x1, align 4 - %1 = load i32, ptr %x1, align 4 - %not3 = icmp eq i32 %1, 0 - br i1 %not3, label %if.then4, label %if.exit5 - -if.then4: ; preds = %expr_block.exit - store double 0.000000e+00, ptr %blockret2, align 8 - br label %expr_block.exit6 - -if.exit5: ; preds = %expr_block.exit - store double 0.000000e+00, ptr %blockret2, align 8 - br label %expr_block.exit6 - -expr_block.exit6: ; preds = %if.exit5, %if.then4 +expr_block.exit: ; preds = %if.then ret void } \ No newline at end of file diff --git a/test/test_suite/macros/macro_defer_with_body.c3t b/test/test_suite/macros/macro_defer_with_body.c3t index 17059c5c0..703e3d20e 100644 --- a/test/test_suite/macros/macro_defer_with_body.c3t +++ b/test/test_suite/macros/macro_defer_with_body.c3t @@ -24,31 +24,27 @@ fn void main() define void @foo.main() #0 { entry: %x = alloca i32, align 4 - %a = alloca i32, align 4 %y = alloca i32, align 4 store i32 0, ptr %x, align 4 - store i32 1, ptr %a, align 4 - %0 = load i32, ptr %a, align 4 - store i32 %0, ptr %y, align 4 - %1 = load i32, ptr %x, align 4 - %add = add i32 %1, 1 + store i32 1, ptr %y, align 4 + %0 = load i32, ptr %x, align 4 + %add = add i32 %0, 1 store i32 %add, ptr %x, align 4 - %2 = call i32 (ptr, ...) @printf(ptr @.str, i32 %1) - %3 = load i32, ptr %x, align 4 - %add1 = add i32 %3, 1 + %1 = call i32 (ptr, ...) @printf(ptr @.str, i32 %0) + %2 = load i32, ptr %x, align 4 + %add1 = add i32 %2, 1 store i32 %add1, ptr %x, align 4 - %4 = call i32 (ptr, ...) @printf(ptr @.str.1, i32 %3) - %5 = load i32, ptr %a, align 4 - store i32 %5, ptr %y, align 4 - %6 = load i32, ptr %x, align 4 - %add2 = add i32 %6, 1 + %3 = call i32 (ptr, ...) @printf(ptr @.str.1, i32 %2) + store i32 1, ptr %y, align 4 + %4 = load i32, ptr %x, align 4 + %add2 = add i32 %4, 1 store i32 %add2, ptr %x, align 4 - %7 = call i32 (ptr, ...) @printf(ptr @.str.2, i32 %6) - %8 = load i32, ptr %x, align 4 - %add3 = add i32 %8, 1 + %5 = call i32 (ptr, ...) @printf(ptr @.str.2, i32 %4) + %6 = load i32, ptr %x, align 4 + %add3 = add i32 %6, 1 store i32 %add3, ptr %x, align 4 - %9 = call i32 (ptr, ...) @printf(ptr @.str.3, i32 %8) - %10 = call i32 (ptr, ...) @printf(ptr @.str.4) + %7 = call i32 (ptr, ...) @printf(ptr @.str.3, i32 %6) + %8 = call i32 (ptr, ...) @printf(ptr @.str.4) ret void } diff --git a/test/test_suite/macros/macro_ref_errors.c3 b/test/test_suite/macros/macro_ref_errors.c3 new file mode 100644 index 000000000..b11b5ee78 --- /dev/null +++ b/test/test_suite/macros/macro_ref_errors.c3 @@ -0,0 +1,28 @@ +module test; + +import std::io; + +macro @foo(int* &hello) +{ + hello = hello; // #error: You cannot assign to a ref +} + +macro @bar(Foo* &f) +{ + f.a = 1; + int* x = &f.a; + Foo **ff = &f; // #error: You may not take the address +} + +struct Foo +{ + int a; +} + +fn void main() +{ + int a; + @foo(a); + Foo x; + @bar(x); +} \ No newline at end of file diff --git a/test/test_suite/macros/macro_typed_varargs.c3t b/test/test_suite/macros/macro_typed_varargs.c3t index 00e51970b..274537fce 100644 --- a/test/test_suite/macros/macro_typed_varargs.c3t +++ b/test/test_suite/macros/macro_typed_varargs.c3t @@ -30,19 +30,19 @@ fn void main() define void @test.main() #0 { entry: - %x = alloca %"int[]", align 8 %literal = alloca [4 x i32], align 16 + %x = alloca %"int[]", align 8 %.anon = alloca i64, align 8 %.anon1 = alloca i64, align 8 %i = alloca i32, align 4 %retparam = alloca i64, align 8 %varargslots = alloca [1 x %any], align 16 - %x2 = alloca %"any[]", align 8 - %literal3 = alloca [4 x %any], align 16 + %literal2 = alloca [4 x %any], align 16 %taddr = alloca i32, align 4 + %taddr3 = alloca i32, align 4 %taddr4 = alloca i32, align 4 %taddr5 = alloca i32, align 4 - %taddr6 = alloca i32, align 4 + %x6 = alloca %"any[]", align 8 %.anon7 = alloca i64, align 8 %.anon8 = alloca i64, align 8 %i12 = alloca %any, align 8 @@ -86,30 +86,30 @@ loop.body: ; preds = %loop.cond store i64 %add, ptr %.anon1, align 8 br label %loop.cond loop.exit: ; preds = %loop.cond - %19 = getelementptr inbounds [4 x %any], ptr %literal3, i64 0, i64 0 + %19 = getelementptr inbounds [4 x %any], ptr %literal2, i64 0, i64 0 store i32 1, ptr %taddr, align 4 %20 = insertvalue %any undef, ptr %taddr, 0 %21 = insertvalue %any %20, i64 ptrtoint (ptr @"$ct.int" to i64), 1 store %any %21, ptr %19, align 8 - %22 = getelementptr inbounds [4 x %any], ptr %literal3, i64 0, i64 1 - store i32 -1, ptr %taddr4, align 4 - %23 = insertvalue %any undef, ptr %taddr4, 0 + %22 = getelementptr inbounds [4 x %any], ptr %literal2, i64 0, i64 1 + store i32 -1, ptr %taddr3, align 4 + %23 = insertvalue %any undef, ptr %taddr3, 0 %24 = insertvalue %any %23, i64 ptrtoint (ptr @"$ct.int" to i64), 1 store %any %24, ptr %22, align 8 - %25 = getelementptr inbounds [4 x %any], ptr %literal3, i64 0, i64 2 - store i32 3141, ptr %taddr5, align 4 - %26 = insertvalue %any undef, ptr %taddr5, 0 + %25 = getelementptr inbounds [4 x %any], ptr %literal2, i64 0, i64 2 + store i32 3141, ptr %taddr4, align 4 + %26 = insertvalue %any undef, ptr %taddr4, 0 %27 = insertvalue %any %26, i64 ptrtoint (ptr @"$ct.int" to i64), 1 store %any %27, ptr %25, align 8 - %28 = getelementptr inbounds [4 x %any], ptr %literal3, i64 0, i64 3 - store i32 1000, ptr %taddr6, align 4 - %29 = insertvalue %any undef, ptr %taddr6, 0 + %28 = getelementptr inbounds [4 x %any], ptr %literal2, i64 0, i64 3 + store i32 1000, ptr %taddr5, align 4 + %29 = insertvalue %any undef, ptr %taddr5, 0 %30 = insertvalue %any %29, i64 ptrtoint (ptr @"$ct.int" to i64), 1 store %any %30, ptr %28, align 8 - %31 = insertvalue %"any[]" undef, ptr %literal3, 0 + %31 = insertvalue %"any[]" undef, ptr %literal2, 0 %32 = insertvalue %"any[]" %31, i64 4, 1 - store %"any[]" %32, ptr %x2, align 8 - %33 = getelementptr inbounds %"any[]", ptr %x2, i32 0, i32 1 + store %"any[]" %32, ptr %x6, align 8 + %33 = getelementptr inbounds %"any[]", ptr %x6, i32 0, i32 1 %34 = load i64, ptr %33, align 8 store i64 %34, ptr %.anon7, align 8 store i64 0, ptr %.anon8, align 8 @@ -120,7 +120,7 @@ loop.cond9: ; preds = %loop.body11, %loop. %lt10 = icmp ult i64 %35, %36 br i1 %lt10, label %loop.body11, label %loop.exit17 loop.body11: ; preds = %loop.cond9 - %37 = getelementptr inbounds %"any[]", ptr %x2, i32 0, i32 0 + %37 = getelementptr inbounds %"any[]", ptr %x6, i32 0, i32 0 %38 = load ptr, ptr %37, align 8 %39 = load i64, ptr %.anon8, align 8 %ptroffset13 = getelementptr inbounds %any, ptr %38, i64 %39 diff --git a/test/test_suite/macros/macro_untyped_varargs_2.c3t b/test/test_suite/macros/macro_untyped_varargs_2.c3t index 7500b80af..325544b89 100644 --- a/test/test_suite/macros/macro_untyped_varargs_2.c3t +++ b/test/test_suite/macros/macro_untyped_varargs_2.c3t @@ -34,9 +34,9 @@ macro foo3(...) macro @foo4(...) { - $typeof($varef(0)) a = $varef(0); - $varef(0) = $varef(1); - $varef(1) = a; + $typeof(*$varef(0)) a = *$varef(0); + *$varef(0) = *$varef(1); + *$varef(1) = a; } fn int ping(int val) { @@ -76,126 +76,124 @@ entry: define void @test.main() #0 { entry: - %.anon = alloca i32, align 4 - %.anon1 = alloca i32, align 4 - %.anon2 = alloca i32, align 4 - %.anon3 = alloca i32, align 4 %i = alloca i32, align 4 %j = alloca i32, align 4 %retparam = alloca i64, align 8 %varargslots = alloca [1 x %any], align 16 + %taddr = alloca i32, align 4 + %retparam2 = alloca i64, align 8 + %varargslots3 = alloca [1 x %any], align 16 + %taddr4 = alloca i32, align 4 %retparam5 = alloca i64, align 8 %varargslots6 = alloca [1 x %any], align 16 - %retparam7 = alloca i64, align 8 - %varargslots8 = alloca [1 x %any], align 16 - %retparam9 = alloca i64, align 8 - %varargslots10 = alloca [1 x %any], align 16 + %taddr7 = alloca i32, align 4 + %retparam8 = alloca i64, align 8 + %varargslots9 = alloca [1 x %any], align 16 + %taddr10 = alloca i32, align 4 %x = alloca i32, align 4 %retparam11 = alloca i64, align 8 %varargslots12 = alloca [1 x %any], align 16 - %taddr = alloca %"char[]", align 8 - %x13 = alloca double, align 8 - %retparam14 = alloca i64, align 8 - %varargslots15 = alloca [1 x %any], align 16 - %taddr16 = alloca %"char[]", align 8 - %retparam17 = alloca i64, align 8 - %varargslots18 = alloca [1 x %any], align 16 - %taddr19 = alloca i32, align 4 - %x20 = alloca i32, align 4 + %taddr13 = alloca %"char[]", align 8 + %x14 = alloca double, align 8 + %retparam15 = alloca i64, align 8 + %varargslots16 = alloca [1 x %any], align 16 + %taddr17 = alloca %"char[]", align 8 + %retparam18 = alloca i64, align 8 + %varargslots19 = alloca [1 x %any], align 16 + %taddr20 = alloca i32, align 4 + %x21 = alloca i32, align 4 %y = alloca i32, align 4 %a = alloca i32, align 4 - %retparam21 = alloca i64, align 8 - %varargslots22 = alloca [2 x %any], align 16 - %a23 = alloca i32, align 4 - %retparam24 = alloca i64, align 8 - %varargslots25 = alloca [2 x %any], align 16 + %retparam22 = alloca i64, align 8 + %varargslots23 = alloca [2 x %any], align 16 + %a24 = alloca i32, align 4 + %retparam25 = alloca i64, align 8 + %varargslots26 = alloca [2 x %any], align 16 %0 = call i32 @test.ping(i32 -1) - store i32 %0, ptr %.anon, align 4 %1 = call i32 @test.ping(i32 1) - store i32 %1, ptr %.anon1, align 4 %2 = call i32 @test.ping(i32 3141) - store i32 %2, ptr %.anon2, align 4 %3 = call i32 @test.ping(i32 1000) - store i32 %3, ptr %.anon3, align 4 - %4 = load i32, ptr %.anon, align 4 - %5 = load i32, ptr %.anon, align 4 - %add = add i32 %4, %5 + %add = add i32 %0, %0 store i32 %add, ptr %i, align 4 - %6 = call i32 @test.ping(i32 3141) - %7 = call i32 @test.ping(i32 3141) - %add4 = add i32 %6, %7 - store i32 %add4, ptr %j, align 4 - %8 = insertvalue %any undef, ptr %.anon1, 0 - %9 = insertvalue %any %8, i64 ptrtoint (ptr @"$ct.int" to i64), 1 - %10 = getelementptr inbounds [1 x %any], ptr %varargslots, i64 0, i64 0 - store %any %9, ptr %10, align 16 - %11 = call i64 @std.io.printfn(ptr %retparam, ptr @.str.1, i64 2, ptr %varargslots, i64 1) - %12 = insertvalue %any undef, ptr %.anon, 0 - %13 = insertvalue %any %12, i64 ptrtoint (ptr @"$ct.int" to i64), 1 - %14 = getelementptr inbounds [1 x %any], ptr %varargslots6, i64 0, i64 0 - store %any %13, ptr %14, align 16 - %15 = call i64 @std.io.printfn(ptr %retparam5, ptr @.str.2, i64 2, ptr %varargslots6, i64 1) - %16 = insertvalue %any undef, ptr %.anon2, 0 - %17 = insertvalue %any %16, i64 ptrtoint (ptr @"$ct.int" to i64), 1 - %18 = getelementptr inbounds [1 x %any], ptr %varargslots8, i64 0, i64 0 - store %any %17, ptr %18, align 16 - %19 = call i64 @std.io.printfn(ptr %retparam7, ptr @.str.3, i64 2, ptr %varargslots8, i64 1) - %20 = insertvalue %any undef, ptr %.anon3, 0 - %21 = insertvalue %any %20, i64 ptrtoint (ptr @"$ct.int" to i64), 1 - %22 = getelementptr inbounds [1 x %any], ptr %varargslots10, i64 0, i64 0 - store %any %21, ptr %22, align 16 - %23 = call i64 @std.io.printfn(ptr %retparam9, ptr @.str.4, i64 2, ptr %varargslots10, i64 1) + %4 = call i32 @test.ping(i32 3141) + %5 = call i32 @test.ping(i32 3141) + %add1 = add i32 %4, %5 + store i32 %add1, ptr %j, align 4 + store i32 %1, ptr %taddr, align 4 + %6 = insertvalue %any undef, ptr %taddr, 0 + %7 = insertvalue %any %6, i64 ptrtoint (ptr @"$ct.int" to i64), 1 + %8 = getelementptr inbounds [1 x %any], ptr %varargslots, i64 0, i64 0 + store %any %7, ptr %8, align 16 + %9 = call i64 @std.io.printfn(ptr %retparam, ptr @.str.1, i64 2, ptr %varargslots, i64 1) + store i32 %0, ptr %taddr4, align 4 + %10 = insertvalue %any undef, ptr %taddr4, 0 + %11 = insertvalue %any %10, i64 ptrtoint (ptr @"$ct.int" to i64), 1 + %12 = getelementptr inbounds [1 x %any], ptr %varargslots3, i64 0, i64 0 + store %any %11, ptr %12, align 16 + %13 = call i64 @std.io.printfn(ptr %retparam2, ptr @.str.2, i64 2, ptr %varargslots3, i64 1) + store i32 %2, ptr %taddr7, align 4 + %14 = insertvalue %any undef, ptr %taddr7, 0 + %15 = insertvalue %any %14, i64 ptrtoint (ptr @"$ct.int" to i64), 1 + %16 = getelementptr inbounds [1 x %any], ptr %varargslots6, i64 0, i64 0 + store %any %15, ptr %16, align 16 + %17 = call i64 @std.io.printfn(ptr %retparam5, ptr @.str.3, i64 2, ptr %varargslots6, i64 1) + store i32 %3, ptr %taddr10, align 4 + %18 = insertvalue %any undef, ptr %taddr10, 0 + %19 = insertvalue %any %18, i64 ptrtoint (ptr @"$ct.int" to i64), 1 + %20 = getelementptr inbounds [1 x %any], ptr %varargslots9, i64 0, i64 0 + store %any %19, ptr %20, align 16 + %21 = call i64 @std.io.printfn(ptr %retparam8, ptr @.str.4, i64 2, ptr %varargslots9, i64 1) store i32 0, ptr %x, align 4 - store %"char[]" { ptr @.str.6, i64 3 }, ptr %taddr, align 8 - %24 = insertvalue %any undef, ptr %taddr, 0 - %25 = insertvalue %any %24, i64 ptrtoint (ptr @"$ct.String" to i64), 1 - %26 = getelementptr inbounds [1 x %any], ptr %varargslots12, i64 0, i64 0 - store %any %25, ptr %26, align 16 - %27 = call i64 @std.io.printfn(ptr %retparam11, ptr @.str.5, i64 2, ptr %varargslots12, i64 1) - store double 0.000000e+00, ptr %x13, align 8 - store %"char[]" { ptr @.str.8, i64 6 }, ptr %taddr16, align 8 - %28 = insertvalue %any undef, ptr %taddr16, 0 - %29 = insertvalue %any %28, i64 ptrtoint (ptr @"$ct.String" to i64), 1 - %30 = getelementptr inbounds [1 x %any], ptr %varargslots15, i64 0, i64 0 - store %any %29, ptr %30, align 16 - %31 = call i64 @std.io.printfn(ptr %retparam14, ptr @.str.7, i64 2, ptr %varargslots15, i64 1) - store i32 105, ptr %taddr19, align 4 - %32 = insertvalue %any undef, ptr %taddr19, 0 - %33 = insertvalue %any %32, i64 ptrtoint (ptr @"$ct.int" to i64), 1 - %34 = getelementptr inbounds [1 x %any], ptr %varargslots18, i64 0, i64 0 - store %any %33, ptr %34, align 16 - %35 = call i64 @std.io.printfn(ptr %retparam17, ptr @.str.9, i64 2, ptr %varargslots18, i64 1) - store i32 123, ptr %x20, align 4 + store %"char[]" { ptr @.str.6, i64 3 }, ptr %taddr13, align 8 + %22 = insertvalue %any undef, ptr %taddr13, 0 + %23 = insertvalue %any %22, i64 ptrtoint (ptr @"$ct.String" to i64), 1 + %24 = getelementptr inbounds [1 x %any], ptr %varargslots12, i64 0, i64 0 + store %any %23, ptr %24, align 16 + %25 = call i64 @std.io.printfn(ptr %retparam11, ptr @.str.5, i64 2, ptr %varargslots12, i64 1) + store double 0.000000e+00, ptr %x14, align 8 + store %"char[]" { ptr @.str.8, i64 6 }, ptr %taddr17, align 8 + %26 = insertvalue %any undef, ptr %taddr17, 0 + %27 = insertvalue %any %26, i64 ptrtoint (ptr @"$ct.String" to i64), 1 + %28 = getelementptr inbounds [1 x %any], ptr %varargslots16, i64 0, i64 0 + store %any %27, ptr %28, align 16 + %29 = call i64 @std.io.printfn(ptr %retparam15, ptr @.str.7, i64 2, ptr %varargslots16, i64 1) + store i32 105, ptr %taddr20, align 4 + %30 = insertvalue %any undef, ptr %taddr20, 0 + %31 = insertvalue %any %30, i64 ptrtoint (ptr @"$ct.int" to i64), 1 + %32 = getelementptr inbounds [1 x %any], ptr %varargslots19, i64 0, i64 0 + store %any %31, ptr %32, align 16 + %33 = call i64 @std.io.printfn(ptr %retparam18, ptr @.str.9, i64 2, ptr %varargslots19, i64 1) + store i32 123, ptr %x21, align 4 store i32 33, ptr %y, align 4 - %36 = load i32, ptr %x20, align 4 - store i32 %36, ptr %a, align 4 - %37 = load i32, ptr %y, align 4 - store i32 %37, ptr %x20, align 4 - %38 = load i32, ptr %a, align 4 - store i32 %38, ptr %y, align 4 - %39 = insertvalue %any undef, ptr %x20, 0 - %40 = insertvalue %any %39, i64 ptrtoint (ptr @"$ct.int" to i64), 1 - %41 = getelementptr inbounds [2 x %any], ptr %varargslots22, i64 0, i64 0 - store %any %40, ptr %41, align 16 - %42 = insertvalue %any undef, ptr %y, 0 - %43 = insertvalue %any %42, i64 ptrtoint (ptr @"$ct.int" to i64), 1 - %44 = getelementptr inbounds [2 x %any], ptr %varargslots22, i64 0, i64 1 - store %any %43, ptr %44, align 16 - %45 = call i64 @std.io.printfn(ptr %retparam21, ptr @.str.10, i64 6, ptr %varargslots22, i64 2) - %46 = load i32, ptr %x20, align 4 - store i32 %46, ptr %a23, align 4 - %47 = load i32, ptr %y, align 4 - store i32 %47, ptr %x20, align 4 - %48 = load i32, ptr %a23, align 4 - store i32 %48, ptr %y, align 4 - %49 = insertvalue %any undef, ptr %x20, 0 - %50 = insertvalue %any %49, i64 ptrtoint (ptr @"$ct.int" to i64), 1 - %51 = getelementptr inbounds [2 x %any], ptr %varargslots25, i64 0, i64 0 - store %any %50, ptr %51, align 16 - %52 = insertvalue %any undef, ptr %y, 0 - %53 = insertvalue %any %52, i64 ptrtoint (ptr @"$ct.int" to i64), 1 - %54 = getelementptr inbounds [2 x %any], ptr %varargslots25, i64 0, i64 1 - store %any %53, ptr %54, align 16 - %55 = call i64 @std.io.printfn(ptr %retparam24, ptr @.str.11, i64 6, ptr %varargslots25, i64 2) + %34 = load i32, ptr %x21, align 4 + store i32 %34, ptr %a, align 4 + %35 = load i32, ptr %y, align 4 + store i32 %35, ptr %x21, align 4 + %36 = load i32, ptr %a, align 4 + store i32 %36, ptr %y, align 4 + %37 = insertvalue %any undef, ptr %x21, 0 + %38 = insertvalue %any %37, i64 ptrtoint (ptr @"$ct.int" to i64), 1 + %39 = getelementptr inbounds [2 x %any], ptr %varargslots23, i64 0, i64 0 + store %any %38, ptr %39, align 16 + %40 = insertvalue %any undef, ptr %y, 0 + %41 = insertvalue %any %40, i64 ptrtoint (ptr @"$ct.int" to i64), 1 + %42 = getelementptr inbounds [2 x %any], ptr %varargslots23, i64 0, i64 1 + store %any %41, ptr %42, align 16 + %43 = call i64 @std.io.printfn(ptr %retparam22, ptr @.str.10, i64 6, ptr %varargslots23, i64 2) + %44 = load i32, ptr %x21, align 4 + store i32 %44, ptr %a24, align 4 + %45 = load i32, ptr %y, align 4 + store i32 %45, ptr %x21, align 4 + %46 = load i32, ptr %a24, align 4 + store i32 %46, ptr %y, align 4 + %47 = insertvalue %any undef, ptr %x21, 0 + %48 = insertvalue %any %47, i64 ptrtoint (ptr @"$ct.int" to i64), 1 + %49 = getelementptr inbounds [2 x %any], ptr %varargslots26, i64 0, i64 0 + store %any %48, ptr %49, align 16 + %50 = insertvalue %any undef, ptr %y, 0 + %51 = insertvalue %any %50, i64 ptrtoint (ptr @"$ct.int" to i64), 1 + %52 = getelementptr inbounds [2 x %any], ptr %varargslots26, i64 0, i64 1 + store %any %51, ptr %52, align 16 + %53 = call i64 @std.io.printfn(ptr %retparam25, ptr @.str.11, i64 6, ptr %varargslots26, i64 2) ret void } \ No newline at end of file diff --git a/test/test_suite/macros/macro_with_body.c3t b/test/test_suite/macros/macro_with_body.c3t index 88bfeb71e..d0a15095c 100644 --- a/test/test_suite/macros/macro_with_body.c3t +++ b/test/test_suite/macros/macro_with_body.c3t @@ -16,8 +16,8 @@ fn int Foo.mutate(Foo *foo) macro @macro_with_body(foo, &x; @body(x, y)) { - x = foo.x; - @body(foo.mutate(), x); + *x = foo.x; + @body(foo.mutate(), *x); } macro @repeat(int times; @body(x)) @@ -63,7 +63,6 @@ entry: %foo = alloca %Foo, align 4 %x = alloca i32, align 4 %dy = alloca i32, align 4 - %times = alloca i32, align 4 %i = alloca i32, align 4 %loop = alloca i32, align 4 call void @llvm.memcpy.p0.p0.i32(ptr align 4 %f, ptr align 4 @.__const, i32 4, i1 false) @@ -79,24 +78,22 @@ entry: %4 = load i32, ptr %x, align 4 %5 = load i32, ptr %dy, align 4 %6 = call i32 (ptr, ...) @printf(ptr @.str, i32 %4, i32 %5) - store i32 10, ptr %times, align 4 store i32 0, ptr %i, align 4 br label %loop.cond loop.cond: ; preds = %loop.body, %entry %7 = load i32, ptr %i, align 4 - %8 = load i32, ptr %times, align 4 - %lt = icmp slt i32 %7, %8 + %lt = icmp slt i32 %7, 10 br i1 %lt, label %loop.body, label %loop.exit loop.body: ; preds = %loop.cond - %9 = load i32, ptr %i, align 4 - %add = add i32 %9, 1 + %8 = load i32, ptr %i, align 4 + %add = add i32 %8, 1 store i32 %add, ptr %loop, align 4 - %10 = load i32, ptr %loop, align 4 - %11 = call i32 (ptr, ...) @printf(ptr @.str.1, i32 %10) - %12 = load i32, ptr %i, align 4 - %add1 = add i32 %12, 1 + %9 = load i32, ptr %loop, align 4 + %10 = call i32 (ptr, ...) @printf(ptr @.str.1, i32 %9) + %11 = load i32, ptr %i, align 4 + %add1 = add i32 %11, 1 store i32 %add1, ptr %i, align 4 br label %loop.cond diff --git a/test/test_suite/macros/macro_with_body_err.c3 b/test/test_suite/macros/macro_with_body_err.c3 new file mode 100644 index 000000000..cb37bb456 --- /dev/null +++ b/test/test_suite/macros/macro_with_body_err.c3 @@ -0,0 +1,33 @@ +module withbody; + + +extern fn int printf(char *, ...); + +struct Foo +{ + int x; +} + +fn int Foo.mutate(Foo *foo) +{ + printf("Mutating\n"); + return 10 * ++foo.x; +} + +macro @macro_with_body(foo, &x; @body(x, y)) +{ + *x = foo.x; + @body(foo.mutate(), x); // #error: Implicitly casting +} + + +fn void main() +{ + Foo f = { 33 }; + int y; + @macro_with_body(f, y; int x, int dy) + { + printf("Got values %d, %d\n", x, dy); + }; + +} \ No newline at end of file diff --git a/test/test_suite/methods/methods_with_inferred_type.c3t b/test/test_suite/methods/methods_with_inferred_type.c3t index f38c5647f..9d2530e04 100644 --- a/test/test_suite/methods/methods_with_inferred_type.c3t +++ b/test/test_suite/methods/methods_with_inferred_type.c3t @@ -16,7 +16,7 @@ fn void Foo.add(&f) macro void Foo.add_macro(&f) { - f++; + (*f)++; } fn int Abc.add(&a) diff --git a/test/test_suite/statements/custom_foreach_with_ref.c3t b/test/test_suite/statements/custom_foreach_with_ref.c3t index db2e53624..94fc6821d 100644 --- a/test/test_suite/statements/custom_foreach_with_ref.c3t +++ b/test/test_suite/statements/custom_foreach_with_ref.c3t @@ -8,17 +8,17 @@ struct Foo extern fn void printf(char*, ...); -macro int* Foo.@operator_element_at_ref(Foo &f, int a) @operator(&[]) +macro int* Foo.@operator_element_at_ref(Foo* &f, int a) @operator(&[]) { return &f.a[a]; } -macro int Foo.@operator_len(Foo &f) @operator(len) +macro int Foo.@operator_len(Foo* &f) @operator(len) { return 3; } -macro int Foo.@operator_element_at(Foo &f, int a) @operator([]) +macro int Foo.@operator_element_at(Foo* &f, int a) @operator([]) { return f.a[a]; } @@ -28,7 +28,7 @@ fn int[5] getFields() printf("getFields\n"); return int[5] { 3, 5, 2, 10, 111}; } -fn Foo *call(Foo *f) +fn Foo *call(Foo* f) { printf("Call made\n"); return f; @@ -102,6 +102,10 @@ fn void main() @.str.12 = private unnamed_addr constant [7 x i8] c"%d %d\0A\00", align 1 @.str.13 = private unnamed_addr constant [7 x i8] c"%d %d\0A\00", align 1 +; Function Attrs: nounwind +declare void @printf(ptr, ...) #0 + +; Function Attrs: nounwind define void @foo.getFields(ptr noalias sret([5 x i32]) align 4 %0) #0 { entry: %literal = alloca [5 x i32], align 16 @@ -129,349 +133,317 @@ entry: define void @foo.main() #0 { entry: %x = alloca %Foo, align 4 - %a = alloca i32, align 4 - %a1 = alloca i32, align 4 - %a3 = alloca i32, align 4 %.anon = alloca ptr, align 8 - %.anon5 = alloca i32, align 4 - %.anon6 = alloca i32, align 4 + %.anon1 = alloca i32, align 4 + %.anon2 = alloca i32, align 4 %i = alloca i32, align 4 %y = alloca i32, align 4 - %a7 = alloca i32, align 4 - %.anon9 = alloca i32, align 4 - %.anon10 = alloca i32, align 4 - %i14 = alloca i32, align 4 - %y15 = alloca ptr, align 8 - %a16 = alloca i32, align 4 - %.anon21 = alloca i32, align 4 - %.anon22 = alloca i32, align 4 - %i26 = alloca i32, align 4 - %y27 = alloca i32, align 4 - %a28 = alloca i32, align 4 - %.anon32 = alloca i32, align 4 - %.anon33 = alloca i32, align 4 - %i37 = alloca i32, align 4 - %y38 = alloca i32, align 4 - %a39 = alloca i32, align 4 - %.anon43 = alloca i32, align 4 - %.anon44 = alloca i32, align 4 - %i48 = alloca i32, align 4 - %y49 = alloca i32, align 4 - %a50 = alloca i32, align 4 - %.anon55 = alloca [5 x i32], align 16 - %.anon56 = alloca i64, align 8 - %i59 = alloca i64, align 8 - %y60 = alloca i32, align 4 - %.anon64 = alloca [5 x i32], align 16 - %.anon65 = alloca i64, align 8 - %i69 = alloca i64, align 8 - %y70 = alloca i32, align 4 - %.anon73 = alloca ptr, align 8 + %a = alloca i32, align 4 + %.anon3 = alloca i32, align 4 + %.anon4 = alloca i32, align 4 + %i8 = alloca i32, align 4 + %y9 = alloca ptr, align 8 + %a10 = alloca i32, align 4 + %.anon15 = alloca i32, align 4 + %.anon16 = alloca i32, align 4 + %i20 = alloca i32, align 4 + %y21 = alloca i32, align 4 + %a22 = alloca i32, align 4 + %.anon26 = alloca i32, align 4 + %.anon27 = alloca i32, align 4 + %i31 = alloca i32, align 4 + %y32 = alloca i32, align 4 + %a33 = alloca i32, align 4 + %.anon37 = alloca i32, align 4 + %.anon38 = alloca i32, align 4 + %i42 = alloca i32, align 4 + %y43 = alloca i32, align 4 + %a44 = alloca i32, align 4 + %.anon49 = alloca [5 x i32], align 16 + %.anon50 = alloca i64, align 8 + %i53 = alloca i64, align 8 + %y54 = alloca i32, align 4 + %.anon58 = alloca [5 x i32], align 16 + %.anon59 = alloca i64, align 8 + %i63 = alloca i64, align 8 + %y64 = alloca i32, align 4 + %.anon67 = alloca ptr, align 8 %sretparam = alloca [5 x i32], align 4 - %.anon74 = alloca i64, align 8 - %i78 = alloca i64, align 8 - %y79 = alloca i32, align 4 - %a82 = alloca i32, align 4 - %a84 = alloca i32, align 4 - %y86 = alloca ptr, align 8 - %a87 = alloca i32, align 4 - %a90 = alloca i32, align 4 - %a92 = alloca i32, align 4 + %.anon68 = alloca i64, align 8 + %i72 = alloca i64, align 8 + %y73 = alloca i32, align 4 + %y76 = alloca ptr, align 8 call void @llvm.memcpy.p0.p0.i32(ptr align 4 %x, ptr align 4 @.__const, i32 12, i1 false) - store i32 0, ptr %a, align 4 %0 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 - %1 = load i32, ptr %a, align 4 - %sext = sext i32 %1 to i64 - %2 = getelementptr inbounds [3 x i32], ptr %0, i64 0, i64 %sext - %3 = load i32, ptr %2, align 4 - store i32 1, ptr %a1, align 4 - %4 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 - %5 = load i32, ptr %a1, align 4 - %sext2 = sext i32 %5 to i64 - %6 = getelementptr inbounds [3 x i32], ptr %4, i64 0, i64 %sext2 - %7 = load i32, ptr %6, align 4 - store i32 2, ptr %a3, align 4 - %8 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 - %9 = load i32, ptr %a3, align 4 - %sext4 = sext i32 %9 to i64 - %10 = getelementptr inbounds [3 x i32], ptr %8, i64 0, i64 %sext4 - %11 = load i32, ptr %10, align 4 - call void (ptr, ...) @printf(ptr @.str.2, i32 %3, i32 %7, i32 %11) - %12 = call ptr @foo.call(ptr %x) - store ptr %12, ptr %.anon, align 8 - store i32 3, ptr %.anon5, align 4 - store i32 0, ptr %.anon6, align 4 + %1 = getelementptr inbounds [3 x i32], ptr %0, i64 0, i64 0 + %2 = load i32, ptr %1, align 4 + %3 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 + %4 = getelementptr inbounds [3 x i32], ptr %3, i64 0, i64 1 + %5 = load i32, ptr %4, align 4 + %6 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 + %7 = getelementptr inbounds [3 x i32], ptr %6, i64 0, i64 2 + %8 = load i32, ptr %7, align 4 + call void (ptr, ...) @printf(ptr @.str.2, i32 %2, i32 %5, i32 %8) + %9 = call ptr @foo.call(ptr %x) + store ptr %9, ptr %.anon, align 8 + store i32 3, ptr %.anon1, align 4 + store i32 0, ptr %.anon2, align 4 br label %loop.cond loop.cond: ; preds = %loop.body, %entry - %13 = load i32, ptr %.anon6, align 4 - %14 = load i32, ptr %.anon5, align 4 - %lt = icmp slt i32 %13, %14 + %10 = load i32, ptr %.anon2, align 4 + %11 = load i32, ptr %.anon1, align 4 + %lt = icmp slt i32 %10, %11 br i1 %lt, label %loop.body, label %loop.exit loop.body: ; preds = %loop.cond - %15 = load i32, ptr %.anon6, align 4 - store i32 %15, ptr %i, align 4 - %16 = load ptr, ptr %.anon, align 8 - %17 = load i32, ptr %.anon6, align 4 - store i32 %17, ptr %a7, align 4 - %18 = getelementptr inbounds %Foo, ptr %16, i32 0, i32 0 - %19 = load i32, ptr %a7, align 4 - %sext8 = sext i32 %19 to i64 - %20 = getelementptr inbounds [3 x i32], ptr %18, i64 0, i64 %sext8 - %21 = load i32, ptr %20, align 4 - store i32 %21, ptr %y, align 4 - %22 = load i32, ptr %i, align 4 - %23 = load i32, ptr %y, align 4 - call void (ptr, ...) @printf(ptr @.str.3, i32 %22, i32 %23) - %24 = load i32, ptr %.anon6, align 4 - %add = add i32 %24, 1 - store i32 %add, ptr %.anon6, align 4 + %12 = load i32, ptr %.anon2, align 4 + store i32 %12, ptr %i, align 4 + %13 = load ptr, ptr %.anon, align 8 + %14 = load i32, ptr %.anon2, align 4 + store i32 %14, ptr %a, align 4 + %15 = getelementptr inbounds %Foo, ptr %13, i32 0, i32 0 + %16 = load i32, ptr %a, align 4 + %sext = sext i32 %16 to i64 + %17 = getelementptr inbounds [3 x i32], ptr %15, i64 0, i64 %sext + %18 = load i32, ptr %17, align 4 + store i32 %18, ptr %y, align 4 + %19 = load i32, ptr %i, align 4 + %20 = load i32, ptr %y, align 4 + call void (ptr, ...) @printf(ptr @.str.3, i32 %19, i32 %20) + %21 = load i32, ptr %.anon2, align 4 + %add = add i32 %21, 1 + store i32 %add, ptr %.anon2, align 4 br label %loop.cond loop.exit: ; preds = %loop.cond - store i32 3, ptr %.anon9, align 4 - store i32 0, ptr %.anon10, align 4 - br label %loop.cond11 - -loop.cond11: ; preds = %loop.body13, %loop.exit - %25 = load i32, ptr %.anon10, align 4 - %26 = load i32, ptr %.anon9, align 4 - %lt12 = icmp slt i32 %25, %26 - br i1 %lt12, label %loop.body13, label %loop.exit20 - -loop.body13: ; preds = %loop.cond11 - %27 = load i32, ptr %.anon10, align 4 - store i32 %27, ptr %i14, align 4 - %28 = load i32, ptr %.anon10, align 4 - store i32 %28, ptr %a16, align 4 - %29 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 - %30 = load i32, ptr %a16, align 4 - %sext17 = sext i32 %30 to i64 - %31 = getelementptr inbounds [3 x i32], ptr %29, i64 0, i64 %sext17 - store ptr %31, ptr %y15, align 8 - %32 = load ptr, ptr %y15, align 8 + store i32 3, ptr %.anon3, align 4 + store i32 0, ptr %.anon4, align 4 + br label %loop.cond5 + +loop.cond5: ; preds = %loop.body7, %loop.exit + %22 = load i32, ptr %.anon4, align 4 + %23 = load i32, ptr %.anon3, align 4 + %lt6 = icmp slt i32 %22, %23 + br i1 %lt6, label %loop.body7, label %loop.exit14 + +loop.body7: ; preds = %loop.cond5 + %24 = load i32, ptr %.anon4, align 4 + store i32 %24, ptr %i8, align 4 + %25 = load i32, ptr %.anon4, align 4 + store i32 %25, ptr %a10, align 4 + %26 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 + %27 = load i32, ptr %a10, align 4 + %sext11 = sext i32 %27 to i64 + %28 = getelementptr inbounds [3 x i32], ptr %26, i64 0, i64 %sext11 + store ptr %28, ptr %y9, align 8 + %29 = load ptr, ptr %y9, align 8 + %30 = load i32, ptr %29, align 4 + %add12 = add i32 %30, 1 + store i32 %add12, ptr %29, align 4 + %31 = load i32, ptr %i8, align 4 + %32 = load ptr, ptr %y9, align 8 %33 = load i32, ptr %32, align 4 - %add18 = add i32 %33, 1 - store i32 %add18, ptr %32, align 4 - %34 = load i32, ptr %i14, align 4 - %35 = load ptr, ptr %y15, align 8 - %36 = load i32, ptr %35, align 4 - call void (ptr, ...) @printf(ptr @.str.4, i32 %34, i32 %36) - %37 = load i32, ptr %.anon10, align 4 - %add19 = add i32 %37, 1 - store i32 %add19, ptr %.anon10, align 4 - br label %loop.cond11 - -loop.exit20: ; preds = %loop.cond11 - store i32 3, ptr %.anon21, align 4 - store i32 0, ptr %.anon22, align 4 - br label %loop.cond23 - -loop.cond23: ; preds = %loop.body25, %loop.exit20 - %38 = load i32, ptr %.anon22, align 4 - %39 = load i32, ptr %.anon21, align 4 - %lt24 = icmp slt i32 %38, %39 - br i1 %lt24, label %loop.body25, label %loop.exit31 - -loop.body25: ; preds = %loop.cond23 - %40 = load i32, ptr %.anon22, align 4 - store i32 %40, ptr %i26, align 4 - %41 = load i32, ptr %.anon22, align 4 - store i32 %41, ptr %a28, align 4 - %42 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 - %43 = load i32, ptr %a28, align 4 - %sext29 = sext i32 %43 to i64 - %44 = getelementptr inbounds [3 x i32], ptr %42, i64 0, i64 %sext29 - %45 = load i32, ptr %44, align 4 - store i32 %45, ptr %y27, align 4 - %46 = load i32, ptr %i26, align 4 - %47 = load i32, ptr %y27, align 4 - call void (ptr, ...) @printf(ptr @.str.5, i32 %46, i32 %47) - %48 = load i32, ptr %.anon22, align 4 - %add30 = add i32 %48, 1 - store i32 %add30, ptr %.anon22, align 4 - br label %loop.cond23 - -loop.exit31: ; preds = %loop.cond23 - store i32 3, ptr %.anon32, align 4 - store i32 0, ptr %.anon33, align 4 - br label %loop.cond34 - -loop.cond34: ; preds = %loop.body36, %loop.exit31 - %49 = load i32, ptr %.anon33, align 4 - %50 = load i32, ptr %.anon32, align 4 - %lt35 = icmp slt i32 %49, %50 - br i1 %lt35, label %loop.body36, label %loop.exit42 - -loop.body36: ; preds = %loop.cond34 - %51 = load i32, ptr %.anon33, align 4 - store i32 %51, ptr %i37, align 4 - %52 = load i32, ptr %.anon33, align 4 - store i32 %52, ptr %a39, align 4 - %53 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 - %54 = load i32, ptr %a39, align 4 - %sext40 = sext i32 %54 to i64 - %55 = getelementptr inbounds [3 x i32], ptr %53, i64 0, i64 %sext40 - %56 = load i32, ptr %55, align 4 - store i32 %56, ptr %y38, align 4 - %57 = load i32, ptr %i37, align 4 - %58 = load i32, ptr %y38, align 4 - call void (ptr, ...) @printf(ptr @.str.6, i32 %57, i32 %58) - %59 = load i32, ptr %.anon33, align 4 - %add41 = add i32 %59, 1 - store i32 %add41, ptr %.anon33, align 4 - br label %loop.cond34 - -loop.exit42: ; preds = %loop.cond34 - store i32 3, ptr %.anon43, align 4 - store i32 0, ptr %.anon44, align 4 - br label %loop.cond45 - -loop.cond45: ; preds = %loop.body47, %loop.exit42 - %60 = load i32, ptr %.anon44, align 4 - %61 = load i32, ptr %.anon43, align 4 - %lt46 = icmp slt i32 %60, %61 - br i1 %lt46, label %loop.body47, label %loop.exit54 - -loop.body47: ; preds = %loop.cond45 - %62 = load i32, ptr %.anon44, align 4 - store i32 %62, ptr %i48, align 4 - %63 = load i32, ptr %.anon44, align 4 - store i32 %63, ptr %a50, align 4 - %64 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 - %65 = load i32, ptr %a50, align 4 - %sext51 = sext i32 %65 to i64 - %66 = getelementptr inbounds [3 x i32], ptr %64, i64 0, i64 %sext51 - %67 = load i32, ptr %66, align 4 - store i32 %67, ptr %y49, align 4 - %68 = load i32, ptr %i48, align 4 - %69 = load i32, ptr %y49, align 4 - call void (ptr, ...) @printf(ptr @.str.7, i32 %68, i32 %69) - %70 = load i32, ptr %i48, align 4 - %add52 = add i32 %70, 1 - store i32 %add52, ptr %i48, align 4 - %71 = load i32, ptr %.anon44, align 4 - %add53 = add i32 %71, 1 - store i32 %add53, ptr %.anon44, align 4 - br label %loop.cond45 - -loop.exit54: ; preds = %loop.cond45 - call void @llvm.memcpy.p0.p0.i32(ptr align 16 %.anon55, ptr align 16 @.__const.8, i32 20, i1 false) - store i64 0, ptr %.anon56, align 8 - br label %loop.cond57 - -loop.cond57: ; preds = %loop.body58, %loop.exit54 - %72 = load i64, ptr %.anon56, align 8 - %gt = icmp ugt i64 5, %72 - br i1 %gt, label %loop.body58, label %loop.exit63 - -loop.body58: ; preds = %loop.cond57 - %73 = load i64, ptr %.anon56, align 8 - store i64 %73, ptr %i59, align 8 - %74 = load i64, ptr %.anon56, align 8 - %75 = getelementptr inbounds [5 x i32], ptr %.anon55, i64 0, i64 %74 - %76 = load i32, ptr %75, align 4 - store i32 %76, ptr %y60, align 4 - %77 = load i64, ptr %i59, align 8 - %78 = load i32, ptr %y60, align 4 - call void (ptr, ...) @printf(ptr @.str.9, i64 %77, i32 %78) - %79 = load i64, ptr %i59, align 8 - %add61 = add i64 %79, 1 - store i64 %add61, ptr %i59, align 8 - %80 = load i64, ptr %.anon56, align 8 - %add62 = add i64 %80, 1 - store i64 %add62, ptr %.anon56, align 8 - br label %loop.cond57 - -loop.exit63: ; preds = %loop.cond57 - call void @foo.getFields(ptr sret([5 x i32]) align 4 %.anon64) - store i64 0, ptr %.anon65, align 8 - br label %loop.cond66 - -loop.cond66: ; preds = %loop.body68, %loop.exit63 - %81 = load i64, ptr %.anon65, align 8 - %gt67 = icmp ugt i64 5, %81 - br i1 %gt67, label %loop.body68, label %loop.exit72 - -loop.body68: ; preds = %loop.cond66 - %82 = load i64, ptr %.anon65, align 8 - store i64 %82, ptr %i69, align 8 - %83 = load i64, ptr %.anon65, align 8 - %84 = getelementptr inbounds [5 x i32], ptr %.anon64, i64 0, i64 %83 - %85 = load i32, ptr %84, align 4 - store i32 %85, ptr %y70, align 4 - %86 = load i64, ptr %i69, align 8 - %87 = load i32, ptr %y70, align 4 - call void (ptr, ...) @printf(ptr @.str.10, i64 %86, i32 %87) - %88 = load i64, ptr %.anon65, align 8 - %add71 = add i64 %88, 1 - store i64 %add71, ptr %.anon65, align 8 - br label %loop.cond66 - -loop.exit72: ; preds = %loop.cond66 + call void (ptr, ...) @printf(ptr @.str.4, i32 %31, i32 %33) + %34 = load i32, ptr %.anon4, align 4 + %add13 = add i32 %34, 1 + store i32 %add13, ptr %.anon4, align 4 + br label %loop.cond5 + +loop.exit14: ; preds = %loop.cond5 + store i32 3, ptr %.anon15, align 4 + store i32 0, ptr %.anon16, align 4 + br label %loop.cond17 + +loop.cond17: ; preds = %loop.body19, %loop.exit14 + %35 = load i32, ptr %.anon16, align 4 + %36 = load i32, ptr %.anon15, align 4 + %lt18 = icmp slt i32 %35, %36 + br i1 %lt18, label %loop.body19, label %loop.exit25 + +loop.body19: ; preds = %loop.cond17 + %37 = load i32, ptr %.anon16, align 4 + store i32 %37, ptr %i20, align 4 + %38 = load i32, ptr %.anon16, align 4 + store i32 %38, ptr %a22, align 4 + %39 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 + %40 = load i32, ptr %a22, align 4 + %sext23 = sext i32 %40 to i64 + %41 = getelementptr inbounds [3 x i32], ptr %39, i64 0, i64 %sext23 + %42 = load i32, ptr %41, align 4 + store i32 %42, ptr %y21, align 4 + %43 = load i32, ptr %i20, align 4 + %44 = load i32, ptr %y21, align 4 + call void (ptr, ...) @printf(ptr @.str.5, i32 %43, i32 %44) + %45 = load i32, ptr %.anon16, align 4 + %add24 = add i32 %45, 1 + store i32 %add24, ptr %.anon16, align 4 + br label %loop.cond17 + +loop.exit25: ; preds = %loop.cond17 + store i32 3, ptr %.anon26, align 4 + store i32 0, ptr %.anon27, align 4 + br label %loop.cond28 + +loop.cond28: ; preds = %loop.body30, %loop.exit25 + %46 = load i32, ptr %.anon27, align 4 + %47 = load i32, ptr %.anon26, align 4 + %lt29 = icmp slt i32 %46, %47 + br i1 %lt29, label %loop.body30, label %loop.exit36 + +loop.body30: ; preds = %loop.cond28 + %48 = load i32, ptr %.anon27, align 4 + store i32 %48, ptr %i31, align 4 + %49 = load i32, ptr %.anon27, align 4 + store i32 %49, ptr %a33, align 4 + %50 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 + %51 = load i32, ptr %a33, align 4 + %sext34 = sext i32 %51 to i64 + %52 = getelementptr inbounds [3 x i32], ptr %50, i64 0, i64 %sext34 + %53 = load i32, ptr %52, align 4 + store i32 %53, ptr %y32, align 4 + %54 = load i32, ptr %i31, align 4 + %55 = load i32, ptr %y32, align 4 + call void (ptr, ...) @printf(ptr @.str.6, i32 %54, i32 %55) + %56 = load i32, ptr %.anon27, align 4 + %add35 = add i32 %56, 1 + store i32 %add35, ptr %.anon27, align 4 + br label %loop.cond28 + +loop.exit36: ; preds = %loop.cond28 + store i32 3, ptr %.anon37, align 4 + store i32 0, ptr %.anon38, align 4 + br label %loop.cond39 + +loop.cond39: ; preds = %loop.body41, %loop.exit36 + %57 = load i32, ptr %.anon38, align 4 + %58 = load i32, ptr %.anon37, align 4 + %lt40 = icmp slt i32 %57, %58 + br i1 %lt40, label %loop.body41, label %loop.exit48 + +loop.body41: ; preds = %loop.cond39 + %59 = load i32, ptr %.anon38, align 4 + store i32 %59, ptr %i42, align 4 + %60 = load i32, ptr %.anon38, align 4 + store i32 %60, ptr %a44, align 4 + %61 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 + %62 = load i32, ptr %a44, align 4 + %sext45 = sext i32 %62 to i64 + %63 = getelementptr inbounds [3 x i32], ptr %61, i64 0, i64 %sext45 + %64 = load i32, ptr %63, align 4 + store i32 %64, ptr %y43, align 4 + %65 = load i32, ptr %i42, align 4 + %66 = load i32, ptr %y43, align 4 + call void (ptr, ...) @printf(ptr @.str.7, i32 %65, i32 %66) + %67 = load i32, ptr %i42, align 4 + %add46 = add i32 %67, 1 + store i32 %add46, ptr %i42, align 4 + %68 = load i32, ptr %.anon38, align 4 + %add47 = add i32 %68, 1 + store i32 %add47, ptr %.anon38, align 4 + br label %loop.cond39 + +loop.exit48: ; preds = %loop.cond39 + call void @llvm.memcpy.p0.p0.i32(ptr align 16 %.anon49, ptr align 16 @.__const.8, i32 20, i1 false) + store i64 0, ptr %.anon50, align 8 + br label %loop.cond51 + +loop.cond51: ; preds = %loop.body52, %loop.exit48 + %69 = load i64, ptr %.anon50, align 8 + %gt = icmp ugt i64 5, %69 + br i1 %gt, label %loop.body52, label %loop.exit57 + +loop.body52: ; preds = %loop.cond51 + %70 = load i64, ptr %.anon50, align 8 + store i64 %70, ptr %i53, align 8 + %71 = load i64, ptr %.anon50, align 8 + %72 = getelementptr inbounds [5 x i32], ptr %.anon49, i64 0, i64 %71 + %73 = load i32, ptr %72, align 4 + store i32 %73, ptr %y54, align 4 + %74 = load i64, ptr %i53, align 8 + %75 = load i32, ptr %y54, align 4 + call void (ptr, ...) @printf(ptr @.str.9, i64 %74, i32 %75) + %76 = load i64, ptr %i53, align 8 + %add55 = add i64 %76, 1 + store i64 %add55, ptr %i53, align 8 + %77 = load i64, ptr %.anon50, align 8 + %add56 = add i64 %77, 1 + store i64 %add56, ptr %.anon50, align 8 + br label %loop.cond51 + +loop.exit57: ; preds = %loop.cond51 + call void @foo.getFields(ptr sret([5 x i32]) align 4 %.anon58) + store i64 0, ptr %.anon59, align 8 + br label %loop.cond60 + +loop.cond60: ; preds = %loop.body62, %loop.exit57 + %78 = load i64, ptr %.anon59, align 8 + %gt61 = icmp ugt i64 5, %78 + br i1 %gt61, label %loop.body62, label %loop.exit66 + +loop.body62: ; preds = %loop.cond60 + %79 = load i64, ptr %.anon59, align 8 + store i64 %79, ptr %i63, align 8 + %80 = load i64, ptr %.anon59, align 8 + %81 = getelementptr inbounds [5 x i32], ptr %.anon58, i64 0, i64 %80 + %82 = load i32, ptr %81, align 4 + store i32 %82, ptr %y64, align 4 + %83 = load i64, ptr %i63, align 8 + %84 = load i32, ptr %y64, align 4 + call void (ptr, ...) @printf(ptr @.str.10, i64 %83, i32 %84) + %85 = load i64, ptr %.anon59, align 8 + %add65 = add i64 %85, 1 + store i64 %add65, ptr %.anon59, align 8 + br label %loop.cond60 + +loop.exit66: ; preds = %loop.cond60 call void @foo.getFields(ptr sret([5 x i32]) align 4 %sretparam) - store ptr %sretparam, ptr %.anon73, align 8 - store i64 0, ptr %.anon74, align 8 - br label %loop.cond75 - -loop.cond75: ; preds = %loop.body77, %loop.exit72 - %89 = load i64, ptr %.anon74, align 8 - %gt76 = icmp ugt i64 5, %89 - br i1 %gt76, label %loop.body77, label %loop.exit81 - -loop.body77: ; preds = %loop.cond75 - %90 = load i64, ptr %.anon74, align 8 - store i64 %90, ptr %i78, align 8 - %91 = load ptr, ptr %.anon73, align 8 - %92 = load i64, ptr %.anon74, align 8 - %93 = getelementptr inbounds [5 x i32], ptr %91, i64 0, i64 %92 - %94 = load i32, ptr %93, align 4 - store i32 %94, ptr %y79, align 4 - %95 = load i64, ptr %i78, align 8 - %96 = load i32, ptr %y79, align 4 - call void (ptr, ...) @printf(ptr @.str.11, i64 %95, i32 %96) - %97 = load i64, ptr %.anon74, align 8 - %add80 = add i64 %97, 1 - store i64 %add80, ptr %.anon74, align 8 - br label %loop.cond75 - -loop.exit81: ; preds = %loop.cond75 - store i32 0, ptr %a82, align 4 + store ptr %sretparam, ptr %.anon67, align 8 + store i64 0, ptr %.anon68, align 8 + br label %loop.cond69 + +loop.cond69: ; preds = %loop.body71, %loop.exit66 + %86 = load i64, ptr %.anon68, align 8 + %gt70 = icmp ugt i64 5, %86 + br i1 %gt70, label %loop.body71, label %loop.exit75 + +loop.body71: ; preds = %loop.cond69 + %87 = load i64, ptr %.anon68, align 8 + store i64 %87, ptr %i72, align 8 + %88 = load ptr, ptr %.anon67, align 8 + %89 = load i64, ptr %.anon68, align 8 + %90 = getelementptr inbounds [5 x i32], ptr %88, i64 0, i64 %89 + %91 = load i32, ptr %90, align 4 + store i32 %91, ptr %y73, align 4 + %92 = load i64, ptr %i72, align 8 + %93 = load i32, ptr %y73, align 4 + call void (ptr, ...) @printf(ptr @.str.11, i64 %92, i32 %93) + %94 = load i64, ptr %.anon68, align 8 + %add74 = add i64 %94, 1 + store i64 %add74, ptr %.anon68, align 8 + br label %loop.cond69 + +loop.exit75: ; preds = %loop.cond69 + %95 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 + %96 = getelementptr inbounds [3 x i32], ptr %95, i64 0, i64 0 + %97 = load i32, ptr %96, align 4 %98 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 - %99 = load i32, ptr %a82, align 4 - %sext83 = sext i32 %99 to i64 - %100 = getelementptr inbounds [3 x i32], ptr %98, i64 0, i64 %sext83 - %101 = load i32, ptr %100, align 4 - store i32 1, ptr %a84, align 4 - %102 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 - %103 = load i32, ptr %a84, align 4 - %sext85 = sext i32 %103 to i64 - %104 = getelementptr inbounds [3 x i32], ptr %102, i64 0, i64 %sext85 - %105 = load i32, ptr %104, align 4 - call void (ptr, ...) @printf(ptr @.str.12, i32 %101, i32 %105) - store i32 1, ptr %a87, align 4 - %106 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 - %107 = load i32, ptr %a87, align 4 - %sext88 = sext i32 %107 to i64 - %108 = getelementptr inbounds [3 x i32], ptr %106, i64 0, i64 %sext88 - store ptr %108, ptr %y86, align 8 - %109 = load ptr, ptr %y86, align 8 + %99 = getelementptr inbounds [3 x i32], ptr %98, i64 0, i64 1 + %100 = load i32, ptr %99, align 4 + call void (ptr, ...) @printf(ptr @.str.12, i32 %97, i32 %100) + %101 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 + %102 = getelementptr inbounds [3 x i32], ptr %101, i64 0, i64 1 + store ptr %102, ptr %y76, align 8 + %103 = load ptr, ptr %y76, align 8 + %104 = load i32, ptr %103, align 4 + %add77 = add i32 %104, 1 + store i32 %add77, ptr %103, align 4 + %105 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 + %106 = getelementptr inbounds [3 x i32], ptr %105, i64 0, i64 0 + %107 = load i32, ptr %106, align 4 + %108 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 + %109 = getelementptr inbounds [3 x i32], ptr %108, i64 0, i64 1 %110 = load i32, ptr %109, align 4 - %add89 = add i32 %110, 1 - store i32 %add89, ptr %109, align 4 - store i32 0, ptr %a90, align 4 - %111 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 - %112 = load i32, ptr %a90, align 4 - %sext91 = sext i32 %112 to i64 - %113 = getelementptr inbounds [3 x i32], ptr %111, i64 0, i64 %sext91 - %114 = load i32, ptr %113, align 4 - store i32 1, ptr %a92, align 4 - %115 = getelementptr inbounds %Foo, ptr %x, i32 0, i32 0 - %116 = load i32, ptr %a92, align 4 - %sext93 = sext i32 %116 to i64 - %117 = getelementptr inbounds [3 x i32], ptr %115, i64 0, i64 %sext93 - %118 = load i32, ptr %117, align 4 - call void (ptr, ...) @printf(ptr @.str.13, i32 %114, i32 %118) + call void (ptr, ...) @printf(ptr @.str.13, i32 %107, i32 %110) ret void } diff --git a/test/test_suite/statements/foreach_custom.c3t b/test/test_suite/statements/foreach_custom.c3t index fd1b5896e..5b0fce27b 100644 --- a/test/test_suite/statements/foreach_custom.c3t +++ b/test/test_suite/statements/foreach_custom.c3t @@ -6,12 +6,12 @@ struct Foo int[] x; } -macro int Foo.@operator_element_at(Foo &foo, usz index) @operator([]) +macro int Foo.@operator_element_at(Foo* &foo, usz index) @operator([]) { return foo.x[index]; } -macro usz Foo.@operator_len(Foo &foo) @operator(len) +macro usz Foo.@operator_len(Foo* &foo) @operator(len) { return foo.x.len; } diff --git a/test/test_suite/statements/foreach_custom_macro.c3t b/test/test_suite/statements/foreach_custom_macro.c3t index 7b9bd61a9..af70fd596 100644 --- a/test/test_suite/statements/foreach_custom_macro.c3t +++ b/test/test_suite/statements/foreach_custom_macro.c3t @@ -5,12 +5,12 @@ struct Foo int[] x; } -macro int Foo.@operator_element_at(Foo &foo, usz index) @operator([]) +macro int Foo.@operator_element_at(Foo* &foo, usz index) @operator([]) { return foo.x[index]; } -macro usz Foo.@operator_len(Foo &foo) @operator(len) +macro usz Foo.@operator_len(Foo* &foo) @operator(len) { return foo.x.len; } diff --git a/test/test_suite/statements/foreach_more_implementations.c3t b/test/test_suite/statements/foreach_more_implementations.c3t index b222657b6..2f73a8f1d 100644 --- a/test/test_suite/statements/foreach_more_implementations.c3t +++ b/test/test_suite/statements/foreach_more_implementations.c3t @@ -48,18 +48,16 @@ entry: %vector = alloca %Vector, align 8 %.anon1 = alloca i64, align 8 %ref = alloca ptr, align 8 - %vector2 = alloca ptr, align 8 %element = alloca i64, align 8 %retparam = alloca i64, align 8 %varargslots = alloca [1 x %any], align 16 - %.anon4 = alloca i64, align 8 - %vector5 = alloca %Vector, align 8 - %.anon6 = alloca i64, align 8 + %.anon3 = alloca i64, align 8 + %vector4 = alloca %Vector, align 8 + %.anon5 = alloca i64, align 8 %i = alloca i32, align 4 - %vector10 = alloca ptr, align 8 - %element11 = alloca i64, align 8 - %retparam13 = alloca i64, align 8 - %varargslots14 = alloca [1 x %any], align 16 + %element9 = alloca i64, align 8 + %retparam11 = alloca i64, align 8 + %varargslots12 = alloca [1 x %any], align 16 call void @llvm.memcpy.p0.p0.i32(ptr align 4 %x, ptr align 4 @.__const, i32 8, i1 false) %0 = getelementptr inbounds %Vector, ptr %v, i32 0, i32 0 store i64 2, ptr %0, align 8 @@ -79,65 +77,61 @@ loop.cond: ; preds = %loop.body, %entry br i1 %lt, label %loop.body, label %loop.exit loop.body: ; preds = %loop.cond - store ptr %v, ptr %vector2, align 8 %6 = load i64, ptr %.anon1, align 8 store i64 %6, ptr %element, align 8 - %7 = load ptr, ptr %vector2, align 8 - %8 = getelementptr inbounds %Vector, ptr %7, i32 0, i32 1 - %9 = load ptr, ptr %8, align 8 - %10 = load i64, ptr %element, align 8 - %ptroffset = getelementptr inbounds i32, ptr %9, i64 %10 + %7 = getelementptr inbounds %Vector, ptr %v, i32 0, i32 1 + %8 = load ptr, ptr %7, align 8 + %9 = load i64, ptr %element, align 8 + %ptroffset = getelementptr inbounds i32, ptr %8, i64 %9 store ptr %ptroffset, ptr %ref, align 8 - %11 = load ptr, ptr %ref, align 8 - %12 = insertvalue %any undef, ptr %11, 0 - %13 = insertvalue %any %12, i64 ptrtoint (ptr @"$ct.int" to i64), 1 - %14 = getelementptr inbounds [1 x %any], ptr %varargslots, i64 0, i64 0 - store %any %13, ptr %14, align 16 - %15 = call i64 @std.io.printf(ptr %retparam, ptr @.str, i64 3, ptr %varargslots, i64 1) - %16 = load ptr, ptr %ref, align 8 - %17 = load i32, ptr %16, align 4 - %add = add i32 %17, 2 - store i32 %add, ptr %16, align 4 - %18 = load i64, ptr %.anon1, align 8 - %add3 = add i64 %18, 1 - store i64 %add3, ptr %.anon1, align 8 + %10 = load ptr, ptr %ref, align 8 + %11 = insertvalue %any undef, ptr %10, 0 + %12 = insertvalue %any %11, i64 ptrtoint (ptr @"$ct.int" to i64), 1 + %13 = getelementptr inbounds [1 x %any], ptr %varargslots, i64 0, i64 0 + store %any %12, ptr %13, align 16 + %14 = call i64 @std.io.printf(ptr %retparam, ptr @.str, i64 3, ptr %varargslots, i64 1) + %15 = load ptr, ptr %ref, align 8 + %16 = load i32, ptr %15, align 4 + %add = add i32 %16, 2 + store i32 %add, ptr %15, align 4 + %17 = load i64, ptr %.anon1, align 8 + %add2 = add i64 %17, 1 + store i64 %add2, ptr %.anon1, align 8 br label %loop.cond loop.exit: ; preds = %loop.cond - call void @llvm.memcpy.p0.p0.i32(ptr align 8 %vector5, ptr align 8 %v, i32 16, i1 false) - %19 = getelementptr inbounds %Vector, ptr %vector5, i32 0, i32 0 - %20 = load i64, ptr %19, align 8 - store i64 %20, ptr %.anon4, align 8 - store i64 0, ptr %.anon6, align 8 - br label %loop.cond7 + call void @llvm.memcpy.p0.p0.i32(ptr align 8 %vector4, ptr align 8 %v, i32 16, i1 false) + %18 = getelementptr inbounds %Vector, ptr %vector4, i32 0, i32 0 + %19 = load i64, ptr %18, align 8 + store i64 %19, ptr %.anon3, align 8 + store i64 0, ptr %.anon5, align 8 + br label %loop.cond6 -loop.cond7: ; preds = %loop.body9, %loop.exit - %21 = load i64, ptr %.anon6, align 8 - %22 = load i64, ptr %.anon4, align 8 - %lt8 = icmp ult i64 %21, %22 - br i1 %lt8, label %loop.body9, label %loop.exit16 +loop.cond6: ; preds = %loop.body8, %loop.exit + %20 = load i64, ptr %.anon5, align 8 + %21 = load i64, ptr %.anon3, align 8 + %lt7 = icmp ult i64 %20, %21 + br i1 %lt7, label %loop.body8, label %loop.exit14 -loop.body9: ; preds = %loop.cond7 - store ptr %v, ptr %vector10, align 8 - %23 = load i64, ptr %.anon6, align 8 - store i64 %23, ptr %element11, align 8 - %24 = load ptr, ptr %vector10, align 8 - %25 = getelementptr inbounds %Vector, ptr %24, i32 0, i32 1 - %26 = load ptr, ptr %25, align 8 - %27 = load i64, ptr %element11, align 8 - %ptroffset12 = getelementptr inbounds i32, ptr %26, i64 %27 - %28 = load i32, ptr %ptroffset12, align 4 - store i32 %28, ptr %i, align 4 - %29 = insertvalue %any undef, ptr %i, 0 - %30 = insertvalue %any %29, i64 ptrtoint (ptr @"$ct.int" to i64), 1 - %31 = getelementptr inbounds [1 x %any], ptr %varargslots14, i64 0, i64 0 - store %any %30, ptr %31, align 16 - %32 = call i64 @std.io.printf(ptr %retparam13, ptr @.str.1, i64 3, ptr %varargslots14, i64 1) - %33 = load i64, ptr %.anon6, align 8 - %add15 = add i64 %33, 1 - store i64 %add15, ptr %.anon6, align 8 - br label %loop.cond7 +loop.body8: ; preds = %loop.cond6 + %22 = load i64, ptr %.anon5, align 8 + store i64 %22, ptr %element9, align 8 + %23 = getelementptr inbounds %Vector, ptr %v, i32 0, i32 1 + %24 = load ptr, ptr %23, align 8 + %25 = load i64, ptr %element9, align 8 + %ptroffset10 = getelementptr inbounds i32, ptr %24, i64 %25 + %26 = load i32, ptr %ptroffset10, align 4 + store i32 %26, ptr %i, align 4 + %27 = insertvalue %any undef, ptr %i, 0 + %28 = insertvalue %any %27, i64 ptrtoint (ptr @"$ct.int" to i64), 1 + %29 = getelementptr inbounds [1 x %any], ptr %varargslots12, i64 0, i64 0 + store %any %28, ptr %29, align 16 + %30 = call i64 @std.io.printf(ptr %retparam11, ptr @.str.1, i64 3, ptr %varargslots12, i64 1) + %31 = load i64, ptr %.anon5, align 8 + %add13 = add i64 %31, 1 + store i64 %add13, ptr %.anon5, align 8 + br label %loop.cond6 -loop.exit16: ; preds = %loop.cond7 +loop.exit14: ; preds = %loop.cond6 ret void } \ No newline at end of file diff --git a/test/test_suite/statements/foreach_r_custom.c3t b/test/test_suite/statements/foreach_r_custom.c3t index 3418df5d4..906f0d596 100644 --- a/test/test_suite/statements/foreach_r_custom.c3t +++ b/test/test_suite/statements/foreach_r_custom.c3t @@ -6,12 +6,12 @@ struct Foo int[] x; } -macro int Foo.@operator_element_at(Foo &foo, usz index) @operator([]) +macro int Foo.@operator_element_at(Foo* &foo, usz index) @operator([]) { return foo.x[index]; } -macro usz Foo.@operator_len(Foo &foo) @operator(len) +macro usz Foo.@operator_len(Foo* &foo) @operator(len) { return foo.x.len; } diff --git a/test/test_suite/statements/foreach_r_custom_macro.c3t b/test/test_suite/statements/foreach_r_custom_macro.c3t index 6f9c250d1..1cd7d4b99 100644 --- a/test/test_suite/statements/foreach_r_custom_macro.c3t +++ b/test/test_suite/statements/foreach_r_custom_macro.c3t @@ -5,12 +5,12 @@ struct Foo int[] x; } -macro int Foo.@operator_element_at(Foo &foo, usz index) @operator([]) +macro int Foo.@operator_element_at(Foo* &foo, usz index) @operator([]) { return foo.x[index]; } -macro usz Foo.@operator_len(Foo &foo) @operator(len) +macro usz Foo.@operator_len(Foo* &foo) @operator(len) { return foo.x.len; } diff --git a/test/test_suite/stdlib/map.c3t b/test/test_suite/stdlib/map.c3t index 925bf912c..1f89af543 100644 --- a/test/test_suite/stdlib/map.c3t +++ b/test/test_suite/stdlib/map.c3t @@ -79,6 +79,7 @@ entry: %14 = load { ptr, i64 }, ptr %result, align 8 ret { ptr, i64 } %14 } + ; Function Attrs: nounwind define void @test.main() #0 { entry: @@ -172,6 +173,7 @@ entry: %not_err = icmp eq i64 %26, 0 %27 = call i1 @llvm.expect.i1(i1 %not_err, i1 true) br i1 %27, label %after_check, label %after_check12 + after_check: ; preds = %entry %28 = getelementptr inbounds %Foo, ptr %retparam10, i32 0, i32 0 %29 = insertvalue %any undef, ptr %28, 0 @@ -182,6 +184,7 @@ after_check: ; preds = %entry %not_err11 = icmp eq i64 %32, 0 %33 = call i1 @llvm.expect.i1(i1 %not_err11, i1 true) br i1 %33, label %after_check12, label %after_check12 + after_check12: ; preds = %entry, %after_check, %after_check %34 = call i8 @"std.collections.map$int$test.Foo$.HashMap.has_key"(ptr %map, i32 1) store i8 %34, ptr %taddr, align 1 @@ -252,18 +255,22 @@ after_check12: ; preds = %entry, %after_check %80 = load ptr, ptr @std.core.mem.thread_temp_allocator, align 8 %not = icmp eq ptr %80, null br i1 %not, label %if.then, label %if.exit + if.then: ; preds = %after_check12 %81 = load ptr, ptr @std.core.mem.thread_allocator, align 8 %82 = call i64 @std.core.mem.allocator.new_temp(ptr %retparam49, i64 262144, ptr %81) %not_err50 = icmp eq i64 %82, 0 %83 = call i1 @llvm.expect.i1(i1 %not_err50, i1 true) br i1 %83, label %after_check51, label %assign_optional + assign_optional: ; preds = %if.then store i64 %82, ptr %error_var, align 8 br label %panic_block + after_check51: ; preds = %if.then %84 = load ptr, ptr %retparam49, align 8 br label %noerr_block + panic_block: ; preds = %assign_optional %85 = insertvalue %any undef, ptr %error_var, 0 %86 = insertvalue %any %85, i64 ptrtoint (ptr @"$ct.anyfault" to i64), 1 @@ -272,11 +279,13 @@ panic_block: ; preds = %assign_optional %88 = insertvalue %"any[]" undef, ptr %varargslots52, 0 %89 = insertvalue %"any[]" %88, i64 1, 1 store %"any[]" %89, ptr %indirectarg, align 8 - call void @std.core.builtin.panicf(ptr @.panic_msg, i64 36, ptr @.file, i64 6, ptr @.func, i64 4, i32 420, ptr byval(%"any[]") align 8 %indirectarg) + call void @std.core.builtin.panicf(ptr @.panic_msg, i64 36, ptr @.file, i64 6, ptr @.func, i64 4, i32 424, ptr byval(%"any[]") align 8 %indirectarg) unreachable + noerr_block: ; preds = %after_check51 store ptr %84, ptr @std.core.mem.thread_temp_allocator, align 8 br label %if.exit + if.exit: ; preds = %noerr_block, %after_check12 %90 = load ptr, ptr @std.core.mem.thread_temp_allocator, align 8 store ptr %90, ptr %allocator, align 8 diff --git a/test/test_suite/vector/vector_consts.c3t b/test/test_suite/vector/vector_consts.c3t index ac8d5e1c7..56749434f 100644 --- a/test/test_suite/vector/vector_consts.c3t +++ b/test/test_suite/vector/vector_consts.c3t @@ -16,7 +16,6 @@ entry: %z = alloca <8 x i8>, align 8 %x = alloca <8 x i8>, align 1 %y = alloca <8 x i8>, align 1 - %x1 = alloca <8 x i8>, align 1 store double %0, ptr %a, align 8 store double %1, ptr %b, align 8 %2 = load <8 x i8>, ptr %a, align 8 @@ -36,11 +35,9 @@ entry: %11 = trunc <8 x i8> %10 to <8 x i1> %12 = sext <8 x i1> %11 to <8 x i8> %bnot = xor <8 x i8> %12, - %and2 = and <8 x i8> %bnot, - %add = add <8 x i8> %and, %and2 - store <8 x i8> %add, ptr %x1, align 1 - %13 = load <8 x i8>, ptr %x1, align 1 - %14 = call i8 @llvm.vector.reduce.umin.v8i8(<8 x i8> %13) - %zext = zext i8 %14 to i32 + %and1 = and <8 x i8> %bnot, + %add = add <8 x i8> %and, %and1 + %13 = call i8 @llvm.vector.reduce.umin.v8i8(<8 x i8> %add) + %zext = zext i8 %13 to i32 ret i32 %zext }