xattr: tolerate ENOTSUP (behave like there are no attributes when not supported on given FS)
--- a/XAttrs.cpp Tue Jan 02 17:50:43 2024 +0100
+++ b/XAttrs.cpp Sat Jan 06 01:04:15 2024 +0100
@@ -26,23 +26,30 @@
std::string xattrGet(
const std::string fileName,
const std::string name,
- bool* exists = nullptr) {
+ bool* exists = nullptr,
+ bool* supported = nullptr) {
std::string buffer;
ssize_t size = getxattr(fileName.c_str(), name.c_str(), nullptr, 0);
if (size > 0) {
buffer.resize(size);
getxattr(fileName.c_str(), name.c_str(), buffer.data(), buffer.size());
if (exists) *exists = true;
+ if (supported) *supported = true;
return buffer;
} else if (size == 0) {
if (exists) *exists = true;
+ if (supported) *supported = true;
return "";
} else if (errno == ENODATA) {
if (exists) *exists = false;
+ if (supported) *supported = true;
return "";
} else if (errno == ERANGE) {
// rare race condition - the value has changed between the two calls
return xattrGet(fileName, name, exists);
+ } else if (errno == ENOTSUP) {
+ if (supported) *supported = false;
+ return "";
} else {
throw std::logic_error(
std::string("Unable to get extended attribute: ")
@@ -53,7 +60,8 @@
bool xattrSet(const std::string fileName,
const std::string name,
const std::string value,
- bool exists = true) {
+ bool exists = true,
+ bool* supported = nullptr) {
int result;
if (exists) {
result = setxattr(
@@ -67,13 +75,16 @@
if (result < 0 && errno == ENODATA) return false;
}
- if (result < 0) throw std::logic_error(
+ if (result < 0 && errno == ENOTSUP && supported) *supported = false;
+ else if (result < 0) throw std::logic_error(
std::string("Unable to set extended attribute: ")
+ strerror(errno));
- else return true;
+
+ return true;
}
-std::vector<std::string> xattrList(const std::string fileName) {
+std::vector<std::string>
+xattrList(const std::string fileName, bool* supported = nullptr) {
std::string buffer;
ssize_t size = listxattr(fileName.c_str(), nullptr, 0);
if (size >= 0) {
@@ -84,10 +95,14 @@
for (const char* k = buffer.c_str(); strlen(k); k += strlen(k) + 1) {
result.push_back(k);
}
+ if (supported) *supported = true;
return result;
} else if (errno == ERANGE) {
// rare race condition - the list has changed between the two calls
return xattrList(fileName);
+ } else if (errno == ENOTSUP) {
+ if (supported) *supported = false;
+ return std::vector<std::string>();
} else {
throw std::logic_error(
std::string("Unable to list extended attributes: ")