replace a %% b
with a catch b
See #632 better fits the convention of using keywords for control flow
This commit is contained in:
parent
66717db735
commit
632d143bff
@ -45,7 +45,7 @@ const State = enum {
|
||||
fn gen(in: &io.InStream, out: &io.OutStream) {
|
||||
var state = State.Start;
|
||||
while (true) {
|
||||
const byte = in.readByte() %% |err| {
|
||||
const byte = in.readByte() catch |err| {
|
||||
if (err == error.EndOfStream) {
|
||||
return;
|
||||
}
|
||||
|
@ -142,7 +142,7 @@ pub fn addOverflow(comptime T: type, a: T, b: T) -> %T {
|
||||
}
|
||||
|
||||
fn getNumberWithDefault(s: []u8) -> u32 {
|
||||
parseUnsigned(u32, s, 10) %% 42
|
||||
parseUnsigned(u32, s, 10) catch 42
|
||||
}
|
||||
|
||||
fn getNumberOrCrash(s: []u8) -> u32 {
|
||||
@ -150,8 +150,8 @@ fn getNumberOrCrash(s: []u8) -> u32 {
|
||||
}
|
||||
|
||||
fn addTwoTogetherOrReturnErr(a_str: []u8, b_str: []u8) -> %u32 {
|
||||
const a = parseUnsigned(u32, a_str, 10) %% |err| return err;
|
||||
const b = parseUnsigned(u32, b_str, 10) %% |err| return err;
|
||||
const a = parseUnsigned(u32, a_str, 10) catch |err| return err;
|
||||
const b = parseUnsigned(u32, b_str, 10) catch |err| return err;
|
||||
return a + b;
|
||||
}</code></pre>
|
||||
<h3 id="hashmap">HashMap with Custom Allocator</h3>
|
||||
@ -424,7 +424,7 @@ pub fn main() -> %void {
|
||||
} else if (arg[0] == '-') {
|
||||
return usage(exe);
|
||||
} else {
|
||||
var is = io.InStream.open(arg, null) %% |err| {
|
||||
var is = io.InStream.open(arg, null) catch |err| {
|
||||
%%io.stderr.printf("Unable to open file: {}\n", @errorName(err));
|
||||
return err;
|
||||
};
|
||||
@ -449,7 +449,7 @@ fn cat_stream(is: &io.InStream) -> %void {
|
||||
var buf: [1024 * 4]u8 = undefined;
|
||||
|
||||
while (true) {
|
||||
const bytes_read = is.read(buf[0..]) %% |err| {
|
||||
const bytes_read = is.read(buf[0..]) catch |err| {
|
||||
%%io.stderr.printf("Unable to read from stream: {}\n", @errorName(err));
|
||||
return err;
|
||||
};
|
||||
@ -458,7 +458,7 @@ fn cat_stream(is: &io.InStream) -> %void {
|
||||
break;
|
||||
}
|
||||
|
||||
io.stdout.write(buf[0..bytes_read]) %% |err| {
|
||||
io.stdout.write(buf[0..bytes_read]) catch |err| {
|
||||
%%io.stderr.printf("Unable to write to stdout: {}\n", @errorName(err));
|
||||
return err;
|
||||
};
|
||||
|
@ -1211,8 +1211,8 @@ unwrapped == 1234</code></pre>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><pre><code class="zig">a %% b
|
||||
a %% |err| b</code></pre></td>
|
||||
<td><pre><code class="zig">a catch b
|
||||
a catch |err| b</code></pre></td>
|
||||
<td>
|
||||
<ul>
|
||||
<li><a href="#errors">Error Unions</a></li>
|
||||
@ -1226,7 +1226,7 @@ a %% |err| b</code></pre></td>
|
||||
</td>
|
||||
<td>
|
||||
<pre><code class="zig">const value: %u32 = null;
|
||||
const unwrapped = value %% 1234;
|
||||
const unwrapped = value catch 1234;
|
||||
unwrapped == 1234</code></pre>
|
||||
</td>
|
||||
</tr>
|
||||
@ -1238,7 +1238,7 @@ unwrapped == 1234</code></pre>
|
||||
</ul>
|
||||
</td>
|
||||
<td>Equivalent to:
|
||||
<pre><code class="zig">a %% unreachable</code></pre>
|
||||
<pre><code class="zig">a catch unreachable</code></pre>
|
||||
</td>
|
||||
<td>
|
||||
<pre><code class="zig">const value: %u32 = 5678;
|
||||
@ -1482,7 +1482,7 @@ x{}
|
||||
== != < > <= >=
|
||||
and
|
||||
or
|
||||
?? %%
|
||||
?? catch
|
||||
= *= /= %= += -= <<= >>= &= ^= |=</code></pre>
|
||||
<h2 id="arrays">Arrays</h2>
|
||||
<pre><code class="zig">const assert = @import("std").debug.assert;
|
||||
@ -1829,7 +1829,7 @@ Test 1/1 pointer alignment safety...incorrect alignment
|
||||
return root.main();
|
||||
^
|
||||
/home/andy/dev/zig/build/lib/zig/std/special/bootstrap.zig:47:13: 0x0000000000216050 in ??? (test)
|
||||
callMain(argc, argv, envp) %% std.os.posix.exit(1);
|
||||
callMain(argc, argv, envp) catch std.os.posix.exit(1);
|
||||
^
|
||||
/home/andy/dev/zig/build/lib/zig/std/special/bootstrap.zig:34:25: 0x0000000000215fa0 in ??? (test)
|
||||
posixCallMainAndExit()
|
||||
@ -1885,7 +1885,7 @@ lib/zig/std/special/bootstrap.zig:60:21: 0x00000000002149e7 in ??? (test)
|
||||
return root.main();
|
||||
^
|
||||
lib/zig/std/special/bootstrap.zig:47:13: 0x00000000002148a0 in ??? (test)
|
||||
callMain(argc, argv, envp) %% std.os.posix.exit(1);
|
||||
callMain(argc, argv, envp) catch std.os.posix.exit(1);
|
||||
^
|
||||
lib/zig/std/special/bootstrap.zig:34:25: 0x00000000002147f0 in ??? (test)
|
||||
posixCallMainAndExit()
|
||||
@ -2965,7 +2965,7 @@ lib/zig/std/special/bootstrap.zig:60:21: 0x0000000000214947 in ??? (test)
|
||||
return root.main();
|
||||
^
|
||||
lib/zig/std/special/bootstrap.zig:47:13: 0x0000000000214800 in ??? (test)
|
||||
callMain(argc, argv, envp) %% std.os.posix.exit(1);
|
||||
callMain(argc, argv, envp) catch std.os.posix.exit(1);
|
||||
^
|
||||
lib/zig/std/special/bootstrap.zig:34:25: 0x0000000000214750 in ??? (test)
|
||||
posixCallMainAndExit()
|
||||
@ -3019,7 +3019,7 @@ extern fn bar(value: u32);</code></pre>
|
||||
<pre><code class="zig">pub extern "kernel32" stdcallcc fn ExitProcess(exit_code: c_uint) -> noreturn;
|
||||
|
||||
fn foo() {
|
||||
const value = bar() %% ExitProcess(1);
|
||||
const value = bar() catch ExitProcess(1);
|
||||
assert(value == 1234);
|
||||
}
|
||||
|
||||
@ -3209,7 +3209,7 @@ pub fn parseU64(buf: []const u8, radix: u8) -> %u64 {
|
||||
</ul>
|
||||
<p>If you want to provide a default value, you can use the <code>%%</code> binary operator:</p>
|
||||
<pre><code class="zig">fn doAThing(str: []u8) {
|
||||
const number = parseU64(str, 10) %% 13;
|
||||
const number = parseU64(str, 10) catch 13;
|
||||
// ...
|
||||
}</code></pre>
|
||||
<p>
|
||||
@ -3220,7 +3220,7 @@ pub fn parseU64(buf: []const u8, radix: u8) -> %u64 {
|
||||
<p>Let's say you wanted to return the error if you got one, otherwise continue with the
|
||||
function logic:</p>
|
||||
<pre><code class="zig">fn doAThing(str: []u8) -> %void {
|
||||
const number = parseU64(str, 10) %% |err| return err;
|
||||
const number = parseU64(str, 10) catch |err| return err;
|
||||
// ...
|
||||
}</code></pre>
|
||||
<p>
|
||||
@ -3239,7 +3239,7 @@ pub fn parseU64(buf: []const u8, radix: u8) -> %u64 {
|
||||
Maybe you know with complete certainty that an expression will never be an error.
|
||||
In this case you can do this:
|
||||
</p>
|
||||
<pre><code class="zig">const number = parseU64("1234", 10) %% unreachable;</code></pre>
|
||||
<pre><code class="zig">const number = parseU64("1234", 10) catch unreachable;</code></pre>
|
||||
<p>
|
||||
Here we know for sure that "1234" will parse successfully. So we put the
|
||||
<code>unreachable</code> value on the right hand side. <code>unreachable</code> generates
|
||||
@ -3250,7 +3250,7 @@ pub fn parseU64(buf: []const u8, radix: u8) -> %u64 {
|
||||
<p>Again there is a syntactic shortcut for this:</p>
|
||||
<pre><code class="zig">const number = %%parseU64("1234", 10);</code></pre>
|
||||
<p>
|
||||
The <code>%%</code> <em>prefix</em> operator is equivalent to <code class="zig">expression %% unreachable</code>. It unwraps an error union type,
|
||||
The <code>%%</code> <em>prefix</em> operator is equivalent to <code class="zig">expression catch unreachable</code>. It unwraps an error union type,
|
||||
and panics in debug mode if the value was an error.
|
||||
</p>
|
||||
<p>
|
||||
@ -4984,7 +4984,7 @@ Test 1/1 safety check...reached unreachable code
|
||||
return root.main();
|
||||
^
|
||||
/home/andy/dev/zig/build/lib/zig/std/special/bootstrap.zig:37:13: 0x00000000002148d0 in ??? (test)
|
||||
callMain(argc, argv, envp) %% exit(1);
|
||||
callMain(argc, argv, envp) catch exit(1);
|
||||
^
|
||||
/home/andy/dev/zig/build/lib/zig/std/special/bootstrap.zig:30:20: 0x0000000000214820 in ??? (test)
|
||||
callMainAndExit()
|
||||
@ -5909,7 +5909,7 @@ UnwrapExpression = BoolOrExpression (UnwrapNullable | UnwrapError) | BoolOrExpre
|
||||
|
||||
UnwrapNullable = "??" Expression
|
||||
|
||||
UnwrapError = "%%" option("|" Symbol "|") Expression
|
||||
UnwrapError = "catch" option("|" Symbol "|") Expression
|
||||
|
||||
AssignmentExpression = UnwrapExpression AssignmentOperator UnwrapExpression | UnwrapExpression
|
||||
|
||||
|
@ -20,7 +20,7 @@ pub fn main() -> %void {
|
||||
} else if (arg[0] == '-') {
|
||||
return usage(exe);
|
||||
} else {
|
||||
var file = io.File.openRead(arg, null) %% |err| {
|
||||
var file = io.File.openRead(arg, null) catch |err| {
|
||||
warn("Unable to open file: {}\n", @errorName(err));
|
||||
return err;
|
||||
};
|
||||
@ -45,7 +45,7 @@ fn cat_file(stdout: &io.File, file: &io.File) -> %void {
|
||||
var buf: [1024 * 4]u8 = undefined;
|
||||
|
||||
while (true) {
|
||||
const bytes_read = file.read(buf[0..]) %% |err| {
|
||||
const bytes_read = file.read(buf[0..]) catch |err| {
|
||||
warn("Unable to read from stream: {}\n", @errorName(err));
|
||||
return err;
|
||||
};
|
||||
@ -54,7 +54,7 @@ fn cat_file(stdout: &io.File, file: &io.File) -> %void {
|
||||
break;
|
||||
}
|
||||
|
||||
stdout.write(buf[0..bytes_read]) %% |err| {
|
||||
stdout.write(buf[0..bytes_read]) catch |err| {
|
||||
warn("Unable to write to stdout: {}\n", @errorName(err));
|
||||
return err;
|
||||
};
|
||||
@ -62,7 +62,7 @@ fn cat_file(stdout: &io.File, file: &io.File) -> %void {
|
||||
}
|
||||
|
||||
fn unwrapArg(arg: %[]u8) -> %[]u8 {
|
||||
return arg %% |err| {
|
||||
return arg catch |err| {
|
||||
warn("Unable to parse command line: {}\n", err);
|
||||
return err;
|
||||
};
|
||||
|
@ -25,12 +25,12 @@ pub fn main() -> %void {
|
||||
try stdout.print("\nGuess a number between 1 and 100: ");
|
||||
var line_buf : [20]u8 = undefined;
|
||||
|
||||
const line_len = stdin_file.read(line_buf[0..]) %% |err| {
|
||||
const line_len = stdin_file.read(line_buf[0..]) catch |err| {
|
||||
try stdout.print("Unable to read from stdin: {}\n", @errorName(err));
|
||||
return err;
|
||||
};
|
||||
|
||||
const guess = fmt.parseUnsigned(u8, line_buf[0..line_len - 1], 10) %% {
|
||||
const guess = fmt.parseUnsigned(u8, line_buf[0..line_len - 1], 10) catch {
|
||||
try stdout.print("Invalid number.\n");
|
||||
continue;
|
||||
};
|
||||
|
@ -21,7 +21,7 @@ error ZigInstallationNotFound;
|
||||
const default_zig_cache_name = "zig-cache";
|
||||
|
||||
pub fn main() -> %void {
|
||||
main2() %% |err| {
|
||||
main2() catch |err| {
|
||||
if (err != error.InvalidCommandLineArguments) {
|
||||
warn("{}\n", @errorName(err));
|
||||
}
|
||||
@ -571,12 +571,12 @@ fn printZen() -> %void {
|
||||
/// Caller must free result
|
||||
fn resolveZigLibDir(allocator: &mem.Allocator, zig_install_prefix_arg: ?[]const u8) -> %[]u8 {
|
||||
if (zig_install_prefix_arg) |zig_install_prefix| {
|
||||
return testZigInstallPrefix(allocator, zig_install_prefix) %% |err| {
|
||||
return testZigInstallPrefix(allocator, zig_install_prefix) catch |err| {
|
||||
warn("No Zig installation found at prefix {}: {}\n", zig_install_prefix_arg, @errorName(err));
|
||||
return error.ZigInstallationNotFound;
|
||||
};
|
||||
} else {
|
||||
return findZigLibDir(allocator) %% |err| {
|
||||
return findZigLibDir(allocator) catch |err| {
|
||||
warn("Unable to find zig lib directory: {}.\nReinstall Zig or use --zig-install-prefix.\n",
|
||||
@errorName(err));
|
||||
return error.ZigLibDirNotFound;
|
||||
@ -611,7 +611,7 @@ fn findZigLibDir(allocator: &mem.Allocator) -> %[]u8 {
|
||||
break;
|
||||
}
|
||||
|
||||
return testZigInstallPrefix(allocator, test_dir) %% |err| {
|
||||
return testZigInstallPrefix(allocator, test_dir) catch |err| {
|
||||
cur_path = test_dir;
|
||||
continue;
|
||||
};
|
||||
|
@ -207,13 +207,13 @@ pub const Module = struct {
|
||||
}
|
||||
|
||||
const root_src_path = self.root_src_path ?? @panic("TODO handle null root src path");
|
||||
const root_src_real_path = os.path.real(self.allocator, root_src_path) %% |err| {
|
||||
const root_src_real_path = os.path.real(self.allocator, root_src_path) catch |err| {
|
||||
try printError("unable to get real path '{}': {}", root_src_path, err);
|
||||
return err;
|
||||
};
|
||||
%defer self.allocator.free(root_src_real_path);
|
||||
|
||||
const source_code = io.readFileAllocExtra(root_src_real_path, self.allocator, 3) %% |err| {
|
||||
const source_code = io.readFileAllocExtra(root_src_real_path, self.allocator, 3) catch |err| {
|
||||
try printError("unable to open '{}': {}", root_src_real_path, err);
|
||||
return err;
|
||||
};
|
||||
|
@ -96,12 +96,12 @@ pub const Parser = struct {
|
||||
var stack = self.initUtilityArrayList(&ast.Node);
|
||||
defer self.deinitUtilityArrayList(stack);
|
||||
|
||||
stack.append(&root_node.base) %% unreachable;
|
||||
stack.append(&root_node.base) catch unreachable;
|
||||
while (stack.popOrNull()) |node| {
|
||||
var i: usize = 0;
|
||||
while (node.iterate(i)) |child| : (i += 1) {
|
||||
if (child.iterate(0) != null) {
|
||||
stack.append(child) %% unreachable;
|
||||
stack.append(child) catch unreachable;
|
||||
} else {
|
||||
child.destroy(self.allocator);
|
||||
}
|
||||
@ -111,7 +111,7 @@ pub const Parser = struct {
|
||||
}
|
||||
|
||||
pub fn parse(self: &Parser) -> %&ast.NodeRoot {
|
||||
const result = self.parseInner() %% |err| x: {
|
||||
const result = self.parseInner() catch |err| x: {
|
||||
if (self.cleanup_root_node) |root_node| {
|
||||
self.freeAst(root_node);
|
||||
}
|
||||
@ -156,14 +156,14 @@ pub const Parser = struct {
|
||||
const token = self.getNextToken();
|
||||
switch (token.id) {
|
||||
Token.Id.Keyword_pub, Token.Id.Keyword_export => {
|
||||
stack.append(State { .TopLevelExtern = token }) %% unreachable;
|
||||
stack.append(State { .TopLevelExtern = token }) catch unreachable;
|
||||
continue;
|
||||
},
|
||||
Token.Id.Eof => return root_node,
|
||||
else => {
|
||||
self.putBackToken(token);
|
||||
// TODO shouldn't need this cast
|
||||
stack.append(State { .TopLevelExtern = null }) %% unreachable;
|
||||
stack.append(State { .TopLevelExtern = null }) catch unreachable;
|
||||
continue;
|
||||
},
|
||||
}
|
||||
@ -176,7 +176,7 @@ pub const Parser = struct {
|
||||
.visib_token = visib_token,
|
||||
.extern_token = token,
|
||||
},
|
||||
}) %% unreachable;
|
||||
}) catch unreachable;
|
||||
continue;
|
||||
}
|
||||
self.putBackToken(token);
|
||||
@ -185,14 +185,14 @@ pub const Parser = struct {
|
||||
.visib_token = visib_token,
|
||||
.extern_token = null,
|
||||
},
|
||||
}) %% unreachable;
|
||||
}) catch unreachable;
|
||||
continue;
|
||||
},
|
||||
State.TopLevelDecl => |ctx| {
|
||||
const token = self.getNextToken();
|
||||
switch (token.id) {
|
||||
Token.Id.Keyword_var, Token.Id.Keyword_const => {
|
||||
stack.append(State.TopLevel) %% unreachable;
|
||||
stack.append(State.TopLevel) catch unreachable;
|
||||
// TODO shouldn't need these casts
|
||||
const var_decl_node = try self.createAttachVarDecl(&root_node.decls, ctx.visib_token,
|
||||
token, (?Token)(null), ctx.extern_token);
|
||||
@ -200,7 +200,7 @@ pub const Parser = struct {
|
||||
continue;
|
||||
},
|
||||
Token.Id.Keyword_fn => {
|
||||
stack.append(State.TopLevel) %% unreachable;
|
||||
stack.append(State.TopLevel) catch unreachable;
|
||||
// TODO shouldn't need these casts
|
||||
const fn_proto = try self.createAttachFnProto(&root_node.decls, token,
|
||||
ctx.extern_token, (?Token)(null), (?Token)(null), (?Token)(null));
|
||||
@ -212,7 +212,7 @@ pub const Parser = struct {
|
||||
@panic("TODO extern with string literal");
|
||||
},
|
||||
Token.Id.Keyword_coldcc, Token.Id.Keyword_nakedcc, Token.Id.Keyword_stdcallcc => {
|
||||
stack.append(State.TopLevel) %% unreachable;
|
||||
stack.append(State.TopLevel) catch unreachable;
|
||||
const fn_token = try self.eatToken(Token.Id.Keyword_fn);
|
||||
// TODO shouldn't need this cast
|
||||
const fn_proto = try self.createAttachFnProto(&root_node.decls, fn_token,
|
||||
@ -226,7 +226,7 @@ pub const Parser = struct {
|
||||
},
|
||||
State.VarDecl => |var_decl| {
|
||||
var_decl.name_token = try self.eatToken(Token.Id.Identifier);
|
||||
stack.append(State { .VarDeclAlign = var_decl }) %% unreachable;
|
||||
stack.append(State { .VarDeclAlign = var_decl }) catch unreachable;
|
||||
|
||||
const next_token = self.getNextToken();
|
||||
if (next_token.id == Token.Id.Colon) {
|
||||
@ -238,7 +238,7 @@ pub const Parser = struct {
|
||||
continue;
|
||||
},
|
||||
State.VarDeclAlign => |var_decl| {
|
||||
stack.append(State { .VarDeclEq = var_decl }) %% unreachable;
|
||||
stack.append(State { .VarDeclEq = var_decl }) catch unreachable;
|
||||
|
||||
const next_token = self.getNextToken();
|
||||
if (next_token.id == Token.Id.Keyword_align) {
|
||||
@ -255,7 +255,7 @@ pub const Parser = struct {
|
||||
const token = self.getNextToken();
|
||||
if (token.id == Token.Id.Equal) {
|
||||
var_decl.eq_token = token;
|
||||
stack.append(State { .ExpectToken = Token.Id.Semicolon }) %% unreachable;
|
||||
stack.append(State { .ExpectToken = Token.Id.Semicolon }) catch unreachable;
|
||||
try stack.append(State {
|
||||
.Expression = DestPtr {.NullableField = &var_decl.init_node},
|
||||
});
|
||||
@ -273,7 +273,7 @@ pub const Parser = struct {
|
||||
|
||||
State.Expression => |dest_ptr| {
|
||||
// save the dest_ptr for later
|
||||
stack.append(state) %% unreachable;
|
||||
stack.append(state) catch unreachable;
|
||||
try stack.append(State.ExpectOperand);
|
||||
continue;
|
||||
},
|
||||
@ -383,7 +383,7 @@ pub const Parser = struct {
|
||||
var token = self.getNextToken();
|
||||
switch (token.id) {
|
||||
Token.Id.Keyword_align => {
|
||||
stack.append(state) %% unreachable;
|
||||
stack.append(state) catch unreachable;
|
||||
if (addr_of_info.align_expr != null) return self.parseError(token, "multiple align qualifiers");
|
||||
_ = try self.eatToken(Token.Id.LParen);
|
||||
try stack.append(State { .ExpectToken = Token.Id.RParen });
|
||||
@ -391,13 +391,13 @@ pub const Parser = struct {
|
||||
continue;
|
||||
},
|
||||
Token.Id.Keyword_const => {
|
||||
stack.append(state) %% unreachable;
|
||||
stack.append(state) catch unreachable;
|
||||
if (addr_of_info.const_token != null) return self.parseError(token, "duplicate qualifier: const");
|
||||
addr_of_info.const_token = token;
|
||||
continue;
|
||||
},
|
||||
Token.Id.Keyword_volatile => {
|
||||
stack.append(state) %% unreachable;
|
||||
stack.append(state) catch unreachable;
|
||||
if (addr_of_info.volatile_token != null) return self.parseError(token, "duplicate qualifier: volatile");
|
||||
addr_of_info.volatile_token = token;
|
||||
continue;
|
||||
@ -416,12 +416,12 @@ pub const Parser = struct {
|
||||
}
|
||||
self.putBackToken(token);
|
||||
|
||||
stack.append(State { .Expression = dest_ptr }) %% unreachable;
|
||||
stack.append(State { .Expression = dest_ptr }) catch unreachable;
|
||||
continue;
|
||||
},
|
||||
|
||||
State.FnProto => |fn_proto| {
|
||||
stack.append(State { .FnProtoAlign = fn_proto }) %% unreachable;
|
||||
stack.append(State { .FnProtoAlign = fn_proto }) catch unreachable;
|
||||
try stack.append(State { .ParamDecl = fn_proto });
|
||||
try stack.append(State { .ExpectToken = Token.Id.LParen });
|
||||
|
||||
@ -442,7 +442,7 @@ pub const Parser = struct {
|
||||
if (token.id == Token.Id.Arrow) {
|
||||
stack.append(State {
|
||||
.TypeExpr = DestPtr {.NullableField = &fn_proto.return_type},
|
||||
}) %% unreachable;
|
||||
}) catch unreachable;
|
||||
continue;
|
||||
} else {
|
||||
self.putBackToken(token);
|
||||
@ -474,13 +474,13 @@ pub const Parser = struct {
|
||||
}
|
||||
if (token.id == Token.Id.Ellipsis3) {
|
||||
param_decl.var_args_token = token;
|
||||
stack.append(State { .ExpectToken = Token.Id.RParen }) %% unreachable;
|
||||
stack.append(State { .ExpectToken = Token.Id.RParen }) catch unreachable;
|
||||
continue;
|
||||
} else {
|
||||
self.putBackToken(token);
|
||||
}
|
||||
|
||||
stack.append(State { .ParamDecl = fn_proto }) %% unreachable;
|
||||
stack.append(State { .ParamDecl = fn_proto }) catch unreachable;
|
||||
try stack.append(State.ParamDeclComma);
|
||||
try stack.append(State {
|
||||
.TypeExpr = DestPtr {.Field = ¶m_decl.type_node}
|
||||
@ -506,7 +506,7 @@ pub const Parser = struct {
|
||||
Token.Id.LBrace => {
|
||||
const block = try self.createBlock(token);
|
||||
fn_proto.body_node = &block.base;
|
||||
stack.append(State { .Block = block }) %% unreachable;
|
||||
stack.append(State { .Block = block }) catch unreachable;
|
||||
continue;
|
||||
},
|
||||
Token.Id.Semicolon => continue,
|
||||
@ -523,7 +523,7 @@ pub const Parser = struct {
|
||||
},
|
||||
else => {
|
||||
self.putBackToken(token);
|
||||
stack.append(State { .Block = block }) %% unreachable;
|
||||
stack.append(State { .Block = block }) catch unreachable;
|
||||
try stack.append(State { .Statement = block });
|
||||
continue;
|
||||
},
|
||||
@ -560,7 +560,7 @@ pub const Parser = struct {
|
||||
self.putBackToken(mut_token);
|
||||
}
|
||||
|
||||
stack.append(State { .ExpectToken = Token.Id.Semicolon }) %% unreachable;
|
||||
stack.append(State { .ExpectToken = Token.Id.Semicolon }) catch unreachable;
|
||||
try stack.append(State { .Expression = DestPtr{.List = &block.statements} });
|
||||
continue;
|
||||
},
|
||||
@ -1112,7 +1112,7 @@ fn testCanonical(source: []const u8) {
|
||||
// Try it once with unlimited memory, make sure it works
|
||||
var fixed_allocator = mem.FixedBufferAllocator.init(fixed_buffer_mem[0..]);
|
||||
var failing_allocator = std.debug.FailingAllocator.init(&fixed_allocator.allocator, @maxValue(usize));
|
||||
const result_source = testParse(source, &failing_allocator.allocator) %% @panic("test failed");
|
||||
const result_source = testParse(source, &failing_allocator.allocator) catch @panic("test failed");
|
||||
if (!mem.eql(u8, result_source, source)) {
|
||||
warn("\n====== expected this output: =========\n");
|
||||
warn("{}", source);
|
||||
|
@ -557,22 +557,22 @@ pub const Tokenizer = struct {
|
||||
return 0;
|
||||
} else {
|
||||
// check utf8-encoded character.
|
||||
const length = std.unicode.utf8ByteSequenceLength(c0) %% return 1;
|
||||
const length = std.unicode.utf8ByteSequenceLength(c0) catch return 1;
|
||||
// the last 3 bytes in the buffer are guaranteed to be '\n',
|
||||
// which means we don't need to do any bounds checking here.
|
||||
const bytes = self.buffer[self.index..self.index + length];
|
||||
switch (length) {
|
||||
2 => {
|
||||
const value = std.unicode.utf8Decode2(bytes) %% return length;
|
||||
const value = std.unicode.utf8Decode2(bytes) catch return length;
|
||||
if (value == 0x85) return length; // U+0085 (NEL)
|
||||
},
|
||||
3 => {
|
||||
const value = std.unicode.utf8Decode3(bytes) %% return length;
|
||||
const value = std.unicode.utf8Decode3(bytes) catch return length;
|
||||
if (value == 0x2028) return length; // U+2028 (LS)
|
||||
if (value == 0x2029) return length; // U+2029 (PS)
|
||||
},
|
||||
4 => {
|
||||
_ = std.unicode.utf8Decode4(bytes) %% return length;
|
||||
_ = std.unicode.utf8Decode4(bytes) catch return length;
|
||||
},
|
||||
else => unreachable,
|
||||
}
|
||||
|
@ -389,7 +389,7 @@ enum NodeType {
|
||||
NodeTypeArrayType,
|
||||
NodeTypeErrorType,
|
||||
NodeTypeVarLiteral,
|
||||
NodeTypeTryExpr,
|
||||
NodeTypeIfErrorExpr,
|
||||
NodeTypeTestExpr,
|
||||
};
|
||||
|
||||
@ -546,7 +546,7 @@ struct AstNodeBinOpExpr {
|
||||
AstNode *op2;
|
||||
};
|
||||
|
||||
struct AstNodeUnwrapErrorExpr {
|
||||
struct AstNodeCatchExpr {
|
||||
AstNode *op1;
|
||||
AstNode *symbol; // can be null
|
||||
AstNode *op2;
|
||||
@ -860,7 +860,7 @@ struct AstNode {
|
||||
AstNodeErrorValueDecl error_value_decl;
|
||||
AstNodeTestDecl test_decl;
|
||||
AstNodeBinOpExpr bin_op_expr;
|
||||
AstNodeUnwrapErrorExpr unwrap_err_expr;
|
||||
AstNodeCatchExpr unwrap_err_expr;
|
||||
AstNodePrefixOpExpr prefix_op_expr;
|
||||
AstNodeAddrOfExpr addr_of_expr;
|
||||
AstNodeFnCallExpr fn_call_expr;
|
||||
@ -868,7 +868,7 @@ struct AstNode {
|
||||
AstNodeSliceExpr slice_expr;
|
||||
AstNodeUse use;
|
||||
AstNodeIfBoolExpr if_bool_expr;
|
||||
AstNodeTryExpr try_expr;
|
||||
AstNodeTryExpr if_err_expr;
|
||||
AstNodeTestExpr test_expr;
|
||||
AstNodeWhileExpr while_expr;
|
||||
AstNodeForExpr for_expr;
|
||||
|
@ -2933,7 +2933,7 @@ void scan_decls(CodeGen *g, ScopeDecls *decls_scope, AstNode *node) {
|
||||
case NodeTypeArrayType:
|
||||
case NodeTypeErrorType:
|
||||
case NodeTypeVarLiteral:
|
||||
case NodeTypeTryExpr:
|
||||
case NodeTypeIfErrorExpr:
|
||||
case NodeTypeTestExpr:
|
||||
zig_unreachable();
|
||||
}
|
||||
|
@ -68,7 +68,7 @@ static const char *prefix_op_str(PrefixOp prefix_op) {
|
||||
case PrefixOpDereference: return "*";
|
||||
case PrefixOpMaybe: return "?";
|
||||
case PrefixOpError: return "%";
|
||||
case PrefixOpUnwrapError: return "%%";
|
||||
case PrefixOpUnwrapError: return "catch";
|
||||
case PrefixOpUnwrapMaybe: return "??";
|
||||
}
|
||||
zig_unreachable();
|
||||
@ -241,8 +241,8 @@ static const char *node_type_str(NodeType node_type) {
|
||||
return "ErrorType";
|
||||
case NodeTypeVarLiteral:
|
||||
return "VarLiteral";
|
||||
case NodeTypeTryExpr:
|
||||
return "TryExpr";
|
||||
case NodeTypeIfErrorExpr:
|
||||
return "IfErrorExpr";
|
||||
case NodeTypeTestExpr:
|
||||
return "TestExpr";
|
||||
}
|
||||
@ -872,23 +872,23 @@ static void render_node_extra(AstRender *ar, AstNode *node, bool grouped) {
|
||||
fprintf(ar->f, "null");
|
||||
break;
|
||||
}
|
||||
case NodeTypeTryExpr:
|
||||
case NodeTypeIfErrorExpr:
|
||||
{
|
||||
fprintf(ar->f, "if (");
|
||||
render_node_grouped(ar, node->data.try_expr.target_node);
|
||||
render_node_grouped(ar, node->data.if_err_expr.target_node);
|
||||
fprintf(ar->f, ") ");
|
||||
if (node->data.try_expr.var_symbol) {
|
||||
const char *ptr_str = node->data.try_expr.var_is_ptr ? "*" : "";
|
||||
const char *var_name = buf_ptr(node->data.try_expr.var_symbol);
|
||||
if (node->data.if_err_expr.var_symbol) {
|
||||
const char *ptr_str = node->data.if_err_expr.var_is_ptr ? "*" : "";
|
||||
const char *var_name = buf_ptr(node->data.if_err_expr.var_symbol);
|
||||
fprintf(ar->f, "|%s%s| ", ptr_str, var_name);
|
||||
}
|
||||
render_node_grouped(ar, node->data.try_expr.then_node);
|
||||
if (node->data.try_expr.else_node) {
|
||||
render_node_grouped(ar, node->data.if_err_expr.then_node);
|
||||
if (node->data.if_err_expr.else_node) {
|
||||
fprintf(ar->f, " else ");
|
||||
if (node->data.try_expr.err_symbol) {
|
||||
fprintf(ar->f, "|%s| ", buf_ptr(node->data.try_expr.err_symbol));
|
||||
if (node->data.if_err_expr.err_symbol) {
|
||||
fprintf(ar->f, "|%s| ", buf_ptr(node->data.if_err_expr.err_symbol));
|
||||
}
|
||||
render_node_grouped(ar, node->data.try_expr.else_node);
|
||||
render_node_grouped(ar, node->data.if_err_expr.else_node);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
20
src/ir.cpp
20
src/ir.cpp
@ -4665,16 +4665,16 @@ static IrInstruction *ir_gen_test_expr(IrBuilder *irb, Scope *scope, AstNode *no
|
||||
return ir_build_phi(irb, scope, node, 2, incoming_blocks, incoming_values);
|
||||
}
|
||||
|
||||
static IrInstruction *ir_gen_try_expr(IrBuilder *irb, Scope *scope, AstNode *node) {
|
||||
assert(node->type == NodeTypeTryExpr);
|
||||
static IrInstruction *ir_gen_if_err_expr(IrBuilder *irb, Scope *scope, AstNode *node) {
|
||||
assert(node->type == NodeTypeIfErrorExpr);
|
||||
|
||||
AstNode *target_node = node->data.try_expr.target_node;
|
||||
AstNode *then_node = node->data.try_expr.then_node;
|
||||
AstNode *else_node = node->data.try_expr.else_node;
|
||||
bool var_is_ptr = node->data.try_expr.var_is_ptr;
|
||||
AstNode *target_node = node->data.if_err_expr.target_node;
|
||||
AstNode *then_node = node->data.if_err_expr.then_node;
|
||||
AstNode *else_node = node->data.if_err_expr.else_node;
|
||||
bool var_is_ptr = node->data.if_err_expr.var_is_ptr;
|
||||
bool var_is_const = true;
|
||||
Buf *var_symbol = node->data.try_expr.var_symbol;
|
||||
Buf *err_symbol = node->data.try_expr.err_symbol;
|
||||
Buf *var_symbol = node->data.if_err_expr.var_symbol;
|
||||
Buf *err_symbol = node->data.if_err_expr.err_symbol;
|
||||
|
||||
IrInstruction *err_val_ptr = ir_gen_node_extra(irb, target_node, scope, LVAL_PTR);
|
||||
if (err_val_ptr == irb->codegen->invalid_instruction)
|
||||
@ -5411,8 +5411,8 @@ static IrInstruction *ir_gen_node_raw(IrBuilder *irb, AstNode *node, Scope *scop
|
||||
return ir_lval_wrap(irb, scope, ir_gen_null_literal(irb, scope, node), lval);
|
||||
case NodeTypeVarLiteral:
|
||||
return ir_lval_wrap(irb, scope, ir_gen_var_literal(irb, scope, node), lval);
|
||||
case NodeTypeTryExpr:
|
||||
return ir_lval_wrap(irb, scope, ir_gen_try_expr(irb, scope, node), lval);
|
||||
case NodeTypeIfErrorExpr:
|
||||
return ir_lval_wrap(irb, scope, ir_gen_if_err_expr(irb, scope, node), lval);
|
||||
case NodeTypeTestExpr:
|
||||
return ir_lval_wrap(irb, scope, ir_gen_test_expr(irb, scope, node), lval);
|
||||
case NodeTypeSwitchExpr:
|
||||
|
@ -1407,15 +1407,15 @@ static AstNode *ast_parse_if_try_test_expr(ParseContext *pc, size_t *token_index
|
||||
}
|
||||
|
||||
if (err_name_tok != nullptr) {
|
||||
AstNode *node = ast_create_node(pc, NodeTypeTryExpr, if_token);
|
||||
node->data.try_expr.target_node = condition;
|
||||
node->data.try_expr.var_is_ptr = var_is_ptr;
|
||||
AstNode *node = ast_create_node(pc, NodeTypeIfErrorExpr, if_token);
|
||||
node->data.if_err_expr.target_node = condition;
|
||||
node->data.if_err_expr.var_is_ptr = var_is_ptr;
|
||||
if (var_name_tok != nullptr) {
|
||||
node->data.try_expr.var_symbol = token_buf(var_name_tok);
|
||||
node->data.if_err_expr.var_symbol = token_buf(var_name_tok);
|
||||
}
|
||||
node->data.try_expr.then_node = body_node;
|
||||
node->data.try_expr.err_symbol = token_buf(err_name_tok);
|
||||
node->data.try_expr.else_node = else_node;
|
||||
node->data.if_err_expr.then_node = body_node;
|
||||
node->data.if_err_expr.err_symbol = token_buf(err_name_tok);
|
||||
node->data.if_err_expr.else_node = else_node;
|
||||
return node;
|
||||
} else if (var_name_tok != nullptr) {
|
||||
AstNode *node = ast_create_node(pc, NodeTypeTestExpr, if_token);
|
||||
@ -2041,7 +2041,7 @@ static BinOpType ast_parse_ass_op(ParseContext *pc, size_t *token_index, bool ma
|
||||
/*
|
||||
UnwrapExpression : BoolOrExpression (UnwrapMaybe | UnwrapError) | BoolOrExpression
|
||||
UnwrapMaybe : "??" BoolOrExpression
|
||||
UnwrapError : "%%" option("|" "Symbol" "|") BoolOrExpression
|
||||
UnwrapError = "catch" option("|" Symbol "|") Expression
|
||||
*/
|
||||
static AstNode *ast_parse_unwrap_expr(ParseContext *pc, size_t *token_index, bool mandatory) {
|
||||
AstNode *lhs = ast_parse_bool_or_expr(pc, token_index, mandatory);
|
||||
@ -2061,7 +2061,7 @@ static AstNode *ast_parse_unwrap_expr(ParseContext *pc, size_t *token_index, boo
|
||||
node->data.bin_op_expr.op2 = rhs;
|
||||
|
||||
return node;
|
||||
} else if (token->id == TokenIdPercentPercent) {
|
||||
} else if (token->id == TokenIdKeywordCatch) {
|
||||
*token_index += 1;
|
||||
|
||||
AstNode *node = ast_create_node(pc, NodeTypeUnwrapErrorExpr, token);
|
||||
@ -2157,10 +2157,10 @@ static bool statement_terminates_without_semicolon(AstNode *node) {
|
||||
if (node->data.if_bool_expr.else_node)
|
||||
return statement_terminates_without_semicolon(node->data.if_bool_expr.else_node);
|
||||
return node->data.if_bool_expr.then_block->type == NodeTypeBlock;
|
||||
case NodeTypeTryExpr:
|
||||
if (node->data.try_expr.else_node)
|
||||
return statement_terminates_without_semicolon(node->data.try_expr.else_node);
|
||||
return node->data.try_expr.then_node->type == NodeTypeBlock;
|
||||
case NodeTypeIfErrorExpr:
|
||||
if (node->data.if_err_expr.else_node)
|
||||
return statement_terminates_without_semicolon(node->data.if_err_expr.else_node);
|
||||
return node->data.if_err_expr.then_node->type == NodeTypeBlock;
|
||||
case NodeTypeTestExpr:
|
||||
if (node->data.test_expr.else_node)
|
||||
return statement_terminates_without_semicolon(node->data.test_expr.else_node);
|
||||
@ -2833,10 +2833,10 @@ void ast_visit_node_children(AstNode *node, void (*visit)(AstNode **, void *cont
|
||||
visit_field(&node->data.if_bool_expr.then_block, visit, context);
|
||||
visit_field(&node->data.if_bool_expr.else_node, visit, context);
|
||||
break;
|
||||
case NodeTypeTryExpr:
|
||||
visit_field(&node->data.try_expr.target_node, visit, context);
|
||||
visit_field(&node->data.try_expr.then_node, visit, context);
|
||||
visit_field(&node->data.try_expr.else_node, visit, context);
|
||||
case NodeTypeIfErrorExpr:
|
||||
visit_field(&node->data.if_err_expr.target_node, visit, context);
|
||||
visit_field(&node->data.if_err_expr.then_node, visit, context);
|
||||
visit_field(&node->data.if_err_expr.else_node, visit, context);
|
||||
break;
|
||||
case NodeTypeTestExpr:
|
||||
visit_field(&node->data.test_expr.target_node, visit, context);
|
||||
|
@ -111,6 +111,7 @@ static const struct ZigKeyword zig_keywords[] = {
|
||||
{"and", TokenIdKeywordAnd},
|
||||
{"asm", TokenIdKeywordAsm},
|
||||
{"break", TokenIdKeywordBreak},
|
||||
{"catch", TokenIdKeywordCatch},
|
||||
{"coldcc", TokenIdKeywordColdCC},
|
||||
{"comptime", TokenIdKeywordCompTime},
|
||||
{"const", TokenIdKeywordConst},
|
||||
@ -1512,6 +1513,7 @@ const char * token_name(TokenId id) {
|
||||
case TokenIdKeywordAnd: return "and";
|
||||
case TokenIdKeywordAsm: return "asm";
|
||||
case TokenIdKeywordBreak: return "break";
|
||||
case TokenIdKeywordCatch: return "catch";
|
||||
case TokenIdKeywordColdCC: return "coldcc";
|
||||
case TokenIdKeywordCompTime: return "comptime";
|
||||
case TokenIdKeywordConst: return "const";
|
||||
|
@ -47,10 +47,10 @@ enum TokenId {
|
||||
TokenIdFloatLiteral,
|
||||
TokenIdIntLiteral,
|
||||
TokenIdKeywordAlign,
|
||||
TokenIdKeywordSection,
|
||||
TokenIdKeywordAnd,
|
||||
TokenIdKeywordAsm,
|
||||
TokenIdKeywordBreak,
|
||||
TokenIdKeywordCatch,
|
||||
TokenIdKeywordColdCC,
|
||||
TokenIdKeywordCompTime,
|
||||
TokenIdKeywordConst,
|
||||
@ -74,6 +74,7 @@ enum TokenId {
|
||||
TokenIdKeywordPacked,
|
||||
TokenIdKeywordPub,
|
||||
TokenIdKeywordReturn,
|
||||
TokenIdKeywordSection,
|
||||
TokenIdKeywordStdcallCC,
|
||||
TokenIdKeywordStruct,
|
||||
TokenIdKeywordSwitch,
|
||||
|
@ -300,7 +300,7 @@ pub const Builder = struct {
|
||||
s.loop_flag = true;
|
||||
|
||||
for (s.dependencies.toSlice()) |dep| {
|
||||
self.makeOneStep(dep) %% |err| {
|
||||
self.makeOneStep(dep) catch |err| {
|
||||
if (err == error.DependencyLoopDetected) {
|
||||
warn(" {}\n", s.name);
|
||||
}
|
||||
@ -573,7 +573,7 @@ pub const Builder = struct {
|
||||
child.cwd = cwd;
|
||||
child.env_map = env_map;
|
||||
|
||||
const term = child.spawnAndWait() %% |err| {
|
||||
const term = child.spawnAndWait() catch |err| {
|
||||
warn("Unable to spawn {}: {}\n", argv[0], @errorName(err));
|
||||
return err;
|
||||
};
|
||||
@ -596,7 +596,7 @@ pub const Builder = struct {
|
||||
}
|
||||
|
||||
pub fn makePath(self: &Builder, path: []const u8) -> %void {
|
||||
os.makePath(self.allocator, self.pathFromRoot(path)) %% |err| {
|
||||
os.makePath(self.allocator, self.pathFromRoot(path)) catch |err| {
|
||||
warn("Unable to create path {}: {}\n", path, @errorName(err));
|
||||
return err;
|
||||
};
|
||||
@ -641,11 +641,11 @@ pub const Builder = struct {
|
||||
|
||||
const dirname = os.path.dirname(dest_path);
|
||||
const abs_source_path = self.pathFromRoot(source_path);
|
||||
os.makePath(self.allocator, dirname) %% |err| {
|
||||
os.makePath(self.allocator, dirname) catch |err| {
|
||||
warn("Unable to create path {}: {}\n", dirname, @errorName(err));
|
||||
return err;
|
||||
};
|
||||
os.copyFileMode(self.allocator, abs_source_path, dest_path, mode) %% |err| {
|
||||
os.copyFileMode(self.allocator, abs_source_path, dest_path, mode) catch |err| {
|
||||
warn("Unable to copy {} to {}: {}\n", abs_source_path, dest_path, @errorName(err));
|
||||
return err;
|
||||
};
|
||||
@ -663,7 +663,7 @@ pub const Builder = struct {
|
||||
if (builtin.environ == builtin.Environ.msvc) {
|
||||
return "cl.exe";
|
||||
} else {
|
||||
return os.getEnvVarOwned(self.allocator, "CC") %% |err|
|
||||
return os.getEnvVarOwned(self.allocator, "CC") catch |err|
|
||||
if (err == error.EnvironmentVariableNotFound)
|
||||
([]const u8)("cc")
|
||||
else
|
||||
@ -723,7 +723,7 @@ pub const Builder = struct {
|
||||
|
||||
pub fn exec(self: &Builder, argv: []const []const u8) -> []u8 {
|
||||
const max_output_size = 100 * 1024;
|
||||
const result = os.ChildProcess.exec(self.allocator, argv, null, null, max_output_size) %% |err| {
|
||||
const result = os.ChildProcess.exec(self.allocator, argv, null, null, max_output_size) catch |err| {
|
||||
std.debug.panic("Unable to spawn {}: {}", argv[0], @errorName(err));
|
||||
};
|
||||
switch (result.term) {
|
||||
@ -1895,11 +1895,11 @@ pub const WriteFileStep = struct {
|
||||
const self = @fieldParentPtr(WriteFileStep, "step", step);
|
||||
const full_path = self.builder.pathFromRoot(self.file_path);
|
||||
const full_path_dir = os.path.dirname(full_path);
|
||||
os.makePath(self.builder.allocator, full_path_dir) %% |err| {
|
||||
os.makePath(self.builder.allocator, full_path_dir) catch |err| {
|
||||
warn("unable to make path {}: {}\n", full_path_dir, @errorName(err));
|
||||
return err;
|
||||
};
|
||||
io.writeFile(full_path, self.data, self.builder.allocator) %% |err| {
|
||||
io.writeFile(full_path, self.data, self.builder.allocator) catch |err| {
|
||||
warn("unable to write {}: {}\n", full_path, @errorName(err));
|
||||
return err;
|
||||
};
|
||||
@ -1942,7 +1942,7 @@ pub const RemoveDirStep = struct {
|
||||
const self = @fieldParentPtr(RemoveDirStep, "step", step);
|
||||
|
||||
const full_path = self.builder.pathFromRoot(self.dir_path);
|
||||
os.deleteTree(self.builder.allocator, full_path) %% |err| {
|
||||
os.deleteTree(self.builder.allocator, full_path) catch |err| {
|
||||
warn("Unable to remove {}: {}\n", full_path, @errorName(err));
|
||||
return err;
|
||||
};
|
||||
@ -1991,13 +1991,13 @@ fn doAtomicSymLinks(allocator: &Allocator, output_path: []const u8, filename_maj
|
||||
const out_basename = os.path.basename(output_path);
|
||||
// sym link for libfoo.so.1 to libfoo.so.1.2.3
|
||||
const major_only_path = %%os.path.join(allocator, out_dir, filename_major_only);
|
||||
os.atomicSymLink(allocator, out_basename, major_only_path) %% |err| {
|
||||
os.atomicSymLink(allocator, out_basename, major_only_path) catch |err| {
|
||||
warn("Unable to symlink {} -> {}\n", major_only_path, out_basename);
|
||||
return err;
|
||||
};
|
||||
// sym link for libfoo.so to libfoo.so.1
|
||||
const name_only_path = %%os.path.join(allocator, out_dir, filename_name_only);
|
||||
os.atomicSymLink(allocator, filename_major_only, name_only_path) %% |err| {
|
||||
os.atomicSymLink(allocator, filename_major_only, name_only_path) catch |err| {
|
||||
warn("Unable to symlink {} -> {}\n", name_only_path, filename_major_only);
|
||||
return err;
|
||||
};
|
||||
|
@ -22,8 +22,8 @@ var stderr_file: io.File = undefined;
|
||||
var stderr_file_out_stream: io.FileOutStream = undefined;
|
||||
var stderr_stream: ?&io.OutStream = null;
|
||||
pub fn warn(comptime fmt: []const u8, args: ...) {
|
||||
const stderr = getStderrStream() %% return;
|
||||
stderr.print(fmt, args) %% return;
|
||||
const stderr = getStderrStream() catch return;
|
||||
stderr.print(fmt, args) catch return;
|
||||
}
|
||||
fn getStderrStream() -> %&io.OutStream {
|
||||
if (stderr_stream) |st| {
|
||||
@ -39,8 +39,8 @@ fn getStderrStream() -> %&io.OutStream {
|
||||
|
||||
/// Tries to print a stack trace to stderr, unbuffered, and ignores any error returned.
|
||||
pub fn dumpStackTrace() {
|
||||
const stderr = getStderrStream() %% return;
|
||||
writeStackTrace(stderr, global_allocator, stderr_file.isTty(), 1) %% return;
|
||||
const stderr = getStderrStream() catch return;
|
||||
writeStackTrace(stderr, global_allocator, stderr_file.isTty(), 1) catch return;
|
||||
}
|
||||
|
||||
/// This function invokes undefined behavior when `ok` is `false`.
|
||||
@ -86,9 +86,9 @@ pub fn panic(comptime format: []const u8, args: ...) -> noreturn {
|
||||
panicking = true;
|
||||
}
|
||||
|
||||
const stderr = getStderrStream() %% os.abort();
|
||||
stderr.print(format ++ "\n", args) %% os.abort();
|
||||
writeStackTrace(stderr, global_allocator, stderr_file.isTty(), 1) %% os.abort();
|
||||
const stderr = getStderrStream() catch os.abort();
|
||||
stderr.print(format ++ "\n", args) catch os.abort();
|
||||
writeStackTrace(stderr, global_allocator, stderr_file.isTty(), 1) catch os.abort();
|
||||
|
||||
os.abort();
|
||||
}
|
||||
@ -146,7 +146,7 @@ pub fn writeStackTrace(out_stream: &io.OutStream, allocator: &mem.Allocator, tty
|
||||
// at compile time. I'll call it issue #313
|
||||
const ptr_hex = if (@sizeOf(usize) == 4) "0x{x8}" else "0x{x16}";
|
||||
|
||||
const compile_unit = findCompileUnit(st, return_address) %% {
|
||||
const compile_unit = findCompileUnit(st, return_address) catch {
|
||||
try out_stream.print("???:?:?: " ++ DIM ++ ptr_hex ++ " in ??? (???)" ++ RESET ++ "\n ???\n\n",
|
||||
return_address);
|
||||
continue;
|
||||
@ -757,7 +757,7 @@ fn getLineNumberInfo(st: &ElfStackTrace, compile_unit: &const CompileUnit, targe
|
||||
});
|
||||
},
|
||||
else => {
|
||||
const fwd_amt = math.cast(isize, op_size - 1) %% return error.InvalidDebugInfo;
|
||||
const fwd_amt = math.cast(isize, op_size - 1) catch return error.InvalidDebugInfo;
|
||||
try in_file.seekForward(fwd_amt);
|
||||
},
|
||||
}
|
||||
|
@ -533,7 +533,7 @@ fn bufPrintIntToSlice(buf: []u8, value: var, base: u8, uppercase: bool, width: u
|
||||
}
|
||||
|
||||
test "parse u64 digit too big" {
|
||||
_ = parseUnsigned(u64, "123a", 10) %% |err| {
|
||||
_ = parseUnsigned(u64, "123a", 10) catch |err| {
|
||||
if (err == error.InvalidChar) return;
|
||||
unreachable;
|
||||
};
|
||||
|
@ -137,9 +137,9 @@ pub const IncrementingAllocator = struct {
|
||||
|
||||
test "c_allocator" {
|
||||
if (builtin.link_libc) {
|
||||
var slice = c_allocator.alloc(u8, 50) %% return;
|
||||
var slice = c_allocator.alloc(u8, 50) catch return;
|
||||
defer c_allocator.free(slice);
|
||||
slice = c_allocator.realloc(u8, slice, 100) %% return;
|
||||
slice = c_allocator.realloc(u8, slice, 100) catch return;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -383,27 +383,27 @@ pub const ChildProcess = struct {
|
||||
// we are the child
|
||||
restore_SIGCHLD();
|
||||
|
||||
setUpChildIo(self.stdin_behavior, stdin_pipe[0], posix.STDIN_FILENO, dev_null_fd) %%
|
||||
setUpChildIo(self.stdin_behavior, stdin_pipe[0], posix.STDIN_FILENO, dev_null_fd) catch
|
||||
|err| forkChildErrReport(err_pipe[1], err);
|
||||
setUpChildIo(self.stdout_behavior, stdout_pipe[1], posix.STDOUT_FILENO, dev_null_fd) %%
|
||||
setUpChildIo(self.stdout_behavior, stdout_pipe[1], posix.STDOUT_FILENO, dev_null_fd) catch
|
||||
|err| forkChildErrReport(err_pipe[1], err);
|
||||
setUpChildIo(self.stderr_behavior, stderr_pipe[1], posix.STDERR_FILENO, dev_null_fd) %%
|
||||
setUpChildIo(self.stderr_behavior, stderr_pipe[1], posix.STDERR_FILENO, dev_null_fd) catch
|
||||
|err| forkChildErrReport(err_pipe[1], err);
|
||||
|
||||
if (self.cwd) |cwd| {
|
||||
os.changeCurDir(self.allocator, cwd) %%
|
||||
os.changeCurDir(self.allocator, cwd) catch
|
||||
|err| forkChildErrReport(err_pipe[1], err);
|
||||
}
|
||||
|
||||
if (self.gid) |gid| {
|
||||
os.posix_setregid(gid, gid) %% |err| forkChildErrReport(err_pipe[1], err);
|
||||
os.posix_setregid(gid, gid) catch |err| forkChildErrReport(err_pipe[1], err);
|
||||
}
|
||||
|
||||
if (self.uid) |uid| {
|
||||
os.posix_setreuid(uid, uid) %% |err| forkChildErrReport(err_pipe[1], err);
|
||||
os.posix_setreuid(uid, uid) catch |err| forkChildErrReport(err_pipe[1], err);
|
||||
}
|
||||
|
||||
os.posixExecve(self.argv, env_map, self.allocator) %%
|
||||
os.posixExecve(self.argv, env_map, self.allocator) catch
|
||||
|err| forkChildErrReport(err_pipe[1], err);
|
||||
}
|
||||
|
||||
@ -573,7 +573,7 @@ pub const ChildProcess = struct {
|
||||
defer self.allocator.free(app_name);
|
||||
|
||||
windowsCreateProcess(app_name.ptr, cmd_line.ptr, envp_ptr, cwd_ptr,
|
||||
&siStartInfo, &piProcInfo) %% |no_path_err|
|
||||
&siStartInfo, &piProcInfo) catch |no_path_err|
|
||||
{
|
||||
if (no_path_err != error.FileNotFound)
|
||||
return no_path_err;
|
||||
@ -767,12 +767,12 @@ const ErrInt = @IntType(false, @sizeOf(error) * 8);
|
||||
fn writeIntFd(fd: i32, value: ErrInt) -> %void {
|
||||
var bytes: [@sizeOf(ErrInt)]u8 = undefined;
|
||||
mem.writeInt(bytes[0..], value, builtin.endian);
|
||||
os.posixWrite(fd, bytes[0..]) %% return error.SystemResources;
|
||||
os.posixWrite(fd, bytes[0..]) catch return error.SystemResources;
|
||||
}
|
||||
|
||||
fn readIntFd(fd: i32) -> %ErrInt {
|
||||
var bytes: [@sizeOf(ErrInt)]u8 = undefined;
|
||||
os.posixRead(fd, bytes[0..]) %% return error.SystemResources;
|
||||
os.posixRead(fd, bytes[0..]) catch return error.SystemResources;
|
||||
return mem.readInt(bytes[0..], ErrInt, builtin.endian);
|
||||
}
|
||||
|
||||
|
@ -842,7 +842,7 @@ pub fn makePath(allocator: &Allocator, full_path: []const u8) -> %void {
|
||||
|
||||
var end_index: usize = resolved_path.len;
|
||||
while (true) {
|
||||
makeDir(allocator, resolved_path[0..end_index]) %% |err| {
|
||||
makeDir(allocator, resolved_path[0..end_index]) catch |err| {
|
||||
if (err == error.PathAlreadyExists) {
|
||||
// TODO stat the file and return an error if it's not a directory
|
||||
// this is important because otherwise a dangling symlink
|
||||
@ -915,7 +915,7 @@ pub fn deleteTree(allocator: &Allocator, full_path: []const u8) -> %void {
|
||||
return err;
|
||||
}
|
||||
{
|
||||
var dir = Dir.open(allocator, full_path) %% |err| {
|
||||
var dir = Dir.open(allocator, full_path) catch |err| {
|
||||
if (err == error.FileNotFound)
|
||||
return;
|
||||
if (err == error.NotDir)
|
||||
|
@ -1102,7 +1102,7 @@ pub fn real(allocator: &Allocator, pathname: []const u8) -> %[]u8 {
|
||||
var buf = try allocator.alloc(u8, 256);
|
||||
%defer allocator.free(buf);
|
||||
while (true) {
|
||||
const buf_len = math.cast(windows.DWORD, buf.len) %% return error.NameTooLong;
|
||||
const buf_len = math.cast(windows.DWORD, buf.len) catch return error.NameTooLong;
|
||||
const result = windows.GetFinalPathNameByHandleA(h_file, buf.ptr, buf_len, windows.VOLUME_NAME_DOS);
|
||||
|
||||
if (result == 0) {
|
||||
|
@ -166,7 +166,7 @@ pub fn windowsUnloadDll(hModule: windows.HMODULE) {
|
||||
test "InvalidDll" {
|
||||
const DllName = "asdf.dll";
|
||||
const allocator = std.debug.global_allocator;
|
||||
const handle = os.windowsLoadDll(allocator, DllName) %% |err| {
|
||||
const handle = os.windowsLoadDll(allocator, DllName) catch |err| {
|
||||
assert(err == error.DllNotFound);
|
||||
return;
|
||||
};
|
||||
|
@ -22,7 +22,7 @@ comptime {
|
||||
|
||||
extern fn zenMain() -> noreturn {
|
||||
// TODO: call exit.
|
||||
root.main() %% {};
|
||||
root.main() catch {};
|
||||
while (true) {}
|
||||
}
|
||||
|
||||
@ -44,7 +44,7 @@ nakedcc fn _start() -> noreturn {
|
||||
extern fn WinMainCRTStartup() -> noreturn {
|
||||
@setAlignStack(16);
|
||||
|
||||
root.main() %% std.os.windows.ExitProcess(1);
|
||||
root.main() catch std.os.windows.ExitProcess(1);
|
||||
std.os.windows.ExitProcess(0);
|
||||
}
|
||||
|
||||
@ -52,7 +52,7 @@ fn posixCallMainAndExit() -> noreturn {
|
||||
const argc = *argc_ptr;
|
||||
const argv = @ptrCast(&&u8, &argc_ptr[1]);
|
||||
const envp = @ptrCast(&?&u8, &argv[argc + 1]);
|
||||
callMain(argc, argv, envp) %% std.os.posix.exit(1);
|
||||
callMain(argc, argv, envp) catch std.os.posix.exit(1);
|
||||
std.os.posix.exit(0);
|
||||
}
|
||||
|
||||
@ -67,6 +67,6 @@ fn callMain(argc: usize, argv: &&u8, envp: &?&u8) -> %void {
|
||||
}
|
||||
|
||||
extern fn main(c_argc: i32, c_argv: &&u8, c_envp: &?&u8) -> i32 {
|
||||
callMain(usize(c_argc), c_argv, c_envp) %% return 1;
|
||||
callMain(usize(c_argc), c_argv, c_envp) catch return 1;
|
||||
return 0;
|
||||
}
|
||||
|
@ -117,7 +117,7 @@ pub fn main() -> %void {
|
||||
if (builder.validateUserInputDidItFail())
|
||||
return usageAndErr(&builder, true, try stderr_stream);
|
||||
|
||||
builder.make(targets.toSliceConst()) %% |err| {
|
||||
builder.make(targets.toSliceConst()) catch |err| {
|
||||
if (err == error.InvalidStepName) {
|
||||
return usageAndErr(&builder, true, try stderr_stream);
|
||||
}
|
||||
@ -184,12 +184,12 @@ fn usage(builder: &Builder, already_ran_build: bool, out_stream: &io.OutStream)
|
||||
}
|
||||
|
||||
fn usageAndErr(builder: &Builder, already_ran_build: bool, out_stream: &io.OutStream) -> error {
|
||||
usage(builder, already_ran_build, out_stream) %% {};
|
||||
usage(builder, already_ran_build, out_stream) catch {};
|
||||
return error.InvalidArgs;
|
||||
}
|
||||
|
||||
fn unwrapArg(arg: %[]u8) -> %[]u8 {
|
||||
return arg %% |err| {
|
||||
return arg catch |err| {
|
||||
warn("Unable to parse command line: {}\n", err);
|
||||
return err;
|
||||
};
|
||||
|
@ -18,7 +18,7 @@ test "mixing normal and error defers" {
|
||||
assert(result[0] == 'c');
|
||||
assert(result[1] == 'a');
|
||||
|
||||
const ok = runSomeErrorDefers(false) %% |err| x: {
|
||||
const ok = runSomeErrorDefers(false) catch |err| x: {
|
||||
assert(err == error.FalseNotAllowed);
|
||||
break :x true;
|
||||
};
|
||||
|
@ -11,7 +11,7 @@ pub fn bar() -> %i32 {
|
||||
}
|
||||
|
||||
pub fn baz() -> %i32 {
|
||||
const y = foo() %% 1234;
|
||||
const y = foo() catch 1234;
|
||||
return y + 1;
|
||||
}
|
||||
|
||||
@ -53,8 +53,8 @@ fn shouldBeNotEqual(a: error, b: error) {
|
||||
|
||||
|
||||
test "error binary operator" {
|
||||
const a = errBinaryOperatorG(true) %% 3;
|
||||
const b = errBinaryOperatorG(false) %% 3;
|
||||
const a = errBinaryOperatorG(true) catch 3;
|
||||
const b = errBinaryOperatorG(false) catch 3;
|
||||
assert(a == 3);
|
||||
assert(b == 10);
|
||||
}
|
||||
|
@ -230,7 +230,7 @@ fn return_a_number() -> %i32 {
|
||||
}
|
||||
|
||||
test "capture value of switch with all unreachable prongs" {
|
||||
const x = return_a_number() %% |err| switch (err) {
|
||||
const x = return_a_number() catch |err| switch (err) {
|
||||
else => unreachable,
|
||||
};
|
||||
assert(x == 1);
|
||||
|
@ -395,7 +395,7 @@ pub fn addCases(cases: &tests.CompareOutputContext) {
|
||||
cases.add("%defer and it fails",
|
||||
\\const io = @import("std").io;
|
||||
\\pub fn main() -> %void {
|
||||
\\ do_test() %% return;
|
||||
\\ do_test() catch return;
|
||||
\\}
|
||||
\\fn do_test() -> %void {
|
||||
\\ const stdout = &(io.FileOutStream.init(&%%io.getStdOut()).stream);
|
||||
@ -415,7 +415,7 @@ pub fn addCases(cases: &tests.CompareOutputContext) {
|
||||
cases.add("%defer and it passes",
|
||||
\\const io = @import("std").io;
|
||||
\\pub fn main() -> %void {
|
||||
\\ do_test() %% return;
|
||||
\\ do_test() catch return;
|
||||
\\}
|
||||
\\fn do_test() -> %void {
|
||||
\\ const stdout = &(io.FileOutStream.init(&%%io.getStdOut()).stream);
|
||||
|
@ -1288,7 +1288,7 @@ pub fn addCases(cases: &tests.CompileErrorContext) {
|
||||
|
||||
cases.add("return from defer expression",
|
||||
\\pub fn testTrickyDefer() -> %void {
|
||||
\\ defer canFail() %% {};
|
||||
\\ defer canFail() catch {};
|
||||
\\
|
||||
\\ defer try canFail();
|
||||
\\
|
||||
|
@ -259,7 +259,7 @@ pub const CompareOutputContext = struct {
|
||||
child.stderr_behavior = StdIo.Pipe;
|
||||
child.env_map = &b.env_map;
|
||||
|
||||
child.spawn() %% |err| debug.panic("Unable to spawn {}: {}\n", full_exe_path, @errorName(err));
|
||||
child.spawn() catch |err| debug.panic("Unable to spawn {}: {}\n", full_exe_path, @errorName(err));
|
||||
|
||||
var stdout = Buffer.initNull(b.allocator);
|
||||
var stderr = Buffer.initNull(b.allocator);
|
||||
@ -270,7 +270,7 @@ pub const CompareOutputContext = struct {
|
||||
%%stdout_file_in_stream.stream.readAllBuffer(&stdout, max_stdout_size);
|
||||
%%stderr_file_in_stream.stream.readAllBuffer(&stderr, max_stdout_size);
|
||||
|
||||
const term = child.wait() %% |err| {
|
||||
const term = child.wait() catch |err| {
|
||||
debug.panic("Unable to spawn {}: {}\n", full_exe_path, @errorName(err));
|
||||
};
|
||||
switch (term) {
|
||||
@ -341,7 +341,7 @@ pub const CompareOutputContext = struct {
|
||||
child.stdout_behavior = StdIo.Ignore;
|
||||
child.stderr_behavior = StdIo.Ignore;
|
||||
|
||||
const term = child.spawnAndWait() %% |err| {
|
||||
const term = child.spawnAndWait() catch |err| {
|
||||
debug.panic("Unable to spawn {}: {}\n", full_exe_path, @errorName(err));
|
||||
};
|
||||
|
||||
@ -590,7 +590,7 @@ pub const CompileErrorContext = struct {
|
||||
child.stdout_behavior = StdIo.Pipe;
|
||||
child.stderr_behavior = StdIo.Pipe;
|
||||
|
||||
child.spawn() %% |err| debug.panic("Unable to spawn {}: {}\n", zig_args.items[0], @errorName(err));
|
||||
child.spawn() catch |err| debug.panic("Unable to spawn {}: {}\n", zig_args.items[0], @errorName(err));
|
||||
|
||||
var stdout_buf = Buffer.initNull(b.allocator);
|
||||
var stderr_buf = Buffer.initNull(b.allocator);
|
||||
@ -601,7 +601,7 @@ pub const CompileErrorContext = struct {
|
||||
%%stdout_file_in_stream.stream.readAllBuffer(&stdout_buf, max_stdout_size);
|
||||
%%stderr_file_in_stream.stream.readAllBuffer(&stderr_buf, max_stdout_size);
|
||||
|
||||
const term = child.wait() %% |err| {
|
||||
const term = child.wait() catch |err| {
|
||||
debug.panic("Unable to spawn {}: {}\n", zig_args.items[0], @errorName(err));
|
||||
};
|
||||
switch (term) {
|
||||
@ -862,7 +862,7 @@ pub const TranslateCContext = struct {
|
||||
child.stdout_behavior = StdIo.Pipe;
|
||||
child.stderr_behavior = StdIo.Pipe;
|
||||
|
||||
child.spawn() %% |err| debug.panic("Unable to spawn {}: {}\n", zig_args.toSliceConst()[0], @errorName(err));
|
||||
child.spawn() catch |err| debug.panic("Unable to spawn {}: {}\n", zig_args.toSliceConst()[0], @errorName(err));
|
||||
|
||||
var stdout_buf = Buffer.initNull(b.allocator);
|
||||
var stderr_buf = Buffer.initNull(b.allocator);
|
||||
@ -873,7 +873,7 @@ pub const TranslateCContext = struct {
|
||||
%%stdout_file_in_stream.stream.readAllBuffer(&stdout_buf, max_stdout_size);
|
||||
%%stderr_file_in_stream.stream.readAllBuffer(&stderr_buf, max_stdout_size);
|
||||
|
||||
const term = child.wait() %% |err| {
|
||||
const term = child.wait() catch |err| {
|
||||
debug.panic("Unable to spawn {}: {}\n", zig_args.toSliceConst()[0], @errorName(err));
|
||||
};
|
||||
switch (term) {
|
||||
|
Loading…
x
Reference in New Issue
Block a user