From 95a1d2feb496d64094d81c9477465cafc73ce49b Mon Sep 17 00:00:00 2001 From: Alexandros Naskos Date: Fri, 28 Feb 2020 02:19:17 +0200 Subject: [PATCH 1/5] Fixed tuple concatenation with runtime and comptime values. --- src/ir.cpp | 16 ++++++++++++---- 1 file changed, 12 insertions(+), 4 deletions(-) diff --git a/src/ir.cpp b/src/ir.cpp index 7de45ebcd..28497b7c8 100644 --- a/src/ir.cpp +++ b/src/ir.cpp @@ -17030,8 +17030,10 @@ static IrInstGen *ir_analyze_tuple_cat(IrAnalyze *ira, IrInst* source_instr, continue; } IrInstGen *deref = ir_get_deref(ira, &elem_result_loc->base, elem_result_loc, nullptr); - elem_result_loc->value->special = ConstValSpecialRuntime; - ir_analyze_store_ptr(ira, &elem_result_loc->base, elem_result_loc, deref, false); + if (!type_requires_comptime(ira->codegen, elem_result_loc->value->type->data.pointer.child_type)) { + elem_result_loc->value->special = ConstValSpecialRuntime; + } + ir_analyze_store_ptr(ira, &elem_result_loc->base, elem_result_loc, deref, true); } } IrInstGen *result = ir_get_deref(ira, source_instr, new_struct_ptr, nullptr); @@ -18904,7 +18906,10 @@ static IrInstGen *ir_analyze_store_ptr(IrAnalyze *ira, IrInst* source_instr, } if (ptr->value->type->data.pointer.is_const && !allow_write_through_const) { - ir_add_error(ira, source_instr, buf_sprintf("cannot assign to constant")); + // @TODO + fprintf(stderr, "store ptr\n"); + ptr->src(); + ir_add_error(ira, source_instr, buf_sprintf("cannot assign to constant [FOO]")); return ira->codegen->invalid_inst_gen; } @@ -23042,8 +23047,11 @@ static IrInstGen *ir_analyze_instruction_container_init_list(IrAnalyze *ira, } } + const_ptrs.deinit(); + IrInstGen *result = ir_get_deref(ira, &instruction->base.base, result_loc, nullptr); - if (instr_is_comptime(result)) + // If the result is a tuple, we are allowed to use ConstValSpecialRuntime fields. + if (instr_is_comptime(result) || is_tuple(container_type)) return result; if (is_comptime) { From c020bc27ac8a8b18fe46c59f0dfb969b032fb303 Mon Sep 17 00:00:00 2001 From: Alexandros Naskos Date: Fri, 28 Feb 2020 02:43:33 +0200 Subject: [PATCH 2/5] More fixes, removed debug prints --- src/ir.cpp | 16 ++-------------- 1 file changed, 2 insertions(+), 14 deletions(-) diff --git a/src/ir.cpp b/src/ir.cpp index 28497b7c8..de81a8765 100644 --- a/src/ir.cpp +++ b/src/ir.cpp @@ -17037,15 +17037,6 @@ static IrInstGen *ir_analyze_tuple_cat(IrAnalyze *ira, IrInst* source_instr, } } IrInstGen *result = ir_get_deref(ira, source_instr, new_struct_ptr, nullptr); - if (instr_is_comptime(result)) - return result; - - if (is_comptime) { - ir_add_error(ira, &first_non_const_instruction->base, - buf_sprintf("unable to evaluate constant expression")); - return ira->codegen->invalid_inst_gen; - } - return result; } @@ -18906,10 +18897,7 @@ static IrInstGen *ir_analyze_store_ptr(IrAnalyze *ira, IrInst* source_instr, } if (ptr->value->type->data.pointer.is_const && !allow_write_through_const) { - // @TODO - fprintf(stderr, "store ptr\n"); - ptr->src(); - ir_add_error(ira, source_instr, buf_sprintf("cannot assign to constant [FOO]")); + ir_add_error(ira, source_instr, buf_sprintf("cannot assign to constant")); return ira->codegen->invalid_inst_gen; } @@ -23050,7 +23038,7 @@ static IrInstGen *ir_analyze_instruction_container_init_list(IrAnalyze *ira, const_ptrs.deinit(); IrInstGen *result = ir_get_deref(ira, &instruction->base.base, result_loc, nullptr); - // If the result is a tuple, we are allowed to use ConstValSpecialRuntime fields. + // If the result is a tuple, we are allowed to return a struct that uses ConstValSpecialRuntime fields at comptime. if (instr_is_comptime(result) || is_tuple(container_type)) return result; From 261c94629e9cb4fb43541d0930fec873e488d66e Mon Sep 17 00:00:00 2001 From: Alexandros Naskos Date: Fri, 28 Feb 2020 02:52:09 +0200 Subject: [PATCH 3/5] Added test --- test/stage1/behavior/tuple.zig | 38 ++++++++++++++++++++++++++++++++++ 1 file changed, 38 insertions(+) diff --git a/test/stage1/behavior/tuple.zig b/test/stage1/behavior/tuple.zig index 13d3d0568..686a9ad83 100644 --- a/test/stage1/behavior/tuple.zig +++ b/test/stage1/behavior/tuple.zig @@ -15,4 +15,42 @@ test "tuple concatenation" { }; S.doTheTest(); comptime S.doTheTest(); + + const T = struct { + fn consume_tuple(tuple: var, len: usize) void { + expect(tuple.len == len); + } + + fn doTheTest() void { + const t1 = .{}; + + var rt_var: u8 = 42; + const t2 = .{rt_var} ++ .{}; + + expect(t2.len == 1); + expect(t2.@"0" == rt_var); + expect(t2.@"0" == 42); + expect(&t2.@"0" != &rt_var); + + consume_tuple(t1 ++ t1, 0); + consume_tuple(.{} ++ .{}, 0); + consume_tuple(.{0} ++ .{}, 1); + consume_tuple(.{0} ++ .{1}, 2); + consume_tuple(.{0, 1, 2} ++ .{u8, 1, noreturn}, 6); + consume_tuple(t2 ++ t1, 1); + consume_tuple(t1 ++ t2, 1); + consume_tuple(t2 ++ t2, 2); + consume_tuple(.{rt_var} ++ .{}, 1); + consume_tuple(.{rt_var} ++ t1, 1); + consume_tuple(.{} ++ .{rt_var}, 1); + consume_tuple(t2 ++ .{void}, 2); + consume_tuple(t2 ++ .{0}, 2); + consume_tuple(.{0} ++ t2, 2); + consume_tuple(.{void} ++ t2, 2); + consume_tuple(.{u8} ++ .{rt_var} ++ .{true}, 3); + } + }; + + T.doTheTest(); + comptime T.doTheTest(); } From 11848fcb5fcb34b778dc19a8c7c2defd8da48f70 Mon Sep 17 00:00:00 2001 From: Alexandros Naskos Date: Fri, 28 Feb 2020 03:48:30 +0200 Subject: [PATCH 4/5] Removed unused variable --- src/ir.cpp | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/ir.cpp b/src/ir.cpp index de81a8765..f0185608a 100644 --- a/src/ir.cpp +++ b/src/ir.cpp @@ -16961,8 +16961,6 @@ static IrInstGen *ir_analyze_tuple_cat(IrAnalyze *ira, IrInst* source_instr, new_type->data.structure.special = StructSpecialInferredTuple; new_type->data.structure.resolve_status = ResolveStatusBeingInferred; - bool is_comptime = ir_should_inline(ira->old_irb.exec, source_instr->scope); - IrInstGen *new_struct_ptr = ir_resolve_result(ira, source_instr, no_result_loc(), new_type, nullptr, false, true); uint32_t new_field_count = op1_field_count + op2_field_count; From 78e4daaa03613da5d1398f7c3bcbfda24086b051 Mon Sep 17 00:00:00 2001 From: Alexandros Naskos Date: Mon, 2 Mar 2020 00:54:57 +0200 Subject: [PATCH 5/5] Removed unused variable --- src/ir.cpp | 3 --- 1 file changed, 3 deletions(-) diff --git a/src/ir.cpp b/src/ir.cpp index f0185608a..977c4b65e 100644 --- a/src/ir.cpp +++ b/src/ir.cpp @@ -16988,7 +16988,6 @@ static IrInstGen *ir_analyze_tuple_cat(IrAnalyze *ira, IrInst* source_instr, return ira->codegen->invalid_inst_gen; ZigList const_ptrs = {}; - IrInstGen *first_non_const_instruction = nullptr; for (uint32_t i = 0; i < new_field_count; i += 1) { TypeStructField *dst_field = new_type->data.structure.fields[i]; IrInstGen *src_struct_op; @@ -17010,8 +17009,6 @@ static IrInstGen *ir_analyze_tuple_cat(IrAnalyze *ira, IrInst* source_instr, return ira->codegen->invalid_inst_gen; if (instr_is_comptime(field_value)) { const_ptrs.append(dest_ptr); - } else { - first_non_const_instruction = field_value; } IrInstGen *store_ptr_inst = ir_analyze_store_ptr(ira, source_instr, dest_ptr, field_value, true);