authorgravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2018-05-17 23:21:44-04:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2018-05-17 23:21:44-04:00
logc38b165db4a16ba6a5c6d13537177db656fc4033
treea8639a11bea5a2fc2b9c5aebf30011f7675f37d7
parent99fc2bd4ddbe36994153f6426f0001d338e90bef

all tests passing with postfix deref syntax


13 files changed, 302 insertions(+), 289 deletions(-)

build.zig+34-25
...@@ -16,7 +16,7 @@ pub fn build(b: &Builder) !void {...@@ -16,7 +16,7 @@ pub fn build(b: &Builder) !void {
16 var docgen_exe = b.addExecutable("docgen", "doc/docgen.zig");16 var docgen_exe = b.addExecutable("docgen", "doc/docgen.zig");
1717
18 const rel_zig_exe = try os.path.relative(b.allocator, b.build_root, b.zig_exe);18 const rel_zig_exe = try os.path.relative(b.allocator, b.build_root, b.zig_exe);
19 var docgen_cmd = b.addCommand(null, b.env_map, [][]const u8 {19 var docgen_cmd = b.addCommand(null, b.env_map, [][]const u8{
20 docgen_exe.getOutputPath(),20 docgen_exe.getOutputPath(),
21 rel_zig_exe,21 rel_zig_exe,
22 "doc/langref.html.in",22 "doc/langref.html.in",
...@@ -30,7 +30,10 @@ pub fn build(b: &Builder) !void {...@@ -30,7 +30,10 @@ pub fn build(b: &Builder) !void {
30 const test_step = b.step("test", "Run all the tests");30 const test_step = b.step("test", "Run all the tests");
3131
32 // find the stage0 build artifacts because we're going to re-use config.h and zig_cpp library32 // find the stage0 build artifacts because we're going to re-use config.h and zig_cpp library
33 const build_info = try b.exec([][]const u8{b.zig_exe, "BUILD_INFO"});33 const build_info = try b.exec([][]const u8{
34 b.zig_exe,
35 "BUILD_INFO",
36 });
34 var index: usize = 0;37 var index: usize = 0;
35 const cmake_binary_dir = nextValue(&index, build_info);38 const cmake_binary_dir = nextValue(&index, build_info);
36 const cxx_compiler = nextValue(&index, build_info);39 const cxx_compiler = nextValue(&index, build_info);
...@@ -67,7 +70,10 @@ pub fn build(b: &Builder) !void {...@@ -67,7 +70,10 @@ pub fn build(b: &Builder) !void {
67 dependOnLib(exe, llvm);70 dependOnLib(exe, llvm);
6871
69 if (exe.target.getOs() == builtin.Os.linux) {72 if (exe.target.getOs() == builtin.Os.linux) {
70 const libstdcxx_path_padded = try b.exec([][]const u8{cxx_compiler, "-print-file-name=libstdc++.a"});73 const libstdcxx_path_padded = try b.exec([][]const u8{
74 cxx_compiler,
75 "-print-file-name=libstdc++.a",
76 });
71 const libstdcxx_path = ??mem.split(libstdcxx_path_padded, "\r\n").next();77 const libstdcxx_path = ??mem.split(libstdcxx_path_padded, "\r\n").next();
72 if (mem.eql(u8, libstdcxx_path, "libstdc++.a")) {78 if (mem.eql(u8, libstdcxx_path, "libstdc++.a")) {
73 warn(79 warn(
...@@ -111,17 +117,11 @@ pub fn build(b: &Builder) !void {...@@ -111,17 +117,11 @@ pub fn build(b: &Builder) !void {
111117
112 test_step.dependOn(docs_step);118 test_step.dependOn(docs_step);
113119
114 test_step.dependOn(tests.addPkgTests(b, test_filter,120 test_step.dependOn(tests.addPkgTests(b, test_filter, "test/behavior.zig", "behavior", "Run the behavior tests", with_lldb));
115 "test/behavior.zig", "behavior", "Run the behavior tests",
116 with_lldb));
117121
118 test_step.dependOn(tests.addPkgTests(b, test_filter,122 test_step.dependOn(tests.addPkgTests(b, test_filter, "std/index.zig", "std", "Run the standard library tests", with_lldb));
119 "std/index.zig", "std", "Run the standard library tests",
120 with_lldb));
121123
122 test_step.dependOn(tests.addPkgTests(b, test_filter,124 test_step.dependOn(tests.addPkgTests(b, test_filter, "std/special/compiler_rt/index.zig", "compiler-rt", "Run the compiler_rt tests", with_lldb));
123 "std/special/compiler_rt/index.zig", "compiler-rt", "Run the compiler_rt tests",
124 with_lldb));
125125
126 test_step.dependOn(tests.addCompareOutputTests(b, test_filter));126 test_step.dependOn(tests.addCompareOutputTests(b, test_filter));
127 test_step.dependOn(tests.addBuildExampleTests(b, test_filter));127 test_step.dependOn(tests.addBuildExampleTests(b, test_filter));
...@@ -149,8 +149,7 @@ fn dependOnLib(lib_exe_obj: &std.build.LibExeObjStep, dep: &const LibraryDep) vo...@@ -149,8 +149,7 @@ fn dependOnLib(lib_exe_obj: &std.build.LibExeObjStep, dep: &const LibraryDep) vo
149149
150fn addCppLib(b: &Builder, lib_exe_obj: &std.build.LibExeObjStep, cmake_binary_dir: []const u8, lib_name: []const u8) void {150fn addCppLib(b: &Builder, lib_exe_obj: &std.build.LibExeObjStep, cmake_binary_dir: []const u8, lib_name: []const u8) void {
151 const lib_prefix = if (lib_exe_obj.target.isWindows()) "" else "lib";151 const lib_prefix = if (lib_exe_obj.target.isWindows()) "" else "lib";
152 lib_exe_obj.addObjectFile(os.path.join(b.allocator, cmake_binary_dir, "zig_cpp",152 lib_exe_obj.addObjectFile(os.path.join(b.allocator, cmake_binary_dir, "zig_cpp", b.fmt("{}{}{}", lib_prefix, lib_name, lib_exe_obj.target.libFileExt())) catch unreachable);
153 b.fmt("{}{}{}", lib_prefix, lib_name, lib_exe_obj.target.libFileExt())) catch unreachable);
154}153}
155154
156const LibraryDep = struct {155const LibraryDep = struct {
...@@ -161,11 +160,21 @@ const LibraryDep = struct {...@@ -161,11 +160,21 @@ const LibraryDep = struct {
161};160};
162161
163fn findLLVM(b: &Builder, llvm_config_exe: []const u8) !LibraryDep {162fn findLLVM(b: &Builder, llvm_config_exe: []const u8) !LibraryDep {
164 const libs_output = try b.exec([][]const u8{llvm_config_exe, "--libs", "--system-libs"});163 const libs_output = try b.exec([][]const u8{
165 const includes_output = try b.exec([][]const u8{llvm_config_exe, "--includedir"});164 llvm_config_exe,
166 const libdir_output = try b.exec([][]const u8{llvm_config_exe, "--libdir"});165 "--libs",
166 "--system-libs",
167 });
168 const includes_output = try b.exec([][]const u8{
169 llvm_config_exe,
170 "--includedir",
171 });
172 const libdir_output = try b.exec([][]const u8{
173 llvm_config_exe,
174 "--libdir",
175 });
167176
168 var result = LibraryDep {177 var result = LibraryDep{
169 .libs = ArrayList([]const u8).init(b.allocator),178 .libs = ArrayList([]const u8).init(b.allocator),
170 .system_libs = ArrayList([]const u8).init(b.allocator),179 .system_libs = ArrayList([]const u8).init(b.allocator),
171 .includes = ArrayList([]const u8).init(b.allocator),180 .includes = ArrayList([]const u8).init(b.allocator),
...@@ -227,17 +236,17 @@ pub fn installCHeaders(b: &Builder, c_header_files: []const u8) void {...@@ -227,17 +236,17 @@ pub fn installCHeaders(b: &Builder, c_header_files: []const u8) void {
227}236}
228237
229fn nextValue(index: &usize, build_info: []const u8) []const u8 {238fn nextValue(index: &usize, build_info: []const u8) []const u8 {
230 const start = *index;239 const start = index.*;
231 while (true) : (*index += 1) {240 while (true) : (index.* += 1) {
232 switch (build_info[*index]) {241 switch (build_info[index.*]) {
233 '\n' => {242 '\n' => {
234 const result = build_info[start..*index];243 const result = build_info[start..index.*];
235 *index += 1;244 index.* += 1;
236 return result;245 return result;
237 },246 },
238 '\r' => {247 '\r' => {
239 const result = build_info[start..*index];248 const result = build_info[start..index.*];
240 *index += 2;249 index.* += 2;
241 return result;250 return result;
242 },251 },
243 else => continue,252 else => continue,
doc/langref.html.in+30-30
...@@ -1232,7 +1232,7 @@ mem.eql(u8, pattern, "ababab")</code></pre>...@@ -1232,7 +1232,7 @@ mem.eql(u8, pattern, "ababab")</code></pre>
1232 </td>1232 </td>
1233 </tr>1233 </tr>
1234 <tr>1234 <tr>
1235 <td><pre><code class="zig">*a<code></pre></td>1235 <td><pre><code class="zig">a.*<code></pre></td>
1236 <td>1236 <td>
1237 <ul>1237 <ul>
1238 <li>{#link|Pointers#}</li>1238 <li>{#link|Pointers#}</li>
...@@ -1244,7 +1244,7 @@ mem.eql(u8, pattern, "ababab")</code></pre>...@@ -1244,7 +1244,7 @@ mem.eql(u8, pattern, "ababab")</code></pre>
1244 <td>1244 <td>
1245 <pre><code class="zig">const x: u32 = 1234;1245 <pre><code class="zig">const x: u32 = 1234;
1246const ptr = &amp;x;1246const ptr = &amp;x;
1247*x == 1234</code></pre>1247x.* == 1234</code></pre>
1248 </td>1248 </td>
1249 </tr>1249 </tr>
1250 <tr>1250 <tr>
...@@ -1258,7 +1258,7 @@ const ptr = &amp;x;...@@ -1258,7 +1258,7 @@ const ptr = &amp;x;
1258 <td>1258 <td>
1259 <pre><code class="zig">const x: u32 = 1234;1259 <pre><code class="zig">const x: u32 = 1234;
1260const ptr = &amp;x;1260const ptr = &amp;x;
1261*x == 1234</code></pre>1261x.* == 1234</code></pre>
1262 </td>1262 </td>
1263 </tr>1263 </tr>
1264 </table>1264 </table>
...@@ -1267,8 +1267,8 @@ const ptr = &amp;x;...@@ -1267,8 +1267,8 @@ const ptr = &amp;x;
1267 {#header_open|Precedence#}1267 {#header_open|Precedence#}
1268 <pre><code>x() x[] x.y1268 <pre><code>x() x[] x.y
1269a!b1269a!b
1270!x -x -%x ~x *x &amp;x ?x ??x1270!x -x -%x ~x &amp;x ?x ??x
1271x{}1271x{} x.*
1272! * / % ** *%1272! * / % ** *%
1273+ - ++ +% -%1273+ - ++ +% -%
1274&lt;&lt; &gt;&gt;1274&lt;&lt; &gt;&gt;
...@@ -1316,7 +1316,7 @@ var some_integers: [100]i32 = undefined;...@@ -1316,7 +1316,7 @@ var some_integers: [100]i32 = undefined;
13161316
1317test "modify an array" {1317test "modify an array" {
1318 for (some_integers) |*item, i| {1318 for (some_integers) |*item, i| {
1319 *item = i32(i);1319 item.* = i32(i);
1320 }1320 }
1321 assert(some_integers[10] == 10);1321 assert(some_integers[10] == 10);
1322 assert(some_integers[99] == 99);1322 assert(some_integers[99] == 99);
...@@ -1357,7 +1357,7 @@ comptime {...@@ -1357,7 +1357,7 @@ comptime {
1357var fancy_array = init: {1357var fancy_array = init: {
1358 var initial_value: [10]Point = undefined;1358 var initial_value: [10]Point = undefined;
1359 for (initial_value) |*pt, i| {1359 for (initial_value) |*pt, i| {
1360 *pt = Point {1360 pt.* = Point {
1361 .x = i32(i),1361 .x = i32(i),
1362 .y = i32(i) * 2,1362 .y = i32(i) * 2,
1363 };1363 };
...@@ -1400,7 +1400,7 @@ test "address of syntax" {...@@ -1400,7 +1400,7 @@ test "address of syntax" {
1400 const x_ptr = &x;1400 const x_ptr = &x;
14011401
1402 // Deference a pointer:1402 // Deference a pointer:
1403 assert(*x_ptr == 1234);1403 assert(x_ptr.* == 1234);
14041404
1405 // When you get the address of a const variable, you get a const pointer.1405 // When you get the address of a const variable, you get a const pointer.
1406 assert(@typeOf(x_ptr) == &const i32);1406 assert(@typeOf(x_ptr) == &const i32);
...@@ -1409,8 +1409,8 @@ test "address of syntax" {...@@ -1409,8 +1409,8 @@ test "address of syntax" {
1409 var y: i32 = 5678;1409 var y: i32 = 5678;
1410 const y_ptr = &y;1410 const y_ptr = &y;
1411 assert(@typeOf(y_ptr) == &i32);1411 assert(@typeOf(y_ptr) == &i32);
1412 *y_ptr += 1;1412 y_ptr.* += 1;
1413 assert(*y_ptr == 5679);1413 assert(y_ptr.* == 5679);
1414}1414}
14151415
1416test "pointer array access" {1416test "pointer array access" {
...@@ -1448,9 +1448,9 @@ comptime {...@@ -1448,9 +1448,9 @@ comptime {
1448 // @ptrCast.1448 // @ptrCast.
1449 var x: i32 = 1;1449 var x: i32 = 1;
1450 const ptr = &x;1450 const ptr = &x;
1451 *ptr += 1;1451 ptr.* += 1;
1452 x += 1;1452 x += 1;
1453 assert(*ptr == 3);1453 assert(ptr.* == 3);
1454}1454}
14551455
1456test "@ptrToInt and @intToPtr" {1456test "@ptrToInt and @intToPtr" {
...@@ -1492,7 +1492,7 @@ test "nullable pointers" {...@@ -1492,7 +1492,7 @@ test "nullable pointers" {
1492 var x: i32 = 1;1492 var x: i32 = 1;
1493 ptr = &x;1493 ptr = &x;
14941494
1495 assert(*??ptr == 1);1495 assert((??ptr).* == 1);
14961496
1497 // Nullable pointers are the same size as normal pointers, because pointer1497 // Nullable pointers are the same size as normal pointers, because pointer
1498 // value 0 is used as the null value.1498 // value 0 is used as the null value.
...@@ -1505,7 +1505,7 @@ test "pointer casting" {...@@ -1505,7 +1505,7 @@ test "pointer casting" {
1505 // conversions are not possible.1505 // conversions are not possible.
1506 const bytes align(@alignOf(u32)) = []u8{0x12, 0x12, 0x12, 0x12};1506 const bytes align(@alignOf(u32)) = []u8{0x12, 0x12, 0x12, 0x12};
1507 const u32_ptr = @ptrCast(&const u32, &bytes[0]);1507 const u32_ptr = @ptrCast(&const u32, &bytes[0]);
1508 assert(*u32_ptr == 0x12121212);1508 assert(u32_ptr.* == 0x12121212);
15091509
1510 // Even this example is contrived - there are better ways to do the above than1510 // Even this example is contrived - there are better ways to do the above than
1511 // pointer casting. For example, using a slice narrowing cast:1511 // pointer casting. For example, using a slice narrowing cast:
...@@ -1610,7 +1610,7 @@ fn foo(bytes: []u8) u32 {...@@ -1610,7 +1610,7 @@ fn foo(bytes: []u8) u32 {
1610 <code>u8</code> can alias any memory.1610 <code>u8</code> can alias any memory.
1611 </p>1611 </p>
1612 <p>As an example, this code produces undefined behavior:</p>1612 <p>As an example, this code produces undefined behavior:</p>
1613 <pre><code class="zig">*@ptrCast(&amp;u32, f32(12.34))</code></pre>1613 <pre><code class="zig">@ptrCast(&amp;u32, f32(12.34)).*</code></pre>
1614 <p>Instead, use {#link|@bitCast#}:1614 <p>Instead, use {#link|@bitCast#}:
1615 <pre><code class="zig">@bitCast(u32, f32(12.34))</code></pre>1615 <pre><code class="zig">@bitCast(u32, f32(12.34))</code></pre>
1616 <p>As an added benefit, the <code>@bitcast</code> version works at compile-time.</p>1616 <p>As an added benefit, the <code>@bitcast</code> version works at compile-time.</p>
...@@ -2040,7 +2040,7 @@ const Variant = union(enum) {...@@ -2040,7 +2040,7 @@ const Variant = union(enum) {
2040 Bool: bool,2040 Bool: bool,
20412041
2042 fn truthy(self: &const Variant) bool {2042 fn truthy(self: &const Variant) bool {
2043 return switch (*self) {2043 return switch (self.*) {
2044 Variant.Int => |x_int| x_int != 0,2044 Variant.Int => |x_int| x_int != 0,
2045 Variant.Bool => |x_bool| x_bool,2045 Variant.Bool => |x_bool| x_bool,
2046 };2046 };
...@@ -2151,7 +2151,7 @@ test "switch enum" {...@@ -2151,7 +2151,7 @@ test "switch enum" {
21512151
2152 // A reference to the matched value can be obtained using `*` syntax.2152 // A reference to the matched value can be obtained using `*` syntax.
2153 Item.C => |*item| blk: {2153 Item.C => |*item| blk: {
2154 (*item).x += 1;2154 item.*.x += 1;
2155 break :blk 6;2155 break :blk 6;
2156 },2156 },
21572157
...@@ -2374,7 +2374,7 @@ test "for reference" {...@@ -2374,7 +2374,7 @@ test "for reference" {
2374 // Iterate over the slice by reference by2374 // Iterate over the slice by reference by
2375 // specifying that the capture value is a pointer.2375 // specifying that the capture value is a pointer.
2376 for (items) |*value| {2376 for (items) |*value| {
2377 *value += 1;2377 value.* += 1;
2378 }2378 }
23792379
2380 assert(items[0] == 4);2380 assert(items[0] == 4);
...@@ -2483,7 +2483,7 @@ test "if nullable" {...@@ -2483,7 +2483,7 @@ test "if nullable" {
2483 // Access the value by reference using a pointer capture.2483 // Access the value by reference using a pointer capture.
2484 var c: ?u32 = 3;2484 var c: ?u32 = 3;
2485 if (c) |*value| {2485 if (c) |*value| {
2486 *value = 2;2486 value.* = 2;
2487 }2487 }
24882488
2489 if (c) |value| {2489 if (c) |value| {
...@@ -2524,7 +2524,7 @@ test "if error union" {...@@ -2524,7 +2524,7 @@ test "if error union" {
2524 // Access the value by reference using a pointer capture.2524 // Access the value by reference using a pointer capture.
2525 var c: error!u32 = 3;2525 var c: error!u32 = 3;
2526 if (c) |*value| {2526 if (c) |*value| {
2527 *value = 9;2527 value.* = 9;
2528 } else |err| {2528 } else |err| {
2529 unreachable;2529 unreachable;
2530 }2530 }
...@@ -3872,7 +3872,7 @@ pub fn main() void {...@@ -3872,7 +3872,7 @@ pub fn main() void {
3872 {#header_open|@addWithOverflow#}3872 {#header_open|@addWithOverflow#}
3873 <pre><code class="zig">@addWithOverflow(comptime T: type, a: T, b: T, result: &T) -&gt; bool</code></pre>3873 <pre><code class="zig">@addWithOverflow(comptime T: type, a: T, b: T, result: &T) -&gt; bool</code></pre>
3874 <p>3874 <p>
3875 Performs <code>*result = a + b</code>. If overflow or underflow occurs,3875 Performs <code>result.* = a + b</code>. If overflow or underflow occurs,
3876 stores the overflowed bits in <code>result</code> and returns <code>true</code>.3876 stores the overflowed bits in <code>result</code> and returns <code>true</code>.
3877 If no overflow or underflow occurs, returns <code>false</code>.3877 If no overflow or underflow occurs, returns <code>false</code>.
3878 </p>3878 </p>
...@@ -4073,9 +4073,9 @@ comptime {...@@ -4073,9 +4073,9 @@ comptime {
4073 </p>4073 </p>
4074 {#code_begin|syntax#}4074 {#code_begin|syntax#}
4075fn cmpxchgStrongButNotAtomic(comptime T: type, ptr: &T, expected_value: T, new_value: T) ?T {4075fn cmpxchgStrongButNotAtomic(comptime T: type, ptr: &T, expected_value: T, new_value: T) ?T {
4076 const old_value = *ptr;4076 const old_value = ptr.*;
4077 if (old_value == expected_value) {4077 if (old_value == expected_value) {
4078 *ptr = new_value;4078 ptr.* = new_value;
4079 return null;4079 return null;
4080 } else {4080 } else {
4081 return old_value;4081 return old_value;
...@@ -4100,9 +4100,9 @@ fn cmpxchgStrongButNotAtomic(comptime T: type, ptr: &T, expected_value: T, new_v...@@ -4100,9 +4100,9 @@ fn cmpxchgStrongButNotAtomic(comptime T: type, ptr: &T, expected_value: T, new_v
4100 </p>4100 </p>
4101 {#code_begin|syntax#}4101 {#code_begin|syntax#}
4102fn cmpxchgWeakButNotAtomic(comptime T: type, ptr: &T, expected_value: T, new_value: T) ?T {4102fn cmpxchgWeakButNotAtomic(comptime T: type, ptr: &T, expected_value: T, new_value: T) ?T {
4103 const old_value = *ptr;4103 const old_value = ptr.*;
4104 if (old_value == expected_value and usuallyTrueButSometimesFalse()) {4104 if (old_value == expected_value and usuallyTrueButSometimesFalse()) {
4105 *ptr = new_value;4105 ptr.* = new_value;
4106 return null;4106 return null;
4107 } else {4107 } else {
4108 return old_value;4108 return old_value;
...@@ -4447,7 +4447,7 @@ mem.copy(u8, dest[0...byte_count], source[0...byte_count]);</code></pre>...@@ -4447,7 +4447,7 @@ mem.copy(u8, dest[0...byte_count], source[0...byte_count]);</code></pre>
4447 This function is a low level intrinsic with no safety mechanisms. Most4447 This function is a low level intrinsic with no safety mechanisms. Most
4448 code should not use this function, instead using something like this:4448 code should not use this function, instead using something like this:
4449 </p>4449 </p>
4450 <pre><code class="zig">for (dest[0...byte_count]) |*b| *b = c;</code></pre>4450 <pre><code class="zig">for (dest[0...byte_count]) |*b| b.* = c;</code></pre>
4451 <p>4451 <p>
4452 The optimizer is intelligent enough to turn the above snippet into a memset.4452 The optimizer is intelligent enough to turn the above snippet into a memset.
4453 </p>4453 </p>
...@@ -4480,7 +4480,7 @@ mem.set(u8, dest, c);</code></pre>...@@ -4480,7 +4480,7 @@ mem.set(u8, dest, c);</code></pre>
4480 {#header_open|@mulWithOverflow#}4480 {#header_open|@mulWithOverflow#}
4481 <pre><code class="zig">@mulWithOverflow(comptime T: type, a: T, b: T, result: &T) -&gt; bool</code></pre>4481 <pre><code class="zig">@mulWithOverflow(comptime T: type, a: T, b: T, result: &T) -&gt; bool</code></pre>
4482 <p>4482 <p>
4483 Performs <code>*result = a * b</code>. If overflow or underflow occurs,4483 Performs <code>result.* = a * b</code>. If overflow or underflow occurs,
4484 stores the overflowed bits in <code>result</code> and returns <code>true</code>.4484 stores the overflowed bits in <code>result</code> and returns <code>true</code>.
4485 If no overflow or underflow occurs, returns <code>false</code>.4485 If no overflow or underflow occurs, returns <code>false</code>.
4486 </p>4486 </p>
...@@ -4514,7 +4514,7 @@ fn targetFunction(x: i32) usize {...@@ -4514,7 +4514,7 @@ fn targetFunction(x: i32) usize {
45144514
4515 var local_variable: i32 = 42;4515 var local_variable: i32 = 42;
4516 const ptr = &local_variable;4516 const ptr = &local_variable;
4517 *ptr += 1;4517 ptr.* += 1;
45184518
4519 assert(local_variable == 43);4519 assert(local_variable == 43);
4520 return @ptrToInt(ptr);4520 return @ptrToInt(ptr);
...@@ -4746,7 +4746,7 @@ pub const FloatMode = enum {...@@ -4746,7 +4746,7 @@ pub const FloatMode = enum {
4746 {#header_open|@shlWithOverflow#}4746 {#header_open|@shlWithOverflow#}
4747 <pre><code class="zig">@shlWithOverflow(comptime T: type, a: T, shift_amt: Log2T, result: &T) -&gt; bool</code></pre>4747 <pre><code class="zig">@shlWithOverflow(comptime T: type, a: T, shift_amt: Log2T, result: &T) -&gt; bool</code></pre>
4748 <p>4748 <p>
4749 Performs <code>*result = a &lt;&lt; b</code>. If overflow or underflow occurs,4749 Performs <code>result.* = a &lt;&lt; b</code>. If overflow or underflow occurs,
4750 stores the overflowed bits in <code>result</code> and returns <code>true</code>.4750 stores the overflowed bits in <code>result</code> and returns <code>true</code>.
4751 If no overflow or underflow occurs, returns <code>false</code>.4751 If no overflow or underflow occurs, returns <code>false</code>.
4752 </p>4752 </p>
...@@ -4790,7 +4790,7 @@ pub const FloatMode = enum {...@@ -4790,7 +4790,7 @@ pub const FloatMode = enum {
4790 {#header_open|@subWithOverflow#}4790 {#header_open|@subWithOverflow#}
4791 <pre><code class="zig">@subWithOverflow(comptime T: type, a: T, b: T, result: &T) -&gt; bool</code></pre>4791 <pre><code class="zig">@subWithOverflow(comptime T: type, a: T, b: T, result: &T) -&gt; bool</code></pre>
4792 <p>4792 <p>
4793 Performs <code>*result = a - b</code>. If overflow or underflow occurs,4793 Performs <code>result.* = a - b</code>. If overflow or underflow occurs,
4794 stores the overflowed bits in <code>result</code> and returns <code>true</code>.4794 stores the overflowed bits in <code>result</code> and returns <code>true</code>.
4795 If no overflow or underflow occurs, returns <code>false</code>.4795 If no overflow or underflow occurs, returns <code>false</code>.
4796 </p>4796 </p>
src-self-hosted/arg.zig+41-33
...@@ -30,24 +30,22 @@ fn argInAllowedSet(maybe_set: ?[]const []const u8, arg: []const u8) bool {...@@ -30,24 +30,22 @@ fn argInAllowedSet(maybe_set: ?[]const []const u8, arg: []const u8) bool {
30}30}
3131
32// Modifies the current argument index during iteration32// Modifies the current argument index during iteration
33fn readFlagArguments(allocator: &Allocator, args: []const []const u8, required: usize,33fn readFlagArguments(allocator: &Allocator, args: []const []const u8, required: usize, allowed_set: ?[]const []const u8, index: &usize) !FlagArg {
34 allowed_set: ?[]const []const u8, index: &usize) !FlagArg {
35
36 switch (required) {34 switch (required) {
37 0 => return FlagArg { .None = undefined }, // TODO: Required to force non-tag but value?35 0 => return FlagArg{ .None = undefined }, // TODO: Required to force non-tag but value?
38 1 => {36 1 => {
39 if (*index + 1 >= args.len) {37 if (index.* + 1 >= args.len) {
40 return error.MissingFlagArguments;38 return error.MissingFlagArguments;
41 }39 }
4240
43 *index += 1;41 index.* += 1;
44 const arg = args[*index];42 const arg = args[index.*];
4543
46 if (!argInAllowedSet(allowed_set, arg)) {44 if (!argInAllowedSet(allowed_set, arg)) {
47 return error.ArgumentNotInAllowedSet;45 return error.ArgumentNotInAllowedSet;
48 }46 }
4947
50 return FlagArg { .Single = arg };48 return FlagArg{ .Single = arg };
51 },49 },
52 else => |needed| {50 else => |needed| {
53 var extra = ArrayList([]const u8).init(allocator);51 var extra = ArrayList([]const u8).init(allocator);
...@@ -55,12 +53,12 @@ fn readFlagArguments(allocator: &Allocator, args: []const []const u8, required:...@@ -55,12 +53,12 @@ fn readFlagArguments(allocator: &Allocator, args: []const []const u8, required:
5553
56 var j: usize = 0;54 var j: usize = 0;
57 while (j < needed) : (j += 1) {55 while (j < needed) : (j += 1) {
58 if (*index + 1 >= args.len) {56 if (index.* + 1 >= args.len) {
59 return error.MissingFlagArguments;57 return error.MissingFlagArguments;
60 }58 }
6159
62 *index += 1;60 index.* += 1;
63 const arg = args[*index];61 const arg = args[index.*];
6462
65 if (!argInAllowedSet(allowed_set, arg)) {63 if (!argInAllowedSet(allowed_set, arg)) {
66 return error.ArgumentNotInAllowedSet;64 return error.ArgumentNotInAllowedSet;
...@@ -69,7 +67,7 @@ fn readFlagArguments(allocator: &Allocator, args: []const []const u8, required:...@@ -69,7 +67,7 @@ fn readFlagArguments(allocator: &Allocator, args: []const []const u8, required:
69 try extra.append(arg);67 try extra.append(arg);
70 }68 }
7169
72 return FlagArg { .Many = extra };70 return FlagArg{ .Many = extra };
73 },71 },
74 }72 }
75}73}
...@@ -82,7 +80,7 @@ pub const Args = struct {...@@ -82,7 +80,7 @@ pub const Args = struct {
82 positionals: ArrayList([]const u8),80 positionals: ArrayList([]const u8),
8381
84 pub fn parse(allocator: &Allocator, comptime spec: []const Flag, args: []const []const u8) !Args {82 pub fn parse(allocator: &Allocator, comptime spec: []const Flag, args: []const []const u8) !Args {
85 var parsed = Args {83 var parsed = Args{
86 .flags = HashMapFlags.init(allocator),84 .flags = HashMapFlags.init(allocator),
87 .positionals = ArrayList([]const u8).init(allocator),85 .positionals = ArrayList([]const u8).init(allocator),
88 };86 };
...@@ -116,11 +114,7 @@ pub const Args = struct {...@@ -116,11 +114,7 @@ pub const Args = struct {
116 };114 };
117115
118 if (flag.mergable) {116 if (flag.mergable) {
119 var prev =117 var prev = if (parsed.flags.get(flag_name_trimmed)) |entry| entry.value.Many else ArrayList([]const u8).init(allocator);
120 if (parsed.flags.get(flag_name_trimmed)) |entry|
121 entry.value.Many
122 else
123 ArrayList([]const u8).init(allocator);
124118
125 // MergeN creation disallows 0 length flag entry (doesn't make sense)119 // MergeN creation disallows 0 length flag entry (doesn't make sense)
126 switch (flag_args) {120 switch (flag_args) {
...@@ -129,7 +123,7 @@ pub const Args = struct {...@@ -129,7 +123,7 @@ pub const Args = struct {
129 FlagArg.Many => |inner| try prev.appendSlice(inner.toSliceConst()),123 FlagArg.Many => |inner| try prev.appendSlice(inner.toSliceConst()),
130 }124 }
131125
132 _ = try parsed.flags.put(flag_name_trimmed, FlagArg { .Many = prev });126 _ = try parsed.flags.put(flag_name_trimmed, FlagArg{ .Many = prev });
133 } else {127 } else {
134 _ = try parsed.flags.put(flag_name_trimmed, flag_args);128 _ = try parsed.flags.put(flag_name_trimmed, flag_args);
135 }129 }
...@@ -163,7 +157,9 @@ pub const Args = struct {...@@ -163,7 +157,9 @@ pub const Args = struct {
163 pub fn single(self: &Args, name: []const u8) ?[]const u8 {157 pub fn single(self: &Args, name: []const u8) ?[]const u8 {
164 if (self.flags.get(name)) |entry| {158 if (self.flags.get(name)) |entry| {
165 switch (entry.value) {159 switch (entry.value) {
166 FlagArg.Single => |inner| { return inner; },160 FlagArg.Single => |inner| {
161 return inner;
162 },
167 else => @panic("attempted to retrieve flag with wrong type"),163 else => @panic("attempted to retrieve flag with wrong type"),
168 }164 }
169 } else {165 } else {
...@@ -175,7 +171,9 @@ pub const Args = struct {...@@ -175,7 +171,9 @@ pub const Args = struct {
175 pub fn many(self: &Args, name: []const u8) ?[]const []const u8 {171 pub fn many(self: &Args, name: []const u8) ?[]const []const u8 {
176 if (self.flags.get(name)) |entry| {172 if (self.flags.get(name)) |entry| {
177 switch (entry.value) {173 switch (entry.value) {
178 FlagArg.Many => |inner| { return inner.toSliceConst(); },174 FlagArg.Many => |inner| {
175 return inner.toSliceConst();
176 },
179 else => @panic("attempted to retrieve flag with wrong type"),177 else => @panic("attempted to retrieve flag with wrong type"),
180 }178 }
181 } else {179 } else {
...@@ -207,7 +205,7 @@ pub const Flag = struct {...@@ -207,7 +205,7 @@ pub const Flag = struct {
207 }205 }
208206
209 pub fn ArgN(comptime name: []const u8, comptime n: usize) Flag {207 pub fn ArgN(comptime name: []const u8, comptime n: usize) Flag {
210 return Flag {208 return Flag{
211 .name = name,209 .name = name,
212 .required = n,210 .required = n,
213 .mergable = false,211 .mergable = false,
...@@ -220,7 +218,7 @@ pub const Flag = struct {...@@ -220,7 +218,7 @@ pub const Flag = struct {
220 @compileError("n must be greater than 0");218 @compileError("n must be greater than 0");
221 }219 }
222220
223 return Flag {221 return Flag{
224 .name = name,222 .name = name,
225 .required = n,223 .required = n,
226 .mergable = true,224 .mergable = true,
...@@ -229,7 +227,7 @@ pub const Flag = struct {...@@ -229,7 +227,7 @@ pub const Flag = struct {
229 }227 }
230228
231 pub fn Option(comptime name: []const u8, comptime set: []const []const u8) Flag {229 pub fn Option(comptime name: []const u8, comptime set: []const []const u8) Flag {
232 return Flag {230 return Flag{
233 .name = name,231 .name = name,
234 .required = 1,232 .required = 1,
235 .mergable = false,233 .mergable = false,
...@@ -239,26 +237,36 @@ pub const Flag = struct {...@@ -239,26 +237,36 @@ pub const Flag = struct {
239};237};
240238
241test "parse arguments" {239test "parse arguments" {
242 const spec1 = comptime []const Flag {240 const spec1 = comptime []const Flag{
243 Flag.Bool("--help"),241 Flag.Bool("--help"),
244 Flag.Bool("--init"),242 Flag.Bool("--init"),
245 Flag.Arg1("--build-file"),243 Flag.Arg1("--build-file"),
246 Flag.Option("--color", []const []const u8 { "on", "off", "auto" }),244 Flag.Option("--color", []const []const u8{
245 "on",
246 "off",
247 "auto",
248 }),
247 Flag.ArgN("--pkg-begin", 2),249 Flag.ArgN("--pkg-begin", 2),
248 Flag.ArgMergeN("--object", 1),250 Flag.ArgMergeN("--object", 1),
249 Flag.ArgN("--library", 1),251 Flag.ArgN("--library", 1),
250 };252 };
251253
252 const cliargs = []const []const u8 {254 const cliargs = []const []const u8{
253 "build",255 "build",
254 "--help",256 "--help",
255 "pos1",257 "pos1",
256 "--build-file", "build.zig",258 "--build-file",
257 "--object", "obj1",259 "build.zig",
258 "--object", "obj2",260 "--object",
259 "--library", "lib1",261 "obj1",
260 "--library", "lib2",262 "--object",
261 "--color", "on",263 "obj2",
264 "--library",
265 "lib1",
266 "--library",
267 "lib2",
268 "--color",
269 "on",
262 "pos2",270 "pos2",
263 };271 };
264272
src-self-hosted/module.zig+9-9
...@@ -96,6 +96,7 @@ pub const Module = struct {...@@ -96,6 +96,7 @@ pub const Module = struct {
96 pub const LinkLib = struct {96 pub const LinkLib = struct {
97 name: []const u8,97 name: []const u8,
98 path: ?[]const u8,98 path: ?[]const u8,
99
99 /// the list of symbols we depend on from this lib100 /// the list of symbols we depend on from this lib
100 symbols: ArrayList([]u8),101 symbols: ArrayList([]u8),
101 provided_explicitly: bool,102 provided_explicitly: bool,
...@@ -130,9 +131,7 @@ pub const Module = struct {...@@ -130,9 +131,7 @@ pub const Module = struct {
130 }131 }
131 };132 };
132133
133 pub fn create(allocator: &mem.Allocator, name: []const u8, root_src_path: ?[]const u8, target: &const Target,134 pub fn create(allocator: &mem.Allocator, name: []const u8, root_src_path: ?[]const u8, target: &const Target, kind: Kind, build_mode: builtin.Mode, zig_lib_dir: []const u8, cache_dir: []const u8) !&Module {
134 kind: Kind, build_mode: builtin.Mode, zig_lib_dir: []const u8, cache_dir: []const u8) !&Module
135 {
136 var name_buffer = try Buffer.init(allocator, name);135 var name_buffer = try Buffer.init(allocator, name);
137 errdefer name_buffer.deinit();136 errdefer name_buffer.deinit();
138137
...@@ -148,14 +147,14 @@ pub const Module = struct {...@@ -148,14 +147,14 @@ pub const Module = struct {
148 const module_ptr = try allocator.create(Module);147 const module_ptr = try allocator.create(Module);
149 errdefer allocator.destroy(module_ptr);148 errdefer allocator.destroy(module_ptr);
150149
151 *module_ptr = Module {150 module_ptr.* = Module{
152 .allocator = allocator,151 .allocator = allocator,
153 .name = name_buffer,152 .name = name_buffer,
154 .root_src_path = root_src_path,153 .root_src_path = root_src_path,
155 .module = module,154 .module = module,
156 .context = context,155 .context = context,
157 .builder = builder,156 .builder = builder,
158 .target = *target,157 .target = target.*,
159 .kind = kind,158 .kind = kind,
160 .build_mode = build_mode,159 .build_mode = build_mode,
161 .zig_lib_dir = zig_lib_dir,160 .zig_lib_dir = zig_lib_dir,
...@@ -221,8 +220,10 @@ pub const Module = struct {...@@ -221,8 +220,10 @@ pub const Module = struct {
221220
222 pub fn build(self: &Module) !void {221 pub fn build(self: &Module) !void {
223 if (self.llvm_argv.len != 0) {222 if (self.llvm_argv.len != 0) {
224 var c_compatible_args = try std.cstr.NullTerminated2DArray.fromSlices(self.allocator,223 var c_compatible_args = try std.cstr.NullTerminated2DArray.fromSlices(self.allocator, [][]const []const u8{
225 [][]const []const u8 { [][]const u8{"zig (LLVM option parsing)"}, self.llvm_argv, });224 [][]const u8{"zig (LLVM option parsing)"},
225 self.llvm_argv,
226 });
226 defer c_compatible_args.deinit();227 defer c_compatible_args.deinit();
227 c.ZigLLVMParseCommandLineOptions(self.llvm_argv.len + 1, c_compatible_args.ptr);228 c.ZigLLVMParseCommandLineOptions(self.llvm_argv.len + 1, c_compatible_args.ptr);
228 }229 }
...@@ -261,7 +262,6 @@ pub const Module = struct {...@@ -261,7 +262,6 @@ pub const Module = struct {
261262
262 warn("====llvm ir:====\n");263 warn("====llvm ir:====\n");
263 self.dump();264 self.dump();
264
265 }265 }
266266
267 pub fn link(self: &Module, out_file: ?[]const u8) !void {267 pub fn link(self: &Module, out_file: ?[]const u8) !void {
...@@ -285,7 +285,7 @@ pub const Module = struct {...@@ -285,7 +285,7 @@ pub const Module = struct {
285 }285 }
286286
287 const link_lib = try self.allocator.create(LinkLib);287 const link_lib = try self.allocator.create(LinkLib);
288 *link_lib = LinkLib {288 link_lib.* = LinkLib{
289 .name = name,289 .name = name,
290 .path = null,290 .path = null,
291 .provided_explicitly = provided_explicitly,291 .provided_explicitly = provided_explicitly,
src-self-hosted/target.zig+4-3
...@@ -12,7 +12,7 @@ pub const Target = union(enum) {...@@ -12,7 +12,7 @@ pub const Target = union(enum) {
12 Cross: CrossTarget,12 Cross: CrossTarget,
1313
14 pub fn oFileExt(self: &const Target) []const u8 {14 pub fn oFileExt(self: &const Target) []const u8 {
15 const environ = switch (*self) {15 const environ = switch (self.*) {
16 Target.Native => builtin.environ,16 Target.Native => builtin.environ,
17 Target.Cross => |t| t.environ,17 Target.Cross => |t| t.environ,
18 };18 };
...@@ -30,7 +30,7 @@ pub const Target = union(enum) {...@@ -30,7 +30,7 @@ pub const Target = union(enum) {
30 }30 }
3131
32 pub fn getOs(self: &const Target) builtin.Os {32 pub fn getOs(self: &const Target) builtin.Os {
33 return switch (*self) {33 return switch (self.*) {
34 Target.Native => builtin.os,34 Target.Native => builtin.os,
35 Target.Cross => |t| t.os,35 Target.Cross => |t| t.os,
36 };36 };
...@@ -38,7 +38,8 @@ pub const Target = union(enum) {...@@ -38,7 +38,8 @@ pub const Target = union(enum) {
3838
39 pub fn isDarwin(self: &const Target) bool {39 pub fn isDarwin(self: &const Target) bool {
40 return switch (self.getOs()) {40 return switch (self.getOs()) {
41 builtin.Os.ios, builtin.Os.macosx => true,41 builtin.Os.ios,
42 builtin.Os.macosx => true,
42 else => false,43 else => false,
43 };44 };
44 }45 }
std/zig/ast.zig+1
...@@ -1485,6 +1485,7 @@ pub const Node = struct {...@@ -1485,6 +1485,7 @@ pub const Node = struct {
1485 BitNot,1485 BitNot,
1486 BoolNot,1486 BoolNot,
1487 Cancel,1487 Cancel,
1488 PointerType,
1488 MaybeType,1489 MaybeType,
1489 Negation,1490 Negation,
1490 NegationWrap,1491 NegationWrap,
std/zig/parse.zig+1-1
...@@ -3134,7 +3134,7 @@ fn tokenIdToPrefixOp(id: @TagType(Token.Id)) ?ast.Node.PrefixOp.Op {...@@ -3134,7 +3134,7 @@ fn tokenIdToPrefixOp(id: @TagType(Token.Id)) ?ast.Node.PrefixOp.Op {
3134 Token.Id.Minus => ast.Node.PrefixOp.Op{ .Negation = void{} },3134 Token.Id.Minus => ast.Node.PrefixOp.Op{ .Negation = void{} },
3135 Token.Id.MinusPercent => ast.Node.PrefixOp.Op{ .NegationWrap = void{} },3135 Token.Id.MinusPercent => ast.Node.PrefixOp.Op{ .NegationWrap = void{} },
3136 Token.Id.Asterisk,3136 Token.Id.Asterisk,
3137 Token.Id.AsteriskAsterisk => ast.Node.PrefixOp.Op{ .Deref = void{} },3137 Token.Id.AsteriskAsterisk => ast.Node.PrefixOp.Op{ .PointerType = void{} },
3138 Token.Id.Ampersand => ast.Node.PrefixOp.Op{ .AddrOf = ast.Node.PrefixOp.AddrOfInfo{3138 Token.Id.Ampersand => ast.Node.PrefixOp.Op{ .AddrOf = ast.Node.PrefixOp.AddrOfInfo{
3139 .align_expr = null,3139 .align_expr = null,
3140 .bit_offset_start_token = null,3140 .bit_offset_start_token = null,
std/zig/render.zig+2-1
...@@ -311,6 +311,7 @@ fn renderExpression(allocator: &mem.Allocator, stream: var, tree: &ast.Tree, ind...@@ -311,6 +311,7 @@ fn renderExpression(allocator: &mem.Allocator, stream: var, tree: &ast.Tree, ind
311 ast.Node.PrefixOp.Op.Try => try stream.write("try "),311 ast.Node.PrefixOp.Op.Try => try stream.write("try "),
312 ast.Node.PrefixOp.Op.UnwrapMaybe => try stream.write("??"),312 ast.Node.PrefixOp.Op.UnwrapMaybe => try stream.write("??"),
313 ast.Node.PrefixOp.Op.MaybeType => try stream.write("?"),313 ast.Node.PrefixOp.Op.MaybeType => try stream.write("?"),
314 ast.Node.PrefixOp.Op.PointerType => try stream.write("*"),
314 ast.Node.PrefixOp.Op.Await => try stream.write("await "),315 ast.Node.PrefixOp.Op.Await => try stream.write("await "),
315 ast.Node.PrefixOp.Op.Cancel => try stream.write("cancel "),316 ast.Node.PrefixOp.Op.Cancel => try stream.write("cancel "),
316 ast.Node.PrefixOp.Op.Resume => try stream.write("resume "),317 ast.Node.PrefixOp.Op.Resume => try stream.write("resume "),
...@@ -350,7 +351,7 @@ fn renderExpression(allocator: &mem.Allocator, stream: var, tree: &ast.Tree, ind...@@ -350,7 +351,7 @@ fn renderExpression(allocator: &mem.Allocator, stream: var, tree: &ast.Tree, ind
350 try stream.write("]");351 try stream.write("]");
351 },352 },
352353
353 ast.Node.SuffixOp.Op.SuffixOp => {354 ast.Node.SuffixOp.Op.Deref => {
354 try renderExpression(allocator, stream, tree, indent, suffix_op.lhs);355 try renderExpression(allocator, stream, tree, indent, suffix_op.lhs);
355 try stream.write(".*");356 try stream.write(".*");
356 },357 },
test/compare_output.zig+2-2
...@@ -287,9 +287,9 @@ pub fn addCases(cases: &tests.CompareOutputContext) void {...@@ -287,9 +287,9 @@ pub fn addCases(cases: &tests.CompareOutputContext) void {
287 \\export fn compare_fn(a: ?&const c_void, b: ?&const c_void) c_int {287 \\export fn compare_fn(a: ?&const c_void, b: ?&const c_void) c_int {
288 \\ const a_int = @ptrCast(&align(1) const i32, a ?? unreachable);288 \\ const a_int = @ptrCast(&align(1) const i32, a ?? unreachable);
289 \\ const b_int = @ptrCast(&align(1) const i32, b ?? unreachable);289 \\ const b_int = @ptrCast(&align(1) const i32, b ?? unreachable);
290 \\ if (*a_int < *b_int) {290 \\ if (a_int.* < b_int.*) {
291 \\ return -1;291 \\ return -1;
292 \\ } else if (*a_int > *b_int) {292 \\ } else if (a_int.* > b_int.*) {
293 \\ return 1;293 \\ return 1;
294 \\ } else {294 \\ } else {
295 \\ return 0;295 \\ return 0;
test/compile_errors.zig+15-15
...@@ -4,7 +4,7 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {...@@ -4,7 +4,7 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {
4 cases.add("invalid deref on switch target",4 cases.add("invalid deref on switch target",
5 \\comptime {5 \\comptime {
6 \\ var tile = Tile.Empty;6 \\ var tile = Tile.Empty;
7 \\ switch (*tile) {7 \\ switch (tile.*) {
8 \\ Tile.Empty => {},8 \\ Tile.Empty => {},
9 \\ Tile.Filled => {},9 \\ Tile.Filled => {},
10 \\ }10 \\ }
...@@ -14,7 +14,7 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {...@@ -14,7 +14,7 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {
14 \\ Filled,14 \\ Filled,
15 \\};15 \\};
16 ,16 ,
17 ".tmp_source.zig:3:13: error: invalid deref on switch target");17 ".tmp_source.zig:3:17: error: invalid deref on switch target");
1818
19 cases.add("invalid field access in comptime",19 cases.add("invalid field access in comptime",
20 \\comptime { var x = doesnt_exist.whatever; }20 \\comptime { var x = doesnt_exist.whatever; }
...@@ -1408,14 +1408,14 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {...@@ -1408,14 +1408,14 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {
1408 \\ Two: i32,1408 \\ Two: i32,
1409 \\};1409 \\};
1410 \\fn bad_eql_2(a: &const EnumWithData, b: &const EnumWithData) bool {1410 \\fn bad_eql_2(a: &const EnumWithData, b: &const EnumWithData) bool {
1411 \\ return *a == *b;1411 \\ return a.* == b.*;
1412 \\}1412 \\}
1413 \\1413 \\
1414 \\export fn entry1() usize { return @sizeOf(@typeOf(bad_eql_1)); }1414 \\export fn entry1() usize { return @sizeOf(@typeOf(bad_eql_1)); }
1415 \\export fn entry2() usize { return @sizeOf(@typeOf(bad_eql_2)); }1415 \\export fn entry2() usize { return @sizeOf(@typeOf(bad_eql_2)); }
1416 ,1416 ,
1417 ".tmp_source.zig:2:14: error: operator not allowed for type '[]u8'",1417 ".tmp_source.zig:2:14: error: operator not allowed for type '[]u8'",
1418 ".tmp_source.zig:9:15: error: operator not allowed for type 'EnumWithData'");1418 ".tmp_source.zig:9:16: error: operator not allowed for type 'EnumWithData'");
14191419
1420 cases.add("non-const switch number literal",1420 cases.add("non-const switch number literal",
1421 \\export fn foo() void {1421 \\export fn foo() void {
...@@ -1513,7 +1513,7 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {...@@ -1513,7 +1513,7 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {
1513 \\var bytes: [ext()]u8 = undefined;1513 \\var bytes: [ext()]u8 = undefined;
1514 \\export fn f() void {1514 \\export fn f() void {
1515 \\ for (bytes) |*b, i| {1515 \\ for (bytes) |*b, i| {
1516 \\ *b = u8(i);1516 \\ b.* = u8(i);
1517 \\ }1517 \\ }
1518 \\}1518 \\}
1519 , ".tmp_source.zig:2:13: error: unable to evaluate constant expression");1519 , ".tmp_source.zig:2:13: error: unable to evaluate constant expression");
...@@ -1819,7 +1819,7 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {...@@ -1819,7 +1819,7 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {
1819 \\}1819 \\}
1820 \\1820 \\
1821 \\fn bar(x: &const u3) u3 {1821 \\fn bar(x: &const u3) u3 {
1822 \\ return *x;1822 \\ return x.*;
1823 \\}1823 \\}
1824 \\1824 \\
1825 \\export fn entry() usize { return @sizeOf(@typeOf(foo)); }1825 \\export fn entry() usize { return @sizeOf(@typeOf(foo)); }
...@@ -1903,12 +1903,12 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {...@@ -1903,12 +1903,12 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {
1903 \\var s_buffer: [10]u8 = undefined;1903 \\var s_buffer: [10]u8 = undefined;
1904 \\pub fn pass(in: []u8) []u8 {1904 \\pub fn pass(in: []u8) []u8 {
1905 \\ var out = &s_buffer;1905 \\ var out = &s_buffer;
1906 \\ *out[0] = in[0];1906 \\ out[0].* = in[0];
1907 \\ return (*out)[0..1];1907 \\ return out.*[0..1];
1908 \\}1908 \\}
1909 \\1909 \\
1910 \\export fn entry() usize { return @sizeOf(@typeOf(pass)); }1910 \\export fn entry() usize { return @sizeOf(@typeOf(pass)); }
1911 , ".tmp_source.zig:4:5: error: attempt to dereference non pointer type '[10]u8'");1911 , ".tmp_source.zig:4:11: error: attempt to dereference non pointer type '[10]u8'");
19121912
1913 cases.add("pass const ptr to mutable ptr fn",1913 cases.add("pass const ptr to mutable ptr fn",
1914 \\fn foo() bool {1914 \\fn foo() bool {
...@@ -2434,7 +2434,7 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {...@@ -2434,7 +2434,7 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {
2434 \\}2434 \\}
2435 \\2435 \\
2436 \\fn bar(x: &u32) void {2436 \\fn bar(x: &u32) void {
2437 \\ *x += 1;2437 \\ x.* += 1;
2438 \\}2438 \\}
2439 ,2439 ,
2440 ".tmp_source.zig:8:13: error: expected type '&u32', found '&align(1) u32'");2440 ".tmp_source.zig:8:13: error: expected type '&u32', found '&align(1) u32'");
...@@ -2461,7 +2461,7 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {...@@ -2461,7 +2461,7 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {
2461 \\export fn entry() u32 {2461 \\export fn entry() u32 {
2462 \\ var bytes: [4]u8 = []u8{0x01, 0x02, 0x03, 0x04};2462 \\ var bytes: [4]u8 = []u8{0x01, 0x02, 0x03, 0x04};
2463 \\ const ptr = @ptrCast(&u32, &bytes[0]);2463 \\ const ptr = @ptrCast(&u32, &bytes[0]);
2464 \\ return *ptr;2464 \\ return ptr.*;
2465 \\}2465 \\}
2466 ,2466 ,
2467 ".tmp_source.zig:3:17: error: cast increases pointer alignment",2467 ".tmp_source.zig:3:17: error: cast increases pointer alignment",
...@@ -2540,14 +2540,14 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {...@@ -2540,14 +2540,14 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {
2540 \\2540 \\
2541 \\export fn entry(opaque: &Opaque) void {2541 \\export fn entry(opaque: &Opaque) void {
2542 \\ var m2 = &2;2542 \\ var m2 = &2;
2543 \\ const y: u32 = *m2;2543 \\ const y: u32 = m2.*;
2544 \\2544 \\
2545 \\ var a = undefined;2545 \\ var a = undefined;
2546 \\ var b = 1;2546 \\ var b = 1;
2547 \\ var c = 1.0;2547 \\ var c = 1.0;
2548 \\ var d = this;2548 \\ var d = this;
2549 \\ var e = null;2549 \\ var e = null;
2550 \\ var f = *opaque;2550 \\ var f = opaque.*;
2551 \\ var g = i32;2551 \\ var g = i32;
2552 \\ var h = @import("std");2552 \\ var h = @import("std");
2553 \\ var i = (Foo {}).bar;2553 \\ var i = (Foo {}).bar;
...@@ -3136,13 +3136,13 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {...@@ -3136,13 +3136,13 @@ pub fn addCases(cases: &tests.CompileErrorContext) void {
3136 \\ foo(a);3136 \\ foo(a);
3137 \\}3137 \\}
3138 \\fn foo(a: &const Payload) void {3138 \\fn foo(a: &const Payload) void {
3139 \\ switch (*a) {3139 \\ switch (a.*) {
3140 \\ Payload.A => {},3140 \\ Payload.A => {},
3141 \\ else => unreachable,3141 \\ else => unreachable,
3142 \\ }3142 \\ }
3143 \\}3143 \\}
3144 ,3144 ,
3145 ".tmp_source.zig:11:13: error: switch on union which has no attached enum",3145 ".tmp_source.zig:11:14: error: switch on union which has no attached enum",
3146 ".tmp_source.zig:1:17: note: consider 'union(enum)' here");3146 ".tmp_source.zig:1:17: note: consider 'union(enum)' here");
31473147
3148 cases.add("enum in field count range but not matching tag",3148 cases.add("enum in field count range but not matching tag",
test/standalone/brace_expansion/main.zig+23-20
...@@ -16,7 +16,7 @@ const Token = union(enum) {...@@ -16,7 +16,7 @@ const Token = union(enum) {
1616
17var global_allocator: &mem.Allocator = undefined;17var global_allocator: &mem.Allocator = undefined;
1818
19fn tokenize(input:[] const u8) !ArrayList(Token) {19fn tokenize(input: []const u8) !ArrayList(Token) {
20 const State = enum {20 const State = enum {
21 Start,21 Start,
22 Word,22 Word,
...@@ -29,7 +29,8 @@ fn tokenize(input:[] const u8) !ArrayList(Token) {...@@ -29,7 +29,8 @@ fn tokenize(input:[] const u8) !ArrayList(Token) {
29 for (input) |b, i| {29 for (input) |b, i| {
30 switch (state) {30 switch (state) {
31 State.Start => switch (b) {31 State.Start => switch (b) {
32 'a'...'z', 'A'...'Z' => {32 'a' ... 'z',
33 'A' ... 'Z' => {
33 state = State.Word;34 state = State.Word;
34 tok_begin = i;35 tok_begin = i;
35 },36 },
...@@ -39,9 +40,12 @@ fn tokenize(input:[] const u8) !ArrayList(Token) {...@@ -39,9 +40,12 @@ fn tokenize(input:[] const u8) !ArrayList(Token) {
39 else => return error.InvalidInput,40 else => return error.InvalidInput,
40 },41 },
41 State.Word => switch (b) {42 State.Word => switch (b) {
42 'a'...'z', 'A'...'Z' => {},43 'a' ... 'z',
43 '{', '}', ',' => {44 'A' ... 'Z' => {},
44 try token_list.append(Token { .Word = input[tok_begin..i] });45 '{',
46 '}',
47 ',' => {
48 try token_list.append(Token{ .Word = input[tok_begin..i] });
45 switch (b) {49 switch (b) {
46 '{' => try token_list.append(Token.OpenBrace),50 '{' => try token_list.append(Token.OpenBrace),
47 '}' => try token_list.append(Token.CloseBrace),51 '}' => try token_list.append(Token.CloseBrace),
...@@ -56,7 +60,7 @@ fn tokenize(input:[] const u8) !ArrayList(Token) {...@@ -56,7 +60,7 @@ fn tokenize(input:[] const u8) !ArrayList(Token) {
56 }60 }
57 switch (state) {61 switch (state) {
58 State.Start => {},62 State.Start => {},
59 State.Word => try token_list.append(Token {.Word = input[tok_begin..] }),63 State.Word => try token_list.append(Token{ .Word = input[tok_begin..] }),
60 }64 }
61 try token_list.append(Token.Eof);65 try token_list.append(Token.Eof);
62 return token_list;66 return token_list;
...@@ -68,24 +72,24 @@ const Node = union(enum) {...@@ -68,24 +72,24 @@ const Node = union(enum) {
68 Combine: []Node,72 Combine: []Node,
69};73};
7074
71const ParseError = error {75const ParseError = error{
72 InvalidInput,76 InvalidInput,
73 OutOfMemory,77 OutOfMemory,
74};78};
7579
76fn parse(tokens: &const ArrayList(Token), token_index: &usize) ParseError!Node {80fn parse(tokens: &const ArrayList(Token), token_index: &usize) ParseError!Node {
77 const first_token = tokens.items[*token_index];81 const first_token = tokens.items[token_index.*];
78 *token_index += 1;82 token_index.* += 1;
7983
80 const result_node = switch (first_token) {84 const result_node = switch (first_token) {
81 Token.Word => |word| Node { .Scalar = word },85 Token.Word => |word| Node{ .Scalar = word },
82 Token.OpenBrace => blk: {86 Token.OpenBrace => blk: {
83 var list = ArrayList(Node).init(global_allocator);87 var list = ArrayList(Node).init(global_allocator);
84 while (true) {88 while (true) {
85 try list.append(try parse(tokens, token_index));89 try list.append(try parse(tokens, token_index));
8690
87 const token = tokens.items[*token_index];91 const token = tokens.items[token_index.*];
88 *token_index += 1;92 token_index.* += 1;
8993
90 switch (token) {94 switch (token) {
91 Token.CloseBrace => break,95 Token.CloseBrace => break,
...@@ -93,17 +97,18 @@ fn parse(tokens: &const ArrayList(Token), token_index: &usize) ParseError!Node {...@@ -93,17 +97,18 @@ fn parse(tokens: &const ArrayList(Token), token_index: &usize) ParseError!Node {
93 else => return error.InvalidInput,97 else => return error.InvalidInput,
94 }98 }
95 }99 }
96 break :blk Node { .List = list };100 break :blk Node{ .List = list };
97 },101 },
98 else => return error.InvalidInput,102 else => return error.InvalidInput,
99 };103 };
100104
101 switch (tokens.items[*token_index]) {105 switch (tokens.items[token_index.*]) {
102 Token.Word, Token.OpenBrace => {106 Token.Word,
107 Token.OpenBrace => {
103 const pair = try global_allocator.alloc(Node, 2);108 const pair = try global_allocator.alloc(Node, 2);
104 pair[0] = result_node;109 pair[0] = result_node;
105 pair[1] = try parse(tokens, token_index);110 pair[1] = try parse(tokens, token_index);
106 return Node { .Combine = pair };111 return Node{ .Combine = pair };
107 },112 },
108 else => return result_node,113 else => return result_node,
109 }114 }
...@@ -137,13 +142,11 @@ fn expandString(input: []const u8, output: &Buffer) !void {...@@ -137,13 +142,11 @@ fn expandString(input: []const u8, output: &Buffer) !void {
137 }142 }
138}143}
139144
140const ExpandNodeError = error {145const ExpandNodeError = error{OutOfMemory};
141 OutOfMemory,
142};
143146
144fn expandNode(node: &const Node, output: &ArrayList(Buffer)) ExpandNodeError!void {147fn expandNode(node: &const Node, output: &ArrayList(Buffer)) ExpandNodeError!void {
145 assert(output.len == 0);148 assert(output.len == 0);
146 switch (*node) {149 switch (node.*) {
147 Node.Scalar => |scalar| {150 Node.Scalar => |scalar| {
148 try output.append(try Buffer.init(global_allocator, scalar));151 try output.append(try Buffer.init(global_allocator, scalar));
149 },152 },
test/tests.zig+90-100
...@@ -27,18 +27,18 @@ const TestTarget = struct {...@@ -27,18 +27,18 @@ const TestTarget = struct {
27 environ: builtin.Environ,27 environ: builtin.Environ,
28};28};
2929
30const test_targets = []TestTarget {30const test_targets = []TestTarget{
31 TestTarget {31 TestTarget{
32 .os = builtin.Os.linux,32 .os = builtin.Os.linux,
33 .arch = builtin.Arch.x86_64,33 .arch = builtin.Arch.x86_64,
34 .environ = builtin.Environ.gnu,34 .environ = builtin.Environ.gnu,
35 },35 },
36 TestTarget {36 TestTarget{
37 .os = builtin.Os.macosx,37 .os = builtin.Os.macosx,
38 .arch = builtin.Arch.x86_64,38 .arch = builtin.Arch.x86_64,
39 .environ = builtin.Environ.unknown,39 .environ = builtin.Environ.unknown,
40 },40 },
41 TestTarget {41 TestTarget{
42 .os = builtin.Os.windows,42 .os = builtin.Os.windows,
43 .arch = builtin.Arch.x86_64,43 .arch = builtin.Arch.x86_64,
44 .environ = builtin.Environ.msvc,44 .environ = builtin.Environ.msvc,
...@@ -49,7 +49,7 @@ const max_stdout_size = 1 * 1024 * 1024; // 1 MB...@@ -49,7 +49,7 @@ const max_stdout_size = 1 * 1024 * 1024; // 1 MB
4949
50pub fn addCompareOutputTests(b: &build.Builder, test_filter: ?[]const u8) &build.Step {50pub fn addCompareOutputTests(b: &build.Builder, test_filter: ?[]const u8) &build.Step {
51 const cases = b.allocator.create(CompareOutputContext) catch unreachable;51 const cases = b.allocator.create(CompareOutputContext) catch unreachable;
52 *cases = CompareOutputContext {52 cases.* = CompareOutputContext{
53 .b = b,53 .b = b,
54 .step = b.step("test-compare-output", "Run the compare output tests"),54 .step = b.step("test-compare-output", "Run the compare output tests"),
55 .test_index = 0,55 .test_index = 0,
...@@ -63,7 +63,7 @@ pub fn addCompareOutputTests(b: &build.Builder, test_filter: ?[]const u8) &build...@@ -63,7 +63,7 @@ pub fn addCompareOutputTests(b: &build.Builder, test_filter: ?[]const u8) &build
6363
64pub fn addRuntimeSafetyTests(b: &build.Builder, test_filter: ?[]const u8) &build.Step {64pub fn addRuntimeSafetyTests(b: &build.Builder, test_filter: ?[]const u8) &build.Step {
65 const cases = b.allocator.create(CompareOutputContext) catch unreachable;65 const cases = b.allocator.create(CompareOutputContext) catch unreachable;
66 *cases = CompareOutputContext {66 cases.* = CompareOutputContext{
67 .b = b,67 .b = b,
68 .step = b.step("test-runtime-safety", "Run the runtime safety tests"),68 .step = b.step("test-runtime-safety", "Run the runtime safety tests"),
69 .test_index = 0,69 .test_index = 0,
...@@ -77,7 +77,7 @@ pub fn addRuntimeSafetyTests(b: &build.Builder, test_filter: ?[]const u8) &build...@@ -77,7 +77,7 @@ pub fn addRuntimeSafetyTests(b: &build.Builder, test_filter: ?[]const u8) &build
7777
78pub fn addCompileErrorTests(b: &build.Builder, test_filter: ?[]const u8) &build.Step {78pub fn addCompileErrorTests(b: &build.Builder, test_filter: ?[]const u8) &build.Step {
79 const cases = b.allocator.create(CompileErrorContext) catch unreachable;79 const cases = b.allocator.create(CompileErrorContext) catch unreachable;
80 *cases = CompileErrorContext {80 cases.* = CompileErrorContext{
81 .b = b,81 .b = b,
82 .step = b.step("test-compile-errors", "Run the compile error tests"),82 .step = b.step("test-compile-errors", "Run the compile error tests"),
83 .test_index = 0,83 .test_index = 0,
...@@ -91,7 +91,7 @@ pub fn addCompileErrorTests(b: &build.Builder, test_filter: ?[]const u8) &build....@@ -91,7 +91,7 @@ pub fn addCompileErrorTests(b: &build.Builder, test_filter: ?[]const u8) &build.
9191
92pub fn addBuildExampleTests(b: &build.Builder, test_filter: ?[]const u8) &build.Step {92pub fn addBuildExampleTests(b: &build.Builder, test_filter: ?[]const u8) &build.Step {
93 const cases = b.allocator.create(BuildExamplesContext) catch unreachable;93 const cases = b.allocator.create(BuildExamplesContext) catch unreachable;
94 *cases = BuildExamplesContext {94 cases.* = BuildExamplesContext{
95 .b = b,95 .b = b,
96 .step = b.step("test-build-examples", "Build the examples"),96 .step = b.step("test-build-examples", "Build the examples"),
97 .test_index = 0,97 .test_index = 0,
...@@ -105,7 +105,7 @@ pub fn addBuildExampleTests(b: &build.Builder, test_filter: ?[]const u8) &build....@@ -105,7 +105,7 @@ pub fn addBuildExampleTests(b: &build.Builder, test_filter: ?[]const u8) &build.
105105
106pub fn addAssembleAndLinkTests(b: &build.Builder, test_filter: ?[]const u8) &build.Step {106pub fn addAssembleAndLinkTests(b: &build.Builder, test_filter: ?[]const u8) &build.Step {
107 const cases = b.allocator.create(CompareOutputContext) catch unreachable;107 const cases = b.allocator.create(CompareOutputContext) catch unreachable;
108 *cases = CompareOutputContext {108 cases.* = CompareOutputContext{
109 .b = b,109 .b = b,
110 .step = b.step("test-asm-link", "Run the assemble and link tests"),110 .step = b.step("test-asm-link", "Run the assemble and link tests"),
111 .test_index = 0,111 .test_index = 0,
...@@ -119,7 +119,7 @@ pub fn addAssembleAndLinkTests(b: &build.Builder, test_filter: ?[]const u8) &bui...@@ -119,7 +119,7 @@ pub fn addAssembleAndLinkTests(b: &build.Builder, test_filter: ?[]const u8) &bui
119119
120pub fn addTranslateCTests(b: &build.Builder, test_filter: ?[]const u8) &build.Step {120pub fn addTranslateCTests(b: &build.Builder, test_filter: ?[]const u8) &build.Step {
121 const cases = b.allocator.create(TranslateCContext) catch unreachable;121 const cases = b.allocator.create(TranslateCContext) catch unreachable;
122 *cases = TranslateCContext {122 cases.* = TranslateCContext{
123 .b = b,123 .b = b,
124 .step = b.step("test-translate-c", "Run the C transation tests"),124 .step = b.step("test-translate-c", "Run the C transation tests"),
125 .test_index = 0,125 .test_index = 0,
...@@ -133,7 +133,7 @@ pub fn addTranslateCTests(b: &build.Builder, test_filter: ?[]const u8) &build.St...@@ -133,7 +133,7 @@ pub fn addTranslateCTests(b: &build.Builder, test_filter: ?[]const u8) &build.St
133133
134pub fn addGenHTests(b: &build.Builder, test_filter: ?[]const u8) &build.Step {134pub fn addGenHTests(b: &build.Builder, test_filter: ?[]const u8) &build.Step {
135 const cases = b.allocator.create(GenHContext) catch unreachable;135 const cases = b.allocator.create(GenHContext) catch unreachable;
136 *cases = GenHContext {136 cases.* = GenHContext{
137 .b = b,137 .b = b,
138 .step = b.step("test-gen-h", "Run the C header file generation tests"),138 .step = b.step("test-gen-h", "Run the C header file generation tests"),
139 .test_index = 0,139 .test_index = 0,
...@@ -145,22 +145,26 @@ pub fn addGenHTests(b: &build.Builder, test_filter: ?[]const u8) &build.Step {...@@ -145,22 +145,26 @@ pub fn addGenHTests(b: &build.Builder, test_filter: ?[]const u8) &build.Step {
145 return cases.step;145 return cases.step;
146}146}
147147
148148pub fn addPkgTests(b: &build.Builder, test_filter: ?[]const u8, root_src: []const u8, name: []const u8, desc: []const u8, with_lldb: bool) &build.Step {
149pub fn addPkgTests(b: &build.Builder, test_filter: ?[]const u8, root_src: []const u8,
150 name:[] const u8, desc: []const u8, with_lldb: bool) &build.Step
151{
152 const step = b.step(b.fmt("test-{}", name), desc);149 const step = b.step(b.fmt("test-{}", name), desc);
153 for (test_targets) |test_target| {150 for (test_targets) |test_target| {
154 const is_native = (test_target.os == builtin.os and test_target.arch == builtin.arch);151 const is_native = (test_target.os == builtin.os and test_target.arch == builtin.arch);
155 for ([]Mode{Mode.Debug, Mode.ReleaseSafe, Mode.ReleaseFast, Mode.ReleaseSmall}) |mode| {152 for ([]Mode{
156 for ([]bool{false, true}) |link_libc| {153 Mode.Debug,
154 Mode.ReleaseSafe,
155 Mode.ReleaseFast,
156 Mode.ReleaseSmall,
157 }) |mode| {
158 for ([]bool{
159 false,
160 true,
161 }) |link_libc| {
157 if (link_libc and !is_native) {162 if (link_libc and !is_native) {
158 // don't assume we have a cross-compiling libc set up163 // don't assume we have a cross-compiling libc set up
159 continue;164 continue;
160 }165 }
161 const these_tests = b.addTest(root_src);166 const these_tests = b.addTest(root_src);
162 these_tests.setNamePrefix(b.fmt("{}-{}-{}-{}-{} ", name, @tagName(test_target.os),167 these_tests.setNamePrefix(b.fmt("{}-{}-{}-{}-{} ", name, @tagName(test_target.os), @tagName(test_target.arch), @tagName(mode), if (link_libc) "c" else "bare"));
163 @tagName(test_target.arch), @tagName(mode), if (link_libc) "c" else "bare"));
164 these_tests.setFilter(test_filter);168 these_tests.setFilter(test_filter);
165 these_tests.setBuildMode(mode);169 these_tests.setBuildMode(mode);
166 if (!is_native) {170 if (!is_native) {
...@@ -171,7 +175,15 @@ pub fn addPkgTests(b: &build.Builder, test_filter: ?[]const u8, root_src: []cons...@@ -171,7 +175,15 @@ pub fn addPkgTests(b: &build.Builder, test_filter: ?[]const u8, root_src: []cons
171 }175 }
172 if (with_lldb) {176 if (with_lldb) {
173 these_tests.setExecCmd([]?[]const u8{177 these_tests.setExecCmd([]?[]const u8{
174 "lldb", null, "-o", "run", "-o", "bt", "-o", "exit"});178 "lldb",
179 null,
180 "-o",
181 "run",
182 "-o",
183 "bt",
184 "-o",
185 "exit",
186 });
175 }187 }
176 step.dependOn(&these_tests.step);188 step.dependOn(&these_tests.step);
177 }189 }
...@@ -206,7 +218,7 @@ pub const CompareOutputContext = struct {...@@ -206,7 +218,7 @@ pub const CompareOutputContext = struct {
206 };218 };
207219
208 pub fn addSourceFile(self: &TestCase, filename: []const u8, source: []const u8) void {220 pub fn addSourceFile(self: &TestCase, filename: []const u8, source: []const u8) void {
209 self.sources.append(SourceFile {221 self.sources.append(SourceFile{
210 .filename = filename,222 .filename = filename,
211 .source = source,223 .source = source,
212 }) catch unreachable;224 }) catch unreachable;
...@@ -226,13 +238,10 @@ pub const CompareOutputContext = struct {...@@ -226,13 +238,10 @@ pub const CompareOutputContext = struct {
226 test_index: usize,238 test_index: usize,
227 cli_args: []const []const u8,239 cli_args: []const []const u8,
228240
229 pub fn create(context: &CompareOutputContext, exe_path: []const u8,241 pub fn create(context: &CompareOutputContext, exe_path: []const u8, name: []const u8, expected_output: []const u8, cli_args: []const []const u8) &RunCompareOutputStep {
230 name: []const u8, expected_output: []const u8,
231 cli_args: []const []const u8) &RunCompareOutputStep
232 {
233 const allocator = context.b.allocator;242 const allocator = context.b.allocator;
234 const ptr = allocator.create(RunCompareOutputStep) catch unreachable;243 const ptr = allocator.create(RunCompareOutputStep) catch unreachable;
235 *ptr = RunCompareOutputStep {244 ptr.* = RunCompareOutputStep{
236 .context = context,245 .context = context,
237 .exe_path = exe_path,246 .exe_path = exe_path,
238 .name = name,247 .name = name,
...@@ -258,7 +267,7 @@ pub const CompareOutputContext = struct {...@@ -258,7 +267,7 @@ pub const CompareOutputContext = struct {
258 args.append(arg) catch unreachable;267 args.append(arg) catch unreachable;
259 }268 }
260269
261 warn("Test {}/{} {}...", self.test_index+1, self.context.test_index, self.name);270 warn("Test {}/{} {}...", self.test_index + 1, self.context.test_index, self.name);
262271
263 const child = os.ChildProcess.init(args.toSliceConst(), b.allocator) catch unreachable;272 const child = os.ChildProcess.init(args.toSliceConst(), b.allocator) catch unreachable;
264 defer child.deinit();273 defer child.deinit();
...@@ -295,7 +304,6 @@ pub const CompareOutputContext = struct {...@@ -295,7 +304,6 @@ pub const CompareOutputContext = struct {
295 },304 },
296 }305 }
297306
298
299 if (!mem.eql(u8, self.expected_output, stdout.toSliceConst())) {307 if (!mem.eql(u8, self.expected_output, stdout.toSliceConst())) {
300 warn(308 warn(
301 \\309 \\
...@@ -318,12 +326,10 @@ pub const CompareOutputContext = struct {...@@ -318,12 +326,10 @@ pub const CompareOutputContext = struct {
318 name: []const u8,326 name: []const u8,
319 test_index: usize,327 test_index: usize,
320328
321 pub fn create(context: &CompareOutputContext, exe_path: []const u8,329 pub fn create(context: &CompareOutputContext, exe_path: []const u8, name: []const u8) &RuntimeSafetyRunStep {
322 name: []const u8) &RuntimeSafetyRunStep
323 {
324 const allocator = context.b.allocator;330 const allocator = context.b.allocator;
325 const ptr = allocator.create(RuntimeSafetyRunStep) catch unreachable;331 const ptr = allocator.create(RuntimeSafetyRunStep) catch unreachable;
326 *ptr = RuntimeSafetyRunStep {332 ptr.* = RuntimeSafetyRunStep{
327 .context = context,333 .context = context,
328 .exe_path = exe_path,334 .exe_path = exe_path,
329 .name = name,335 .name = name,
...@@ -340,7 +346,7 @@ pub const CompareOutputContext = struct {...@@ -340,7 +346,7 @@ pub const CompareOutputContext = struct {
340346
341 const full_exe_path = b.pathFromRoot(self.exe_path);347 const full_exe_path = b.pathFromRoot(self.exe_path);
342348
343 warn("Test {}/{} {}...", self.test_index+1, self.context.test_index, self.name);349 warn("Test {}/{} {}...", self.test_index + 1, self.context.test_index, self.name);
344350
345 const child = os.ChildProcess.init([][]u8{full_exe_path}, b.allocator) catch unreachable;351 const child = os.ChildProcess.init([][]u8{full_exe_path}, b.allocator) catch unreachable;
346 defer child.deinit();352 defer child.deinit();
...@@ -358,19 +364,16 @@ pub const CompareOutputContext = struct {...@@ -358,19 +364,16 @@ pub const CompareOutputContext = struct {
358 switch (term) {364 switch (term) {
359 Term.Exited => |code| {365 Term.Exited => |code| {
360 if (code != expected_exit_code) {366 if (code != expected_exit_code) {
361 warn("\nProgram expected to exit with code {} " ++367 warn("\nProgram expected to exit with code {} " ++ "but exited with code {}\n", expected_exit_code, code);
362 "but exited with code {}\n", expected_exit_code, code);
363 return error.TestFailed;368 return error.TestFailed;
364 }369 }
365 },370 },
366 Term.Signal => |sig| {371 Term.Signal => |sig| {
367 warn("\nProgram expected to exit with code {} " ++372 warn("\nProgram expected to exit with code {} " ++ "but instead signaled {}\n", expected_exit_code, sig);
368 "but instead signaled {}\n", expected_exit_code, sig);
369 return error.TestFailed;373 return error.TestFailed;
370 },374 },
371 else => {375 else => {
372 warn("\nProgram expected to exit with code {}" ++376 warn("\nProgram expected to exit with code {}" ++ " but exited in an unexpected way\n", expected_exit_code);
373 " but exited in an unexpected way\n", expected_exit_code);
374 return error.TestFailed;377 return error.TestFailed;
375 },378 },
376 }379 }
...@@ -379,10 +382,8 @@ pub const CompareOutputContext = struct {...@@ -379,10 +382,8 @@ pub const CompareOutputContext = struct {
379 }382 }
380 };383 };
381384
382 pub fn createExtra(self: &CompareOutputContext, name: []const u8, source: []const u8,385 pub fn createExtra(self: &CompareOutputContext, name: []const u8, source: []const u8, expected_output: []const u8, special: Special) TestCase {
383 expected_output: []const u8, special: Special) TestCase386 var tc = TestCase{
384 {
385 var tc = TestCase {
386 .name = name,387 .name = name,
387 .sources = ArrayList(TestCase.SourceFile).init(self.b.allocator),388 .sources = ArrayList(TestCase.SourceFile).init(self.b.allocator),
388 .expected_output = expected_output,389 .expected_output = expected_output,
...@@ -395,9 +396,7 @@ pub const CompareOutputContext = struct {...@@ -395,9 +396,7 @@ pub const CompareOutputContext = struct {
395 return tc;396 return tc;
396 }397 }
397398
398 pub fn create(self: &CompareOutputContext, name: []const u8, source: []const u8,399 pub fn create(self: &CompareOutputContext, name: []const u8, source: []const u8, expected_output: []const u8) TestCase {
399 expected_output: []const u8) TestCase
400 {
401 return createExtra(self, name, source, expected_output, Special.None);400 return createExtra(self, name, source, expected_output, Special.None);
402 }401 }
403402
...@@ -431,8 +430,7 @@ pub const CompareOutputContext = struct {...@@ -431,8 +430,7 @@ pub const CompareOutputContext = struct {
431 Special.Asm => {430 Special.Asm => {
432 const annotated_case_name = fmt.allocPrint(self.b.allocator, "assemble-and-link {}", case.name) catch unreachable;431 const annotated_case_name = fmt.allocPrint(self.b.allocator, "assemble-and-link {}", case.name) catch unreachable;
433 if (self.test_filter) |filter| {432 if (self.test_filter) |filter| {
434 if (mem.indexOf(u8, annotated_case_name, filter) == null)433 if (mem.indexOf(u8, annotated_case_name, filter) == null) return;
435 return;
436 }434 }
437435
438 const exe = b.addExecutable("test", null);436 const exe = b.addExecutable("test", null);
...@@ -444,19 +442,21 @@ pub const CompareOutputContext = struct {...@@ -444,19 +442,21 @@ pub const CompareOutputContext = struct {
444 exe.step.dependOn(&write_src.step);442 exe.step.dependOn(&write_src.step);
445 }443 }
446444
447 const run_and_cmp_output = RunCompareOutputStep.create(self, exe.getOutputPath(), annotated_case_name,445 const run_and_cmp_output = RunCompareOutputStep.create(self, exe.getOutputPath(), annotated_case_name, case.expected_output, case.cli_args);
448 case.expected_output, case.cli_args);
449 run_and_cmp_output.step.dependOn(&exe.step);446 run_and_cmp_output.step.dependOn(&exe.step);
450447
451 self.step.dependOn(&run_and_cmp_output.step);448 self.step.dependOn(&run_and_cmp_output.step);
452 },449 },
453 Special.None => {450 Special.None => {
454 for ([]Mode{Mode.Debug, Mode.ReleaseSafe, Mode.ReleaseFast, Mode.ReleaseSmall}) |mode| {451 for ([]Mode{
455 const annotated_case_name = fmt.allocPrint(self.b.allocator, "{} {} ({})",452 Mode.Debug,
456 "compare-output", case.name, @tagName(mode)) catch unreachable;453 Mode.ReleaseSafe,
454 Mode.ReleaseFast,
455 Mode.ReleaseSmall,
456 }) |mode| {
457 const annotated_case_name = fmt.allocPrint(self.b.allocator, "{} {} ({})", "compare-output", case.name, @tagName(mode)) catch unreachable;
457 if (self.test_filter) |filter| {458 if (self.test_filter) |filter| {
458 if (mem.indexOf(u8, annotated_case_name, filter) == null)459 if (mem.indexOf(u8, annotated_case_name, filter) == null) continue;
459 continue;
460 }460 }
461461
462 const exe = b.addExecutable("test", root_src);462 const exe = b.addExecutable("test", root_src);
...@@ -471,8 +471,7 @@ pub const CompareOutputContext = struct {...@@ -471,8 +471,7 @@ pub const CompareOutputContext = struct {
471 exe.step.dependOn(&write_src.step);471 exe.step.dependOn(&write_src.step);
472 }472 }
473473
474 const run_and_cmp_output = RunCompareOutputStep.create(self, exe.getOutputPath(),474 const run_and_cmp_output = RunCompareOutputStep.create(self, exe.getOutputPath(), annotated_case_name, case.expected_output, case.cli_args);
475 annotated_case_name, case.expected_output, case.cli_args);
476 run_and_cmp_output.step.dependOn(&exe.step);475 run_and_cmp_output.step.dependOn(&exe.step);
477476
478 self.step.dependOn(&run_and_cmp_output.step);477 self.step.dependOn(&run_and_cmp_output.step);
...@@ -481,8 +480,7 @@ pub const CompareOutputContext = struct {...@@ -481,8 +480,7 @@ pub const CompareOutputContext = struct {
481 Special.RuntimeSafety => {480 Special.RuntimeSafety => {
482 const annotated_case_name = fmt.allocPrint(self.b.allocator, "safety {}", case.name) catch unreachable;481 const annotated_case_name = fmt.allocPrint(self.b.allocator, "safety {}", case.name) catch unreachable;
483 if (self.test_filter) |filter| {482 if (self.test_filter) |filter| {
484 if (mem.indexOf(u8, annotated_case_name, filter) == null)483 if (mem.indexOf(u8, annotated_case_name, filter) == null) return;
485 return;
486 }484 }
487485
488 const exe = b.addExecutable("test", root_src);486 const exe = b.addExecutable("test", root_src);
...@@ -524,7 +522,7 @@ pub const CompileErrorContext = struct {...@@ -524,7 +522,7 @@ pub const CompileErrorContext = struct {
524 };522 };
525523
526 pub fn addSourceFile(self: &TestCase, filename: []const u8, source: []const u8) void {524 pub fn addSourceFile(self: &TestCase, filename: []const u8, source: []const u8) void {
527 self.sources.append(SourceFile {525 self.sources.append(SourceFile{
528 .filename = filename,526 .filename = filename,
529 .source = source,527 .source = source,
530 }) catch unreachable;528 }) catch unreachable;
...@@ -543,12 +541,10 @@ pub const CompileErrorContext = struct {...@@ -543,12 +541,10 @@ pub const CompileErrorContext = struct {
543 case: &const TestCase,541 case: &const TestCase,
544 build_mode: Mode,542 build_mode: Mode,
545543
546 pub fn create(context: &CompileErrorContext, name: []const u8,544 pub fn create(context: &CompileErrorContext, name: []const u8, case: &const TestCase, build_mode: Mode) &CompileCmpOutputStep {
547 case: &const TestCase, build_mode: Mode) &CompileCmpOutputStep
548 {
549 const allocator = context.b.allocator;545 const allocator = context.b.allocator;
550 const ptr = allocator.create(CompileCmpOutputStep) catch unreachable;546 const ptr = allocator.create(CompileCmpOutputStep) catch unreachable;
551 *ptr = CompileCmpOutputStep {547 ptr.* = CompileCmpOutputStep{
552 .step = build.Step.init("CompileCmpOutput", allocator, make),548 .step = build.Step.init("CompileCmpOutput", allocator, make),
553 .context = context,549 .context = context,
554 .name = name,550 .name = name,
...@@ -586,7 +582,7 @@ pub const CompileErrorContext = struct {...@@ -586,7 +582,7 @@ pub const CompileErrorContext = struct {
586 Mode.ReleaseSmall => zig_args.append("--release-small") catch unreachable,582 Mode.ReleaseSmall => zig_args.append("--release-small") catch unreachable,
587 }583 }
588584
589 warn("Test {}/{} {}...", self.test_index+1, self.context.test_index, self.name);585 warn("Test {}/{} {}...", self.test_index + 1, self.context.test_index, self.name);
590586
591 if (b.verbose) {587 if (b.verbose) {
592 printInvocation(zig_args.toSliceConst());588 printInvocation(zig_args.toSliceConst());
...@@ -626,7 +622,6 @@ pub const CompileErrorContext = struct {...@@ -626,7 +622,6 @@ pub const CompileErrorContext = struct {
626 },622 },
627 }623 }
628624
629
630 const stdout = stdout_buf.toSliceConst();625 const stdout = stdout_buf.toSliceConst();
631 const stderr = stderr_buf.toSliceConst();626 const stderr = stderr_buf.toSliceConst();
632627
...@@ -666,11 +661,9 @@ pub const CompileErrorContext = struct {...@@ -666,11 +661,9 @@ pub const CompileErrorContext = struct {
666 warn("\n");661 warn("\n");
667 }662 }
668663
669 pub fn create(self: &CompileErrorContext, name: []const u8, source: []const u8,664 pub fn create(self: &CompileErrorContext, name: []const u8, source: []const u8, expected_lines: ...) &TestCase {
670 expected_lines: ...) &TestCase
671 {
672 const tc = self.b.allocator.create(TestCase) catch unreachable;665 const tc = self.b.allocator.create(TestCase) catch unreachable;
673 *tc = TestCase {666 tc.* = TestCase{
674 .name = name,667 .name = name,
675 .sources = ArrayList(TestCase.SourceFile).init(self.b.allocator),668 .sources = ArrayList(TestCase.SourceFile).init(self.b.allocator),
676 .expected_errors = ArrayList([]const u8).init(self.b.allocator),669 .expected_errors = ArrayList([]const u8).init(self.b.allocator),
...@@ -705,12 +698,13 @@ pub const CompileErrorContext = struct {...@@ -705,12 +698,13 @@ pub const CompileErrorContext = struct {
705 pub fn addCase(self: &CompileErrorContext, case: &const TestCase) void {698 pub fn addCase(self: &CompileErrorContext, case: &const TestCase) void {
706 const b = self.b;699 const b = self.b;
707700
708 for ([]Mode{Mode.Debug, Mode.ReleaseFast}) |mode| {701 for ([]Mode{
709 const annotated_case_name = fmt.allocPrint(self.b.allocator, "compile-error {} ({})",702 Mode.Debug,
710 case.name, @tagName(mode)) catch unreachable;703 Mode.ReleaseFast,
704 }) |mode| {
705 const annotated_case_name = fmt.allocPrint(self.b.allocator, "compile-error {} ({})", case.name, @tagName(mode)) catch unreachable;
711 if (self.test_filter) |filter| {706 if (self.test_filter) |filter| {
712 if (mem.indexOf(u8, annotated_case_name, filter) == null)707 if (mem.indexOf(u8, annotated_case_name, filter) == null) continue;
713 continue;
714 }708 }
715709
716 const compile_and_cmp_errors = CompileCmpOutputStep.create(self, annotated_case_name, case, mode);710 const compile_and_cmp_errors = CompileCmpOutputStep.create(self, annotated_case_name, case, mode);
...@@ -744,8 +738,7 @@ pub const BuildExamplesContext = struct {...@@ -744,8 +738,7 @@ pub const BuildExamplesContext = struct {
744738
745 const annotated_case_name = b.fmt("build {} (Debug)", build_file);739 const annotated_case_name = b.fmt("build {} (Debug)", build_file);
746 if (self.test_filter) |filter| {740 if (self.test_filter) |filter| {
747 if (mem.indexOf(u8, annotated_case_name, filter) == null)741 if (mem.indexOf(u8, annotated_case_name, filter) == null) return;
748 return;
749 }742 }
750743
751 var zig_args = ArrayList([]const u8).init(b.allocator);744 var zig_args = ArrayList([]const u8).init(b.allocator);
...@@ -773,12 +766,15 @@ pub const BuildExamplesContext = struct {...@@ -773,12 +766,15 @@ pub const BuildExamplesContext = struct {
773 pub fn addAllArgs(self: &BuildExamplesContext, root_src: []const u8, link_libc: bool) void {766 pub fn addAllArgs(self: &BuildExamplesContext, root_src: []const u8, link_libc: bool) void {
774 const b = self.b;767 const b = self.b;
775768
776 for ([]Mode{Mode.Debug, Mode.ReleaseSafe, Mode.ReleaseFast, Mode.ReleaseSmall}) |mode| {769 for ([]Mode{
777 const annotated_case_name = fmt.allocPrint(self.b.allocator, "build {} ({})",770 Mode.Debug,
778 root_src, @tagName(mode)) catch unreachable;771 Mode.ReleaseSafe,
772 Mode.ReleaseFast,
773 Mode.ReleaseSmall,
774 }) |mode| {
775 const annotated_case_name = fmt.allocPrint(self.b.allocator, "build {} ({})", root_src, @tagName(mode)) catch unreachable;
779 if (self.test_filter) |filter| {776 if (self.test_filter) |filter| {
780 if (mem.indexOf(u8, annotated_case_name, filter) == null)777 if (mem.indexOf(u8, annotated_case_name, filter) == null) continue;
781 continue;
782 }778 }
783779
784 const exe = b.addExecutable("test", root_src);780 const exe = b.addExecutable("test", root_src);
...@@ -813,7 +809,7 @@ pub const TranslateCContext = struct {...@@ -813,7 +809,7 @@ pub const TranslateCContext = struct {
813 };809 };
814810
815 pub fn addSourceFile(self: &TestCase, filename: []const u8, source: []const u8) void {811 pub fn addSourceFile(self: &TestCase, filename: []const u8, source: []const u8) void {
816 self.sources.append(SourceFile {812 self.sources.append(SourceFile{
817 .filename = filename,813 .filename = filename,
818 .source = source,814 .source = source,
819 }) catch unreachable;815 }) catch unreachable;
...@@ -834,7 +830,7 @@ pub const TranslateCContext = struct {...@@ -834,7 +830,7 @@ pub const TranslateCContext = struct {
834 pub fn create(context: &TranslateCContext, name: []const u8, case: &const TestCase) &TranslateCCmpOutputStep {830 pub fn create(context: &TranslateCContext, name: []const u8, case: &const TestCase) &TranslateCCmpOutputStep {
835 const allocator = context.b.allocator;831 const allocator = context.b.allocator;
836 const ptr = allocator.create(TranslateCCmpOutputStep) catch unreachable;832 const ptr = allocator.create(TranslateCCmpOutputStep) catch unreachable;
837 *ptr = TranslateCCmpOutputStep {833 ptr.* = TranslateCCmpOutputStep{
838 .step = build.Step.init("ParseCCmpOutput", allocator, make),834 .step = build.Step.init("ParseCCmpOutput", allocator, make),
839 .context = context,835 .context = context,
840 .name = name,836 .name = name,
...@@ -857,7 +853,7 @@ pub const TranslateCContext = struct {...@@ -857,7 +853,7 @@ pub const TranslateCContext = struct {
857 zig_args.append("translate-c") catch unreachable;853 zig_args.append("translate-c") catch unreachable;
858 zig_args.append(b.pathFromRoot(root_src)) catch unreachable;854 zig_args.append(b.pathFromRoot(root_src)) catch unreachable;
859855
860 warn("Test {}/{} {}...", self.test_index+1, self.context.test_index, self.name);856 warn("Test {}/{} {}...", self.test_index + 1, self.context.test_index, self.name);
861857
862 if (b.verbose) {858 if (b.verbose) {
863 printInvocation(zig_args.toSliceConst());859 printInvocation(zig_args.toSliceConst());
...@@ -939,11 +935,9 @@ pub const TranslateCContext = struct {...@@ -939,11 +935,9 @@ pub const TranslateCContext = struct {
939 warn("\n");935 warn("\n");
940 }936 }
941937
942 pub fn create(self: &TranslateCContext, allow_warnings: bool, filename: []const u8, name: []const u8,938 pub fn create(self: &TranslateCContext, allow_warnings: bool, filename: []const u8, name: []const u8, source: []const u8, expected_lines: ...) &TestCase {
943 source: []const u8, expected_lines: ...) &TestCase
944 {
945 const tc = self.b.allocator.create(TestCase) catch unreachable;939 const tc = self.b.allocator.create(TestCase) catch unreachable;
946 *tc = TestCase {940 tc.* = TestCase{
947 .name = name,941 .name = name,
948 .sources = ArrayList(TestCase.SourceFile).init(self.b.allocator),942 .sources = ArrayList(TestCase.SourceFile).init(self.b.allocator),
949 .expected_lines = ArrayList([]const u8).init(self.b.allocator),943 .expected_lines = ArrayList([]const u8).init(self.b.allocator),
...@@ -977,8 +971,7 @@ pub const TranslateCContext = struct {...@@ -977,8 +971,7 @@ pub const TranslateCContext = struct {
977971
978 const annotated_case_name = fmt.allocPrint(self.b.allocator, "translate-c {}", case.name) catch unreachable;972 const annotated_case_name = fmt.allocPrint(self.b.allocator, "translate-c {}", case.name) catch unreachable;
979 if (self.test_filter) |filter| {973 if (self.test_filter) |filter| {
980 if (mem.indexOf(u8, annotated_case_name, filter) == null)974 if (mem.indexOf(u8, annotated_case_name, filter) == null) return;
981 return;
982 }975 }
983976
984 const translate_c_and_cmp = TranslateCCmpOutputStep.create(self, annotated_case_name, case);977 const translate_c_and_cmp = TranslateCCmpOutputStep.create(self, annotated_case_name, case);
...@@ -1009,7 +1002,7 @@ pub const GenHContext = struct {...@@ -1009,7 +1002,7 @@ pub const GenHContext = struct {
1009 };1002 };
10101003
1011 pub fn addSourceFile(self: &TestCase, filename: []const u8, source: []const u8) void {1004 pub fn addSourceFile(self: &TestCase, filename: []const u8, source: []const u8) void {
1012 self.sources.append(SourceFile {1005 self.sources.append(SourceFile{
1013 .filename = filename,1006 .filename = filename,
1014 .source = source,1007 .source = source,
1015 }) catch unreachable;1008 }) catch unreachable;
...@@ -1031,7 +1024,7 @@ pub const GenHContext = struct {...@@ -1031,7 +1024,7 @@ pub const GenHContext = struct {
1031 pub fn create(context: &GenHContext, h_path: []const u8, name: []const u8, case: &const TestCase) &GenHCmpOutputStep {1024 pub fn create(context: &GenHContext, h_path: []const u8, name: []const u8, case: &const TestCase) &GenHCmpOutputStep {
1032 const allocator = context.b.allocator;1025 const allocator = context.b.allocator;
1033 const ptr = allocator.create(GenHCmpOutputStep) catch unreachable;1026 const ptr = allocator.create(GenHCmpOutputStep) catch unreachable;
1034 *ptr = GenHCmpOutputStep {1027 ptr.* = GenHCmpOutputStep{
1035 .step = build.Step.init("ParseCCmpOutput", allocator, make),1028 .step = build.Step.init("ParseCCmpOutput", allocator, make),
1036 .context = context,1029 .context = context,
1037 .h_path = h_path,1030 .h_path = h_path,
...@@ -1047,7 +1040,7 @@ pub const GenHContext = struct {...@@ -1047,7 +1040,7 @@ pub const GenHContext = struct {
1047 const self = @fieldParentPtr(GenHCmpOutputStep, "step", step);1040 const self = @fieldParentPtr(GenHCmpOutputStep, "step", step);
1048 const b = self.context.b;1041 const b = self.context.b;
10491042
1050 warn("Test {}/{} {}...", self.test_index+1, self.context.test_index, self.name);1043 warn("Test {}/{} {}...", self.test_index + 1, self.context.test_index, self.name);
10511044
1052 const full_h_path = b.pathFromRoot(self.h_path);1045 const full_h_path = b.pathFromRoot(self.h_path);
1053 const actual_h = try io.readFileAlloc(b.allocator, full_h_path);1046 const actual_h = try io.readFileAlloc(b.allocator, full_h_path);
...@@ -1076,11 +1069,9 @@ pub const GenHContext = struct {...@@ -1076,11 +1069,9 @@ pub const GenHContext = struct {
1076 warn("\n");1069 warn("\n");
1077 }1070 }
10781071
1079 pub fn create(self: &GenHContext, filename: []const u8, name: []const u8,1072 pub fn create(self: &GenHContext, filename: []const u8, name: []const u8, source: []const u8, expected_lines: ...) &TestCase {
1080 source: []const u8, expected_lines: ...) &TestCase
1081 {
1082 const tc = self.b.allocator.create(TestCase) catch unreachable;1073 const tc = self.b.allocator.create(TestCase) catch unreachable;
1083 *tc = TestCase {1074 tc.* = TestCase{
1084 .name = name,1075 .name = name,
1085 .sources = ArrayList(TestCase.SourceFile).init(self.b.allocator),1076 .sources = ArrayList(TestCase.SourceFile).init(self.b.allocator),
1086 .expected_lines = ArrayList([]const u8).init(self.b.allocator),1077 .expected_lines = ArrayList([]const u8).init(self.b.allocator),
...@@ -1105,8 +1096,7 @@ pub const GenHContext = struct {...@@ -1105,8 +1096,7 @@ pub const GenHContext = struct {
1105 const mode = builtin.Mode.Debug;1096 const mode = builtin.Mode.Debug;
1106 const annotated_case_name = fmt.allocPrint(self.b.allocator, "gen-h {} ({})", case.name, @tagName(mode)) catch unreachable;1097 const annotated_case_name = fmt.allocPrint(self.b.allocator, "gen-h {} ({})", case.name, @tagName(mode)) catch unreachable;
1107 if (self.test_filter) |filter| {1098 if (self.test_filter) |filter| {
1108 if (mem.indexOf(u8, annotated_case_name, filter) == null)1099 if (mem.indexOf(u8, annotated_case_name, filter) == null) return;
1109 return;
1110 }1100 }
11111101
1112 const obj = b.addObject("test", root_src);1102 const obj = b.addObject("test", root_src);
test/translate_c.zig+50-50
...@@ -720,43 +720,43 @@ pub fn addCases(cases: &tests.TranslateCContext) void {...@@ -720,43 +720,43 @@ pub fn addCases(cases: &tests.TranslateCContext) void {
720 \\ var a: c_int = 0;720 \\ var a: c_int = 0;
721 \\ a += x: {721 \\ a += x: {
722 \\ const _ref = &a;722 \\ const _ref = &a;
723 \\ (*_ref) = ((*_ref) + 1);723 \\ _ref.* = (_ref.* + 1);
724 \\ break :x *_ref;724 \\ break :x _ref.*;
725 \\ };725 \\ };
726 \\ a -= x: {726 \\ a -= x: {
727 \\ const _ref = &a;727 \\ const _ref = &a;
728 \\ (*_ref) = ((*_ref) - 1);728 \\ _ref.* = (_ref.* - 1);
729 \\ break :x *_ref;729 \\ break :x _ref.*;
730 \\ };730 \\ };
731 \\ a *= x: {731 \\ a *= x: {
732 \\ const _ref = &a;732 \\ const _ref = &a;
733 \\ (*_ref) = ((*_ref) * 1);733 \\ _ref.* = (_ref.* * 1);
734 \\ break :x *_ref;734 \\ break :x _ref.*;
735 \\ };735 \\ };
736 \\ a &= x: {736 \\ a &= x: {
737 \\ const _ref = &a;737 \\ const _ref = &a;
738 \\ (*_ref) = ((*_ref) & 1);738 \\ _ref.* = (_ref.* & 1);
739 \\ break :x *_ref;739 \\ break :x _ref.*;
740 \\ };740 \\ };
741 \\ a |= x: {741 \\ a |= x: {
742 \\ const _ref = &a;742 \\ const _ref = &a;
743 \\ (*_ref) = ((*_ref) | 1);743 \\ _ref.* = (_ref.* | 1);
744 \\ break :x *_ref;744 \\ break :x _ref.*;
745 \\ };745 \\ };
746 \\ a ^= x: {746 \\ a ^= x: {
747 \\ const _ref = &a;747 \\ const _ref = &a;
748 \\ (*_ref) = ((*_ref) ^ 1);748 \\ _ref.* = (_ref.* ^ 1);
749 \\ break :x *_ref;749 \\ break :x _ref.*;
750 \\ };750 \\ };
751 \\ a >>= @import("std").math.Log2Int(c_int)(x: {751 \\ a >>= @import("std").math.Log2Int(c_int)(x: {
752 \\ const _ref = &a;752 \\ const _ref = &a;
753 \\ (*_ref) = ((*_ref) >> @import("std").math.Log2Int(c_int)(1));753 \\ _ref.* = (_ref.* >> @import("std").math.Log2Int(c_int)(1));
754 \\ break :x *_ref;754 \\ break :x _ref.*;
755 \\ });755 \\ });
756 \\ a <<= @import("std").math.Log2Int(c_int)(x: {756 \\ a <<= @import("std").math.Log2Int(c_int)(x: {
757 \\ const _ref = &a;757 \\ const _ref = &a;
758 \\ (*_ref) = ((*_ref) << @import("std").math.Log2Int(c_int)(1));758 \\ _ref.* = (_ref.* << @import("std").math.Log2Int(c_int)(1));
759 \\ break :x *_ref;759 \\ break :x _ref.*;
760 \\ });760 \\ });
761 \\}761 \\}
762 );762 );
...@@ -778,43 +778,43 @@ pub fn addCases(cases: &tests.TranslateCContext) void {...@@ -778,43 +778,43 @@ pub fn addCases(cases: &tests.TranslateCContext) void {
778 \\ var a: c_uint = c_uint(0);778 \\ var a: c_uint = c_uint(0);
779 \\ a +%= x: {779 \\ a +%= x: {
780 \\ const _ref = &a;780 \\ const _ref = &a;
781 \\ (*_ref) = ((*_ref) +% c_uint(1));781 \\ _ref.* = (_ref.* +% c_uint(1));
782 \\ break :x *_ref;782 \\ break :x _ref.*;
783 \\ };783 \\ };
784 \\ a -%= x: {784 \\ a -%= x: {
785 \\ const _ref = &a;785 \\ const _ref = &a;
786 \\ (*_ref) = ((*_ref) -% c_uint(1));786 \\ _ref.* = (_ref.* -% c_uint(1));
787 \\ break :x *_ref;787 \\ break :x _ref.*;
788 \\ };788 \\ };
789 \\ a *%= x: {789 \\ a *%= x: {
790 \\ const _ref = &a;790 \\ const _ref = &a;
791 \\ (*_ref) = ((*_ref) *% c_uint(1));791 \\ _ref.* = (_ref.* *% c_uint(1));
792 \\ break :x *_ref;792 \\ break :x _ref.*;
793 \\ };793 \\ };
794 \\ a &= x: {794 \\ a &= x: {
795 \\ const _ref = &a;795 \\ const _ref = &a;
796 \\ (*_ref) = ((*_ref) & c_uint(1));796 \\ _ref.* = (_ref.* & c_uint(1));
797 \\ break :x *_ref;797 \\ break :x _ref.*;
798 \\ };798 \\ };
799 \\ a |= x: {799 \\ a |= x: {
800 \\ const _ref = &a;800 \\ const _ref = &a;
801 \\ (*_ref) = ((*_ref) | c_uint(1));801 \\ _ref.* = (_ref.* | c_uint(1));
802 \\ break :x *_ref;802 \\ break :x _ref.*;
803 \\ };803 \\ };
804 \\ a ^= x: {804 \\ a ^= x: {
805 \\ const _ref = &a;805 \\ const _ref = &a;
806 \\ (*_ref) = ((*_ref) ^ c_uint(1));806 \\ _ref.* = (_ref.* ^ c_uint(1));
807 \\ break :x *_ref;807 \\ break :x _ref.*;
808 \\ };808 \\ };
809 \\ a >>= @import("std").math.Log2Int(c_uint)(x: {809 \\ a >>= @import("std").math.Log2Int(c_uint)(x: {
810 \\ const _ref = &a;810 \\ const _ref = &a;
811 \\ (*_ref) = ((*_ref) >> @import("std").math.Log2Int(c_uint)(1));811 \\ _ref.* = (_ref.* >> @import("std").math.Log2Int(c_uint)(1));
812 \\ break :x *_ref;812 \\ break :x _ref.*;
813 \\ });813 \\ });
814 \\ a <<= @import("std").math.Log2Int(c_uint)(x: {814 \\ a <<= @import("std").math.Log2Int(c_uint)(x: {
815 \\ const _ref = &a;815 \\ const _ref = &a;
816 \\ (*_ref) = ((*_ref) << @import("std").math.Log2Int(c_uint)(1));816 \\ _ref.* = (_ref.* << @import("std").math.Log2Int(c_uint)(1));
817 \\ break :x *_ref;817 \\ break :x _ref.*;
818 \\ });818 \\ });
819 \\}819 \\}
820 );820 );
...@@ -853,26 +853,26 @@ pub fn addCases(cases: &tests.TranslateCContext) void {...@@ -853,26 +853,26 @@ pub fn addCases(cases: &tests.TranslateCContext) void {
853 \\ u -%= 1;853 \\ u -%= 1;
854 \\ i = x: {854 \\ i = x: {
855 \\ const _ref = &i;855 \\ const _ref = &i;
856 \\ const _tmp = *_ref;856 \\ const _tmp = _ref.*;
857 \\ (*_ref) += 1;857 \\ _ref.* += 1;
858 \\ break :x _tmp;858 \\ break :x _tmp;
859 \\ };859 \\ };
860 \\ i = x: {860 \\ i = x: {
861 \\ const _ref = &i;861 \\ const _ref = &i;
862 \\ const _tmp = *_ref;862 \\ const _tmp = _ref.*;
863 \\ (*_ref) -= 1;863 \\ _ref.* -= 1;
864 \\ break :x _tmp;864 \\ break :x _tmp;
865 \\ };865 \\ };
866 \\ u = x: {866 \\ u = x: {
867 \\ const _ref = &u;867 \\ const _ref = &u;
868 \\ const _tmp = *_ref;868 \\ const _tmp = _ref.*;
869 \\ (*_ref) +%= 1;869 \\ _ref.* +%= 1;
870 \\ break :x _tmp;870 \\ break :x _tmp;
871 \\ };871 \\ };
872 \\ u = x: {872 \\ u = x: {
873 \\ const _ref = &u;873 \\ const _ref = &u;
874 \\ const _tmp = *_ref;874 \\ const _tmp = _ref.*;
875 \\ (*_ref) -%= 1;875 \\ _ref.* -%= 1;
876 \\ break :x _tmp;876 \\ break :x _tmp;
877 \\ };877 \\ };
878 \\}878 \\}
...@@ -901,23 +901,23 @@ pub fn addCases(cases: &tests.TranslateCContext) void {...@@ -901,23 +901,23 @@ pub fn addCases(cases: &tests.TranslateCContext) void {
901 \\ u -%= 1;901 \\ u -%= 1;
902 \\ i = x: {902 \\ i = x: {
903 \\ const _ref = &i;903 \\ const _ref = &i;
904 \\ (*_ref) += 1;904 \\ _ref.* += 1;
905 \\ break :x *_ref;905 \\ break :x _ref.*;
906 \\ };906 \\ };
907 \\ i = x: {907 \\ i = x: {
908 \\ const _ref = &i;908 \\ const _ref = &i;
909 \\ (*_ref) -= 1;909 \\ _ref.* -= 1;
910 \\ break :x *_ref;910 \\ break :x _ref.*;
911 \\ };911 \\ };
912 \\ u = x: {912 \\ u = x: {
913 \\ const _ref = &u;913 \\ const _ref = &u;
914 \\ (*_ref) +%= 1;914 \\ _ref.* +%= 1;
915 \\ break :x *_ref;915 \\ break :x _ref.*;
916 \\ };916 \\ };
917 \\ u = x: {917 \\ u = x: {
918 \\ const _ref = &u;918 \\ const _ref = &u;
919 \\ (*_ref) -%= 1;919 \\ _ref.* -%= 1;
920 \\ break :x *_ref;920 \\ break :x _ref.*;
921 \\ };921 \\ };
922 \\}922 \\}
923 );923 );
...@@ -985,7 +985,7 @@ pub fn addCases(cases: &tests.TranslateCContext) void {...@@ -985,7 +985,7 @@ pub fn addCases(cases: &tests.TranslateCContext) void {
985 \\}985 \\}
986 ,986 ,
987 \\pub export fn foo(x: ?&c_int) void {987 \\pub export fn foo(x: ?&c_int) void {
988 \\ (*??x) = 1;988 \\ (??x).* = 1;
989 \\}989 \\}
990 );990 );
991991
...@@ -1013,7 +1013,7 @@ pub fn addCases(cases: &tests.TranslateCContext) void {...@@ -1013,7 +1013,7 @@ pub fn addCases(cases: &tests.TranslateCContext) void {
1013 \\pub fn foo() c_int {1013 \\pub fn foo() c_int {
1014 \\ var x: c_int = 1234;1014 \\ var x: c_int = 1234;
1015 \\ var ptr: ?&c_int = &x;1015 \\ var ptr: ?&c_int = &x;
1016 \\ return *??ptr;1016 \\ return (??ptr).*;
1017 \\}1017 \\}
1018 );1018 );
10191019