mirror of
https://github.com/octoleo/restic.git
synced 2024-12-12 14:17:57 +00:00
8c02ebb029
Linux allows the use of non-`user.` extended attributes on symlinks. One of the main users of this functionality is SELinux's `security.selinux` xattr for storing a path's label. By storing symlink xattrs, restic is now suitable for backing up the root filesystem on Linux distributions that use SELinux. This commit adds support for symlink xattrs when backing up data, restoring data, and mounting snapshots via a fuse mount. All calls to the xattr library have been updated to the use `L` variants of the various functions, which always operate on the path given, without following symlinks. Fixes: #4375 Signed-off-by: Andrew Gunnerson <accounts+github@chiller3.com>
50 lines
1.1 KiB
Go
50 lines
1.1 KiB
Go
//go:build darwin || freebsd || linux || solaris
|
|
// +build darwin freebsd linux solaris
|
|
|
|
package restic
|
|
|
|
import (
|
|
"syscall"
|
|
|
|
"github.com/restic/restic/internal/errors"
|
|
|
|
"github.com/pkg/xattr"
|
|
)
|
|
|
|
// Getxattr retrieves extended attribute data associated with path.
|
|
func Getxattr(path, name string) ([]byte, error) {
|
|
b, err := xattr.LGet(path, name)
|
|
return b, handleXattrErr(err)
|
|
}
|
|
|
|
// Listxattr retrieves a list of names of extended attributes associated with the
|
|
// given path in the file system.
|
|
func Listxattr(path string) ([]string, error) {
|
|
l, err := xattr.LList(path)
|
|
return l, handleXattrErr(err)
|
|
}
|
|
|
|
// Setxattr associates name and data together as an attribute of path.
|
|
func Setxattr(path, name string, data []byte) error {
|
|
return handleXattrErr(xattr.LSet(path, name, data))
|
|
}
|
|
|
|
func handleXattrErr(err error) error {
|
|
switch e := err.(type) {
|
|
case nil:
|
|
return nil
|
|
|
|
case *xattr.Error:
|
|
// On Linux, xattr calls on files in an SMB/CIFS mount can return
|
|
// ENOATTR instead of ENOTSUP.
|
|
switch e.Err {
|
|
case syscall.ENOTSUP, xattr.ENOATTR:
|
|
return nil
|
|
}
|
|
return errors.WithStack(e)
|
|
|
|
default:
|
|
return errors.WithStack(e)
|
|
}
|
|
}
|