Merge remote-tracking branch 'origin/master' into stage2-whole-file-astgen
In particular I wanted the change that makes `suspend;` illegal in the parser.
This commit is contained in:
@@ -1021,7 +1021,7 @@ pub fn addCases(cases: *tests.CompileErrorContext) void {
|
||||
\\export fn entry() void {
|
||||
\\ nosuspend {
|
||||
\\ const bar = async foo();
|
||||
\\ suspend;
|
||||
\\ suspend {}
|
||||
\\ resume bar;
|
||||
\\ }
|
||||
\\}
|
||||
@@ -2120,7 +2120,7 @@ pub fn addCases(cases: *tests.CompileErrorContext) void {
|
||||
\\ non_async_fn = func;
|
||||
\\}
|
||||
\\fn func() void {
|
||||
\\ suspend;
|
||||
\\ suspend {}
|
||||
\\}
|
||||
, &[_][]const u8{
|
||||
"tmp.zig:5:1: error: 'func' cannot be async",
|
||||
@@ -2198,7 +2198,7 @@ pub fn addCases(cases: *tests.CompileErrorContext) void {
|
||||
\\ var x: anyframe = &f;
|
||||
\\}
|
||||
\\fn func() void {
|
||||
\\ suspend;
|
||||
\\ suspend {}
|
||||
\\}
|
||||
, &[_][]const u8{
|
||||
"tmp.zig:3:12: error: expected type 'anyframe', found '*const @Frame(func)'",
|
||||
@@ -2231,10 +2231,10 @@ pub fn addCases(cases: *tests.CompileErrorContext) void {
|
||||
\\ frame = async bar();
|
||||
\\}
|
||||
\\fn foo() void {
|
||||
\\ suspend;
|
||||
\\ suspend {}
|
||||
\\}
|
||||
\\fn bar() void {
|
||||
\\ suspend;
|
||||
\\ suspend {}
|
||||
\\}
|
||||
, &[_][]const u8{
|
||||
"tmp.zig:3:13: error: expected type '*@Frame(bar)', found '*@Frame(foo)'",
|
||||
@@ -2269,7 +2269,7 @@ pub fn addCases(cases: *tests.CompileErrorContext) void {
|
||||
\\ var result = await frame;
|
||||
\\}
|
||||
\\fn func() void {
|
||||
\\ suspend;
|
||||
\\ suspend {}
|
||||
\\}
|
||||
, &[_][]const u8{
|
||||
"tmp.zig:1:1: error: function with calling convention 'C' cannot be async",
|
||||
@@ -2347,7 +2347,7 @@ pub fn addCases(cases: *tests.CompileErrorContext) void {
|
||||
\\ bar();
|
||||
\\}
|
||||
\\fn bar() void {
|
||||
\\ suspend;
|
||||
\\ suspend {}
|
||||
\\}
|
||||
, &[_][]const u8{
|
||||
"tmp.zig:1:1: error: function with calling convention 'C' cannot be async",
|
||||
|
||||
@@ -1453,4 +1453,27 @@ pub fn addCases(cases: *tests.RunTranslatedCContext) void {
|
||||
\\ return 0;
|
||||
\\}
|
||||
, "");
|
||||
|
||||
cases.add("Cast to enum from larger integral type. Issue #6011",
|
||||
\\#include <stdint.h>
|
||||
\\#include <stdlib.h>
|
||||
\\enum Foo { A, B, C };
|
||||
\\static inline enum Foo do_stuff(void) {
|
||||
\\ int64_t i = 1;
|
||||
\\ return (enum Foo)i;
|
||||
\\}
|
||||
\\int main(void) {
|
||||
\\ if (do_stuff() != B) abort();
|
||||
\\ return 0;
|
||||
\\}
|
||||
, "");
|
||||
|
||||
cases.add("Render array LHS as grouped node if necessary",
|
||||
\\#include <stdlib.h>
|
||||
\\int main(void) {
|
||||
\\ int arr[] = {40, 41, 42, 43};
|
||||
\\ if ((arr + 1)[1] != 42) abort();
|
||||
\\ return 0;
|
||||
\\}
|
||||
, "");
|
||||
}
|
||||
|
||||
@@ -13,7 +13,7 @@ pub fn addCases(cases: *tests.CompareOutputContext) void {
|
||||
|
||||
cases.addRuntimeSafety("switch on corrupted enum value",
|
||||
\\const std = @import("std");
|
||||
++ check_panic_msg ++
|
||||
++ check_panic_msg ++
|
||||
\\const E = enum(u32) {
|
||||
\\ X = 1,
|
||||
\\};
|
||||
@@ -28,7 +28,7 @@ pub fn addCases(cases: *tests.CompareOutputContext) void {
|
||||
|
||||
cases.addRuntimeSafety("switch on corrupted union value",
|
||||
\\const std = @import("std");
|
||||
++ check_panic_msg ++
|
||||
++ check_panic_msg ++
|
||||
\\const U = union(enum(u32)) {
|
||||
\\ X: u8,
|
||||
\\};
|
||||
@@ -54,7 +54,7 @@ pub fn addCases(cases: *tests.CompareOutputContext) void {
|
||||
|
||||
cases.addRuntimeSafety("@tagName on corrupted enum value",
|
||||
\\const std = @import("std");
|
||||
++ check_panic_msg ++
|
||||
++ check_panic_msg ++
|
||||
\\const E = enum(u32) {
|
||||
\\ X = 1,
|
||||
\\};
|
||||
@@ -67,7 +67,7 @@ pub fn addCases(cases: *tests.CompareOutputContext) void {
|
||||
|
||||
cases.addRuntimeSafety("@tagName on corrupted union value",
|
||||
\\const std = @import("std");
|
||||
++ check_panic_msg ++
|
||||
++ check_panic_msg ++
|
||||
\\const U = union(enum(u32)) {
|
||||
\\ X: u8,
|
||||
\\};
|
||||
@@ -92,7 +92,7 @@ pub fn addCases(cases: *tests.CompareOutputContext) void {
|
||||
|
||||
cases.addRuntimeSafety("slicing operator with sentinel",
|
||||
\\const std = @import("std");
|
||||
++ check_panic_msg ++
|
||||
++ check_panic_msg ++
|
||||
\\pub fn main() void {
|
||||
\\ var buf = [4]u8{'a','b','c',0};
|
||||
\\ const slice = buf[0..4 :0];
|
||||
@@ -100,7 +100,7 @@ pub fn addCases(cases: *tests.CompareOutputContext) void {
|
||||
);
|
||||
cases.addRuntimeSafety("slicing operator with sentinel",
|
||||
\\const std = @import("std");
|
||||
++ check_panic_msg ++
|
||||
++ check_panic_msg ++
|
||||
\\pub fn main() void {
|
||||
\\ var buf = [4]u8{'a','b','c',0};
|
||||
\\ const slice = buf[0..:0];
|
||||
@@ -108,7 +108,7 @@ pub fn addCases(cases: *tests.CompareOutputContext) void {
|
||||
);
|
||||
cases.addRuntimeSafety("slicing operator with sentinel",
|
||||
\\const std = @import("std");
|
||||
++ check_panic_msg ++
|
||||
++ check_panic_msg ++
|
||||
\\pub fn main() void {
|
||||
\\ var buf_zero = [0]u8{};
|
||||
\\ const slice = buf_zero[0..0 :0];
|
||||
@@ -116,7 +116,7 @@ pub fn addCases(cases: *tests.CompareOutputContext) void {
|
||||
);
|
||||
cases.addRuntimeSafety("slicing operator with sentinel",
|
||||
\\const std = @import("std");
|
||||
++ check_panic_msg ++
|
||||
++ check_panic_msg ++
|
||||
\\pub fn main() void {
|
||||
\\ var buf_zero = [0]u8{};
|
||||
\\ const slice = buf_zero[0..:0];
|
||||
@@ -124,7 +124,7 @@ pub fn addCases(cases: *tests.CompareOutputContext) void {
|
||||
);
|
||||
cases.addRuntimeSafety("slicing operator with sentinel",
|
||||
\\const std = @import("std");
|
||||
++ check_panic_msg ++
|
||||
++ check_panic_msg ++
|
||||
\\pub fn main() void {
|
||||
\\ var buf_sentinel = [2:0]u8{'a','b'};
|
||||
\\ @ptrCast(*[3]u8, &buf_sentinel)[2] = 0;
|
||||
@@ -133,7 +133,7 @@ pub fn addCases(cases: *tests.CompareOutputContext) void {
|
||||
);
|
||||
cases.addRuntimeSafety("slicing operator with sentinel",
|
||||
\\const std = @import("std");
|
||||
++ check_panic_msg ++
|
||||
++ check_panic_msg ++
|
||||
\\pub fn main() void {
|
||||
\\ var buf_slice: []const u8 = &[3]u8{ 'a', 'b', 0 };
|
||||
\\ const slice = buf_slice[0..3 :0];
|
||||
@@ -141,7 +141,7 @@ pub fn addCases(cases: *tests.CompareOutputContext) void {
|
||||
);
|
||||
cases.addRuntimeSafety("slicing operator with sentinel",
|
||||
\\const std = @import("std");
|
||||
++ check_panic_msg ++
|
||||
++ check_panic_msg ++
|
||||
\\pub fn main() void {
|
||||
\\ var buf_slice: []const u8 = &[3]u8{ 'a', 'b', 0 };
|
||||
\\ const slice = buf_slice[0.. :0];
|
||||
@@ -367,7 +367,7 @@ pub fn addCases(cases: *tests.CompareOutputContext) void {
|
||||
\\}
|
||||
\\fn add(a: i32, b: i32) i32 {
|
||||
\\ if (a > 100) {
|
||||
\\ suspend;
|
||||
\\ suspend {}
|
||||
\\ }
|
||||
\\ return a + b;
|
||||
\\}
|
||||
@@ -407,7 +407,7 @@ pub fn addCases(cases: *tests.CompareOutputContext) void {
|
||||
\\ var frame = @asyncCall(&bytes, {}, ptr, .{});
|
||||
\\}
|
||||
\\fn other() callconv(.Async) void {
|
||||
\\ suspend;
|
||||
\\ suspend {}
|
||||
\\}
|
||||
);
|
||||
|
||||
@@ -424,7 +424,7 @@ pub fn addCases(cases: *tests.CompareOutputContext) void {
|
||||
\\ await frame;
|
||||
\\}
|
||||
\\fn other() void {
|
||||
\\ suspend;
|
||||
\\ suspend {}
|
||||
\\}
|
||||
);
|
||||
|
||||
@@ -440,7 +440,7 @@ pub fn addCases(cases: *tests.CompareOutputContext) void {
|
||||
\\ other();
|
||||
\\}
|
||||
\\fn other() void {
|
||||
\\ suspend;
|
||||
\\ suspend {}
|
||||
\\}
|
||||
);
|
||||
|
||||
@@ -454,7 +454,7 @@ pub fn addCases(cases: *tests.CompareOutputContext) void {
|
||||
\\ resume p; //bad
|
||||
\\}
|
||||
\\fn suspendOnce() void {
|
||||
\\ suspend;
|
||||
\\ suspend {}
|
||||
\\}
|
||||
);
|
||||
|
||||
@@ -1019,7 +1019,7 @@ pub fn addCases(cases: *tests.CompareOutputContext) void {
|
||||
\\}
|
||||
\\
|
||||
\\fn failing() anyerror!void {
|
||||
\\ suspend;
|
||||
\\ suspend {}
|
||||
\\ return second();
|
||||
\\}
|
||||
\\
|
||||
|
||||
@@ -18,9 +18,9 @@ test "simple coroutine suspend and resume" {
|
||||
}
|
||||
fn simpleAsyncFn() void {
|
||||
global_x += 1;
|
||||
suspend;
|
||||
suspend {}
|
||||
global_x += 1;
|
||||
suspend;
|
||||
suspend {}
|
||||
global_x += 1;
|
||||
}
|
||||
|
||||
@@ -34,7 +34,7 @@ test "pass parameter to coroutine" {
|
||||
}
|
||||
fn simpleAsyncFnWithArg(delta: i32) void {
|
||||
global_y += delta;
|
||||
suspend;
|
||||
suspend {}
|
||||
global_y += delta;
|
||||
}
|
||||
|
||||
@@ -50,7 +50,7 @@ test "suspend at end of function" {
|
||||
|
||||
fn suspendAtEnd() void {
|
||||
x += 1;
|
||||
suspend;
|
||||
suspend {}
|
||||
}
|
||||
};
|
||||
S.doTheTest();
|
||||
@@ -74,11 +74,11 @@ test "local variable in async function" {
|
||||
|
||||
fn add(a: i32, b: i32) void {
|
||||
var accum: i32 = 0;
|
||||
suspend;
|
||||
suspend {}
|
||||
accum += a;
|
||||
suspend;
|
||||
suspend {}
|
||||
accum += b;
|
||||
suspend;
|
||||
suspend {}
|
||||
x = accum;
|
||||
}
|
||||
};
|
||||
@@ -102,7 +102,7 @@ test "calling an inferred async function" {
|
||||
}
|
||||
fn other() void {
|
||||
other_frame = @frame();
|
||||
suspend;
|
||||
suspend {}
|
||||
x += 1;
|
||||
}
|
||||
};
|
||||
@@ -129,7 +129,7 @@ test "@frameSize" {
|
||||
}
|
||||
fn other(param: i32) void {
|
||||
var local: i32 = undefined;
|
||||
suspend;
|
||||
suspend {}
|
||||
}
|
||||
};
|
||||
S.doTheTest();
|
||||
@@ -269,7 +269,7 @@ test "async function with dot syntax" {
|
||||
var y: i32 = 1;
|
||||
fn foo() callconv(.Async) void {
|
||||
y += 1;
|
||||
suspend;
|
||||
suspend {}
|
||||
}
|
||||
};
|
||||
const p = async S.foo();
|
||||
@@ -298,7 +298,7 @@ fn doTheAwait(f: anyframe->void) void {
|
||||
fn simpleAsyncFn2(y: *i32) callconv(.Async) void {
|
||||
defer y.* += 2;
|
||||
y.* += 1;
|
||||
suspend;
|
||||
suspend {}
|
||||
}
|
||||
|
||||
test "@asyncCall with return type" {
|
||||
@@ -312,7 +312,7 @@ test "@asyncCall with return type" {
|
||||
|
||||
fn afunc() i32 {
|
||||
global_frame = @frame();
|
||||
suspend;
|
||||
suspend {}
|
||||
return 1234;
|
||||
}
|
||||
};
|
||||
@@ -348,7 +348,7 @@ test "async fn with inferred error set" {
|
||||
|
||||
fn failing() !void {
|
||||
global_frame = @frame();
|
||||
suspend;
|
||||
suspend {}
|
||||
return error.Fail;
|
||||
}
|
||||
};
|
||||
@@ -375,7 +375,7 @@ fn nonFailing() (anyframe->anyerror!void) {
|
||||
return &Static.frame;
|
||||
}
|
||||
fn suspendThenFail() callconv(.Async) anyerror!void {
|
||||
suspend;
|
||||
suspend {}
|
||||
return error.Fail;
|
||||
}
|
||||
fn printTrace(p: anyframe->(anyerror!void)) callconv(.Async) void {
|
||||
@@ -400,7 +400,7 @@ fn testBreakFromSuspend(my_result: *i32) callconv(.Async) void {
|
||||
resume @frame();
|
||||
}
|
||||
my_result.* += 1;
|
||||
suspend;
|
||||
suspend {}
|
||||
my_result.* += 1;
|
||||
}
|
||||
|
||||
@@ -421,7 +421,7 @@ test "heap allocated async function frame" {
|
||||
|
||||
fn someFunc() void {
|
||||
x += 1;
|
||||
suspend;
|
||||
suspend {}
|
||||
x += 1;
|
||||
}
|
||||
};
|
||||
@@ -454,7 +454,7 @@ test "async function call return value" {
|
||||
|
||||
fn other(x: i32, y: i32) Point {
|
||||
frame = @frame();
|
||||
suspend;
|
||||
suspend {}
|
||||
return Point{
|
||||
.x = x,
|
||||
.y = y,
|
||||
@@ -487,7 +487,7 @@ test "suspension points inside branching control flow" {
|
||||
|
||||
fn func(b: bool) void {
|
||||
while (b) {
|
||||
suspend;
|
||||
suspend {}
|
||||
result += 1;
|
||||
}
|
||||
}
|
||||
@@ -541,7 +541,7 @@ test "pass string literal to async function" {
|
||||
|
||||
fn hello(msg: []const u8) void {
|
||||
frame = @frame();
|
||||
suspend;
|
||||
suspend {}
|
||||
expectEqualStrings("hello", msg);
|
||||
ok = true;
|
||||
}
|
||||
@@ -566,7 +566,7 @@ test "await inside an errdefer" {
|
||||
|
||||
fn func() void {
|
||||
frame = @frame();
|
||||
suspend;
|
||||
suspend {}
|
||||
}
|
||||
};
|
||||
S.doTheTest();
|
||||
@@ -590,7 +590,7 @@ test "try in an async function with error union and non-zero-bit payload" {
|
||||
|
||||
fn theProblem() ![]u8 {
|
||||
frame = @frame();
|
||||
suspend;
|
||||
suspend {}
|
||||
const result = try other();
|
||||
return result;
|
||||
}
|
||||
@@ -622,7 +622,7 @@ test "returning a const error from async function" {
|
||||
|
||||
fn fetchUrl(unused: i32, url: []const u8) ![]u8 {
|
||||
frame = @frame();
|
||||
suspend;
|
||||
suspend {}
|
||||
ok = true;
|
||||
return error.OutOfMemory;
|
||||
}
|
||||
@@ -967,7 +967,7 @@ test "@asyncCall with comptime-known function, but not awaited directly" {
|
||||
|
||||
fn failing() !void {
|
||||
global_frame = @frame();
|
||||
suspend;
|
||||
suspend {}
|
||||
return error.Fail;
|
||||
}
|
||||
};
|
||||
@@ -977,7 +977,7 @@ test "@asyncCall with comptime-known function, but not awaited directly" {
|
||||
test "@asyncCall with actual frame instead of byte buffer" {
|
||||
const S = struct {
|
||||
fn func() i32 {
|
||||
suspend;
|
||||
suspend {}
|
||||
return 1234;
|
||||
}
|
||||
};
|
||||
@@ -993,7 +993,7 @@ test "@asyncCall using the result location inside the frame" {
|
||||
fn simple2(y: *i32) callconv(.Async) i32 {
|
||||
defer y.* += 2;
|
||||
y.* += 1;
|
||||
suspend;
|
||||
suspend {}
|
||||
return 1234;
|
||||
}
|
||||
fn getAnswer(f: anyframe->i32, out: *i32) void {
|
||||
@@ -1095,7 +1095,7 @@ test "nosuspend function call" {
|
||||
}
|
||||
fn add(a: i32, b: i32) i32 {
|
||||
if (a > 100) {
|
||||
suspend;
|
||||
suspend {}
|
||||
}
|
||||
return a + b;
|
||||
}
|
||||
@@ -1170,7 +1170,7 @@ test "suspend in for loop" {
|
||||
global_frame = @frame();
|
||||
var sum: u32 = 0;
|
||||
for (stuff) |x| {
|
||||
suspend;
|
||||
suspend {}
|
||||
sum += x;
|
||||
}
|
||||
global_frame = null;
|
||||
@@ -1197,7 +1197,7 @@ test "suspend in while loop" {
|
||||
global_frame = @frame();
|
||||
defer global_frame = null;
|
||||
while (stuff) |val| {
|
||||
suspend;
|
||||
suspend {}
|
||||
return val;
|
||||
}
|
||||
return 0;
|
||||
@@ -1206,7 +1206,7 @@ test "suspend in while loop" {
|
||||
global_frame = @frame();
|
||||
defer global_frame = null;
|
||||
while (stuff) |val| {
|
||||
suspend;
|
||||
suspend {}
|
||||
return val;
|
||||
} else |err| {
|
||||
return 0;
|
||||
@@ -1339,7 +1339,7 @@ test "async function passed 0-bit arg after non-0-bit arg" {
|
||||
|
||||
fn bar(x: i32, args: anytype) anyerror!void {
|
||||
global_frame = @frame();
|
||||
suspend;
|
||||
suspend {}
|
||||
global_int = x;
|
||||
}
|
||||
};
|
||||
@@ -1361,7 +1361,7 @@ test "async function passed align(16) arg after align(8) arg" {
|
||||
fn bar(x: u64, args: anytype) anyerror!void {
|
||||
expect(x == 10);
|
||||
global_frame = @frame();
|
||||
suspend;
|
||||
suspend {}
|
||||
global_int = args[0];
|
||||
}
|
||||
};
|
||||
@@ -1383,7 +1383,7 @@ test "async function call resolves target fn frame, comptime func" {
|
||||
|
||||
fn bar() anyerror!void {
|
||||
global_frame = @frame();
|
||||
suspend;
|
||||
suspend {}
|
||||
global_int += 1;
|
||||
}
|
||||
};
|
||||
@@ -1406,7 +1406,7 @@ test "async function call resolves target fn frame, runtime func" {
|
||||
|
||||
fn bar() anyerror!void {
|
||||
global_frame = @frame();
|
||||
suspend;
|
||||
suspend {}
|
||||
global_int += 1;
|
||||
}
|
||||
};
|
||||
@@ -1430,7 +1430,7 @@ test "properly spill optional payload capture value" {
|
||||
|
||||
fn bar() void {
|
||||
global_frame = @frame();
|
||||
suspend;
|
||||
suspend {}
|
||||
global_int += 1;
|
||||
}
|
||||
};
|
||||
@@ -1466,13 +1466,13 @@ test "handle defer interfering with return value spill" {
|
||||
|
||||
fn bar() anyerror!void {
|
||||
global_frame1 = @frame();
|
||||
suspend;
|
||||
suspend {}
|
||||
return error.Bad;
|
||||
}
|
||||
|
||||
fn baz() void {
|
||||
global_frame2 = @frame();
|
||||
suspend;
|
||||
suspend {}
|
||||
baz_happened = true;
|
||||
}
|
||||
};
|
||||
@@ -1497,7 +1497,7 @@ test "take address of temporary async frame" {
|
||||
|
||||
fn foo(arg: i32) i32 {
|
||||
global_frame = @frame();
|
||||
suspend;
|
||||
suspend {}
|
||||
return arg + 1234;
|
||||
}
|
||||
|
||||
@@ -1520,7 +1520,7 @@ test "nosuspend await" {
|
||||
|
||||
fn foo(want_suspend: bool) i32 {
|
||||
if (want_suspend) {
|
||||
suspend;
|
||||
suspend {}
|
||||
}
|
||||
return 42;
|
||||
}
|
||||
@@ -1569,11 +1569,11 @@ test "nosuspend on async function calls" {
|
||||
// };
|
||||
// const S1 = struct {
|
||||
// fn c() S0 {
|
||||
// suspend;
|
||||
// suspend {}
|
||||
// return S0{};
|
||||
// }
|
||||
// fn d() !S0 {
|
||||
// suspend;
|
||||
// suspend {}
|
||||
// return S0{};
|
||||
// }
|
||||
// };
|
||||
@@ -1591,11 +1591,11 @@ test "nosuspend resume async function calls" {
|
||||
};
|
||||
const S1 = struct {
|
||||
fn c() S0 {
|
||||
suspend;
|
||||
suspend {}
|
||||
return S0{};
|
||||
}
|
||||
fn d() !S0 {
|
||||
suspend;
|
||||
suspend {}
|
||||
return S0{};
|
||||
}
|
||||
};
|
||||
|
||||
@@ -229,16 +229,26 @@ fn testSignedWrappingEval(x: i32) void {
|
||||
expect(max_val == maxInt(i32));
|
||||
}
|
||||
|
||||
test "negation wrapping" {
|
||||
testNegationWrappingEval(minInt(i16));
|
||||
comptime testNegationWrappingEval(minInt(i16));
|
||||
test "signed negation wrapping" {
|
||||
testSignedNegationWrappingEval(minInt(i16));
|
||||
comptime testSignedNegationWrappingEval(minInt(i16));
|
||||
}
|
||||
fn testNegationWrappingEval(x: i16) void {
|
||||
fn testSignedNegationWrappingEval(x: i16) void {
|
||||
expect(x == -32768);
|
||||
const neg = -%x;
|
||||
expect(neg == -32768);
|
||||
}
|
||||
|
||||
test "unsigned negation wrapping" {
|
||||
testUnsignedNegationWrappingEval(1);
|
||||
comptime testUnsignedNegationWrappingEval(1);
|
||||
}
|
||||
fn testUnsignedNegationWrappingEval(x: u16) void {
|
||||
expect(x == 1);
|
||||
const neg = -%x;
|
||||
expect(neg == maxInt(u16));
|
||||
}
|
||||
|
||||
test "unsigned 64-bit division" {
|
||||
test_u64_div();
|
||||
comptime test_u64_div();
|
||||
@@ -843,3 +853,20 @@ test "compare undefined literal with comptime_int" {
|
||||
x = true;
|
||||
expect(x);
|
||||
}
|
||||
|
||||
test "signed zeros are represented properly" {
|
||||
const S = struct {
|
||||
fn doTheTest() void {
|
||||
inline for ([_]type{ f16, f32, f64, f128 }) |T| {
|
||||
const ST = std.meta.Int(.unsigned, @typeInfo(T).Float.bits);
|
||||
var as_fp_val = -@as(T, 0.0);
|
||||
var as_uint_val = @bitCast(ST, as_fp_val);
|
||||
// Ensure the sign bit is set.
|
||||
expect(as_uint_val >> (@typeInfo(T).Float.bits - 1) == 1);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
S.doTheTest();
|
||||
comptime S.doTheTest();
|
||||
}
|
||||
|
||||
@@ -212,6 +212,22 @@ const test_targets = blk: {
|
||||
// .link_libc = true,
|
||||
//},
|
||||
|
||||
TestTarget{
|
||||
.target = .{
|
||||
.cpu_arch = .powerpc,
|
||||
.os_tag = .linux,
|
||||
.abi = .none,
|
||||
},
|
||||
},
|
||||
TestTarget{
|
||||
.target = .{
|
||||
.cpu_arch = .powerpc,
|
||||
.os_tag = .linux,
|
||||
.abi = .musl,
|
||||
},
|
||||
.link_libc = true,
|
||||
},
|
||||
|
||||
TestTarget{
|
||||
.target = .{
|
||||
.cpu_arch = .riscv64,
|
||||
|
||||
@@ -3,6 +3,22 @@ const std = @import("std");
|
||||
const CrossTarget = std.zig.CrossTarget;
|
||||
|
||||
pub fn addCases(cases: *tests.TranslateCContext) void {
|
||||
cases.add("field access is grouped if necessary",
|
||||
\\unsigned long foo(unsigned long x) {
|
||||
\\ return ((union{unsigned long _x}){x})._x;
|
||||
\\}
|
||||
, &[_][]const u8{
|
||||
\\pub export fn foo(arg_x: c_ulong) c_ulong {
|
||||
\\ var x = arg_x;
|
||||
\\ const union_unnamed_1 = extern union {
|
||||
\\ _x: c_ulong,
|
||||
\\ };
|
||||
\\ return (union_unnamed_1{
|
||||
\\ ._x = x,
|
||||
\\ })._x;
|
||||
\\}
|
||||
});
|
||||
|
||||
cases.add("unnamed child types of typedef receive typedef's name",
|
||||
\\typedef enum {
|
||||
\\ FooA,
|
||||
@@ -111,7 +127,7 @@ pub fn addCases(cases: *tests.TranslateCContext) void {
|
||||
\\ const A = @enumToInt(enum_Foo.A);
|
||||
\\ const B = @enumToInt(enum_Foo.B);
|
||||
\\ const C = @enumToInt(enum_Foo.C);
|
||||
\\ var a: enum_Foo = @intToEnum(enum_Foo, B);
|
||||
\\ var a: enum_Foo = @import("std").meta.cast(enum_Foo, B);
|
||||
\\ {
|
||||
\\ const enum_Foo = extern enum(c_int) {
|
||||
\\ A,
|
||||
@@ -122,7 +138,7 @@ pub fn addCases(cases: *tests.TranslateCContext) void {
|
||||
\\ const A_2 = @enumToInt(enum_Foo.A);
|
||||
\\ const B_3 = @enumToInt(enum_Foo.B);
|
||||
\\ const C_4 = @enumToInt(enum_Foo.C);
|
||||
\\ var a_5: enum_Foo = @intToEnum(enum_Foo, B_3);
|
||||
\\ var a_5: enum_Foo = @import("std").meta.cast(enum_Foo, B_3);
|
||||
\\ }
|
||||
\\}
|
||||
});
|
||||
@@ -1676,7 +1692,7 @@ pub fn addCases(cases: *tests.TranslateCContext) void {
|
||||
\\pub const e = @enumToInt(enum_unnamed_1.e);
|
||||
\\pub const f = @enumToInt(enum_unnamed_1.f);
|
||||
\\pub const g = @enumToInt(enum_unnamed_1.g);
|
||||
\\pub export var h: enum_unnamed_1 = @intToEnum(enum_unnamed_1, e);
|
||||
\\pub export var h: enum_unnamed_1 = @import("std").meta.cast(enum_unnamed_1, e);
|
||||
\\const enum_unnamed_2 = extern enum(c_int) {
|
||||
\\ i,
|
||||
\\ j,
|
||||
@@ -2308,7 +2324,7 @@ pub fn addCases(cases: *tests.TranslateCContext) void {
|
||||
\\ var a = arg_a;
|
||||
\\ var b = arg_b;
|
||||
\\ var c = arg_c;
|
||||
\\ var d: enum_Foo = @intToEnum(enum_Foo, FooA);
|
||||
\\ var d: enum_Foo = @import("std").meta.cast(enum_Foo, FooA);
|
||||
\\ var e: c_int = @boolToInt((a != 0) and (b != 0));
|
||||
\\ var f: c_int = @boolToInt((b != 0) and (c != null));
|
||||
\\ var g: c_int = @boolToInt((a != 0) and (c != null));
|
||||
|
||||
Reference in New Issue
Block a user