diff --git a/src/shared/copy.c b/src/shared/copy.c index 0c79121b68..1726838756 100644 --- a/src/shared/copy.c +++ b/src/shared/copy.c @@ -817,7 +817,11 @@ static int copy_fs_verity(int fdf, int *fdt) { * so the correct thing to do is to do nothing at all. */ if (errno == ENODATA) return 0; - return log_error_errno(errno, "Failed to read fs-verity metadata from source file: %m"); + log_error_errno(errno, "Failed to read fs-verity metadata from source file: %m"); + /* For cases where fs-verity is unsupported we return a special error code */ + if (ERRNO_IS_NOT_SUPPORTED(errno)) + return -ESOCKTNOSUPPORT; + return -errno; } /* Make sure that the descriptor is completely initialized */ @@ -844,8 +848,13 @@ static int copy_fs_verity(int fdf, int *fdt) { .salt_ptr = (uintptr_t) &desc.salt, }; - if (ioctl(*fdt, FS_IOC_ENABLE_VERITY, &enable_arg) < 0) - return log_error_errno(errno, "Failed to set fs-verity metadata: %m"); + if (ioctl(*fdt, FS_IOC_ENABLE_VERITY, &enable_arg) < 0) { + log_error_errno(errno, "Failed to set fs-verity metadata: %m"); + /* For cases where fs-verity is unsupported we return a special error code */ + if (ERRNO_IS_NOT_SUPPORTED(errno)) + return -ESOCKTNOSUPPORT; + return -errno; + } return 0; } @@ -1222,7 +1231,8 @@ static int fd_copy_directory( denylist, subvolumes, hardlink_context, child_display_path, progress_path, progress_bytes, userdata); - if (IN_SET(r, -EINTR, -ENOSPC)) /* Propagate SIGINT/SIGTERM and ENOSPC up instantly */ + /* Propagate SIGINT/SIGTERM, ENOSPC, and fs-verity fails up instantly */ + if (IN_SET(r, -EINTR, -ENOSPC, -ESOCKTNOSUPPORT)) return r; if (r == -EEXIST && (copy_flags & COPY_MERGE)) r = 0; diff --git a/src/test/test-copy.c b/src/test/test-copy.c index 9da7778655..86de5c4b63 100644 --- a/src/test/test-copy.c +++ b/src/test/test-copy.c @@ -676,7 +676,7 @@ TEST_RET(copy_with_verity) { /* Copy *with* fs-verity enabled and make sure it works properly */ int r = copy_tree_at(src, ".", dst, ".", UID_INVALID, GID_INVALID, COPY_REFLINK|COPY_REPLACE|COPY_MERGE|COPY_PRESERVE_FS_VERITY, NULL, NULL); - if (r == -ENOTTY) + if (r == -ESOCKTNOSUPPORT) /* This can happen on some versions of btrfs, for example */ return log_tests_skipped_errno(errno, "/var/tmp: fs-verity supported, but not reading metadata"); ASSERT_OK(r); @@ -697,14 +697,14 @@ TEST_RET(copy_with_verity) { /* Copy from our non-verity filesystem into dst, requesting verity and making sure we notice that * we failed to read verity from the source. */ - ASSERT_ERROR(copy_tree_at(badsrc, ".", dst, ".", UID_INVALID, GID_INVALID, COPY_REFLINK|COPY_REPLACE|COPY_MERGE|COPY_PRESERVE_FS_VERITY, NULL, NULL), ENOTTY); + ASSERT_ERROR(copy_tree_at(badsrc, ".", dst, ".", UID_INVALID, GID_INVALID, COPY_REFLINK|COPY_REPLACE|COPY_MERGE|COPY_PRESERVE_FS_VERITY, NULL, NULL), ESOCKTNOSUPPORT); /* Copy from our verity filesystem into our baddst, requesting verity and making sure we notice that * we failed to set verity on the destination. */ - ASSERT_ERROR(copy_tree_at(src, ".", baddst, ".", UID_INVALID, GID_INVALID, COPY_REFLINK|COPY_REPLACE|COPY_MERGE|COPY_PRESERVE_FS_VERITY, NULL, NULL), ENOTTY); + ASSERT_ERROR(copy_tree_at(src, ".", baddst, ".", UID_INVALID, GID_INVALID, COPY_REFLINK|COPY_REPLACE|COPY_MERGE|COPY_PRESERVE_FS_VERITY, NULL, NULL), ESOCKTNOSUPPORT); /* Of course this should fail too... */ - ASSERT_ERROR(copy_tree_at(badsrc, ".", baddst, ".", UID_INVALID, GID_INVALID, COPY_REFLINK|COPY_REPLACE|COPY_MERGE|COPY_PRESERVE_FS_VERITY, NULL, NULL), ENOTTY); + ASSERT_ERROR(copy_tree_at(badsrc, ".", baddst, ".", UID_INVALID, GID_INVALID, COPY_REFLINK|COPY_REPLACE|COPY_MERGE|COPY_PRESERVE_FS_VERITY, NULL, NULL), ESOCKTNOSUPPORT); return 0; }