linux: try preadv64/pwritev64 before preadv/pwritev (#4683)
Fixes: https://github.com/libuv/libuv/issues/4678 Refs: https://github.com/libuv/libuv/issues/4532
This commit is contained in:
parent
82351168b3
commit
a6ddf41edf
@ -461,12 +461,7 @@ static ssize_t uv__pwritev_emul(int fd,
|
|||||||
|
|
||||||
/* The function pointer cache is an uintptr_t because _Atomic void*
|
/* The function pointer cache is an uintptr_t because _Atomic void*
|
||||||
* doesn't work on macos/ios/etc...
|
* doesn't work on macos/ios/etc...
|
||||||
* Disable optimization on armv7 to work around the bug described in
|
|
||||||
* https://github.com/libuv/libuv/issues/4532
|
|
||||||
*/
|
*/
|
||||||
#if defined(__arm__) && (__ARM_ARCH == 7)
|
|
||||||
__attribute__((optimize("O0")))
|
|
||||||
#endif
|
|
||||||
static ssize_t uv__preadv_or_pwritev(int fd,
|
static ssize_t uv__preadv_or_pwritev(int fd,
|
||||||
const struct iovec* bufs,
|
const struct iovec* bufs,
|
||||||
size_t nbufs,
|
size_t nbufs,
|
||||||
@ -479,7 +474,12 @@ static ssize_t uv__preadv_or_pwritev(int fd,
|
|||||||
p = (void*) atomic_load_explicit(cache, memory_order_relaxed);
|
p = (void*) atomic_load_explicit(cache, memory_order_relaxed);
|
||||||
if (p == NULL) {
|
if (p == NULL) {
|
||||||
#ifdef RTLD_DEFAULT
|
#ifdef RTLD_DEFAULT
|
||||||
p = dlsym(RTLD_DEFAULT, is_pread ? "preadv" : "pwritev");
|
/* Try _LARGEFILE_SOURCE version of preadv/pwritev first,
|
||||||
|
* then fall back to the plain version, for libcs like musl.
|
||||||
|
*/
|
||||||
|
p = dlsym(RTLD_DEFAULT, is_pread ? "preadv64" : "pwritev64");
|
||||||
|
if (p == NULL)
|
||||||
|
p = dlsym(RTLD_DEFAULT, is_pread ? "preadv" : "pwritev");
|
||||||
dlerror(); /* Clear errors. */
|
dlerror(); /* Clear errors. */
|
||||||
#endif /* RTLD_DEFAULT */
|
#endif /* RTLD_DEFAULT */
|
||||||
if (p == NULL)
|
if (p == NULL)
|
||||||
@ -487,10 +487,7 @@ static ssize_t uv__preadv_or_pwritev(int fd,
|
|||||||
atomic_store_explicit(cache, (uintptr_t) p, memory_order_relaxed);
|
atomic_store_explicit(cache, (uintptr_t) p, memory_order_relaxed);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Use memcpy instead of `f = p` to work around a compiler bug,
|
f = p;
|
||||||
* see https://github.com/libuv/libuv/issues/4532
|
|
||||||
*/
|
|
||||||
memcpy(&f, &p, sizeof(p));
|
|
||||||
return f(fd, bufs, nbufs, off);
|
return f(fd, bufs, nbufs, off);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user