[openwrt/openwrt] tools/gnulib: add fallocate-posix module
LEDE Commits
lede-commits at lists.infradead.org
Wed Jun 19 02:22:21 PDT 2024
robimarko pushed a commit to openwrt/openwrt.git, branch main:
https://git.openwrt.org/f07621e10b2ed85391eee7f489d843fb3f01ff6a
commit f07621e10b2ed85391eee7f489d843fb3f01ff6a
Author: Michael Pratt <mcpratt at pm.me>
AuthorDate: Mon Jun 10 04:04:41 2024 -0400
tools/gnulib: add fallocate-posix module
Add a module to gnulib to support posix_fallocate()
for macOS and other systems that are missing it.
Apple-specific code is sourced from Mozilla,
and the rest from glibc, both licensed under LGPL.
Signed-off-by: Michael Pratt <mcpratt at pm.me>
Link: https://github.com/openwrt/openwrt/pull/15690
Signed-off-by: Robert Marko <robimarko at gmail.com>
---
.../patches/320-modules-fallocate-posix.patch | 326 +++++++++++++++++++++
1 file changed, 326 insertions(+)
diff --git a/tools/gnulib/patches/320-modules-fallocate-posix.patch b/tools/gnulib/patches/320-modules-fallocate-posix.patch
new file mode 100644
index 0000000000..e30a7172aa
--- /dev/null
+++ b/tools/gnulib/patches/320-modules-fallocate-posix.patch
@@ -0,0 +1,326 @@
+--- /dev/null
++++ b/modules/fallocate-posix
+@@ -0,0 +1,43 @@
++Description:
++posix_fallocate function that is glibc compatible.
++
++Files:
++lib/posix_fallocate.c
++m4/fcntl_h.m4
++m4/posix_fallocate.m4
++
++Depends-on:
++errno [test $HAVE_FALLOCATE_POSIX = 0 || test $REPLACE_FALLOCATE_POSIX = 1]
++fcntl [test $HAVE_FALLOCATE_POSIX = 0 || test $REPLACE_FALLOCATE_POSIX = 1]
++fstat [test $HAVE_FALLOCATE_POSIX = 0 || test $REPLACE_FALLOCATE_POSIX = 1]
++ftruncate [test $HAVE_FALLOCATE_POSIX = 0 || test $REPLACE_FALLOCATE_POSIX = 1]
++pread [test $HAVE_FALLOCATE_POSIX = 0 || test $REPLACE_FALLOCATE_POSIX = 1]
++pwrite [test $HAVE_FALLOCATE_POSIX = 0 || test $REPLACE_FALLOCATE_POSIX = 1]
++stdint [test $HAVE_FALLOCATE_POSIX = 0 || test $REPLACE_FALLOCATE_POSIX = 1]
++sys_stat [test $HAVE_FALLOCATE_POSIX = 0 || test $REPLACE_FALLOCATE_POSIX = 1]
++unistd [test $HAVE_FALLOCATE_POSIX = 0 || test $REPLACE_FALLOCATE_POSIX = 1]
++fcntl-h
++
++configure.ac:
++gl_FUNC_POSIX_FALLOCATE
++gl_CONDITIONAL([GL_COND_OBJ_POSIX_FALLOCATE],
++ [test $HAVE_FALLOCATE_POSIX = 0 || test $REPLACE_FALLOCATE_POSIX = 1])
++AM_COND_IF([GL_COND_OBJ_POSIX_FALLOCATE], [
++ gl_PREREQ_POSIX_FALLOCATE
++])
++gl_MODULE_INDICATOR([fallocate-posix])
++gl_FCNTL_MODULE_INDICATOR([fallocate-posix])
++
++Makefile.am:
++if GL_COND_OBJ_POSIX_FALLOCATE
++lib_SOURCES += posix_fallocate.c
++endif
++
++Include:
++<fcntl.h>
++
++License:
++LGPLv2+
++
++Maintainer:
++all
+--- /dev/null
++++ b/m4/posix_fallocate.m4
+@@ -0,0 +1,20 @@
++# posix_fallocate.m4 serial 1
++dnl Copyright (C) 2024 Free Software Foundation, Inc.
++dnl This file is free software; the Free Software Foundation
++dnl gives unlimited permission to copy and/or distribute it,
++dnl with or without modifications, as long as this notice is preserved.
++
++AC_DEFUN([gl_FUNC_POSIX_FALLOCATE],
++[
++ AC_REQUIRE([gl_FCNTL_H_DEFAULTS])
++ gl_CHECK_FUNCS_ANDROID([posix_fallocate], [[#include <fcntl.h>]])
++ if test "$ac_cv_func_posix_fallocate" = no; then
++ HAVE_FALLOCATE_POSIX=0
++ case "$gl_cv_onwards_func_posix_fallocate" in
++ future*) REPLACE_FALLOCATE_POSIX=1 ;;
++ esac
++ fi
++])
++
++# Prerequisites of lib/posix_fallocate.c.
++AC_DEFUN([gl_PREREQ_POSIX_FALLOCATE], [:])
+--- a/m4/fcntl_h.m4
++++ b/m4/fcntl_h.m4
+@@ -23,7 +23,7 @@ AC_DEFUN_ONCE([gl_FCNTL_H],
+ dnl corresponding gnulib module is not in use, if it is not common
+ dnl enough to be declared everywhere.
+ gl_WARN_ON_USE_PREPARE([[#include <fcntl.h>
+- ]], [fcntl openat])
++ ]], [fcntl openat posix_fallocate])
+ ])
+
+ # gl_FCNTL_MODULE_INDICATOR([modulename])
+@@ -50,6 +50,7 @@ AC_DEFUN([gl_FCNTL_H_REQUIRE_DEFAULTS],
+ gl_MODULE_INDICATOR_INIT_VARIABLE([GNULIB_NONBLOCKING])
+ gl_MODULE_INDICATOR_INIT_VARIABLE([GNULIB_OPEN])
+ gl_MODULE_INDICATOR_INIT_VARIABLE([GNULIB_OPENAT])
++ gl_MODULE_INDICATOR_INIT_VARIABLE([GNULIB_FALLOCATE_POSIX])
+ dnl Support Microsoft deprecated alias function names by default.
+ gl_MODULE_INDICATOR_INIT_VARIABLE([GNULIB_MDA_CREAT], [1])
+ gl_MODULE_INDICATOR_INIT_VARIABLE([GNULIB_MDA_OPEN], [1])
+@@ -61,10 +62,12 @@ AC_DEFUN([gl_FCNTL_H_REQUIRE_DEFAULTS],
+ AC_DEFUN([gl_FCNTL_H_DEFAULTS],
+ [
+ dnl Assume proper GNU behavior unless another module says otherwise.
+- HAVE_FCNTL=1; AC_SUBST([HAVE_FCNTL])
+- HAVE_OPENAT=1; AC_SUBST([HAVE_OPENAT])
+- REPLACE_CREAT=0; AC_SUBST([REPLACE_CREAT])
+- REPLACE_FCNTL=0; AC_SUBST([REPLACE_FCNTL])
+- REPLACE_OPEN=0; AC_SUBST([REPLACE_OPEN])
+- REPLACE_OPENAT=0; AC_SUBST([REPLACE_OPENAT])
++ HAVE_FCNTL=1; AC_SUBST([HAVE_FCNTL])
++ HAVE_OPENAT=1; AC_SUBST([HAVE_OPENAT])
++ HAVE_FALLOCATE_POSIX=1; AC_SUBST([HAVE_FALLOCATE_POSIX])
++ REPLACE_CREAT=0; AC_SUBST([REPLACE_CREAT])
++ REPLACE_FCNTL=0; AC_SUBST([REPLACE_FCNTL])
++ REPLACE_OPEN=0; AC_SUBST([REPLACE_OPEN])
++ REPLACE_OPENAT=0; AC_SUBST([REPLACE_OPENAT])
++ REPLACE_FALLOCATE_POSIX=0; AC_SUBST([REPLACE_FALLOCATE_POSIX])
+ ])
+--- a/modules/fcntl-h
++++ b/modules/fcntl-h
+@@ -40,14 +40,17 @@ fcntl.h: fcntl.in.h $(top_builddir)/conf
+ -e 's/@''GNULIB_NONBLOCKING''@/$(GNULIB_NONBLOCKING)/g' \
+ -e 's/@''GNULIB_OPEN''@/$(GNULIB_OPEN)/g' \
+ -e 's/@''GNULIB_OPENAT''@/$(GNULIB_OPENAT)/g' \
++ -e 's/@''GNULIB_FALLOCATE_POSIX''@/$(GNULIB_FALLOCATE_POSIX)/g' \
+ -e 's/@''GNULIB_MDA_CREAT''@/$(GNULIB_MDA_CREAT)/g' \
+ -e 's/@''GNULIB_MDA_OPEN''@/$(GNULIB_MDA_OPEN)/g' \
+ -e 's|@''HAVE_FCNTL''@|$(HAVE_FCNTL)|g' \
+ -e 's|@''HAVE_OPENAT''@|$(HAVE_OPENAT)|g' \
++ -e 's|@''HAVE_FALLOCATE_POSIX''@|$(HAVE_FALLOCATE_POSIX)|g' \
+ -e 's|@''REPLACE_CREAT''@|$(REPLACE_CREAT)|g' \
+ -e 's|@''REPLACE_FCNTL''@|$(REPLACE_FCNTL)|g' \
+ -e 's|@''REPLACE_OPEN''@|$(REPLACE_OPEN)|g' \
+ -e 's|@''REPLACE_OPENAT''@|$(REPLACE_OPENAT)|g' \
++ -e 's|@''REPLACE_FALLOCATE_POSIX''@|$(REPLACE_FALLOCATE_POSIX)|g' \
+ -e '/definitions of _GL_FUNCDECL_RPL/r $(CXXDEFS_H)' \
+ -e '/definition of _GL_ARG_NONNULL/r $(ARG_NONNULL_H)' \
+ -e '/definition of _GL_WARN_ON_USE/r $(WARN_ON_USE_H)' \
+--- a/lib/fcntl.in.h
++++ b/lib/fcntl.in.h
+@@ -238,6 +238,33 @@ _GL_WARN_ON_USE (openat, "openat is not
+ # endif
+ #endif
+
++#if @GNULIB_FALLOCATE_POSIX@
++# if @REPLACE_FALLOCATE_POSIX@
++# if !(defined __cplusplus && defined GNULIB_NAMESPACE)
++# undef posix_fallocate
++# define posix_fallocate rpl_posix_fallocate
++# endif
++_GL_FUNCDECL_RPL (posix_fallocate, int,
++ (int fd, off_t offset, off_t len));
++_GL_CXXALIAS_RPL (posix_fallocate, int,
++ (int fd, off_t offset, off_t len));
++# else
++# if !@HAVE_FALLOCATE_POSIX@
++_GL_FUNCDECL_SYS (posix_fallocate, int,
++ (int fd, off_t offset, off_t len));
++# endif
++_GL_CXXALIAS_SYS (posix_fallocate, int,
++ (int fd, off_t offset, off_t len));
++# endif
++_GL_CXXALIASWARN (posix_fallocate);
++#elif defined GNULIB_POSIXCHECK
++# undef posix_fallocate
++# if HAVE_RAW_DECL_POSIX_FALLOCATE
++_GL_WARN_ON_USE (posix_fallocate, "posix_fallocate is not portable - "
++ "use gnulib module fallocate-posix for portability");
++# endif
++#endif
++
+
+ /* Fix up the FD_* macros, only known to be missing on mingw. */
+
+--- /dev/null
++++ b/lib/posix_fallocate.c
+@@ -0,0 +1,150 @@
++/* posix_fallocate function that is glibc compatible.
++
++ Copyright (C) 2024 Free Software Foundation, Inc.
++
++ This file is free software: you can redistribute it and/or modify
++ it under the terms of the GNU Lesser General Public License as
++ published by the Free Software Foundation; either version 2.1 of the
++ License, or (at your option) any later version.
++
++ This file is distributed in the hope that it will be useful,
++ but WITHOUT ANY WARRANTY; without even the implied warranty of
++ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
++ GNU Lesser General Public License for more details.
++
++ You should have received a copy of the GNU Lesser General Public License
++ along with this program. If not, see <https://www.gnu.org/licenses/>. */
++
++#include <config.h>
++
++#include <errno.h>
++#include <fcntl.h>
++#include <unistd.h>
++#include <stdint.h>
++#include <sys/fcntl.h>
++#include <sys/stat.h>
++
++#ifdef __APPLE__
++# include <sys/param.h>
++# include <sys/mount.h>
++#else
++# include <sys/statfs.h>
++#endif
++
++/* Reserve storage for the data of the file associated with FD. This
++ emulation is far from perfect, but the kernel cannot do not much
++ better for network file systems, either. */
++
++int
++posix_fallocate (int fd, off_t offset, off_t len)
++{
++ int ret;
++ struct stat st;
++
++ if (fd < 0 || offset < 0 || len < 0)
++ return EINVAL;
++
++ /* Perform overflow check. The outer cast relies on a GCC
++ extension. */
++ if ((off_t) ((uint64_t) offset + (uint64_t) len) < 0)
++ return EFBIG;
++
++ /* pwrite below will not do the right thing in O_APPEND mode. */
++ {
++ int flags = fcntl (fd, F_GETFL, 0);
++ if (flags < 0 || (flags & O_APPEND) != 0)
++ return EBADF;
++ }
++
++ /* We have to make sure that this is really a regular file. */
++ if (fstat (fd, &st) != 0)
++ return EBADF;
++ if (S_ISFIFO (st.st_mode))
++ return ESPIPE;
++ if (! S_ISREG (st.st_mode))
++ return ENODEV;
++
++ if (len == 0)
++ {
++ /* This is racy, but there is no good way to satisfy a
++ zero-length allocation request. */
++ if (st.st_size < offset)
++ {
++ ret = ftruncate (fd, offset);
++
++ if (ret != 0)
++ ret = errno;
++ return ret;
++ }
++ return ret;
++ }
++
++#ifdef __APPLE__
++ fstore_t sto = {F_ALLOCATECONTIG, F_PEOFPOSMODE, 0, offset + len, 0};
++ /* allocate continuous */
++ ret = fcntl (fd, F_PREALLOCATE, &sto);
++ if (ret < 0)
++ {
++ /* allocate non-continuous */
++ sto.fst_flags = F_ALLOCATEALL;
++ ret = fcntl (fd, F_PREALLOCATE, &sto);
++ if (ret < 0)
++ {
++ return ret;
++ }
++ }
++ ret = ftruncate(fd, offset + len);
++#else
++
++ /* Minimize data transfer for network file systems, by issuing
++ single-byte write requests spaced by the file system block size.
++ (Most local file systems have fallocate support, so this fallback
++ code is not used there.) */
++
++ unsigned increment;
++ {
++ struct statfs f;
++
++ if (fstatfs (fd, &f) != 0)
++ return errno;
++ if (f.f_bsize == 0)
++ increment = 512;
++ else if (f.f_bsize < 4096)
++ increment = f.f_bsize;
++ else
++ /* NFS does not propagate the block size of the underlying
++ storage and may report a much larger value which would still
++ leave holes after the loop below, so we cap the increment at
++ 4096. */
++ increment = 4096;
++ }
++
++ /* Write a null byte to every block. This is racy; we currently
++ lack a better option. Compare-and-swap against a file mapping
++ might additional local races, but requires interposition of a
++ signal handler to catch SIGBUS. */
++ for (offset += (len - 1) % increment; len > 0; offset += increment)
++ {
++ len -= increment;
++
++ if (offset < st.st_size)
++ {
++ unsigned char c;
++ ssize_t rsize = pread (fd, &c, 1, offset);
++
++ if (rsize < 0)
++ return errno;
++ /* If there is a non-zero byte, the block must have been
++ allocated already. */
++ else if (rsize == 1 && c != 0)
++ continue;
++ }
++
++ if (pwrite (fd, "", 1, offset) != 1)
++ return errno;
++ }
++
++#endif /* __APPLE__ */
++
++ return ret;
++}
+--- a/MODULES.html.sh
++++ b/MODULES.html.sh
+@@ -2552,6 +2552,7 @@ func_all_modules ()
+ func_module execve
+ func_module execvp
+ func_module execvpe
++ func_module fallocate-posix
+ func_module fchdir
+ func_module fclose
+ func_module fcntl-h
More information about the lede-commits
mailing list