Skip to content

Can't resolve inferred error set for function that returns conditional expression #4672

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
ghost opened this issue Mar 7, 2020 · 0 comments
Labels
bug Observed behavior contradicts documented or intended behavior stage1 The process of building from source via WebAssembly and the C backend.
Milestone

Comments

@ghost
Copy link

ghost commented Mar 7, 2020

const std = @import("std");

pub fn main() !void {
    const allocator = std.heap.page_allocator;
    const file = try openDataFile(allocator, .read);
    file.close();
}

fn openDataFile(
    allocator: *std.mem.Allocator,
    mode: enum { read, write },
) !std.fs.File {
    return switch (mode) {
        .read => std.fs.cwd().openFile("aaa", .{}),
        .write => std.fs.cwd().createFile("aaa", .{}),
    };
}
./asdf12.zig:12:10: error: cannot resolve inferred error set '@TypeOf(openDataFile).ReturnType.ErrorSet': function 'openDataFile' not fully analyzed yet
) !std.fs.File {
         ^
./asdf12.zig:5:18: note: referenced here
    const file = try openDataFile(allocator, .read);
                 ^

It also fails using return if (mode == .read) ... else ...;.

I can get it to work by adding trys:

  • return try switch (mode) { ... };
  • return switch (mode) { .read => try ... , .write => try ... };

Or by returning inside the switch statement:

  • switch (mode) { .read => return ..., .write => return ... }

Or by assigning the conditional expression then returning the variable:

  • const x = switch (mode) { .read => ... , .write => ... }; return x;

It becomes weirder if I have another try in the function. Now it does compile, but the compiler doesn't know about the possible error values from the return expression.

const std = @import("std");

pub fn main() !void {
    const allocator = std.heap.page_allocator;
    const file = openDataFile(allocator, .read) catch |err| {
        if (err == error.FileNotFound) {
            std.debug.warn("oh\n", .{});
        }
        return err;
    };
    file.close();
}

fn openDataFile(
    allocator: *std.mem.Allocator,
    mode: enum { read, write },
) !std.fs.File {
    const file_path = try std.fs.path.join(
        allocator,
        &[_][]const u8 { "one", "two" },
    );

    return switch (mode) {
        .read => std.fs.cwd().openFile(file_path, .{}),
        .write => std.fs.cwd().createFile(file_path, .{}),
    };
}
./asdf12.zig:6:17: error: error sets '@TypeOf(openDataFile).ReturnType.ErrorSet' and 'error{FileNotFound}' have no common errors
        if (err == error.FileNotFound) {
                ^

Note: I think this is a recent (as in the last week or two?) regression.

@andrewrk andrewrk added bug Observed behavior contradicts documented or intended behavior stage1 The process of building from source via WebAssembly and the C backend. labels Mar 8, 2020
@andrewrk andrewrk added this to the 0.6.0 milestone Mar 8, 2020
@andrewrk andrewrk modified the milestones: 0.6.0, 0.7.0 Apr 3, 2020
@andrewrk andrewrk modified the milestones: 0.7.0, 0.8.0 Aug 13, 2020
@andrewrk andrewrk modified the milestones: 0.8.0, 0.9.0 Nov 6, 2020
@andrewrk andrewrk modified the milestones: 0.9.0, 0.10.0 May 19, 2021
Vexu added a commit to Vexu/zig that referenced this issue Dec 31, 2022
Vexu added a commit to Vexu/zig that referenced this issue Dec 31, 2022
@andrewrk andrewrk modified the milestones: 0.12.0, 0.11.0 Jan 1, 2023
TUSF pushed a commit to TUSF/zig that referenced this issue May 9, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Observed behavior contradicts documented or intended behavior stage1 The process of building from source via WebAssembly and the C backend.
Projects
None yet
Development

No branches or pull requests

1 participant