diff options
| author | Andrew Kelley <superjoe30@gmail.com> | 2017-01-16 15:24:03 -0500 |
|---|---|---|
| committer | Andrew Kelley <superjoe30@gmail.com> | 2017-01-16 15:24:03 -0500 |
| commit | fdbc2d8da1c707859af8f8bb42a27ae9d3a62159 (patch) | |
| tree | 1a1289cac097941e6bef0757a1c7e0fdf3c1668c | |
| parent | 98faf4f74984db615ba62de285308dfc5092ec7c (diff) | |
| download | zig-fdbc2d8da1c707859af8f8bb42a27ae9d3a62159.tar.gz zig-fdbc2d8da1c707859af8f8bb42a27ae9d3a62159.zip | |
implement error when assigning to field of const struct
closes #48
| -rw-r--r-- | src/ir.cpp | 6 | ||||
| -rw-r--r-- | std/debug.zig | 4 | ||||
| -rw-r--r-- | test/run_tests.cpp | 10 | ||||
| -rw-r--r-- | test/self_hosted.zig | 2 |
4 files changed, 17 insertions, 5 deletions
diff --git a/src/ir.cpp b/src/ir.cpp index 98d56de989..f6b932a9e7 100644 --- a/src/ir.cpp +++ b/src/ir.cpp @@ -8423,6 +8423,8 @@ static TypeTableEntry *ir_analyze_container_field_ptr(IrAnalyze *ira, Buf *field TypeTableEntry *bare_type = container_ref_type(container_type); ensure_complete_type(ira->codegen, bare_type); + assert(container_ptr->value.type->id == TypeTableEntryIdPointer); + bool is_const = container_ptr->value.type->data.pointer.is_const; if (bare_type->id == TypeTableEntryIdStruct) { if (bare_type->data.structure.is_invalid) return ira->codegen->builtin_types.entry_invalid; @@ -8430,7 +8432,7 @@ static TypeTableEntry *ir_analyze_container_field_ptr(IrAnalyze *ira, Buf *field TypeStructField *field = find_struct_type_field(bare_type, field_name); if (field) { ir_build_struct_field_ptr_from(&ira->new_irb, &field_ptr_instruction->base, container_ptr, field); - return get_pointer_to_type(ira->codegen, field->type_entry, false); + return get_pointer_to_type(ira->codegen, field->type_entry, is_const); } else { return ir_analyze_container_member_access_inner(ira, bare_type, field_name, field_ptr_instruction, container_ptr, container_type); @@ -8442,7 +8444,7 @@ static TypeTableEntry *ir_analyze_container_field_ptr(IrAnalyze *ira, Buf *field TypeEnumField *field = find_enum_type_field(bare_type, field_name); if (field) { ir_build_enum_field_ptr_from(&ira->new_irb, &field_ptr_instruction->base, container_ptr, field); - return get_pointer_to_type(ira->codegen, field->type_entry, false); + return get_pointer_to_type(ira->codegen, field->type_entry, is_const); } else { return ir_analyze_container_member_access_inner(ira, bare_type, field_name, field_ptr_instruction, container_ptr, container_type); diff --git a/std/debug.zig b/std/debug.zig index a5213dfbea..ba43dba83d 100644 --- a/std/debug.zig +++ b/std/debug.zig @@ -327,8 +327,8 @@ fn parseAbbrevTable(in_stream: &io.InStream) -> %AbbrevTable { /// Gets an already existing AbbrevTable given the abbrev_offset, or if not found, /// seeks in the stream and parses it. -fn getAbbrevTable(st: &ElfStackTrace, abbrev_offset: u64) -> %&AbbrevTable { - for (st.abbrev_table_list.toSlice()) |header| { +fn getAbbrevTable(st: &ElfStackTrace, abbrev_offset: u64) -> %&const AbbrevTable { + for (st.abbrev_table_list.toSlice()) |*header| { if (header.offset == abbrev_offset) { return &header.table; } diff --git a/test/run_tests.cpp b/test/run_tests.cpp index 7ecc1ca36c..bd551d9294 100644 --- a/test/run_tests.cpp +++ b/test/run_tests.cpp @@ -1595,6 +1595,16 @@ const zero: i32 = 0; const a = zero{1}; )SOURCE", 1, ".tmp_source.zig:3:11: error: expected type, found 'i32'"); + add_compile_fail_case("assign to constant field", R"SOURCE( +const Foo = struct { + field: i32, +}; +fn derp() { + const f = Foo {.field = 1234,}; + f.field = 0; +} + )SOURCE", 1, ".tmp_source.zig:7:13: error: cannot assign to constant"); + } ////////////////////////////////////////////////////////////////////////////// diff --git a/test/self_hosted.zig b/test/self_hosted.zig index 4c791313db..a636f87cc7 100644 --- a/test/self_hosted.zig +++ b/test/self_hosted.zig @@ -2,7 +2,7 @@ const test_array = @import("cases/array.zig"); const test_atomics = @import("cases/atomics.zig"); const test_bool = @import("cases/bool.zig"); -const test_cast= @import("cases/cast.zig"); +const test_cast = @import("cases/cast.zig"); const test_const_slice_child = @import("cases/const_slice_child.zig"); const test_defer = @import("cases/defer.zig"); const test_enum = @import("cases/enum.zig"); |
