mirror of
https://github.com/freebsd/freebsd-src
synced 2024-10-15 12:54:27 +00:00
xinstall: use copy_file_range(2) with fallback to previous behavior
This allows to use special filesystem features like server-side copying on NFS 4.2 or block cloning on OpenZFS 2.2. Note: copy_file_range(2) is not used when a digest calculation is requested as this would require to read the input file twice. Reviewed by: asomers, imp, rmacklem Differential revision: https://reviews.freebsd.org/D40898
This commit is contained in:
parent
8113cc8276
commit
5a50d52f11
|
@ -1300,6 +1300,7 @@ copy(int from_fd, const char *from_name, int to_fd, const char *to_name,
|
|||
static size_t bufsize;
|
||||
int nr, nw;
|
||||
int serrno;
|
||||
ssize_t ret;
|
||||
char *p;
|
||||
int done_copy;
|
||||
DIGEST_CTX ctx;
|
||||
|
@ -1310,6 +1311,26 @@ copy(int from_fd, const char *from_name, int to_fd, const char *to_name,
|
|||
if (lseek(to_fd, (off_t)0, SEEK_SET) == (off_t)-1)
|
||||
err(EX_OSERR, "lseek: %s", to_name);
|
||||
|
||||
/* Try copy_file_range() if no digest is requested */
|
||||
if (digesttype == DIGEST_NONE) {
|
||||
ret = 1;
|
||||
while (ret > 0) {
|
||||
ret = copy_file_range(from_fd, NULL, to_fd, NULL,
|
||||
SSIZE_MAX, 0);
|
||||
}
|
||||
if (ret == 0) {
|
||||
/* DIGEST_NONE always returns NULL */
|
||||
return (NULL);
|
||||
}
|
||||
if (errno != EINVAL) {
|
||||
serrno = errno;
|
||||
(void)unlink(to_name);
|
||||
errno = serrno;
|
||||
err(EX_OSERR, "%s", to_name);
|
||||
}
|
||||
/* Fall back */
|
||||
}
|
||||
|
||||
digest_init(&ctx);
|
||||
|
||||
done_copy = 0;
|
||||
|
|
Loading…
Reference in a new issue