rfjakob/gocryptfs

Enable mounting to "/Volumes" on macOS

alexanderharm opened this issue · 13 comments

Right now running gocryptfs encdir /Volumes/encdir errors out. However, osxfuse automatically creates the encdir if mounted to /Volumes because this would require root permissions which the user might not have.

I guess mount.go needs to be modified to not check the directory existence when the mount path matches /Volumes/* on macOS.

I'm willing to write a PR myself but I'm a total Go newbie. Not sure that these are the only critical references in the source:

gocryptfs/mount.go

Lines 38 to 65 in a4dff6a

args.mountpoint, err = filepath.Abs(flagSet.Arg(1))
if err != nil {
tlog.Fatal.Printf("Invalid mountpoint: %v", err)
os.Exit(exitcodes.MountPoint)
}
// We cannot mount "/home/user/.cipher" at "/home/user" because the mount
// will hide ".cipher" also for us.
if args.cipherdir == args.mountpoint || strings.HasPrefix(args.cipherdir, args.mountpoint+"/") {
tlog.Fatal.Printf("Mountpoint %q would shadow cipherdir %q, this is not supported",
args.mountpoint, args.cipherdir)
os.Exit(exitcodes.MountPoint)
}
// Reverse-mounting "/foo" at "/foo/mnt" means we would be recursively
// encrypting ourselves.
if strings.HasPrefix(args.mountpoint, args.cipherdir+"/") {
tlog.Fatal.Printf("Mountpoint %q is contained in cipherdir %q, this is not supported",
args.mountpoint, args.cipherdir)
os.Exit(exitcodes.MountPoint)
}
if args.nonempty {
err = checkDir(args.mountpoint)
} else {
err = checkDirEmpty(args.mountpoint)
}
if err != nil {
tlog.Fatal.Printf("Invalid mountpoint: %v", err)
os.Exit(exitcodes.MountPoint)
}

Sounds like a good idea. I can implement this, can you test?

Sure. Can you also check #124? This has been fixed upstream.

Pushed to https://github.com/rfjakob/gocryptfs/commits/macos_volumes , MacOS binary attached - could you test? Binary: gocryptfs.gz

It creates the dir in Volumes but it is not mounted in Finder. I will read some more tonight and come back.

@rfjakob I tested a bit more and it works perfectly fine. However I noticed two things:

  • osxfuse always creates the dir even if several levels don't exist. So on macOS one could completely omit the dirstat (e. g. gocryptfs cipher ~/this/path/does/not/exist works).

  • passing fuse options via -o doesn't work (e. g. -o local)

It might also make sense to pass the following mount options on macOS to avoid the creation of these additional files:

  • noapplexattr
  • noappledouble

Do you get an error when passing options via -o ?

Oh, you have to use -ko !

gocryptfs test /Volumes/Test -o local
Wrong number of arguments (have 3, want 2). You passed: "test" "/Volumes/Test" "-olocal"
Usage: gocryptfs [OPTIONS] CIPHERDIR MOUNTPOINT [-o COMMA-SEPARATED-OPTIONS]

Same result with -ko.

$ gocryptfs -ko local a b
Password: 
[...]

Great! But I find this a bit misleading or incomplete for beginners like me:

  -ko string
    	Pass additional options directly to the kernel, comma-separated list

I agree, it's not explained very clearly. How about this: 277ad08 ?

With bac7ef4 , gocryptfs continues if the mountpoint does not exist, for all paths. I'll declare this DONE :)

Great. Thank you very much for your efforts.