Skip to content

file system watching on linux fails to avoid placing marks from different mounts into the same fanotify descriptor #20670

@andrewrk

Description

@andrewrk

Follow-up from #20580.

name_to_handle_at gives us a mount ID here:

try posix.name_to_handle_at(path.root_dir.handle.fd, adjusted_path, stack_ptr, &mount_id, std.os.linux.AT.HANDLE_FID);

A given fanotify file descriptor (created by fanotify_init) can only contain marks from the same mount ID. So if we get a different mount ID here, we need to put it into a new fanotify set. The poll later on needs to poll all of them.

Without this fix, we get errors such as

error: unable to watch /nix/store/0c5jp9d9h9818arr6s21xibgjl1ybql0-glibc-2.39-52-dev/include: NotSameFileSystem

Some commonly used Linux distributions will put the Zig standard library into a different mount than the user's home directory, resulting in this problem.

Workaround:

--- a/lib/std/Build/Watch.zig
+++ b/lib/std/Build/Watch.zig
@@ -175,7 +175,7 @@ const Os = switch (builtin.os.tag) {
                                     .ADD = true,
                                     .ONLYDIR = true,
                                 }, fan_mask, path.root_dir.handle.fd, path.subPathOrDot()) catch |err| {
-                                    fatal("unable to watch {}: {s}", .{ path, @errorName(err) });
+                                    std.log.warn("unable to watch {}: {s}", .{ path, @errorName(err) });
                                 };
                             }
                             break :rs dh_gop.value_ptr;

You can apply this workaround without recompiling Zig.

Related:

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugObserved behavior contradicts documented or intended behaviorcontributor friendlyThis issue is limited in scope and/or knowledge of Zig internals.os-linuxzig build systemstd.Build, the build runner, `zig build` subcommand, package management

    Type

    No type

    Projects

    No projects

    Milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions