5
0
mirror of git://git.proxmox.com/git/pve-common.git synced 2025-01-10 09:17:37 +03:00

tools: add set/get xattr methods

Signed-off-by: Thomas Lamprecht <t.lamprecht@proxmox.com>
This commit is contained in:
Thomas Lamprecht 2021-10-19 08:18:00 +02:00
parent bfa10639d9
commit 4c0c5c905d
2 changed files with 38 additions and 0 deletions

View File

@ -24,6 +24,10 @@ BEGIN {
fsconfig => &SYS_fsconfig,
fsmount => &SYS_fsmount,
fspick => &SYS_fspick,
getxattr => &SYS_getxattr,
setxattr => &SYS_setxattr,
fgetxattr => &SYS_fgetxattr,
fsetxattr => &SYS_fsetxattr,
# Below aren't yet in perl's syscall.ph but use asm-generic, so the same across (sane) archs
# -> none unknown currently, yay

View File

@ -1864,6 +1864,40 @@ sub mount($$$$$) {
);
}
# size is optional and defaults to 256, note that xattr limits are FS specific and that xattrs can
# get arbitrary long. NOTE: $! is set to ENOBUFS if the xattr is longer than the buffer size used.
sub getxattr($$;$) {
my ($path_or_handle, $name, $size) = @_;
$size //= 256;
my $buf = pack("x${size}");
my $xattr_size = -1; # the actual size of the xattr, can be zero
if (defined(my $fd = fileno($path_or_handle))) {
$xattr_size = syscall(&PVE::Syscall::fgetxattr, $fd, $name, $buf, $size);
} else {
$xattr_size = syscall(&PVE::Syscall::getxattr, $path_or_handle, $name, $buf, $size);
}
if ($xattr_size < 0) {
warn "$xattr_size <0 - $!";
return undef;
} elsif ($xattr_size > $size) {
$! = POSIX::ENOBUFS;
}
return wantarray ? ($buf, $xattr_size) : $buf;
}
# NOTE: can take either a path or an open file handle, i.e., its multiplexing setxattr and fsetxattr
sub setxattr($$$;$) {
my ($path_or_handle, $name, $value, $flags) = @_;
my $size = length($value); # NOTE: seems to get correct length also for wide-characters in text..
if (defined(my $fd = fileno($path_or_handle))) {
return 0 == syscall(&PVE::Syscall::fsetxattr, $fd, $name, $value, $size, $flags // 0);
} else {
return 0 == syscall(&PVE::Syscall::setxattr, $path_or_handle, $name, $value, $size, $flags // 0);
}
}
sub safe_compare {
my ($left, $right, $cmp) = @_;