]> ruderich.org/simon Gitweb - safcm/safcm.git/blobdiff - cmd/safcm-remote/sync/files.go
Improve and add comments
[safcm/safcm.git] / cmd / safcm-remote / sync / files.go
index 6e001a8186d14675864b4d90794d77694269cee0..119a3534239f68e2e5d10aee08ec2559590ada87 100644 (file)
@@ -113,7 +113,7 @@ reopen:
        oldFh, err := OpenFileNoFollow(file.Path)
        if err != nil {
                err := err.(*fs.PathError)
-               if err.Err == syscall.ELOOP {
+               if err.Err == syscall.ELOOP || err.Err == syscall.EMLINK {
                        // Check if ELOOP was caused not by O_NOFOLLOW but by
                        // too many nested symlinks before the final path
                        // component.
@@ -149,6 +149,15 @@ reopen:
        if !change.Created {
                // Compare permissions
                change.Old.Mode = oldStat.Mode()
+               if change.Old.Mode.Type() == fs.ModeSymlink {
+                       // Some BSD systems permit changing permissions of
+                       // symlinks but ignore them on traversal. To keep it
+                       // simple we don't support that and always use 0777
+                       // for symlink permissions (the value on GNU/Linux).
+                       //
+                       // TODO: Add proper support for symlinks on BSD
+                       change.Old.Mode |= 0777
+               }
                if change.Old.Mode != file.Mode {
                        if change.Old.Mode.Type() != file.Mode.Type() {
                                changeType = true
@@ -258,7 +267,7 @@ reopen:
                }
        }
 
-       // Directory: create new directory (also type change to directory)
+       // Directory: create new directory, also type change to directory
        if file.Mode.IsDir() && (change.Created || changeType) {
                debugf("creating directory")
                err := os.Mkdir(file.Path, 0700)
@@ -364,7 +373,7 @@ reopen:
                        os.Remove(tmpPath)
                        return err
                }
-               // Permissions are irrelevant for symlinks
+               // Permissions are irrelevant for symlinks (on most systems)
 
        default:
                panic(fmt.Sprintf("invalid file type %s", file.Mode))
@@ -376,7 +385,7 @@ reopen:
                os.Remove(tmpPath)
                return err
        }
-       err = syncPath(dir)
+       err = SyncPath(dir)
        if err != nil {
                return err
        }
@@ -517,7 +526,7 @@ func WriteTemp(dir, base string, data []byte, uid, gid int, mode fs.FileMode) (
        return tmpPath, nil
 }
 
-// syncPath syncs path, which should be a directory. To guarantee durability
+// SyncPath syncs path, which should be a directory. To guarantee durability
 // it must be called on a parent directory after adding, renaming or removing
 // files therein.
 //
@@ -525,7 +534,7 @@ func WriteTemp(dir, base string, data []byte, uid, gid int, mode fs.FileMode) (
 // fsync: "Calling fsync() does not necessarily ensure that the entry in the
 // directory containing the file has also reached disk. For that an explicit
 // fsync() on a file descriptor for the directory is also needed."
-func syncPath(path string) error {
+func SyncPath(path string) error {
        x, err := os.Open(path)
        if err != nil {
                return err