diff --git a/internal/fusefrontend/fs.go b/internal/fusefrontend/fs.go index 279c755..de168dc 100644 --- a/internal/fusefrontend/fs.go +++ b/internal/fusefrontend/fs.go @@ -205,7 +205,7 @@ func (fs *FS) Mknod(path string, mode uint32, dev uint32, context *fuse.Context) } // Create device node - err = syscall.Mknodat(int(dirfd.Fd()), cName, uint32(mode), int(dev)) + err = syscallcompat.Mknodat(int(dirfd.Fd()), cName, uint32(mode), int(dev)) if err != nil { nametransform.DeleteLongName(dirfd, cName) } diff --git a/internal/syscallcompat/sys_darwin.go b/internal/syscallcompat/sys_darwin.go index 6300317..852eee4 100644 --- a/internal/syscallcompat/sys_darwin.go +++ b/internal/syscallcompat/sys_darwin.go @@ -87,6 +87,24 @@ func Unlinkat(dirfd int, path string) (err error) { return syscall.Unlink(path) } +// Poor man's Mknodat +func Mknodat(dirfd int, path string, mode uint32, dev int) (err error) { + chdirMutex.Lock() + defer chdirMutex.Unlock() + if !filepath.IsAbs(path) { + oldWd, err := os.Getwd() + if err != nil { + return err + } + defer os.Chdir(oldWd) + } + path, err = dirfdAbs(dirfd, path) + if err != nil { + return err + } + return syscall.Mknod(path, mode, dev) +} + // dirfdAbs transforms the dirfd-relative "path" to an absolute one. If the // path is not already absolute, this function will change the working // directory. The caller has to chdir back. diff --git a/internal/syscallcompat/sys_linux.go b/internal/syscallcompat/sys_linux.go index ded5d17..81cdb15 100644 --- a/internal/syscallcompat/sys_linux.go +++ b/internal/syscallcompat/sys_linux.go @@ -52,3 +52,7 @@ func Renameat(olddirfd int, oldpath string, newdirfd int, newpath string) (err e func Unlinkat(dirfd int, path string) error { return syscall.Unlinkat(dirfd, path) } + +func Mknodat(dirfd int, path string, mode uint32, dev int) (err error) { + return syscall.Mknodat(dirfd, path, mode, dev) +}