diff --git a/src/all_types.hpp b/src/all_types.hpp index 650dcfd0c7..56ce74caae 100644 --- a/src/all_types.hpp +++ b/src/all_types.hpp @@ -3519,8 +3519,6 @@ struct IrInstSrcRef { IrInstSrc base; IrInstSrc *value; - bool is_const; - bool is_volatile; }; struct IrInstGenRef { diff --git a/src/ir.cpp b/src/ir.cpp index 5a96bc2d52..b570117177 100644 --- a/src/ir.cpp +++ b/src/ir.cpp @@ -3290,13 +3290,9 @@ static IrInstSrc *ir_build_import(IrBuilderSrc *irb, Scope *scope, AstNode *sour return &instruction->base; } -static IrInstSrc *ir_build_ref_src(IrBuilderSrc *irb, Scope *scope, AstNode *source_node, IrInstSrc *value, - bool is_const, bool is_volatile) -{ +static IrInstSrc *ir_build_ref_src(IrBuilderSrc *irb, Scope *scope, AstNode *source_node, IrInstSrc *value) { IrInstSrcRef *instruction = ir_build_instruction(irb, scope, source_node); instruction->value = value; - instruction->is_const = is_const; - instruction->is_volatile = is_volatile; ir_ref_instruction(value, irb->current_basic_block); @@ -5938,7 +5934,7 @@ static IrInstSrc *ir_gen_symbol(IrBuilderSrc *irb, Scope *scope, AstNode *node, } else { IrInstSrc *value = ir_build_const_type(irb, scope, node, primitive_type); if (lval == LValPtr) { - return ir_build_ref_src(irb, scope, node, value, false, false); + return ir_build_ref_src(irb, scope, node, value); } else { return ir_expr_wrap(irb, scope, value, result_loc); } @@ -7486,7 +7482,7 @@ static IrInstSrc *ir_lval_wrap(IrBuilderSrc *irb, Scope *scope, IrInstSrc *value if (lval == LValPtr) { // We needed a pointer to a value, but we got a value. So we create // an instruction which just makes a pointer of it. - return ir_build_ref_src(irb, scope, value->base.source_node, value, false, false); + return ir_build_ref_src(irb, scope, value->base.source_node, value); } else if (result_loc != nullptr) { return ir_expr_wrap(irb, scope, value, result_loc); } else { @@ -23348,7 +23344,16 @@ static IrInstGen *ir_analyze_instruction_ref(IrAnalyze *ira, IrInstSrcRef *ref_i IrInstGen *value = ref_instruction->value->child; if (type_is_invalid(value->value->type)) return ira->codegen->invalid_inst_gen; - return ir_get_ref(ira, &ref_instruction->base.base, value, ref_instruction->is_const, ref_instruction->is_volatile); + + bool is_const = false; + bool is_volatile = false; + + ZigValue *child_value = value->value; + if (child_value->special == ConstValSpecialStatic) { + is_const = true; + } + + return ir_get_ref(ira, &ref_instruction->base.base, value, is_const, is_volatile); } static IrInstGen *ir_analyze_union_init(IrAnalyze *ira, IrInst* source_instruction, diff --git a/src/ir_print.cpp b/src/ir_print.cpp index e66b4a3cdf..0477f3edaa 100644 --- a/src/ir_print.cpp +++ b/src/ir_print.cpp @@ -1476,9 +1476,7 @@ static void ir_print_import(IrPrintSrc *irp, IrInstSrcImport *instruction) { } static void ir_print_ref(IrPrintSrc *irp, IrInstSrcRef *instruction) { - const char *const_str = instruction->is_const ? "const " : ""; - const char *volatile_str = instruction->is_volatile ? "volatile " : ""; - fprintf(irp->f, "%s%sref ", const_str, volatile_str); + fprintf(irp->f, "ref "); ir_print_other_inst_src(irp, instruction->value); } diff --git a/test/compile_errors.zig b/test/compile_errors.zig index 166ed67561..696ef1f6ce 100644 --- a/test/compile_errors.zig +++ b/test/compile_errors.zig @@ -2,6 +2,34 @@ const tests = @import("tests.zig"); const std = @import("std"); pub fn addCases(cases: *tests.CompileErrorContext) void { + cases.addTest("reference to const data", + \\export fn foo() void { + \\ var ptr = &[_]u8{0,0,0,0}; + \\ ptr[1] = 2; + \\} + \\export fn bar() void { + \\ var ptr = &@as(u32, 2); + \\ ptr.* = 2; + \\} + \\export fn baz() void { + \\ var ptr = &true; + \\ ptr.* = false; + \\} + \\export fn qux() void { + \\ const S = struct{ + \\ x: usize, + \\ y: usize, + \\ }; + \\ var ptr = &S{.x=1,.y=2}; + \\ ptr.x = 2; + \\} + , &[_][]const u8{ + "tmp.zig:3:14: error: cannot assign to constant", + "tmp.zig:7:13: error: cannot assign to constant", + "tmp.zig:11:13: error: cannot assign to constant", + "tmp.zig:19:13: error: cannot assign to constant", + }); + cases.addTest("cast between ?T where T is not a pointer", \\pub const fnty1 = ?fn (i8) void; \\pub const fnty2 = ?fn (u64) void;