mirror of
https://github.com/libguestfs/libguestfs.git
synced 2026-03-21 22:53:37 +00:00
build: Remove gnulib.
As part of our efforts to clean up and simplify libguestfs, removing gnulib deletes a large dependency that we mostly no longer use and causes problems for new users trying to build the library from source. A few modules from gnulib are still used (under a compatible license) and these are copied into gnulib/lib/
This commit is contained in:
3
.gitignore
vendored
3
.gitignore
vendored
@@ -205,8 +205,6 @@ Makefile.in
|
||||
/generator/stamp-generator
|
||||
/.gitattributes
|
||||
/.git-module-status
|
||||
/gnulib
|
||||
/GNUmakefile
|
||||
/gobject/bindtests.js
|
||||
/gobject/Guestfs-1.0.gir
|
||||
/gobject/Guestfs-1.0.typelib
|
||||
@@ -266,7 +264,6 @@ Makefile.in
|
||||
/lua/guestfs.so
|
||||
/lua/lua-guestfs.c
|
||||
/m4/ChangeLog
|
||||
/m4/gnulib-cache.m4
|
||||
/m4/intmax.m4
|
||||
/m4/libtool.m4
|
||||
/m4/lt~obsolete.m4
|
||||
|
||||
3
.gitmodules
vendored
3
.gitmodules
vendored
@@ -1,6 +1,3 @@
|
||||
[submodule "gnulib"]
|
||||
path = .gnulib
|
||||
url = https://git.savannah.gnu.org/git/gnulib.git
|
||||
[submodule "common"]
|
||||
path = common
|
||||
url = https://github.com/libguestfs/libguestfs-common
|
||||
|
||||
1
.gnulib
1
.gnulib
Submodule .gnulib deleted from 25a7d014d6
15
Makefile.am
15
Makefile.am
@@ -26,13 +26,8 @@ SUBDIRS = common/mlstdutils generator
|
||||
# tests run.
|
||||
SUBDIRS += test-data
|
||||
|
||||
# Gnulib - must be built and tested before the library.
|
||||
SUBDIRS += gnulib/lib
|
||||
if ENABLE_GNULIB_TESTS
|
||||
SUBDIRS += gnulib/tests
|
||||
endif
|
||||
|
||||
# Basic source for the library.
|
||||
SUBDIRS += gnulib/lib
|
||||
SUBDIRS += common/errnostring common/protocol common/qemuopts
|
||||
SUBDIRS += common/utils
|
||||
SUBDIRS += common/structs
|
||||
@@ -126,12 +121,9 @@ EXTRA_DIST = \
|
||||
.gitignore \
|
||||
.lvimrc \
|
||||
.mailmap \
|
||||
bootstrap \
|
||||
bugs-in-changelog.sh \
|
||||
autogen.sh \
|
||||
bindtests \
|
||||
build-aux/config.rpath \
|
||||
cfg.mk \
|
||||
check-mli.sh \
|
||||
common/.gitignore \
|
||||
common/README \
|
||||
@@ -234,7 +226,7 @@ BUGS: configure.ac
|
||||
docs/C_SOURCE_FILES: configure.ac
|
||||
rm -f $@ $@-t
|
||||
find $(DIST_SUBDIRS) -name '*.[ch]' | \
|
||||
grep -v -E '^(builder/index-parse\.|builder/index-scan\.|examples/|gnulib/|gobject/|java/com_redhat_et_libguestfs|perl/|php/extension/config\.h|ruby/ext/guestfs/extconf\.h|tests/|test-data/|bundled/)' | \
|
||||
grep -v -E '^(builder/index-parse\.|builder/index-scan\.|examples/|gobject/|java/com_redhat_et_libguestfs|perl/|php/extension/config\.h|ruby/ext/guestfs/extconf\.h|tests/|test-data/|bundled/)' | \
|
||||
grep -v -E '/(guestfs|rc)_protocol\.' | \
|
||||
grep -v -E '.*/errnostring\.' | \
|
||||
grep -v -E '.*-gperf\.' | \
|
||||
@@ -247,7 +239,7 @@ po/POTFILES: configure.ac
|
||||
rm -f $@ $@-t
|
||||
cd $(srcdir); \
|
||||
find $(DIST_SUBDIRS) -name '*.c' | \
|
||||
grep -v -E '^(examples|gnulib|perl/(blib|examples)|po-docs|tests|test-data|bundled)/' | \
|
||||
grep -v -E '^(examples|perl/(blib|examples)|po-docs|tests|test-data|bundled)/' | \
|
||||
grep -v -E '/((guestfs|rc)_protocol\.c|dummy\.c)$$' | \
|
||||
grep -v -E '^python/utils\.c$$' | \
|
||||
grep -v -E '^perl/lib/Sys/Guestfs\.c$$' | \
|
||||
@@ -490,7 +482,6 @@ maintainer-check-extra-dist:
|
||||
grep -v '^common/mlxml/' | \
|
||||
grep -v '^intltool-.*\.in' | \
|
||||
grep -v '^\.gitmodules' | \
|
||||
grep -v '^\.gnulib' | \
|
||||
sort > tmp/gitfiles
|
||||
comm -13 tmp/tarfiles tmp/gitfiles > tmp/comm-out
|
||||
@echo Checking for differences between EXTRA_DIST and git ...
|
||||
|
||||
51
autogen.sh
51
autogen.sh
@@ -1,51 +0,0 @@
|
||||
#!/bin/bash -
|
||||
# libguestfs
|
||||
# Copyright (C) 2009 Red Hat Inc.
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# This program 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
#
|
||||
# Rebuild the autotools environment.
|
||||
|
||||
set -e
|
||||
set -v
|
||||
|
||||
# Ensure that whenever we pull in a gnulib update or otherwise change to a
|
||||
# different version (i.e., when switching branches), we also rerun ./bootstrap.
|
||||
curr_status=.git-module-status
|
||||
t=$(git submodule status | grep gnulib | sed 's/^[ +-]//;s/ .*//')
|
||||
if test "$t" = "$(cat $curr_status 2>/dev/null)"; then
|
||||
: # good, it's up to date
|
||||
else
|
||||
echo running bootstrap...
|
||||
./bootstrap && echo "$t" > $curr_status
|
||||
fi
|
||||
|
||||
CONFIGUREDIR=.
|
||||
|
||||
# Run configure in BUILDDIR if it's set
|
||||
if [ ! -z "$BUILDDIR" ]; then
|
||||
mkdir -p $BUILDDIR
|
||||
cd $BUILDDIR
|
||||
|
||||
CONFIGUREDIR=..
|
||||
fi
|
||||
|
||||
# If no arguments were specified and configure has run before, use the previous
|
||||
# arguments
|
||||
if test $# -eq 0 && test -x ./config.status; then
|
||||
./config.status --recheck
|
||||
else
|
||||
$CONFIGUREDIR/configure "$@"
|
||||
fi
|
||||
174
bootstrap
174
bootstrap
@@ -1,174 +0,0 @@
|
||||
#!/bin/sh
|
||||
|
||||
usage() {
|
||||
echo >&2 "\
|
||||
Usage: $0 [OPTION]...
|
||||
Bootstrap this package from the checked-out sources.
|
||||
|
||||
Options:
|
||||
--gnulib-srcdir=DIRNAME specify the local directory where gnulib
|
||||
sources reside. Use this if you already
|
||||
have gnulib sources on your machine, and
|
||||
do not want to waste your bandwidth downloading
|
||||
them again. Defaults to \$GNULIB_SRCDIR
|
||||
"
|
||||
}
|
||||
|
||||
for option
|
||||
do
|
||||
case $option in
|
||||
--help)
|
||||
usage
|
||||
exit;;
|
||||
--gnulib-srcdir=*)
|
||||
GNULIB_SRCDIR=${option#--gnulib-srcdir=};;
|
||||
*)
|
||||
echo >&2 "$0: $option: unknown option"
|
||||
exit 1;;
|
||||
esac
|
||||
done
|
||||
|
||||
cleanup_gnulib() {
|
||||
status=$?
|
||||
rm -fr "$gnulib_path"
|
||||
exit $status
|
||||
}
|
||||
|
||||
git_modules_config () {
|
||||
test -f .gitmodules && git config --file .gitmodules "$@"
|
||||
}
|
||||
|
||||
gnulib_path=$(git_modules_config submodule.gnulib.path)
|
||||
test -z "$gnulib_path" && gnulib_path=gnulib
|
||||
|
||||
# Get gnulib files. Populate $GNULIB_SRCDIR, possibly updating a
|
||||
# submodule, for use in the rest of the script.
|
||||
|
||||
case ${GNULIB_SRCDIR--} in
|
||||
-)
|
||||
if git_modules_config submodule.gnulib.url >/dev/null; then
|
||||
echo "$0: getting gnulib files..."
|
||||
git submodule init -- "$gnulib_path" || exit $?
|
||||
git submodule update -- "$gnulib_path" || exit $?
|
||||
|
||||
elif [ ! -d "$gnulib_path" ]; then
|
||||
echo "$0: getting gnulib files..."
|
||||
|
||||
trap cleanup_gnulib 1 2 13 15
|
||||
|
||||
shallow=
|
||||
git clone -h 2>&1 | grep -- --depth > /dev/null && shallow='--depth 2'
|
||||
git clone $shallow git://git.sv.gnu.org/gnulib "$gnulib_path" ||
|
||||
cleanup_gnulib
|
||||
|
||||
trap - 1 2 13 15
|
||||
fi
|
||||
GNULIB_SRCDIR=$gnulib_path
|
||||
;;
|
||||
*)
|
||||
# Use GNULIB_SRCDIR directly or as a reference.
|
||||
if test -d "$GNULIB_SRCDIR"/.git && \
|
||||
git_modules_config submodule.gnulib.url >/dev/null; then
|
||||
echo "$0: getting gnulib files..."
|
||||
if git submodule -h|grep -- --reference > /dev/null; then
|
||||
# Prefer the one-liner available in git 1.6.4 or newer.
|
||||
git submodule update --init --reference "$GNULIB_SRCDIR" \
|
||||
"$gnulib_path" || exit $?
|
||||
else
|
||||
# This fallback allows at least git 1.5.5.
|
||||
if test -f "$gnulib_path"/gnulib-tool; then
|
||||
# Since file already exists, assume submodule init already complete.
|
||||
git submodule update -- "$gnulib_path" || exit $?
|
||||
else
|
||||
# Older git can't clone into an empty directory.
|
||||
rmdir "$gnulib_path" 2>/dev/null
|
||||
git clone --reference "$GNULIB_SRCDIR" \
|
||||
"$(git_modules_config submodule.gnulib.url)" "$gnulib_path" \
|
||||
&& git submodule init -- "$gnulib_path" \
|
||||
&& git submodule update -- "$gnulib_path" \
|
||||
|| exit $?
|
||||
fi
|
||||
fi
|
||||
GNULIB_SRCDIR=$gnulib_path
|
||||
fi
|
||||
;;
|
||||
esac
|
||||
|
||||
# Autoreconf runs aclocal before libtoolize, which causes spurious
|
||||
# warnings if the initial aclocal is confused by the libtoolized
|
||||
# (or worse out-of-date) macro directory.
|
||||
libtoolize --copy --install
|
||||
|
||||
gnulib_tool=$GNULIB_SRCDIR/gnulib-tool
|
||||
<$gnulib_tool || exit
|
||||
|
||||
modules='
|
||||
accept4
|
||||
areadlinkat
|
||||
base64
|
||||
byteswap
|
||||
c-ctype
|
||||
cloexec
|
||||
closeout
|
||||
connect
|
||||
error
|
||||
fstatat
|
||||
full-read
|
||||
full-write
|
||||
futimens
|
||||
getline
|
||||
getprogname
|
||||
gitlog-to-changelog
|
||||
glob
|
||||
gnumakefile
|
||||
hash
|
||||
hash-pjw
|
||||
human
|
||||
ignore-value
|
||||
intprops
|
||||
lock
|
||||
maintainer-makefile
|
||||
manywarnings
|
||||
memmem
|
||||
mkdtemp
|
||||
mkstemps
|
||||
netdb
|
||||
nonblocking
|
||||
perror
|
||||
pipe2
|
||||
pread
|
||||
readlink
|
||||
select
|
||||
setenv
|
||||
sleep
|
||||
socket
|
||||
strchrnul
|
||||
strerror
|
||||
strndup
|
||||
sys_select
|
||||
sys_types
|
||||
sys_wait
|
||||
tls
|
||||
vasprintf
|
||||
vc-list-files
|
||||
warnings
|
||||
xstrtol
|
||||
xstrtoll
|
||||
xvasprintf
|
||||
'
|
||||
|
||||
# If any tests fail, avoid including them by adding them to
|
||||
# this list.
|
||||
avoid="--avoid=dummy --avoid=getlogin_r-tests"
|
||||
|
||||
$gnulib_tool \
|
||||
$avoid \
|
||||
--with-tests \
|
||||
--m4-base=m4 \
|
||||
--source-base=gnulib/lib \
|
||||
--tests-base=gnulib/tests \
|
||||
--libtool \
|
||||
--import $modules
|
||||
|
||||
# Disable autopoint and libtoolize, since they were already done above.
|
||||
AUTOPOINT=true LIBTOOLIZE=true autoreconf --verbose --install
|
||||
141
cfg.mk
141
cfg.mk
@@ -1,141 +0,0 @@
|
||||
# Customize Makefile.maint. -*- makefile -*-
|
||||
# Copyright (C) 2003-2012 Free Software Foundation, Inc.
|
||||
|
||||
# This program is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation, either version 3 of the License, or
|
||||
# (at your option) any later version.
|
||||
|
||||
# This program 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 General Public License for more details.
|
||||
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
# Use alpha.gnu.org for alpha and beta releases.
|
||||
# Use ftp.gnu.org for major releases.
|
||||
gnu_ftp_host-alpha = alpha.gnu.org
|
||||
gnu_ftp_host-beta = alpha.gnu.org
|
||||
gnu_ftp_host-major = ftp.gnu.org
|
||||
gnu_rel_host = $(gnu_ftp_host-$(RELEASE_TYPE))
|
||||
|
||||
url_dir_list = \
|
||||
ftp://$(gnu_rel_host)/gnu/coreutils
|
||||
|
||||
# Exclude some filenames.
|
||||
exclude_file_name_regexp--sc_bindtextdomain = ^(daemon|erlang|examples|tests)/|/test-
|
||||
exclude_file_name_regexp--sc_error_message_period = ^(generator|php|po-docs)/
|
||||
exclude_file_name_regexp--sc_prohibit_always-defined_macros = ^examples/|^tests/xml/fake-libvirt-xml\.c|^daemon/guestfsd\.c
|
||||
exclude_file_name_regexp--sc_prohibit_doubled_word = ^po/
|
||||
exclude_file_name_regexp--sc_prohibit_empty_lines_at_EOF = ^test-data/|\.patch$|\.png$
|
||||
exclude_file_name_regexp--sc_prohibit_magic_number_exit = ^(po|po-docs)/|\.pod$|^fuse/guestunmount\.c
|
||||
exclude_file_name_regexp--sc_prohibit_strcmp = ^(examples|po-docs)/|\.pod$
|
||||
exclude_file_name_regexp--sc_prohibit_strcmp_and_strncmp = ^(examples|po-docs)/|\.pod$
|
||||
exclude_file_name_regexp--sc_prohibit_strncpy = ^lib/launch-.*\.c$
|
||||
exclude_file_name_regexp--sc_require_config_h = ^examples/|^tests/c-api/test-just-header\.c$
|
||||
exclude_file_name_regexp--sc_require_config_h_first = ^examples/|^tests/c-api/test-just-header\.c$|^python/guestfs-py-byhand\.c$
|
||||
|
||||
# Tests not to run as part of "make distcheck".
|
||||
local-checks-to-skip = \
|
||||
sc_po_check \
|
||||
sc_GPL_version \
|
||||
sc_error_exit_success \
|
||||
sc_file_system \
|
||||
sc_makefile_path_separator_check \
|
||||
sc_obsolete_symbols \
|
||||
sc_prohibit_atoi_atof \
|
||||
sc_prohibit_quote_without_use \
|
||||
sc_prohibit_quotearg_without_use \
|
||||
sc_prohibit_stat_st_blocks \
|
||||
sc_space_tab \
|
||||
sc_two_space_separator_in_usage \
|
||||
sc_error_message_uppercase \
|
||||
sc_program_name \
|
||||
$(disable_temporarily) \
|
||||
sc_useless_cpp_parens \
|
||||
sc_cast_of_argument_to_free
|
||||
|
||||
disable_temporarily = \
|
||||
sc_makefile_check \
|
||||
sc_unmarked_diagnostics \
|
||||
sc_prohibit_ctype_h \
|
||||
sc_prohibit_asprintf \
|
||||
sc_avoid_write
|
||||
|
||||
# Avoid uses of write(2). Either switch to streams (fwrite), or use
|
||||
# the safewrite wrapper.
|
||||
sc_avoid_write:
|
||||
@if $(VC_LIST_EXCEPT) | grep '\.c$$' > /dev/null; then \
|
||||
grep '\<write *(' $$($(VC_LIST_EXCEPT) | grep '\.c$$') && \
|
||||
{ echo "$(ME): the above files use write;" \
|
||||
" consider using the safewrite wrapper instead" \
|
||||
1>&2; exit 1; } || :; \
|
||||
else :; \
|
||||
fi
|
||||
|
||||
# Use STREQ rather than comparing strcmp == 0, or != 0.
|
||||
# Similarly, use STREQLEN or STRPREFIX rather than strncmp.
|
||||
sc_prohibit_strcmp_and_strncmp:
|
||||
@grep -nE '! *strn?cmp *\(|\<strn?cmp *\([^)]+\) *==' \
|
||||
$$($(VC_LIST_EXCEPT)) \
|
||||
| grep -vE ':# *define STREQ(LEN)?\(' && \
|
||||
{ echo '$(ME): use STREQ(LEN) in place of the above uses of strcmp(strncmp)' \
|
||||
1>&2; exit 1; } || :
|
||||
|
||||
# Use virAsprintf rather than a'sprintf since *strp is undefined on error.
|
||||
sc_prohibit_asprintf:
|
||||
@re='\<[a]sprintf\>' \
|
||||
msg='use virAsprintf, not a'sprintf \
|
||||
$(_prohibit_regexp)
|
||||
|
||||
# Prohibit the inclusion of <ctype.h>.
|
||||
sc_prohibit_ctype_h:
|
||||
@grep -E '^# *include *<ctype\.h>' $$($(VC_LIST_EXCEPT)) && \
|
||||
{ echo "$(ME): don't use ctype.h; instead, use c-ctype.h" \
|
||||
1>&2; exit 1; } || :
|
||||
|
||||
ctype_re = isalnum|isalpha|isascii|isblank|iscntrl|isdigit|isgraph|islower\
|
||||
|isprint|ispunct|isspace|isupper|isxdigit|tolower|toupper
|
||||
|
||||
sc_avoid_ctype_macros:
|
||||
@grep -E '\b($(ctype_re)) *\(' /dev/null \
|
||||
$$($(VC_LIST_EXCEPT)) && \
|
||||
{ echo "$(ME): don't use ctype macros (use c-ctype.h)" \
|
||||
1>&2; exit 1; } || :
|
||||
|
||||
sc_prohibit_virBufferAdd_with_string_literal:
|
||||
@prohibit='\<virBufferAdd *\([^,]+, *"[^"]' \
|
||||
halt='use virBufferAddLit, not virBufferAdd, with a string literal' \
|
||||
$(_sc_search_regexp)
|
||||
|
||||
# Not only do they fail to deal well with ipv6, but the gethostby*
|
||||
# functions are also not thread-safe.
|
||||
sc_prohibit_gethostby:
|
||||
@prohibit='\<gethostby(addr|name2?) *\(' \
|
||||
halt='use getaddrinfo, not gethostby*' \
|
||||
$(_sc_search_regexp)
|
||||
|
||||
# We don't use this feature of maint.mk.
|
||||
prev_version_file = /dev/null
|
||||
|
||||
ifeq (0,$(MAKELEVEL))
|
||||
_curr_status = .git-module-status
|
||||
# The sed filter accommodates those who check out on a commit from which
|
||||
# no tag is reachable. In that case, git submodule status prints a "-"
|
||||
# in column 1 and does not print a "git describe"-style string after the
|
||||
# submodule name. Contrast these:
|
||||
# -b653eda3ac4864de205419d9f41eec267cb89eeb .gnulib
|
||||
# b653eda3ac4864de205419d9f41eec267cb89eeb .gnulib (v0.0-2286-gb653eda)
|
||||
# $ cat .git-module-status
|
||||
# b653eda3ac4864de205419d9f41eec267cb89eeb
|
||||
_submodule_hash = sed 's/^[ +-]//;s/ .*//'
|
||||
_update_required := $(shell \
|
||||
actual=$$(git submodule status | grep gnulib | $(_submodule_hash)); \
|
||||
stamp="$$($(_submodule_hash) $(_curr_status) 2>/dev/null)"; \
|
||||
test "$$stamp" = "$$actual"; echo $$?)
|
||||
ifeq (1,$(_update_required))
|
||||
$(error gnulib update required; run ./autogen.sh first)
|
||||
endif
|
||||
endif
|
||||
@@ -85,11 +85,6 @@ PACKAGE_VERSION_FULL="libguestfs_major.libguestfs_minor.libguestfs_release${libg
|
||||
AC_DEFINE_UNQUOTED([PACKAGE_VERSION_FULL],["$PACKAGE_VERSION_FULL"],[Full version string.])
|
||||
AC_SUBST([PACKAGE_VERSION_FULL])
|
||||
|
||||
dnl Early gnulib initialization.
|
||||
HEADING([Configuring Gnulib])
|
||||
gl_EARLY
|
||||
gl_INIT
|
||||
|
||||
dnl Check for external programs required to either build or run
|
||||
dnl libguestfs.
|
||||
HEADING([Checking for external programs])
|
||||
@@ -242,7 +237,6 @@ AC_CONFIG_FILES([Makefile
|
||||
fuse/Makefile
|
||||
generator/Makefile
|
||||
gnulib/lib/Makefile
|
||||
gnulib/tests/Makefile
|
||||
gobject/libguestfs-gobject-1.0.pc
|
||||
gobject/Makefile
|
||||
golang/Makefile
|
||||
|
||||
@@ -25,14 +25,15 @@
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdarg.h>
|
||||
#include <string.h>
|
||||
#include <unistd.h>
|
||||
#include <fcntl.h>
|
||||
#include <error.h>
|
||||
#include <errno.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/wait.h>
|
||||
#include <error.h>
|
||||
#include <errno.h>
|
||||
|
||||
#include "ignore-value.h"
|
||||
|
||||
|
||||
@@ -49,7 +49,6 @@
|
||||
|
||||
#include "c-ctype.h"
|
||||
#include "ignore-value.h"
|
||||
#include "sockets.h"
|
||||
|
||||
#include "daemon.h"
|
||||
|
||||
|
||||
@@ -24,8 +24,8 @@
|
||||
#include <fcntl.h>
|
||||
#include <unistd.h>
|
||||
#include <limits.h>
|
||||
|
||||
#include "areadlink.h"
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
|
||||
#include "daemon.h"
|
||||
#include "actions.h"
|
||||
@@ -47,20 +47,36 @@ do_internal_readlinklist (const char *path, char *const *names)
|
||||
}
|
||||
|
||||
for (i = 0; names[i] != NULL; ++i) {
|
||||
CLEANUP_FREE char *link = NULL;
|
||||
struct stat statbuf;
|
||||
size_t n;
|
||||
ssize_t r;
|
||||
|
||||
/* Because of the way this function is intended to be used,
|
||||
* we actually expect to see errors here, and they are not fatal.
|
||||
*/
|
||||
CLEANUP_FREE char *link = areadlinkat (fd_cwd, names[i]);
|
||||
|
||||
if (link != NULL) {
|
||||
if (add_string (&ret, link) == -1) {
|
||||
add_string_failed:
|
||||
if (fstatat (fd_cwd, names[i], &statbuf, AT_SYMLINK_NOFOLLOW) == -1) {
|
||||
add_empty_string:
|
||||
if (add_string (&ret, "") == -1) {
|
||||
close (fd_cwd);
|
||||
return NULL;
|
||||
}
|
||||
} else {
|
||||
if (add_string (&ret, "") == -1)
|
||||
goto add_string_failed;
|
||||
}
|
||||
if (!S_ISLNK (statbuf.st_mode))
|
||||
goto add_empty_string;
|
||||
n = statbuf.st_size;
|
||||
link = malloc (n+1);
|
||||
if (link == NULL)
|
||||
goto add_empty_string;
|
||||
r = readlinkat (fd_cwd, names[i], link, n);
|
||||
if (r == -1 || r != n)
|
||||
goto add_empty_string;
|
||||
link[n] = '\0';
|
||||
|
||||
if (add_string (&ret, link) == -1) {
|
||||
close (fd_cwd);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -402,7 +402,8 @@ git.
|
||||
git clone https://github.com/libguestfs/libguestfs
|
||||
cd libguestfs
|
||||
git submodule update --init
|
||||
CFLAGS=-fPIC ./autogen.sh
|
||||
autoreconf -i
|
||||
./configure CFLAGS=-fPIC
|
||||
make
|
||||
|
||||
=head1 BUILDING FROM TARBALLS
|
||||
@@ -497,11 +498,11 @@ are ignored by git. These files can contain local configuration or
|
||||
scripts that you need to build libguestfs.
|
||||
|
||||
I have a file called F<localconfigure> which is a simple wrapper
|
||||
around F<autogen.sh> containing local configure customizations that I
|
||||
around F<configure> containing local configure customizations that I
|
||||
need. It looks like this:
|
||||
|
||||
. localenv
|
||||
./autogen.sh \
|
||||
./configure.sh \
|
||||
-C \
|
||||
--enable-werror \
|
||||
"$@"
|
||||
@@ -570,11 +571,6 @@ OCaml tools.
|
||||
|
||||
Disable FUSE support in the API and the L<guestmount(1)> tool.
|
||||
|
||||
=item B<--disable-gnulib-tests>
|
||||
|
||||
On some platforms the GNUlib test suite can be flaky. This disables
|
||||
it, since errors in the GNUlib test suite are often not important.
|
||||
|
||||
=item B<--disable-static>
|
||||
|
||||
Don’t build a static linked version of the libguestfs library.
|
||||
|
||||
@@ -403,7 +403,7 @@ should contain:
|
||||
|
||||
source localenv
|
||||
#export PATH=/tmp/qemu/x86_64-softmmu:$PATH
|
||||
./autogen.sh --prefix /usr "$@"
|
||||
./configure --prefix /usr "$@"
|
||||
|
||||
Make C<localconfigure> executable.
|
||||
|
||||
@@ -431,7 +431,7 @@ enough supermin installed, then see the previous question.
|
||||
If supermin 5 doesn't support your distro at all, you will need to use
|
||||
the "fixed appliance method" where you use a pre-compiled binary
|
||||
appliance. To build libguestfs without supermin, you need to pass
|
||||
C<--disable-appliance --disable-daemon> to either F<./autogen.sh> or
|
||||
C<--disable-appliance --disable-daemon> to either F<./configure> or
|
||||
F<./configure> (depending whether you are building respectively from
|
||||
git or from tarballs). Then, when using libguestfs, you B<must> set
|
||||
the C<LIBGUESTFS_PATH> environment variable to the directory of a
|
||||
|
||||
@@ -14,7 +14,7 @@ L<https://github.com/libguestfs/libguestfs>
|
||||
Large amounts of boilerplate code in libguestfs (RPC, bindings,
|
||||
documentation) are generated. This means that many source files will
|
||||
appear to be missing from a straightforward git checkout. You have to
|
||||
run the generator (C<./autogen.sh && make -C generator>) in order to
|
||||
run the generator (C<./configure && make -C generator>) in order to
|
||||
create those files.
|
||||
|
||||
Libguestfs uses an autotools-based build system, with the main files
|
||||
@@ -250,11 +250,6 @@ large amounts of boilerplate C code for things like RPC and bindings.
|
||||
|
||||
L<virt-get-kernel(1)> command and documentation.
|
||||
|
||||
=item F<gnulib>
|
||||
|
||||
Gnulib is used as a portability library. A copy of gnulib is included
|
||||
under here.
|
||||
|
||||
=item F<inspector>
|
||||
|
||||
L<virt-inspector(1)>, the virtual machine image inspector.
|
||||
@@ -799,7 +794,7 @@ the libguestfs source tree must be the same.
|
||||
|
||||
Do:
|
||||
|
||||
./autogen.sh
|
||||
./configure
|
||||
make clean ||:
|
||||
make
|
||||
make installcheck
|
||||
@@ -921,7 +916,7 @@ command, the list of objects and the C<-cclib> libraries in the
|
||||
correct order otherwise.
|
||||
|
||||
virt_customize_LINK = \
|
||||
$(top_builddir)/ocaml-link.sh -cclib '-lutils -lgnu' -- ...
|
||||
$(top_builddir)/ocaml-link.sh -cclib '-lutils' -- ...
|
||||
|
||||
The actual rules, which you can examine in F<customize/Makefile.am>, are a
|
||||
little bit more complicated than this because they have to handle:
|
||||
@@ -1029,10 +1024,6 @@ Finalize F<guestfs-release-notes.pod>
|
||||
|
||||
=item *
|
||||
|
||||
Consider updating gnulib to latest upstream version.
|
||||
|
||||
=item *
|
||||
|
||||
Create new stable and development directories under
|
||||
L<http://libguestfs.org/download>.
|
||||
|
||||
|
||||
@@ -33,6 +33,7 @@
|
||||
#include <signal.h>
|
||||
#include <errno.h>
|
||||
#include <error.h>
|
||||
#include <limits.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/wait.h>
|
||||
#include <locale.h>
|
||||
@@ -52,7 +53,6 @@
|
||||
#include "progress.h"
|
||||
|
||||
#include "c-ctype.h"
|
||||
#include "closeout.h"
|
||||
#include "ignore-value.h"
|
||||
#include "getprogname.h"
|
||||
|
||||
@@ -178,9 +178,6 @@ usage (int status)
|
||||
int
|
||||
main (int argc, char *argv[])
|
||||
{
|
||||
/* Initialize gnulib closeout module. */
|
||||
atexit (close_stdout);
|
||||
|
||||
setlocale (LC_ALL, "");
|
||||
bindtextdomain (PACKAGE, LOCALEBASEDIR);
|
||||
textdomain (PACKAGE);
|
||||
|
||||
@@ -30,6 +30,7 @@
|
||||
#include <error.h>
|
||||
#include <getopt.h>
|
||||
#include <signal.h>
|
||||
#include <limits.h>
|
||||
#include <locale.h>
|
||||
#include <libintl.h>
|
||||
|
||||
|
||||
@@ -31,6 +31,7 @@
|
||||
#include <locale.h>
|
||||
#include <libintl.h>
|
||||
#include <poll.h>
|
||||
#include <limits.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/wait.h>
|
||||
|
||||
|
||||
57
gnulib/lib/Makefile.am
Normal file
57
gnulib/lib/Makefile.am
Normal file
@@ -0,0 +1,57 @@
|
||||
# libguestfs
|
||||
# Copyright (C) 2017-2021 Red Hat Inc.
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# This program 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
|
||||
# This directory contains some dependencies originally from gnulib.
|
||||
# The aim is for everything in this directory to eventually go away,
|
||||
# probably being moved to common/utils.
|
||||
|
||||
include $(top_srcdir)/subdir-rules.mk
|
||||
|
||||
noinst_LTLIBRARIES = libgnu.la
|
||||
libgnu_la_SOURCES = \
|
||||
base64.c \
|
||||
base64.h \
|
||||
bitrotate.h \
|
||||
c-ctype.h \
|
||||
cloexec.c \
|
||||
cloexec.h \
|
||||
full-read.c \
|
||||
full-read.h \
|
||||
full-write.c \
|
||||
full-write.h \
|
||||
getprogname.h \
|
||||
hash.c \
|
||||
hash.h \
|
||||
hash-pjw.c \
|
||||
hash-pjw.h \
|
||||
ignore-value.h \
|
||||
nonblocking.c \
|
||||
nonblocking.h \
|
||||
safe-read.c \
|
||||
safe-read.h \
|
||||
safe-write.c \
|
||||
safe-write.h \
|
||||
xalloc-oversized.h \
|
||||
xstrtol.c \
|
||||
xstrtol.h \
|
||||
xstrtoll.c \
|
||||
xstrtoul.c \
|
||||
xstrtoull.c \
|
||||
xstrtoumax.c
|
||||
libutils_la_CFLAGS = \
|
||||
$(WARN_CFLAGS) $(WERROR_CFLAGS) \
|
||||
$(GCC_VISIBILITY_HIDDEN)
|
||||
612
gnulib/lib/base64.c
Normal file
612
gnulib/lib/base64.c
Normal file
@@ -0,0 +1,612 @@
|
||||
/* base64.c -- Encode binary data using printable characters.
|
||||
Copyright (C) 1999-2001, 2004-2006, 2009-2021 Free Software Foundation, Inc.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
/* Written by Simon Josefsson. Partially adapted from GNU MailUtils
|
||||
* (mailbox/filter_trans.c, as of 2004-11-28). Improved by review
|
||||
* from Paul Eggert, Bruno Haible, and Stepan Kasal.
|
||||
*
|
||||
* See also RFC 4648 <https://www.ietf.org/rfc/rfc4648.txt>.
|
||||
*
|
||||
* Be careful with error checking. Here is how you would typically
|
||||
* use these functions:
|
||||
*
|
||||
* bool ok = base64_decode_alloc (in, inlen, &out, &outlen);
|
||||
* if (!ok)
|
||||
* FAIL: input was not valid base64
|
||||
* if (out == NULL)
|
||||
* FAIL: memory allocation error
|
||||
* OK: data in OUT/OUTLEN
|
||||
*
|
||||
* size_t outlen = base64_encode_alloc (in, inlen, &out);
|
||||
* if (out == NULL && outlen == 0 && inlen != 0)
|
||||
* FAIL: input too long
|
||||
* if (out == NULL)
|
||||
* FAIL: memory allocation error
|
||||
* OK: data in OUT/OUTLEN.
|
||||
*
|
||||
*/
|
||||
|
||||
#include <config.h>
|
||||
|
||||
/* Get prototype. */
|
||||
#include "base64.h"
|
||||
|
||||
/* Get malloc. */
|
||||
#include <stdlib.h>
|
||||
|
||||
/* Get UCHAR_MAX. */
|
||||
#include <limits.h>
|
||||
|
||||
#include <string.h>
|
||||
|
||||
/* C89 compliant way to cast 'char' to 'unsigned char'. */
|
||||
static unsigned char
|
||||
to_uchar (char ch)
|
||||
{
|
||||
return ch;
|
||||
}
|
||||
|
||||
static const char b64c[64] =
|
||||
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
|
||||
|
||||
/* Base64 encode IN array of size INLEN into OUT array. OUT needs
|
||||
to be of length >= BASE64_LENGTH(INLEN), and INLEN needs to be
|
||||
a multiple of 3. */
|
||||
static void
|
||||
base64_encode_fast (const char *restrict in, size_t inlen, char *restrict out)
|
||||
{
|
||||
while (inlen)
|
||||
{
|
||||
*out++ = b64c[(to_uchar (in[0]) >> 2) & 0x3f];
|
||||
*out++ = b64c[((to_uchar (in[0]) << 4) + (to_uchar (in[1]) >> 4)) & 0x3f];
|
||||
*out++ = b64c[((to_uchar (in[1]) << 2) + (to_uchar (in[2]) >> 6)) & 0x3f];
|
||||
*out++ = b64c[to_uchar (in[2]) & 0x3f];
|
||||
|
||||
inlen -= 3;
|
||||
in += 3;
|
||||
}
|
||||
}
|
||||
|
||||
/* Base64 encode IN array of size INLEN into OUT array of size OUTLEN.
|
||||
If OUTLEN is less than BASE64_LENGTH(INLEN), write as many bytes as
|
||||
possible. If OUTLEN is larger than BASE64_LENGTH(INLEN), also zero
|
||||
terminate the output buffer. */
|
||||
void
|
||||
base64_encode (const char *restrict in, size_t inlen,
|
||||
char *restrict out, size_t outlen)
|
||||
{
|
||||
/* Note this outlen constraint can be enforced at compile time.
|
||||
I.E. that the output buffer is exactly large enough to hold
|
||||
the encoded inlen bytes. The inlen constraints (of corresponding
|
||||
to outlen, and being a multiple of 3) can change at runtime
|
||||
at the end of input. However the common case when reading
|
||||
large inputs is to have both constraints satisfied, so we depend
|
||||
on both in base_encode_fast(). */
|
||||
if (outlen % 4 == 0 && inlen == outlen / 4 * 3)
|
||||
{
|
||||
base64_encode_fast (in, inlen, out);
|
||||
return;
|
||||
}
|
||||
|
||||
while (inlen && outlen)
|
||||
{
|
||||
*out++ = b64c[(to_uchar (in[0]) >> 2) & 0x3f];
|
||||
if (!--outlen)
|
||||
break;
|
||||
*out++ = b64c[((to_uchar (in[0]) << 4)
|
||||
+ (--inlen ? to_uchar (in[1]) >> 4 : 0))
|
||||
& 0x3f];
|
||||
if (!--outlen)
|
||||
break;
|
||||
*out++ =
|
||||
(inlen
|
||||
? b64c[((to_uchar (in[1]) << 2)
|
||||
+ (--inlen ? to_uchar (in[2]) >> 6 : 0))
|
||||
& 0x3f]
|
||||
: '=');
|
||||
if (!--outlen)
|
||||
break;
|
||||
*out++ = inlen ? b64c[to_uchar (in[2]) & 0x3f] : '=';
|
||||
if (!--outlen)
|
||||
break;
|
||||
if (inlen)
|
||||
inlen--;
|
||||
if (inlen)
|
||||
in += 3;
|
||||
}
|
||||
|
||||
if (outlen)
|
||||
*out = '\0';
|
||||
}
|
||||
|
||||
/* Allocate a buffer and store zero terminated base64 encoded data
|
||||
from array IN of size INLEN, returning BASE64_LENGTH(INLEN), i.e.,
|
||||
the length of the encoded data, excluding the terminating zero. On
|
||||
return, the OUT variable will hold a pointer to newly allocated
|
||||
memory that must be deallocated by the caller. If output string
|
||||
length would overflow, 0 is returned and OUT is set to NULL. If
|
||||
memory allocation failed, OUT is set to NULL, and the return value
|
||||
indicates length of the requested memory block, i.e.,
|
||||
BASE64_LENGTH(inlen) + 1. */
|
||||
size_t
|
||||
base64_encode_alloc (const char *in, size_t inlen, char **out)
|
||||
{
|
||||
size_t outlen = 1 + BASE64_LENGTH (inlen);
|
||||
|
||||
/* Check for overflow in outlen computation.
|
||||
*
|
||||
* If there is no overflow, outlen >= inlen.
|
||||
*
|
||||
* If the operation (inlen + 2) overflows then it yields at most +1, so
|
||||
* outlen is 0.
|
||||
*
|
||||
* If the multiplication overflows, we lose at least half of the
|
||||
* correct value, so the result is < ((inlen + 2) / 3) * 2, which is
|
||||
* less than (inlen + 2) * 0.66667, which is less than inlen as soon as
|
||||
* (inlen > 4).
|
||||
*/
|
||||
if (inlen > outlen)
|
||||
{
|
||||
*out = NULL;
|
||||
return 0;
|
||||
}
|
||||
|
||||
*out = malloc (outlen);
|
||||
if (!*out)
|
||||
return outlen;
|
||||
|
||||
base64_encode (in, inlen, *out, outlen);
|
||||
|
||||
return outlen - 1;
|
||||
}
|
||||
|
||||
/* With this approach this file works independent of the charset used
|
||||
(think EBCDIC). However, it does assume that the characters in the
|
||||
Base64 alphabet (A-Za-z0-9+/) are encoded in 0..255. POSIX
|
||||
1003.1-2001 require that char and unsigned char are 8-bit
|
||||
quantities, though, taking care of that problem. But this may be a
|
||||
potential problem on non-POSIX C99 platforms.
|
||||
|
||||
IBM C V6 for AIX mishandles "#define B64(x) ...'x'...", so use "_"
|
||||
as the formal parameter rather than "x". */
|
||||
#define B64(_) \
|
||||
((_) == 'A' ? 0 \
|
||||
: (_) == 'B' ? 1 \
|
||||
: (_) == 'C' ? 2 \
|
||||
: (_) == 'D' ? 3 \
|
||||
: (_) == 'E' ? 4 \
|
||||
: (_) == 'F' ? 5 \
|
||||
: (_) == 'G' ? 6 \
|
||||
: (_) == 'H' ? 7 \
|
||||
: (_) == 'I' ? 8 \
|
||||
: (_) == 'J' ? 9 \
|
||||
: (_) == 'K' ? 10 \
|
||||
: (_) == 'L' ? 11 \
|
||||
: (_) == 'M' ? 12 \
|
||||
: (_) == 'N' ? 13 \
|
||||
: (_) == 'O' ? 14 \
|
||||
: (_) == 'P' ? 15 \
|
||||
: (_) == 'Q' ? 16 \
|
||||
: (_) == 'R' ? 17 \
|
||||
: (_) == 'S' ? 18 \
|
||||
: (_) == 'T' ? 19 \
|
||||
: (_) == 'U' ? 20 \
|
||||
: (_) == 'V' ? 21 \
|
||||
: (_) == 'W' ? 22 \
|
||||
: (_) == 'X' ? 23 \
|
||||
: (_) == 'Y' ? 24 \
|
||||
: (_) == 'Z' ? 25 \
|
||||
: (_) == 'a' ? 26 \
|
||||
: (_) == 'b' ? 27 \
|
||||
: (_) == 'c' ? 28 \
|
||||
: (_) == 'd' ? 29 \
|
||||
: (_) == 'e' ? 30 \
|
||||
: (_) == 'f' ? 31 \
|
||||
: (_) == 'g' ? 32 \
|
||||
: (_) == 'h' ? 33 \
|
||||
: (_) == 'i' ? 34 \
|
||||
: (_) == 'j' ? 35 \
|
||||
: (_) == 'k' ? 36 \
|
||||
: (_) == 'l' ? 37 \
|
||||
: (_) == 'm' ? 38 \
|
||||
: (_) == 'n' ? 39 \
|
||||
: (_) == 'o' ? 40 \
|
||||
: (_) == 'p' ? 41 \
|
||||
: (_) == 'q' ? 42 \
|
||||
: (_) == 'r' ? 43 \
|
||||
: (_) == 's' ? 44 \
|
||||
: (_) == 't' ? 45 \
|
||||
: (_) == 'u' ? 46 \
|
||||
: (_) == 'v' ? 47 \
|
||||
: (_) == 'w' ? 48 \
|
||||
: (_) == 'x' ? 49 \
|
||||
: (_) == 'y' ? 50 \
|
||||
: (_) == 'z' ? 51 \
|
||||
: (_) == '0' ? 52 \
|
||||
: (_) == '1' ? 53 \
|
||||
: (_) == '2' ? 54 \
|
||||
: (_) == '3' ? 55 \
|
||||
: (_) == '4' ? 56 \
|
||||
: (_) == '5' ? 57 \
|
||||
: (_) == '6' ? 58 \
|
||||
: (_) == '7' ? 59 \
|
||||
: (_) == '8' ? 60 \
|
||||
: (_) == '9' ? 61 \
|
||||
: (_) == '+' ? 62 \
|
||||
: (_) == '/' ? 63 \
|
||||
: -1)
|
||||
|
||||
static const signed char b64[0x100] = {
|
||||
B64 (0), B64 (1), B64 (2), B64 (3),
|
||||
B64 (4), B64 (5), B64 (6), B64 (7),
|
||||
B64 (8), B64 (9), B64 (10), B64 (11),
|
||||
B64 (12), B64 (13), B64 (14), B64 (15),
|
||||
B64 (16), B64 (17), B64 (18), B64 (19),
|
||||
B64 (20), B64 (21), B64 (22), B64 (23),
|
||||
B64 (24), B64 (25), B64 (26), B64 (27),
|
||||
B64 (28), B64 (29), B64 (30), B64 (31),
|
||||
B64 (32), B64 (33), B64 (34), B64 (35),
|
||||
B64 (36), B64 (37), B64 (38), B64 (39),
|
||||
B64 (40), B64 (41), B64 (42), B64 (43),
|
||||
B64 (44), B64 (45), B64 (46), B64 (47),
|
||||
B64 (48), B64 (49), B64 (50), B64 (51),
|
||||
B64 (52), B64 (53), B64 (54), B64 (55),
|
||||
B64 (56), B64 (57), B64 (58), B64 (59),
|
||||
B64 (60), B64 (61), B64 (62), B64 (63),
|
||||
B64 (64), B64 (65), B64 (66), B64 (67),
|
||||
B64 (68), B64 (69), B64 (70), B64 (71),
|
||||
B64 (72), B64 (73), B64 (74), B64 (75),
|
||||
B64 (76), B64 (77), B64 (78), B64 (79),
|
||||
B64 (80), B64 (81), B64 (82), B64 (83),
|
||||
B64 (84), B64 (85), B64 (86), B64 (87),
|
||||
B64 (88), B64 (89), B64 (90), B64 (91),
|
||||
B64 (92), B64 (93), B64 (94), B64 (95),
|
||||
B64 (96), B64 (97), B64 (98), B64 (99),
|
||||
B64 (100), B64 (101), B64 (102), B64 (103),
|
||||
B64 (104), B64 (105), B64 (106), B64 (107),
|
||||
B64 (108), B64 (109), B64 (110), B64 (111),
|
||||
B64 (112), B64 (113), B64 (114), B64 (115),
|
||||
B64 (116), B64 (117), B64 (118), B64 (119),
|
||||
B64 (120), B64 (121), B64 (122), B64 (123),
|
||||
B64 (124), B64 (125), B64 (126), B64 (127),
|
||||
B64 (128), B64 (129), B64 (130), B64 (131),
|
||||
B64 (132), B64 (133), B64 (134), B64 (135),
|
||||
B64 (136), B64 (137), B64 (138), B64 (139),
|
||||
B64 (140), B64 (141), B64 (142), B64 (143),
|
||||
B64 (144), B64 (145), B64 (146), B64 (147),
|
||||
B64 (148), B64 (149), B64 (150), B64 (151),
|
||||
B64 (152), B64 (153), B64 (154), B64 (155),
|
||||
B64 (156), B64 (157), B64 (158), B64 (159),
|
||||
B64 (160), B64 (161), B64 (162), B64 (163),
|
||||
B64 (164), B64 (165), B64 (166), B64 (167),
|
||||
B64 (168), B64 (169), B64 (170), B64 (171),
|
||||
B64 (172), B64 (173), B64 (174), B64 (175),
|
||||
B64 (176), B64 (177), B64 (178), B64 (179),
|
||||
B64 (180), B64 (181), B64 (182), B64 (183),
|
||||
B64 (184), B64 (185), B64 (186), B64 (187),
|
||||
B64 (188), B64 (189), B64 (190), B64 (191),
|
||||
B64 (192), B64 (193), B64 (194), B64 (195),
|
||||
B64 (196), B64 (197), B64 (198), B64 (199),
|
||||
B64 (200), B64 (201), B64 (202), B64 (203),
|
||||
B64 (204), B64 (205), B64 (206), B64 (207),
|
||||
B64 (208), B64 (209), B64 (210), B64 (211),
|
||||
B64 (212), B64 (213), B64 (214), B64 (215),
|
||||
B64 (216), B64 (217), B64 (218), B64 (219),
|
||||
B64 (220), B64 (221), B64 (222), B64 (223),
|
||||
B64 (224), B64 (225), B64 (226), B64 (227),
|
||||
B64 (228), B64 (229), B64 (230), B64 (231),
|
||||
B64 (232), B64 (233), B64 (234), B64 (235),
|
||||
B64 (236), B64 (237), B64 (238), B64 (239),
|
||||
B64 (240), B64 (241), B64 (242), B64 (243),
|
||||
B64 (244), B64 (245), B64 (246), B64 (247),
|
||||
B64 (248), B64 (249), B64 (250), B64 (251),
|
||||
B64 (252), B64 (253), B64 (254), B64 (255)
|
||||
};
|
||||
|
||||
#if UCHAR_MAX == 255
|
||||
# define uchar_in_range(c) true
|
||||
#else
|
||||
# define uchar_in_range(c) ((c) <= 255)
|
||||
#endif
|
||||
|
||||
/* Return true if CH is a character from the Base64 alphabet, and
|
||||
false otherwise. Note that '=' is padding and not considered to be
|
||||
part of the alphabet. */
|
||||
bool
|
||||
isbase64 (char ch)
|
||||
{
|
||||
return uchar_in_range (to_uchar (ch)) && 0 <= b64[to_uchar (ch)];
|
||||
}
|
||||
|
||||
/* Initialize decode-context buffer, CTX. */
|
||||
void
|
||||
base64_decode_ctx_init (struct base64_decode_context *ctx)
|
||||
{
|
||||
ctx->i = 0;
|
||||
}
|
||||
|
||||
/* If CTX->i is 0 or 4, there are four or more bytes in [*IN..IN_END), and
|
||||
none of those four is a newline, then return *IN. Otherwise, copy up to
|
||||
4 - CTX->i non-newline bytes from that range into CTX->buf, starting at
|
||||
index CTX->i and setting CTX->i to reflect the number of bytes copied,
|
||||
and return CTX->buf. In either case, advance *IN to point to the byte
|
||||
after the last one processed, and set *N_NON_NEWLINE to the number of
|
||||
verified non-newline bytes accessible through the returned pointer. */
|
||||
static char *
|
||||
get_4 (struct base64_decode_context *ctx,
|
||||
char const *restrict *in, char const *restrict in_end,
|
||||
size_t *n_non_newline)
|
||||
{
|
||||
if (ctx->i == 4)
|
||||
ctx->i = 0;
|
||||
|
||||
if (ctx->i == 0)
|
||||
{
|
||||
char const *t = *in;
|
||||
if (4 <= in_end - *in && memchr (t, '\n', 4) == NULL)
|
||||
{
|
||||
/* This is the common case: no newline. */
|
||||
*in += 4;
|
||||
*n_non_newline = 4;
|
||||
return (char *) t;
|
||||
}
|
||||
}
|
||||
|
||||
{
|
||||
/* Copy non-newline bytes into BUF. */
|
||||
char const *p = *in;
|
||||
while (p < in_end)
|
||||
{
|
||||
char c = *p++;
|
||||
if (c != '\n')
|
||||
{
|
||||
ctx->buf[ctx->i++] = c;
|
||||
if (ctx->i == 4)
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
*in = p;
|
||||
*n_non_newline = ctx->i;
|
||||
return ctx->buf;
|
||||
}
|
||||
}
|
||||
|
||||
#define return_false \
|
||||
do \
|
||||
{ \
|
||||
*outp = out; \
|
||||
return false; \
|
||||
} \
|
||||
while (false)
|
||||
|
||||
/* Decode up to four bytes of base64-encoded data, IN, of length INLEN
|
||||
into the output buffer, *OUT, of size *OUTLEN bytes. Return true if
|
||||
decoding is successful, false otherwise. If *OUTLEN is too small,
|
||||
as many bytes as possible are written to *OUT. On return, advance
|
||||
*OUT to point to the byte after the last one written, and decrement
|
||||
*OUTLEN to reflect the number of bytes remaining in *OUT. */
|
||||
static bool
|
||||
decode_4 (char const *restrict in, size_t inlen,
|
||||
char *restrict *outp, size_t *outleft)
|
||||
{
|
||||
char *out = *outp;
|
||||
if (inlen < 2)
|
||||
return false;
|
||||
|
||||
if (!isbase64 (in[0]) || !isbase64 (in[1]))
|
||||
return false;
|
||||
|
||||
if (*outleft)
|
||||
{
|
||||
*out++ = ((b64[to_uchar (in[0])] << 2)
|
||||
| (b64[to_uchar (in[1])] >> 4));
|
||||
--*outleft;
|
||||
}
|
||||
|
||||
if (inlen == 2)
|
||||
return_false;
|
||||
|
||||
if (in[2] == '=')
|
||||
{
|
||||
if (inlen != 4)
|
||||
return_false;
|
||||
|
||||
if (in[3] != '=')
|
||||
return_false;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!isbase64 (in[2]))
|
||||
return_false;
|
||||
|
||||
if (*outleft)
|
||||
{
|
||||
*out++ = (((b64[to_uchar (in[1])] << 4) & 0xf0)
|
||||
| (b64[to_uchar (in[2])] >> 2));
|
||||
--*outleft;
|
||||
}
|
||||
|
||||
if (inlen == 3)
|
||||
return_false;
|
||||
|
||||
if (in[3] == '=')
|
||||
{
|
||||
if (inlen != 4)
|
||||
return_false;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!isbase64 (in[3]))
|
||||
return_false;
|
||||
|
||||
if (*outleft)
|
||||
{
|
||||
*out++ = (((b64[to_uchar (in[2])] << 6) & 0xc0)
|
||||
| b64[to_uchar (in[3])]);
|
||||
--*outleft;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
*outp = out;
|
||||
return true;
|
||||
}
|
||||
|
||||
/* Decode base64-encoded input array IN of length INLEN to output array
|
||||
OUT that can hold *OUTLEN bytes. The input data may be interspersed
|
||||
with newlines. Return true if decoding was successful, i.e. if the
|
||||
input was valid base64 data, false otherwise. If *OUTLEN is too
|
||||
small, as many bytes as possible will be written to OUT. On return,
|
||||
*OUTLEN holds the length of decoded bytes in OUT. Note that as soon
|
||||
as any non-alphabet, non-newline character is encountered, decoding
|
||||
is stopped and false is returned. If INLEN is zero, then process
|
||||
only whatever data is stored in CTX.
|
||||
|
||||
Initially, CTX must have been initialized via base64_decode_ctx_init.
|
||||
Subsequent calls to this function must reuse whatever state is recorded
|
||||
in that buffer. It is necessary for when a quadruple of base64 input
|
||||
bytes spans two input buffers.
|
||||
|
||||
If CTX is NULL then newlines are treated as garbage and the input
|
||||
buffer is processed as a unit. */
|
||||
|
||||
bool
|
||||
base64_decode_ctx (struct base64_decode_context *ctx,
|
||||
const char *restrict in, size_t inlen,
|
||||
char *restrict out, size_t *outlen)
|
||||
{
|
||||
size_t outleft = *outlen;
|
||||
bool ignore_newlines = ctx != NULL;
|
||||
bool flush_ctx = false;
|
||||
unsigned int ctx_i = 0;
|
||||
|
||||
if (ignore_newlines)
|
||||
{
|
||||
ctx_i = ctx->i;
|
||||
flush_ctx = inlen == 0;
|
||||
}
|
||||
|
||||
|
||||
while (true)
|
||||
{
|
||||
size_t outleft_save = outleft;
|
||||
if (ctx_i == 0 && !flush_ctx)
|
||||
{
|
||||
while (true)
|
||||
{
|
||||
/* Save a copy of outleft, in case we need to re-parse this
|
||||
block of four bytes. */
|
||||
outleft_save = outleft;
|
||||
if (!decode_4 (in, inlen, &out, &outleft))
|
||||
break;
|
||||
|
||||
in += 4;
|
||||
inlen -= 4;
|
||||
}
|
||||
}
|
||||
|
||||
if (inlen == 0 && !flush_ctx)
|
||||
break;
|
||||
|
||||
/* Handle the common case of 72-byte wrapped lines.
|
||||
This also handles any other multiple-of-4-byte wrapping. */
|
||||
if (inlen && *in == '\n' && ignore_newlines)
|
||||
{
|
||||
++in;
|
||||
--inlen;
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Restore OUT and OUTLEFT. */
|
||||
out -= outleft_save - outleft;
|
||||
outleft = outleft_save;
|
||||
|
||||
{
|
||||
char const *in_end = in + inlen;
|
||||
char const *non_nl;
|
||||
|
||||
if (ignore_newlines)
|
||||
non_nl = get_4 (ctx, &in, in_end, &inlen);
|
||||
else
|
||||
non_nl = in; /* Might have nl in this case. */
|
||||
|
||||
/* If the input is empty or consists solely of newlines (0 non-newlines),
|
||||
then we're done. Likewise if there are fewer than 4 bytes when not
|
||||
flushing context and not treating newlines as garbage. */
|
||||
if (inlen == 0 || (inlen < 4 && !flush_ctx && ignore_newlines))
|
||||
{
|
||||
inlen = 0;
|
||||
break;
|
||||
}
|
||||
if (!decode_4 (non_nl, inlen, &out, &outleft))
|
||||
break;
|
||||
|
||||
inlen = in_end - in;
|
||||
}
|
||||
}
|
||||
|
||||
*outlen -= outleft;
|
||||
|
||||
return inlen == 0;
|
||||
}
|
||||
|
||||
/* Allocate an output buffer in *OUT, and decode the base64 encoded
|
||||
data stored in IN of size INLEN to the *OUT buffer. On return, the
|
||||
size of the decoded data is stored in *OUTLEN. OUTLEN may be NULL,
|
||||
if the caller is not interested in the decoded length. *OUT may be
|
||||
NULL to indicate an out of memory error, in which case *OUTLEN
|
||||
contains the size of the memory block needed. The function returns
|
||||
true on successful decoding and memory allocation errors. (Use the
|
||||
*OUT and *OUTLEN parameters to differentiate between successful
|
||||
decoding and memory error.) The function returns false if the
|
||||
input was invalid, in which case *OUT is NULL and *OUTLEN is
|
||||
undefined. */
|
||||
bool
|
||||
base64_decode_alloc_ctx (struct base64_decode_context *ctx,
|
||||
const char *in, size_t inlen, char **out,
|
||||
size_t *outlen)
|
||||
{
|
||||
/* This may allocate a few bytes too many, depending on input,
|
||||
but it's not worth the extra CPU time to compute the exact size.
|
||||
The exact size is 3 * (inlen + (ctx ? ctx->i : 0)) / 4, minus 1 if the
|
||||
input ends with "=" and minus another 1 if the input ends with "==".
|
||||
Dividing before multiplying avoids the possibility of overflow. */
|
||||
size_t needlen = 3 * (inlen / 4) + 3;
|
||||
|
||||
*out = malloc (needlen);
|
||||
if (!*out)
|
||||
return true;
|
||||
|
||||
if (!base64_decode_ctx (ctx, in, inlen, *out, &needlen))
|
||||
{
|
||||
free (*out);
|
||||
*out = NULL;
|
||||
return false;
|
||||
}
|
||||
|
||||
if (outlen)
|
||||
*outlen = needlen;
|
||||
|
||||
return true;
|
||||
}
|
||||
75
gnulib/lib/base64.h
Normal file
75
gnulib/lib/base64.h
Normal file
@@ -0,0 +1,75 @@
|
||||
/* base64.h -- Encode binary data using printable characters.
|
||||
Copyright (C) 2004-2006, 2009-2021 Free Software Foundation, Inc.
|
||||
Written by Simon Josefsson.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef BASE64_H
|
||||
# define BASE64_H
|
||||
|
||||
/* Get size_t. */
|
||||
# include <stddef.h>
|
||||
|
||||
/* Get bool. */
|
||||
# include <stdbool.h>
|
||||
|
||||
# ifdef __cplusplus
|
||||
extern "C" {
|
||||
# endif
|
||||
|
||||
/* This uses that the expression (n+(k-1))/k means the smallest
|
||||
integer >= n/k, i.e., the ceiling of n/k. */
|
||||
# define BASE64_LENGTH(inlen) ((((inlen) + 2) / 3) * 4)
|
||||
|
||||
struct base64_decode_context
|
||||
{
|
||||
unsigned int i;
|
||||
char buf[4];
|
||||
};
|
||||
|
||||
extern bool isbase64 (char ch);
|
||||
|
||||
extern void base64_encode (const char *restrict in, size_t inlen,
|
||||
char *restrict out, size_t outlen);
|
||||
|
||||
extern size_t base64_encode_alloc (const char *in, size_t inlen, char **out);
|
||||
|
||||
extern void base64_decode_ctx_init (struct base64_decode_context *ctx);
|
||||
|
||||
extern bool base64_decode_ctx (struct base64_decode_context *ctx,
|
||||
const char *restrict in, size_t inlen,
|
||||
char *restrict out, size_t *outlen);
|
||||
|
||||
extern bool base64_decode_alloc_ctx (struct base64_decode_context *ctx,
|
||||
const char *in, size_t inlen,
|
||||
char **out, size_t *outlen);
|
||||
|
||||
#define base64_decode(in, inlen, out, outlen) \
|
||||
base64_decode_ctx (NULL, in, inlen, out, outlen)
|
||||
|
||||
#define base64_decode_alloc(in, inlen, out, outlen) \
|
||||
base64_decode_alloc_ctx (NULL, in, inlen, out, outlen)
|
||||
|
||||
# ifdef __cplusplus
|
||||
}
|
||||
# endif
|
||||
|
||||
#endif /* BASE64_H */
|
||||
135
gnulib/lib/bitrotate.h
Executable file
135
gnulib/lib/bitrotate.h
Executable file
@@ -0,0 +1,135 @@
|
||||
/* bitrotate.h - Rotate bits in integers
|
||||
Copyright (C) 2008-2021 Free Software Foundation, Inc.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
/* Written by Simon Josefsson <simon@josefsson.org>, 2008. */
|
||||
|
||||
#ifndef _GL_BITROTATE_H
|
||||
#define _GL_BITROTATE_H
|
||||
|
||||
#include <limits.h>
|
||||
#include <stdint.h>
|
||||
#include <sys/types.h>
|
||||
|
||||
#ifdef UINT64_MAX
|
||||
/* Given an unsigned 64-bit argument X, return the value corresponding
|
||||
to rotating the bits N steps to the left. N must be between 1 and
|
||||
63 inclusive. */
|
||||
static inline uint64_t
|
||||
rotl64 (uint64_t x, int n)
|
||||
{
|
||||
return ((x << n) | (x >> (64 - n))) & UINT64_MAX;
|
||||
}
|
||||
|
||||
/* Given an unsigned 64-bit argument X, return the value corresponding
|
||||
to rotating the bits N steps to the right. N must be between 1 to
|
||||
63 inclusive.*/
|
||||
static inline uint64_t
|
||||
rotr64 (uint64_t x, int n)
|
||||
{
|
||||
return ((x >> n) | (x << (64 - n))) & UINT64_MAX;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* Given an unsigned 32-bit argument X, return the value corresponding
|
||||
to rotating the bits N steps to the left. N must be between 1 and
|
||||
31 inclusive. */
|
||||
static inline uint32_t
|
||||
rotl32 (uint32_t x, int n)
|
||||
{
|
||||
return ((x << n) | (x >> (32 - n))) & UINT32_MAX;
|
||||
}
|
||||
|
||||
/* Given an unsigned 32-bit argument X, return the value corresponding
|
||||
to rotating the bits N steps to the right. N must be between 1 to
|
||||
31 inclusive.*/
|
||||
static inline uint32_t
|
||||
rotr32 (uint32_t x, int n)
|
||||
{
|
||||
return ((x >> n) | (x << (32 - n))) & UINT32_MAX;
|
||||
}
|
||||
|
||||
/* Given a size_t argument X, return the value corresponding
|
||||
to rotating the bits N steps to the left. N must be between 1 and
|
||||
(CHAR_BIT * sizeof (size_t) - 1) inclusive. */
|
||||
static inline size_t
|
||||
rotl_sz (size_t x, int n)
|
||||
{
|
||||
return ((x << n) | (x >> ((CHAR_BIT * sizeof x) - n))) & SIZE_MAX;
|
||||
}
|
||||
|
||||
/* Given a size_t argument X, return the value corresponding
|
||||
to rotating the bits N steps to the right. N must be between 1 to
|
||||
(CHAR_BIT * sizeof (size_t) - 1) inclusive. */
|
||||
static inline size_t
|
||||
rotr_sz (size_t x, int n)
|
||||
{
|
||||
return ((x >> n) | (x << ((CHAR_BIT * sizeof x) - n))) & SIZE_MAX;
|
||||
}
|
||||
|
||||
/* Given an unsigned 16-bit argument X, return the value corresponding
|
||||
to rotating the bits N steps to the left. N must be between 1 to
|
||||
15 inclusive, but on most relevant targets N can also be 0 and 16
|
||||
because 'int' is at least 32 bits and the arguments must widen
|
||||
before shifting. */
|
||||
static inline uint16_t
|
||||
rotl16 (uint16_t x, int n)
|
||||
{
|
||||
return (((unsigned int) x << n) | ((unsigned int) x >> (16 - n)))
|
||||
& UINT16_MAX;
|
||||
}
|
||||
|
||||
/* Given an unsigned 16-bit argument X, return the value corresponding
|
||||
to rotating the bits N steps to the right. N must be in 1 to 15
|
||||
inclusive, but on most relevant targets N can also be 0 and 16
|
||||
because 'int' is at least 32 bits and the arguments must widen
|
||||
before shifting. */
|
||||
static inline uint16_t
|
||||
rotr16 (uint16_t x, int n)
|
||||
{
|
||||
return (((unsigned int) x >> n) | ((unsigned int) x << (16 - n)))
|
||||
& UINT16_MAX;
|
||||
}
|
||||
|
||||
/* Given an unsigned 8-bit argument X, return the value corresponding
|
||||
to rotating the bits N steps to the left. N must be between 1 to 7
|
||||
inclusive, but on most relevant targets N can also be 0 and 8
|
||||
because 'int' is at least 32 bits and the arguments must widen
|
||||
before shifting. */
|
||||
static inline uint8_t
|
||||
rotl8 (uint8_t x, int n)
|
||||
{
|
||||
return (((unsigned int) x << n) | ((unsigned int) x >> (8 - n))) & UINT8_MAX;
|
||||
}
|
||||
|
||||
/* Given an unsigned 8-bit argument X, return the value corresponding
|
||||
to rotating the bits N steps to the right. N must be in 1 to 7
|
||||
inclusive, but on most relevant targets N can also be 0 and 8
|
||||
because 'int' is at least 32 bits and the arguments must widen
|
||||
before shifting. */
|
||||
static inline uint8_t
|
||||
rotr8 (uint8_t x, int n)
|
||||
{
|
||||
return (((unsigned int) x >> n) | ((unsigned int) x << (8 - n))) & UINT8_MAX;
|
||||
}
|
||||
|
||||
#endif /* _GL_BITROTATE_H */
|
||||
363
gnulib/lib/c-ctype.h
Executable file
363
gnulib/lib/c-ctype.h
Executable file
@@ -0,0 +1,363 @@
|
||||
/* Character handling in C locale.
|
||||
|
||||
These functions work like the corresponding functions in <ctype.h>,
|
||||
except that they have the C (POSIX) locale hardwired, whereas the
|
||||
<ctype.h> functions' behaviour depends on the current locale set via
|
||||
setlocale.
|
||||
|
||||
Copyright (C) 2000-2003, 2006, 2008-2021 Free Software Foundation, Inc.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef C_CTYPE_H
|
||||
#define C_CTYPE_H
|
||||
|
||||
#include <stdbool.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
|
||||
/* The functions defined in this file assume the "C" locale and a character
|
||||
set without diacritics (ASCII-US or EBCDIC-US or something like that).
|
||||
Even if the "C" locale on a particular system is an extension of the ASCII
|
||||
character set (like on BeOS, where it is UTF-8, or on AmigaOS, where it
|
||||
is ISO-8859-1), the functions in this file recognize only the ASCII
|
||||
characters. */
|
||||
|
||||
|
||||
#if (' ' == 32) && ('!' == 33) && ('"' == 34) && ('#' == 35) \
|
||||
&& ('%' == 37) && ('&' == 38) && ('\'' == 39) && ('(' == 40) \
|
||||
&& (')' == 41) && ('*' == 42) && ('+' == 43) && (',' == 44) \
|
||||
&& ('-' == 45) && ('.' == 46) && ('/' == 47) && ('0' == 48) \
|
||||
&& ('1' == 49) && ('2' == 50) && ('3' == 51) && ('4' == 52) \
|
||||
&& ('5' == 53) && ('6' == 54) && ('7' == 55) && ('8' == 56) \
|
||||
&& ('9' == 57) && (':' == 58) && (';' == 59) && ('<' == 60) \
|
||||
&& ('=' == 61) && ('>' == 62) && ('?' == 63) && ('A' == 65) \
|
||||
&& ('B' == 66) && ('C' == 67) && ('D' == 68) && ('E' == 69) \
|
||||
&& ('F' == 70) && ('G' == 71) && ('H' == 72) && ('I' == 73) \
|
||||
&& ('J' == 74) && ('K' == 75) && ('L' == 76) && ('M' == 77) \
|
||||
&& ('N' == 78) && ('O' == 79) && ('P' == 80) && ('Q' == 81) \
|
||||
&& ('R' == 82) && ('S' == 83) && ('T' == 84) && ('U' == 85) \
|
||||
&& ('V' == 86) && ('W' == 87) && ('X' == 88) && ('Y' == 89) \
|
||||
&& ('Z' == 90) && ('[' == 91) && ('\\' == 92) && (']' == 93) \
|
||||
&& ('^' == 94) && ('_' == 95) && ('a' == 97) && ('b' == 98) \
|
||||
&& ('c' == 99) && ('d' == 100) && ('e' == 101) && ('f' == 102) \
|
||||
&& ('g' == 103) && ('h' == 104) && ('i' == 105) && ('j' == 106) \
|
||||
&& ('k' == 107) && ('l' == 108) && ('m' == 109) && ('n' == 110) \
|
||||
&& ('o' == 111) && ('p' == 112) && ('q' == 113) && ('r' == 114) \
|
||||
&& ('s' == 115) && ('t' == 116) && ('u' == 117) && ('v' == 118) \
|
||||
&& ('w' == 119) && ('x' == 120) && ('y' == 121) && ('z' == 122) \
|
||||
&& ('{' == 123) && ('|' == 124) && ('}' == 125) && ('~' == 126)
|
||||
/* The character set is ASCII or one of its variants or extensions, not EBCDIC.
|
||||
Testing the value of '\n' and '\r' is not relevant. */
|
||||
# define C_CTYPE_ASCII 1
|
||||
#elif ! (' ' == '\x40' && '0' == '\xf0' \
|
||||
&& 'A' == '\xc1' && 'J' == '\xd1' && 'S' == '\xe2' \
|
||||
&& 'a' == '\x81' && 'j' == '\x91' && 's' == '\xa2')
|
||||
# error "Only ASCII and EBCDIC are supported"
|
||||
#endif
|
||||
|
||||
#if 'A' < 0
|
||||
# error "EBCDIC and char is signed -- not supported"
|
||||
#endif
|
||||
|
||||
/* Cases for control characters. */
|
||||
|
||||
#define _C_CTYPE_CNTRL \
|
||||
case '\a': case '\b': case '\f': case '\n': \
|
||||
case '\r': case '\t': case '\v': \
|
||||
_C_CTYPE_OTHER_CNTRL
|
||||
|
||||
/* ASCII control characters other than those with \-letter escapes. */
|
||||
|
||||
#if C_CTYPE_ASCII
|
||||
# define _C_CTYPE_OTHER_CNTRL \
|
||||
case '\x00': case '\x01': case '\x02': case '\x03': \
|
||||
case '\x04': case '\x05': case '\x06': case '\x0e': \
|
||||
case '\x0f': case '\x10': case '\x11': case '\x12': \
|
||||
case '\x13': case '\x14': case '\x15': case '\x16': \
|
||||
case '\x17': case '\x18': case '\x19': case '\x1a': \
|
||||
case '\x1b': case '\x1c': case '\x1d': case '\x1e': \
|
||||
case '\x1f': case '\x7f'
|
||||
#else
|
||||
/* Use EBCDIC code page 1047's assignments for ASCII control chars;
|
||||
assume all EBCDIC code pages agree about these assignments. */
|
||||
# define _C_CTYPE_OTHER_CNTRL \
|
||||
case '\x00': case '\x01': case '\x02': case '\x03': \
|
||||
case '\x07': case '\x0e': case '\x0f': case '\x10': \
|
||||
case '\x11': case '\x12': case '\x13': case '\x18': \
|
||||
case '\x19': case '\x1c': case '\x1d': case '\x1e': \
|
||||
case '\x1f': case '\x26': case '\x27': case '\x2d': \
|
||||
case '\x2e': case '\x32': case '\x37': case '\x3c': \
|
||||
case '\x3d': case '\x3f'
|
||||
#endif
|
||||
|
||||
/* Cases for lowercase hex letters, and lowercase letters, all offset by N. */
|
||||
|
||||
#define _C_CTYPE_LOWER_A_THRU_F_N(N) \
|
||||
case 'a' + (N): case 'b' + (N): case 'c' + (N): case 'd' + (N): \
|
||||
case 'e' + (N): case 'f' + (N)
|
||||
#define _C_CTYPE_LOWER_N(N) \
|
||||
_C_CTYPE_LOWER_A_THRU_F_N(N): \
|
||||
case 'g' + (N): case 'h' + (N): case 'i' + (N): case 'j' + (N): \
|
||||
case 'k' + (N): case 'l' + (N): case 'm' + (N): case 'n' + (N): \
|
||||
case 'o' + (N): case 'p' + (N): case 'q' + (N): case 'r' + (N): \
|
||||
case 's' + (N): case 't' + (N): case 'u' + (N): case 'v' + (N): \
|
||||
case 'w' + (N): case 'x' + (N): case 'y' + (N): case 'z' + (N)
|
||||
|
||||
/* Cases for hex letters, digits, lower, punct, and upper. */
|
||||
|
||||
#define _C_CTYPE_A_THRU_F \
|
||||
_C_CTYPE_LOWER_A_THRU_F_N (0): \
|
||||
_C_CTYPE_LOWER_A_THRU_F_N ('A' - 'a')
|
||||
#define _C_CTYPE_DIGIT \
|
||||
case '0': case '1': case '2': case '3': \
|
||||
case '4': case '5': case '6': case '7': \
|
||||
case '8': case '9'
|
||||
#define _C_CTYPE_LOWER _C_CTYPE_LOWER_N (0)
|
||||
#define _C_CTYPE_PUNCT \
|
||||
case '!': case '"': case '#': case '$': \
|
||||
case '%': case '&': case '\'': case '(': \
|
||||
case ')': case '*': case '+': case ',': \
|
||||
case '-': case '.': case '/': case ':': \
|
||||
case ';': case '<': case '=': case '>': \
|
||||
case '?': case '@': case '[': case '\\': \
|
||||
case ']': case '^': case '_': case '`': \
|
||||
case '{': case '|': case '}': case '~'
|
||||
#define _C_CTYPE_UPPER _C_CTYPE_LOWER_N ('A' - 'a')
|
||||
|
||||
|
||||
/* Function definitions. */
|
||||
|
||||
/* Unlike the functions in <ctype.h>, which require an argument in the range
|
||||
of the 'unsigned char' type, the functions here operate on values that are
|
||||
in the 'unsigned char' range or in the 'char' range. In other words,
|
||||
when you have a 'char' value, you need to cast it before using it as
|
||||
argument to a <ctype.h> function:
|
||||
|
||||
const char *s = ...;
|
||||
if (isalpha ((unsigned char) *s)) ...
|
||||
|
||||
but you don't need to cast it for the functions defined in this file:
|
||||
|
||||
const char *s = ...;
|
||||
if (c_isalpha (*s)) ...
|
||||
*/
|
||||
|
||||
static inline bool
|
||||
c_isalnum (int c)
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
_C_CTYPE_DIGIT:
|
||||
_C_CTYPE_LOWER:
|
||||
_C_CTYPE_UPPER:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
static inline bool
|
||||
c_isalpha (int c)
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
_C_CTYPE_LOWER:
|
||||
_C_CTYPE_UPPER:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/* The function isascii is not locale dependent.
|
||||
Its use in EBCDIC is questionable. */
|
||||
static inline bool
|
||||
c_isascii (int c)
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
case ' ':
|
||||
_C_CTYPE_CNTRL:
|
||||
_C_CTYPE_DIGIT:
|
||||
_C_CTYPE_LOWER:
|
||||
_C_CTYPE_PUNCT:
|
||||
_C_CTYPE_UPPER:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
static inline bool
|
||||
c_isblank (int c)
|
||||
{
|
||||
return c == ' ' || c == '\t';
|
||||
}
|
||||
|
||||
static inline bool
|
||||
c_iscntrl (int c)
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
_C_CTYPE_CNTRL:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
static inline bool
|
||||
c_isdigit (int c)
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
_C_CTYPE_DIGIT:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
static inline bool
|
||||
c_isgraph (int c)
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
_C_CTYPE_DIGIT:
|
||||
_C_CTYPE_LOWER:
|
||||
_C_CTYPE_PUNCT:
|
||||
_C_CTYPE_UPPER:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
static inline bool
|
||||
c_islower (int c)
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
_C_CTYPE_LOWER:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
static inline bool
|
||||
c_isprint (int c)
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
case ' ':
|
||||
_C_CTYPE_DIGIT:
|
||||
_C_CTYPE_LOWER:
|
||||
_C_CTYPE_PUNCT:
|
||||
_C_CTYPE_UPPER:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
static inline bool
|
||||
c_ispunct (int c)
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
_C_CTYPE_PUNCT:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
static inline bool
|
||||
c_isspace (int c)
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
case ' ': case '\t': case '\n': case '\v': case '\f': case '\r':
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
static inline bool
|
||||
c_isupper (int c)
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
_C_CTYPE_UPPER:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
static inline bool
|
||||
c_isxdigit (int c)
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
_C_CTYPE_DIGIT:
|
||||
_C_CTYPE_A_THRU_F:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
static inline int
|
||||
c_tolower (int c)
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
_C_CTYPE_UPPER:
|
||||
return c - 'A' + 'a';
|
||||
default:
|
||||
return c;
|
||||
}
|
||||
}
|
||||
|
||||
static inline int
|
||||
c_toupper (int c)
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
_C_CTYPE_LOWER:
|
||||
return c - 'a' + 'A';
|
||||
default:
|
||||
return c;
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* C_CTYPE_H */
|
||||
88
gnulib/lib/cloexec.c
Normal file
88
gnulib/lib/cloexec.c
Normal file
@@ -0,0 +1,88 @@
|
||||
/* cloexec.c - set or clear the close-on-exec descriptor flag
|
||||
|
||||
Copyright (C) 1991, 2004-2006, 2009-2021 Free Software Foundation, Inc.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#include <config.h>
|
||||
|
||||
#include "cloexec.h"
|
||||
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <unistd.h>
|
||||
|
||||
/* Set the 'FD_CLOEXEC' flag of DESC if VALUE is true,
|
||||
or clear the flag if VALUE is false.
|
||||
Return 0 on success, or -1 on error with 'errno' set.
|
||||
|
||||
Note that on MingW, this function does NOT protect DESC from being
|
||||
inherited into spawned children. Instead, either use dup_cloexec
|
||||
followed by closing the original DESC, or use interfaces such as
|
||||
open or pipe2 that accept flags like O_CLOEXEC to create DESC
|
||||
non-inheritable in the first place. */
|
||||
|
||||
int
|
||||
set_cloexec_flag (int desc, bool value)
|
||||
{
|
||||
#ifdef F_SETFD
|
||||
|
||||
int flags = fcntl (desc, F_GETFD, 0);
|
||||
|
||||
if (0 <= flags)
|
||||
{
|
||||
int newflags = (value ? flags | FD_CLOEXEC : flags & ~FD_CLOEXEC);
|
||||
|
||||
if (flags == newflags
|
||||
|| fcntl (desc, F_SETFD, newflags) != -1)
|
||||
return 0;
|
||||
}
|
||||
|
||||
return -1;
|
||||
|
||||
#else /* !F_SETFD */
|
||||
|
||||
/* Use dup2 to reject invalid file descriptors; the cloexec flag
|
||||
will be unaffected. */
|
||||
if (desc < 0)
|
||||
{
|
||||
errno = EBADF;
|
||||
return -1;
|
||||
}
|
||||
if (dup2 (desc, desc) < 0)
|
||||
/* errno is EBADF here. */
|
||||
return -1;
|
||||
|
||||
/* There is nothing we can do on this kind of platform. Punt. */
|
||||
return 0;
|
||||
#endif /* !F_SETFD */
|
||||
}
|
||||
|
||||
|
||||
/* Duplicates a file handle FD, while marking the copy to be closed
|
||||
prior to exec or spawn. Returns -1 and sets errno if FD could not
|
||||
be duplicated. */
|
||||
|
||||
int
|
||||
dup_cloexec (int fd)
|
||||
{
|
||||
return fcntl (fd, F_DUPFD_CLOEXEC, 0);
|
||||
}
|
||||
43
gnulib/lib/cloexec.h
Normal file
43
gnulib/lib/cloexec.h
Normal file
@@ -0,0 +1,43 @@
|
||||
/* cloexec.c - set or clear the close-on-exec descriptor flag
|
||||
|
||||
Copyright (C) 2004, 2009-2021 Free Software Foundation, Inc.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#include <stdbool.h>
|
||||
|
||||
/* Set the 'FD_CLOEXEC' flag of DESC if VALUE is true,
|
||||
or clear the flag if VALUE is false.
|
||||
Return 0 on success, or -1 on error with 'errno' set.
|
||||
|
||||
Note that on MingW, this function does NOT protect DESC from being
|
||||
inherited into spawned children. Instead, either use dup_cloexec
|
||||
followed by closing the original DESC, or use interfaces such as
|
||||
open or pipe2 that accept flags like O_CLOEXEC to create DESC
|
||||
non-inheritable in the first place. */
|
||||
|
||||
int set_cloexec_flag (int desc, bool value);
|
||||
|
||||
/* Duplicates a file handle FD, while marking the copy to be closed
|
||||
prior to exec or spawn. Returns -1 and sets errno if FD could not
|
||||
be duplicated. */
|
||||
|
||||
int dup_cloexec (int fd);
|
||||
25
gnulib/lib/full-read.c
Normal file
25
gnulib/lib/full-read.c
Normal file
@@ -0,0 +1,25 @@
|
||||
/* An interface to read that retries after partial reads and interrupts.
|
||||
Copyright (C) 2002-2003, 2009-2021 Free Software Foundation, Inc.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#define FULL_READ
|
||||
#include "full-write.c"
|
||||
30
gnulib/lib/full-read.h
Normal file
30
gnulib/lib/full-read.h
Normal file
@@ -0,0 +1,30 @@
|
||||
/* An interface to read() that reads all it is asked to read.
|
||||
|
||||
Copyright (C) 2002, 2009-2021 Free Software Foundation, Inc.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#include <stddef.h>
|
||||
|
||||
/* Read COUNT bytes at BUF to descriptor FD, retrying if interrupted
|
||||
or if partial reads occur. Return the number of bytes successfully
|
||||
read, setting errno if that is less than COUNT. errno = 0 means EOF. */
|
||||
extern size_t full_read (int fd, void *buf, size_t count);
|
||||
86
gnulib/lib/full-write.c
Normal file
86
gnulib/lib/full-write.c
Normal file
@@ -0,0 +1,86 @@
|
||||
/* An interface to read and write that retries (if necessary) until complete.
|
||||
|
||||
Copyright (C) 1993-1994, 1997-2006, 2009-2021 Free Software Foundation, Inc.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#include <config.h>
|
||||
|
||||
/* Specification. */
|
||||
#ifdef FULL_READ
|
||||
# include "full-read.h"
|
||||
#else
|
||||
# include "full-write.h"
|
||||
#endif
|
||||
|
||||
#include <errno.h>
|
||||
|
||||
#ifdef FULL_READ
|
||||
# include "safe-read.h"
|
||||
# define safe_rw safe_read
|
||||
# define full_rw full_read
|
||||
# undef const
|
||||
# define const /* empty */
|
||||
#else
|
||||
# include "safe-write.h"
|
||||
# define safe_rw safe_write
|
||||
# define full_rw full_write
|
||||
#endif
|
||||
|
||||
#ifdef FULL_READ
|
||||
/* Set errno to zero upon EOF. */
|
||||
# define ZERO_BYTE_TRANSFER_ERRNO 0
|
||||
#else
|
||||
/* Some buggy drivers return 0 when one tries to write beyond
|
||||
a device's end. (Example: Linux 1.2.13 on /dev/fd0.)
|
||||
Set errno to ENOSPC so they get a sensible diagnostic. */
|
||||
# define ZERO_BYTE_TRANSFER_ERRNO ENOSPC
|
||||
#endif
|
||||
|
||||
/* Write(read) COUNT bytes at BUF to(from) descriptor FD, retrying if
|
||||
interrupted or if a partial write(read) occurs. Return the number
|
||||
of bytes transferred.
|
||||
When writing, set errno if fewer than COUNT bytes are written.
|
||||
When reading, if fewer than COUNT bytes are read, you must examine
|
||||
errno to distinguish failure from EOF (errno == 0). */
|
||||
size_t
|
||||
full_rw (int fd, const void *buf, size_t count)
|
||||
{
|
||||
size_t total = 0;
|
||||
const char *ptr = (const char *) buf;
|
||||
|
||||
while (count > 0)
|
||||
{
|
||||
size_t n_rw = safe_rw (fd, ptr, count);
|
||||
if (n_rw == (size_t) -1)
|
||||
break;
|
||||
if (n_rw == 0)
|
||||
{
|
||||
errno = ZERO_BYTE_TRANSFER_ERRNO;
|
||||
break;
|
||||
}
|
||||
total += n_rw;
|
||||
ptr += n_rw;
|
||||
count -= n_rw;
|
||||
}
|
||||
|
||||
return total;
|
||||
}
|
||||
41
gnulib/lib/full-write.h
Normal file
41
gnulib/lib/full-write.h
Normal file
@@ -0,0 +1,41 @@
|
||||
/* An interface to write() that writes all it is asked to write.
|
||||
|
||||
Copyright (C) 2002-2003, 2009-2021 Free Software Foundation, Inc.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#include <stddef.h>
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
|
||||
/* Write COUNT bytes at BUF to descriptor FD, retrying if interrupted
|
||||
or if partial writes occur. Return the number of bytes successfully
|
||||
written, setting errno if that is less than COUNT. */
|
||||
extern size_t full_write (int fd, const void *buf, size_t count);
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
30
gnulib/lib/getprogname.h
Normal file
30
gnulib/lib/getprogname.h
Normal file
@@ -0,0 +1,30 @@
|
||||
/* libguestfs
|
||||
* Copyright (C) 2013-2020 Red Hat Inc.
|
||||
*
|
||||
* This library 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 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library 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 library; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef GUESTFS_GETPROGNAME
|
||||
#define GUESTFS_GETPROGNAME
|
||||
|
||||
#include <errno.h>
|
||||
|
||||
static inline char const *
|
||||
getprogname (void)
|
||||
{
|
||||
return program_invocation_short_name;
|
||||
}
|
||||
|
||||
#endif /* GUESTFS_GETPROGNAME */
|
||||
40
gnulib/lib/hash-pjw.c
Normal file
40
gnulib/lib/hash-pjw.c
Normal file
@@ -0,0 +1,40 @@
|
||||
/* hash-pjw.c -- compute a hash value from a NUL-terminated string.
|
||||
|
||||
Copyright (C) 2001, 2003, 2006, 2009-2021 Free Software Foundation, Inc.
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program 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 General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program. If not, see <https://www.gnu.org/licenses/>. */
|
||||
|
||||
#include <config.h>
|
||||
|
||||
#include "hash-pjw.h"
|
||||
|
||||
#include <limits.h>
|
||||
|
||||
#define SIZE_BITS (sizeof (size_t) * CHAR_BIT)
|
||||
|
||||
/* A hash function for NUL-terminated char* strings using
|
||||
the method described by Bruno Haible.
|
||||
See https://www.haible.de/bruno/hashfunc.html. */
|
||||
|
||||
size_t
|
||||
hash_pjw (const void *x, size_t tablesize)
|
||||
{
|
||||
const char *s;
|
||||
size_t h = 0;
|
||||
|
||||
for (s = x; *s; s++)
|
||||
h = *s + ((h << 9) | (h >> (SIZE_BITS - 9)));
|
||||
|
||||
return h % tablesize;
|
||||
}
|
||||
23
gnulib/lib/hash-pjw.h
Normal file
23
gnulib/lib/hash-pjw.h
Normal file
@@ -0,0 +1,23 @@
|
||||
/* hash-pjw.h -- declaration for a simple hash function
|
||||
Copyright (C) 2001, 2003, 2009-2021 Free Software Foundation, Inc.
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program 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 General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program. If not, see <https://www.gnu.org/licenses/>. */
|
||||
|
||||
#include <stddef.h>
|
||||
|
||||
/* Compute a hash code for a NUL-terminated string starting at X,
|
||||
and return the hash code modulo TABLESIZE.
|
||||
The result is platform dependent: it depends on the size of the 'size_t'
|
||||
type and on the signedness of the 'char' type. */
|
||||
extern size_t hash_pjw (void const *x, size_t tablesize);
|
||||
1113
gnulib/lib/hash.c
Executable file
1113
gnulib/lib/hash.c
Executable file
File diff suppressed because it is too large
Load Diff
256
gnulib/lib/hash.h
Executable file
256
gnulib/lib/hash.h
Executable file
@@ -0,0 +1,256 @@
|
||||
/* hash - hashing table processing.
|
||||
Copyright (C) 1998-1999, 2001, 2003, 2009-2021 Free Software Foundation,
|
||||
Inc.
|
||||
Written by Jim Meyering <meyering@ascend.com>, 1998.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
/* A generic hash table package. */
|
||||
|
||||
/* Make sure USE_OBSTACK is defined to 1 if you want the allocator to use
|
||||
obstacks instead of malloc, and recompile 'hash.c' with same setting. */
|
||||
|
||||
#ifndef HASH_H_
|
||||
# define HASH_H_
|
||||
|
||||
# include <stdio.h>
|
||||
# include <stdbool.h>
|
||||
|
||||
# ifdef __cplusplus
|
||||
extern "C" {
|
||||
# endif
|
||||
|
||||
struct hash_tuning
|
||||
{
|
||||
/* This structure is mainly used for 'hash_initialize', see the block
|
||||
documentation of 'hash_reset_tuning' for more complete comments. */
|
||||
|
||||
float shrink_threshold; /* ratio of used buckets to trigger a shrink */
|
||||
float shrink_factor; /* ratio of new smaller size to original size */
|
||||
float growth_threshold; /* ratio of used buckets to trigger a growth */
|
||||
float growth_factor; /* ratio of new bigger size to original size */
|
||||
bool is_n_buckets; /* if CANDIDATE really means table size */
|
||||
};
|
||||
|
||||
typedef struct hash_tuning Hash_tuning;
|
||||
|
||||
struct hash_table;
|
||||
|
||||
typedef struct hash_table Hash_table;
|
||||
|
||||
/*
|
||||
* Information and lookup.
|
||||
*/
|
||||
|
||||
/* The following few functions provide information about the overall hash
|
||||
table organization: the number of entries, number of buckets and maximum
|
||||
length of buckets. */
|
||||
|
||||
/* Return the number of buckets in the hash table. The table size, the total
|
||||
number of buckets (used plus unused), or the maximum number of slots, are
|
||||
the same quantity. */
|
||||
extern size_t hash_get_n_buckets (const Hash_table *table);
|
||||
|
||||
/* Return the number of slots in use (non-empty buckets). */
|
||||
extern size_t hash_get_n_buckets_used (const Hash_table *table);
|
||||
|
||||
/* Return the number of active entries. */
|
||||
extern size_t hash_get_n_entries (const Hash_table *table);
|
||||
|
||||
/* Return the length of the longest chain (bucket). */
|
||||
extern size_t hash_get_max_bucket_length (const Hash_table *table);
|
||||
|
||||
/* Do a mild validation of a hash table, by traversing it and checking two
|
||||
statistics. */
|
||||
extern bool hash_table_ok (const Hash_table *table);
|
||||
|
||||
extern void hash_print_statistics (const Hash_table *table, FILE *stream);
|
||||
|
||||
/* If ENTRY matches an entry already in the hash table, return the
|
||||
entry from the table. Otherwise, return NULL. */
|
||||
extern void *hash_lookup (const Hash_table *table, const void *entry);
|
||||
|
||||
/*
|
||||
* Walking.
|
||||
*/
|
||||
|
||||
/* The functions in this page traverse the hash table and process the
|
||||
contained entries. For the traversal to work properly, the hash table
|
||||
should not be resized nor modified while any particular entry is being
|
||||
processed. In particular, entries should not be added, and an entry
|
||||
may be removed only if there is no shrink threshold and the entry being
|
||||
removed has already been passed to hash_get_next. */
|
||||
|
||||
/* Return the first data in the table, or NULL if the table is empty. */
|
||||
extern void *hash_get_first (const Hash_table *table);
|
||||
|
||||
/* Return the user data for the entry following ENTRY, where ENTRY has been
|
||||
returned by a previous call to either 'hash_get_first' or 'hash_get_next'.
|
||||
Return NULL if there are no more entries. */
|
||||
extern void *hash_get_next (const Hash_table *table, const void *entry);
|
||||
|
||||
/* Fill BUFFER with pointers to active user entries in the hash table, then
|
||||
return the number of pointers copied. Do not copy more than BUFFER_SIZE
|
||||
pointers. */
|
||||
extern size_t hash_get_entries (const Hash_table *table, void **buffer,
|
||||
size_t buffer_size);
|
||||
|
||||
typedef bool (*Hash_processor) (void *entry, void *processor_data);
|
||||
|
||||
/* Call a PROCESSOR function for each entry of a hash table, and return the
|
||||
number of entries for which the processor function returned success. A
|
||||
pointer to some PROCESSOR_DATA which will be made available to each call to
|
||||
the processor function. The PROCESSOR accepts two arguments: the first is
|
||||
the user entry being walked into, the second is the value of PROCESSOR_DATA
|
||||
as received. The walking continue for as long as the PROCESSOR function
|
||||
returns nonzero. When it returns zero, the walking is interrupted. */
|
||||
extern size_t hash_do_for_each (const Hash_table *table,
|
||||
Hash_processor processor, void *processor_data);
|
||||
|
||||
/*
|
||||
* Allocation and clean-up.
|
||||
*/
|
||||
|
||||
/* Return a hash index for a NUL-terminated STRING between 0 and N_BUCKETS-1.
|
||||
This is a convenience routine for constructing other hashing functions. */
|
||||
extern size_t hash_string (const char *string, size_t n_buckets);
|
||||
|
||||
extern void hash_reset_tuning (Hash_tuning *tuning);
|
||||
|
||||
typedef size_t (*Hash_hasher) (const void *entry, size_t table_size);
|
||||
typedef bool (*Hash_comparator) (const void *entry1, const void *entry2);
|
||||
typedef void (*Hash_data_freer) (void *entry);
|
||||
|
||||
/* Allocate and return a new hash table, or NULL upon failure. The initial
|
||||
number of buckets is automatically selected so as to _guarantee_ that you
|
||||
may insert at least CANDIDATE different user entries before any growth of
|
||||
the hash table size occurs. So, if have a reasonably tight a-priori upper
|
||||
bound on the number of entries you intend to insert in the hash table, you
|
||||
may save some table memory and insertion time, by specifying it here. If
|
||||
the IS_N_BUCKETS field of the TUNING structure is true, the CANDIDATE
|
||||
argument has its meaning changed to the wanted number of buckets.
|
||||
|
||||
TUNING points to a structure of user-supplied values, in case some fine
|
||||
tuning is wanted over the default behavior of the hasher. If TUNING is
|
||||
NULL, the default tuning parameters are used instead. If TUNING is
|
||||
provided but the values requested are out of bounds or might cause
|
||||
rounding errors, return NULL.
|
||||
|
||||
The user-supplied HASHER function, when not NULL, accepts two
|
||||
arguments ENTRY and TABLE_SIZE. It computes, by hashing ENTRY contents, a
|
||||
slot number for that entry which should be in the range 0..TABLE_SIZE-1.
|
||||
This slot number is then returned.
|
||||
|
||||
The user-supplied COMPARATOR function, when not NULL, accepts two
|
||||
arguments pointing to user data, it then returns true for a pair of entries
|
||||
that compare equal, or false otherwise. This function is internally called
|
||||
on entries which are already known to hash to the same bucket index,
|
||||
but which are distinct pointers.
|
||||
|
||||
The user-supplied DATA_FREER function, when not NULL, may be later called
|
||||
with the user data as an argument, just before the entry containing the
|
||||
data gets freed. This happens from within 'hash_free' or 'hash_clear'.
|
||||
You should specify this function only if you want these functions to free
|
||||
all of your 'data' data. This is typically the case when your data is
|
||||
simply an auxiliary struct that you have malloc'd to aggregate several
|
||||
values. */
|
||||
extern Hash_table *hash_initialize (size_t candidate,
|
||||
const Hash_tuning *tuning,
|
||||
Hash_hasher hasher,
|
||||
Hash_comparator comparator,
|
||||
Hash_data_freer data_freer);
|
||||
|
||||
/* Same as hash_initialize, but invokes xalloc_die on memory exhaustion. */
|
||||
/* This function is defined by module 'xhash'. */
|
||||
extern Hash_table *hash_xinitialize (size_t candidate,
|
||||
const Hash_tuning *tuning,
|
||||
Hash_hasher hasher,
|
||||
Hash_comparator comparator,
|
||||
Hash_data_freer data_freer);
|
||||
|
||||
/* Make all buckets empty, placing any chained entries on the free list.
|
||||
Apply the user-specified function data_freer (if any) to the datas of any
|
||||
affected entries. */
|
||||
extern void hash_clear (Hash_table *table);
|
||||
|
||||
/* Reclaim all storage associated with a hash table. If a data_freer
|
||||
function has been supplied by the user when the hash table was created,
|
||||
this function applies it to the data of each entry before freeing that
|
||||
entry. */
|
||||
extern void hash_free (Hash_table *table);
|
||||
|
||||
/*
|
||||
* Insertion and deletion.
|
||||
*/
|
||||
|
||||
/* For an already existing hash table, change the number of buckets through
|
||||
specifying CANDIDATE. The contents of the hash table are preserved. The
|
||||
new number of buckets is automatically selected so as to _guarantee_ that
|
||||
the table may receive at least CANDIDATE different user entries, including
|
||||
those already in the table, before any other growth of the hash table size
|
||||
occurs. If TUNING->IS_N_BUCKETS is true, then CANDIDATE specifies the
|
||||
exact number of buckets desired. Return true iff the rehash succeeded. */
|
||||
extern bool hash_rehash (Hash_table *table, size_t candidate);
|
||||
|
||||
/* If ENTRY matches an entry already in the hash table, return the pointer
|
||||
to the entry from the table. Otherwise, insert ENTRY and return ENTRY.
|
||||
Return NULL if the storage required for insertion cannot be allocated.
|
||||
This implementation does not support duplicate entries or insertion of
|
||||
NULL. */
|
||||
extern void *hash_insert (Hash_table *table, const void *entry);
|
||||
|
||||
/* Same as hash_insert, but invokes xalloc_die on memory exhaustion. */
|
||||
/* This function is defined by module 'xhash'. */
|
||||
extern void *hash_xinsert (Hash_table *table, const void *entry);
|
||||
|
||||
/* Insert ENTRY into hash TABLE if there is not already a matching entry.
|
||||
|
||||
Return -1 upon memory allocation failure.
|
||||
Return 1 if insertion succeeded.
|
||||
Return 0 if there is already a matching entry in the table,
|
||||
and in that case, if MATCHED_ENT is non-NULL, set *MATCHED_ENT
|
||||
to that entry.
|
||||
|
||||
This interface is easier to use than hash_insert when you must
|
||||
distinguish between the latter two cases. More importantly,
|
||||
hash_insert is unusable for some types of ENTRY values. When using
|
||||
hash_insert, the only way to distinguish those cases is to compare
|
||||
the return value and ENTRY. That works only when you can have two
|
||||
different ENTRY values that point to data that compares "equal". Thus,
|
||||
when the ENTRY value is a simple scalar, you must use
|
||||
hash_insert_if_absent. ENTRY must not be NULL. */
|
||||
extern int hash_insert_if_absent (Hash_table *table, const void *entry,
|
||||
const void **matched_ent);
|
||||
|
||||
/* If ENTRY is already in the table, remove it and return the just-deleted
|
||||
data (the user may want to deallocate its storage). If ENTRY is not in the
|
||||
table, don't modify the table and return NULL. */
|
||||
extern void *hash_remove (Hash_table *table, const void *entry);
|
||||
|
||||
/* Same as hash_remove. This interface is deprecated.
|
||||
FIXME: Remove in 2022. */
|
||||
extern void *hash_delete (Hash_table *table, const void *entry);
|
||||
|
||||
# ifdef __cplusplus
|
||||
}
|
||||
# endif
|
||||
|
||||
#endif
|
||||
58
gnulib/lib/ignore-value.h
Executable file
58
gnulib/lib/ignore-value.h
Executable file
@@ -0,0 +1,58 @@
|
||||
/* ignore a function return without a compiler warning. -*- coding: utf-8 -*-
|
||||
|
||||
Copyright (C) 2008-2021 Free Software Foundation, Inc.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
/* Written by Jim Meyering, Eric Blake and Pádraig Brady. */
|
||||
|
||||
/* Use "ignore_value" to avoid a warning when using a function declared with
|
||||
gcc's warn_unused_result attribute, but for which you really do want to
|
||||
ignore the result. Traditionally, people have used a "(void)" cast to
|
||||
indicate that a function's return value is deliberately unused. However,
|
||||
if the function is declared with __attribute__((warn_unused_result)),
|
||||
gcc issues a warning even with the cast.
|
||||
|
||||
Caution: most of the time, you really should heed gcc's warning, and
|
||||
check the return value. However, in those exceptional cases in which
|
||||
you're sure you know what you're doing, use this function.
|
||||
|
||||
For the record, here's one of the ignorable warnings:
|
||||
"copy.c:233: warning: ignoring return value of 'fchown',
|
||||
declared with attribute warn_unused_result". */
|
||||
|
||||
#ifndef _GL_IGNORE_VALUE_H
|
||||
#define _GL_IGNORE_VALUE_H
|
||||
|
||||
/* Normally casting an expression to void discards its value, but GCC
|
||||
versions 3.4 and newer have __attribute__ ((__warn_unused_result__))
|
||||
which may cause unwanted diagnostics in that case. Use __typeof__
|
||||
and __extension__ to work around the problem, if the workaround is
|
||||
known to be needed.
|
||||
The workaround is not needed with clang. */
|
||||
#if (3 < __GNUC__ + (4 <= __GNUC_MINOR__)) && !defined __clang__
|
||||
# define ignore_value(x) \
|
||||
(__extension__ ({ __typeof__ (x) __x = (x); (void) __x; }))
|
||||
#else
|
||||
# define ignore_value(x) ((void) (x))
|
||||
#endif
|
||||
|
||||
#endif
|
||||
170
gnulib/lib/nonblocking.c
Normal file
170
gnulib/lib/nonblocking.c
Normal file
@@ -0,0 +1,170 @@
|
||||
/* Non-blocking I/O for pipe or socket descriptors.
|
||||
Copyright (C) 2011-2021 Free Software Foundation, Inc.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#include <config.h>
|
||||
|
||||
/* Specification. */
|
||||
#include "nonblocking.h"
|
||||
|
||||
#include <errno.h>
|
||||
|
||||
#if defined _WIN32 && ! defined __CYGWIN__
|
||||
/* Native Windows API. */
|
||||
|
||||
# include <sys/ioctl.h>
|
||||
# include <sys/socket.h>
|
||||
# include <unistd.h>
|
||||
|
||||
/* Get declarations of the native Windows API functions. */
|
||||
# define WIN32_LEAN_AND_MEAN
|
||||
# include <windows.h>
|
||||
|
||||
# if GNULIB_MSVC_NOTHROW
|
||||
# include "msvc-nothrow.h"
|
||||
# else
|
||||
# include <io.h>
|
||||
# endif
|
||||
|
||||
/* Don't assume that UNICODE is not defined. */
|
||||
# undef GetNamedPipeHandleState
|
||||
# define GetNamedPipeHandleState GetNamedPipeHandleStateA
|
||||
|
||||
int
|
||||
get_nonblocking_flag (int desc)
|
||||
{
|
||||
HANDLE h = (HANDLE) _get_osfhandle (desc);
|
||||
if (h == INVALID_HANDLE_VALUE)
|
||||
{
|
||||
errno = EBADF;
|
||||
return -1;
|
||||
}
|
||||
if (GetFileType (h) == FILE_TYPE_PIPE)
|
||||
{
|
||||
/* h is a pipe or socket. */
|
||||
DWORD state;
|
||||
if (GetNamedPipeHandleState (h, &state, NULL, NULL, NULL, NULL, 0))
|
||||
/* h is a pipe. */
|
||||
return (state & PIPE_NOWAIT) != 0;
|
||||
else
|
||||
/* h is a socket. */
|
||||
errno = ENOSYS;
|
||||
return -1;
|
||||
}
|
||||
else
|
||||
/* The native Windows API does not support non-blocking on regular
|
||||
files. */
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
set_nonblocking_flag (int desc, bool value)
|
||||
{
|
||||
HANDLE h = (HANDLE) _get_osfhandle (desc);
|
||||
if (h == INVALID_HANDLE_VALUE)
|
||||
{
|
||||
errno = EBADF;
|
||||
return -1;
|
||||
}
|
||||
if (GetFileType (h) == FILE_TYPE_PIPE)
|
||||
{
|
||||
/* h is a pipe or socket. */
|
||||
DWORD state;
|
||||
if (GetNamedPipeHandleState (h, &state, NULL, NULL, NULL, NULL, 0))
|
||||
{
|
||||
/* h is a pipe. */
|
||||
if ((state & PIPE_NOWAIT) != 0)
|
||||
{
|
||||
if (value)
|
||||
return 0;
|
||||
state &= ~PIPE_NOWAIT;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!value)
|
||||
return 0;
|
||||
state |= PIPE_NOWAIT;
|
||||
}
|
||||
if (SetNamedPipeHandleState (h, &state, NULL, NULL))
|
||||
return 0;
|
||||
errno = EINVAL;
|
||||
return -1;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* h is a socket. */
|
||||
int v = value;
|
||||
return ioctl (desc, FIONBIO, &v);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* The native Windows API does not support non-blocking on regular
|
||||
files. */
|
||||
if (!value)
|
||||
return 0;
|
||||
errno = ENOTSUP;
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
#else
|
||||
/* Unix API. */
|
||||
|
||||
# include <fcntl.h>
|
||||
|
||||
# if GNULIB_defined_O_NONBLOCK
|
||||
# error Please port nonblocking to your platform
|
||||
# endif
|
||||
|
||||
/* We don't need the gnulib replacement of fcntl() here. */
|
||||
# undef fcntl
|
||||
|
||||
int
|
||||
get_nonblocking_flag (int desc)
|
||||
{
|
||||
int fcntl_flags;
|
||||
|
||||
fcntl_flags = fcntl (desc, F_GETFL, 0);
|
||||
if (fcntl_flags < 0)
|
||||
return -1;
|
||||
return (fcntl_flags & O_NONBLOCK) != 0;
|
||||
}
|
||||
|
||||
int
|
||||
set_nonblocking_flag (int desc, bool value)
|
||||
{
|
||||
int fcntl_flags;
|
||||
|
||||
fcntl_flags = fcntl (desc, F_GETFL, 0);
|
||||
if (fcntl_flags < 0)
|
||||
return -1;
|
||||
if (((fcntl_flags & O_NONBLOCK) != 0) == value)
|
||||
return 0;
|
||||
if (value)
|
||||
fcntl_flags |= O_NONBLOCK;
|
||||
else
|
||||
fcntl_flags &= ~O_NONBLOCK;
|
||||
return fcntl (desc, F_SETFL, fcntl_flags);
|
||||
}
|
||||
|
||||
#endif
|
||||
69
gnulib/lib/nonblocking.h
Normal file
69
gnulib/lib/nonblocking.h
Normal file
@@ -0,0 +1,69 @@
|
||||
/* Non-blocking I/O for pipe or socket descriptors.
|
||||
Copyright (C) 2011-2021 Free Software Foundation, Inc.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef _NONBLOCKING_H
|
||||
#define _NONBLOCKING_H
|
||||
|
||||
#include <stdbool.h>
|
||||
|
||||
/* Non-blocking I/O is an I/O mode by which read(), write() calls avoid
|
||||
blocking the current thread. When non-blocking is enabled:
|
||||
- A read() call returns -1 with errno set to EAGAIN when no data or EOF
|
||||
information is immediately available.
|
||||
- A write() call returns -1 with errno set to EAGAIN when it cannot
|
||||
transport the requested amount of data (but at most one pipe buffer)
|
||||
without blocking.
|
||||
Non-blocking I/O is most useful for character devices, pipes, and sockets.
|
||||
Whether it also works on regular files and block devices is platform
|
||||
dependent.
|
||||
|
||||
There are three modern alternatives to non-blocking I/O:
|
||||
- use select() or poll() followed by read() or write() if the descriptor
|
||||
is ready,
|
||||
- call read() or write() in separate threads,
|
||||
- use <aio.h> interfaces. */
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
|
||||
/* Return 1 if I/O to the descriptor DESC is currently non-blocking, 0
|
||||
it is blocking, or -1 with errno set if fd is invalid or blocking
|
||||
status cannot be determined (such as with sockets on mingw). */
|
||||
extern int get_nonblocking_flag (int desc);
|
||||
|
||||
/* Specify the non-blocking flag for the descriptor DESC.
|
||||
Return 0 upon success, or -1 with errno set upon failure.
|
||||
The default depends on the presence of the O_NONBLOCK flag for files
|
||||
or pipes opened with open() or on the presence of the SOCK_NONBLOCK
|
||||
flag for sockets. */
|
||||
extern int set_nonblocking_flag (int desc, bool value);
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* _NONBLOCKING_H */
|
||||
79
gnulib/lib/safe-read.c
Normal file
79
gnulib/lib/safe-read.c
Normal file
@@ -0,0 +1,79 @@
|
||||
/* An interface to read and write that retries after interrupts.
|
||||
|
||||
Copyright (C) 1993-1994, 1998, 2002-2006, 2009-2021 Free Software
|
||||
Foundation, Inc.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#include <config.h>
|
||||
|
||||
/* Specification. */
|
||||
#ifdef SAFE_WRITE
|
||||
# include "safe-write.h"
|
||||
#else
|
||||
# include "safe-read.h"
|
||||
#endif
|
||||
|
||||
/* Get ssize_t. */
|
||||
#include <sys/types.h>
|
||||
#include <unistd.h>
|
||||
#include <limits.h>
|
||||
|
||||
#include <errno.h>
|
||||
|
||||
#ifdef EINTR
|
||||
# define IS_EINTR(x) ((x) == EINTR)
|
||||
#else
|
||||
# define IS_EINTR(x) 0
|
||||
#endif
|
||||
|
||||
enum { SYS_BUFSIZE_MAX = INT_MAX >> 20 << 20 };
|
||||
|
||||
#ifdef SAFE_WRITE
|
||||
# define safe_rw safe_write
|
||||
# define rw write
|
||||
#else
|
||||
# define safe_rw safe_read
|
||||
# define rw read
|
||||
# undef const
|
||||
# define const /* empty */
|
||||
#endif
|
||||
|
||||
/* Read(write) up to COUNT bytes at BUF from(to) descriptor FD, retrying if
|
||||
interrupted. Return the actual number of bytes read(written), zero for EOF,
|
||||
or SAFE_READ_ERROR(SAFE_WRITE_ERROR) upon error. */
|
||||
size_t
|
||||
safe_rw (int fd, void const *buf, size_t count)
|
||||
{
|
||||
for (;;)
|
||||
{
|
||||
ssize_t result = rw (fd, buf, count);
|
||||
|
||||
if (0 <= result)
|
||||
return result;
|
||||
else if (IS_EINTR (errno))
|
||||
continue;
|
||||
else if (errno == EINVAL && SYS_BUFSIZE_MAX < count)
|
||||
count = SYS_BUFSIZE_MAX;
|
||||
else
|
||||
return result;
|
||||
}
|
||||
}
|
||||
54
gnulib/lib/safe-read.h
Normal file
54
gnulib/lib/safe-read.h
Normal file
@@ -0,0 +1,54 @@
|
||||
/* An interface to read() that retries after interrupts.
|
||||
Copyright (C) 2002, 2006, 2009-2021 Free Software Foundation, Inc.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
/* Some system calls may be interrupted and fail with errno = EINTR in the
|
||||
following situations:
|
||||
- The process is stopped and restarted (signal SIGSTOP and SIGCONT, user
|
||||
types Ctrl-Z) on some platforms: Mac OS X.
|
||||
- The process receives a signal for which a signal handler was installed
|
||||
with sigaction() with an sa_flags field that does not contain
|
||||
SA_RESTART.
|
||||
- The process receives a signal for which a signal handler was installed
|
||||
with signal() and for which no call to siginterrupt(sig,0) was done,
|
||||
on some platforms: AIX, HP-UX, IRIX, OSF/1, Solaris.
|
||||
|
||||
This module provides a wrapper around read() that handles EINTR. */
|
||||
|
||||
#include <stddef.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
|
||||
#define SAFE_READ_ERROR ((size_t) -1)
|
||||
|
||||
/* Read up to COUNT bytes at BUF from descriptor FD, retrying if interrupted.
|
||||
Return the actual number of bytes read, zero for EOF, or SAFE_READ_ERROR
|
||||
upon error. */
|
||||
extern size_t safe_read (int fd, void *buf, size_t count);
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
25
gnulib/lib/safe-write.c
Normal file
25
gnulib/lib/safe-write.c
Normal file
@@ -0,0 +1,25 @@
|
||||
/* An interface to write that retries after interrupts.
|
||||
Copyright (C) 2002, 2009-2021 Free Software Foundation, Inc.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#define SAFE_WRITE
|
||||
#include "safe-read.c"
|
||||
44
gnulib/lib/safe-write.h
Normal file
44
gnulib/lib/safe-write.h
Normal file
@@ -0,0 +1,44 @@
|
||||
/* An interface to write() that retries after interrupts.
|
||||
Copyright (C) 2002, 2009-2021 Free Software Foundation, Inc.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
/* Some system calls may be interrupted and fail with errno = EINTR in the
|
||||
following situations:
|
||||
- The process is stopped and restarted (signal SIGSTOP and SIGCONT, user
|
||||
types Ctrl-Z) on some platforms: Mac OS X.
|
||||
- The process receives a signal for which a signal handler was installed
|
||||
with sigaction() with an sa_flags field that does not contain
|
||||
SA_RESTART.
|
||||
- The process receives a signal for which a signal handler was installed
|
||||
with signal() and for which no call to siginterrupt(sig,0) was done,
|
||||
on some platforms: AIX, HP-UX, IRIX, OSF/1, Solaris.
|
||||
|
||||
This module provides a wrapper around write() that handles EINTR. */
|
||||
|
||||
#include <stddef.h>
|
||||
|
||||
#define SAFE_WRITE_ERROR ((size_t) -1)
|
||||
|
||||
/* Write up to COUNT bytes at BUF to descriptor FD, retrying if interrupted.
|
||||
Return the actual number of bytes written, zero for EOF, or SAFE_WRITE_ERROR
|
||||
upon error. */
|
||||
extern size_t safe_write (int fd, const void *buf, size_t count);
|
||||
67
gnulib/lib/xalloc-oversized.h
Executable file
67
gnulib/lib/xalloc-oversized.h
Executable file
@@ -0,0 +1,67 @@
|
||||
/* xalloc-oversized.h -- memory allocation size checking
|
||||
|
||||
Copyright (C) 1990-2000, 2003-2004, 2006-2021 Free Software Foundation, Inc.
|
||||
|
||||
(NB: I modified the original GPL boilerplate here to LGPLv2+. This
|
||||
is because of the weird way that gnulib uses licenses, where the
|
||||
real license is covered in the modules/X file. The real license
|
||||
for this file is LGPLv2+, not GPL. - RWMJ)
|
||||
|
||||
This library 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 of the License, or (at your option) any later version.
|
||||
|
||||
This library 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 library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef XALLOC_OVERSIZED_H_
|
||||
#define XALLOC_OVERSIZED_H_
|
||||
|
||||
#include <stddef.h>
|
||||
#include <stdint.h>
|
||||
|
||||
/* True if N * S would overflow in a size_t calculation,
|
||||
or would generate a value larger than PTRDIFF_MAX.
|
||||
This expands to a constant expression if N and S are both constants.
|
||||
By gnulib convention, SIZE_MAX represents overflow in size
|
||||
calculations, so the conservative size_t-based dividend to use here
|
||||
is SIZE_MAX - 1. */
|
||||
#define __xalloc_oversized(n, s) \
|
||||
((size_t) (PTRDIFF_MAX < SIZE_MAX ? PTRDIFF_MAX : SIZE_MAX - 1) / (s) < (n))
|
||||
|
||||
#if PTRDIFF_MAX < SIZE_MAX
|
||||
typedef ptrdiff_t __xalloc_count_type;
|
||||
#else
|
||||
typedef size_t __xalloc_count_type;
|
||||
#endif
|
||||
|
||||
/* Return 1 if an array of N objects, each of size S, cannot exist
|
||||
reliably due to size or ptrdiff_t arithmetic overflow. S must be
|
||||
positive and N must be nonnegative. This is a macro, not a
|
||||
function, so that it works correctly even when SIZE_MAX < N. */
|
||||
|
||||
#if 7 <= __GNUC__ && !defined __clang__
|
||||
# define xalloc_oversized(n, s) \
|
||||
__builtin_mul_overflow_p (n, s, (__xalloc_count_type) 1)
|
||||
#elif 5 <= __GNUC__ && !defined __ICC && !__STRICT_ANSI__
|
||||
# define xalloc_oversized(n, s) \
|
||||
(__builtin_constant_p (n) && __builtin_constant_p (s) \
|
||||
? __xalloc_oversized (n, s) \
|
||||
: ({ __xalloc_count_type __xalloc_count; \
|
||||
__builtin_mul_overflow (n, s, &__xalloc_count); }))
|
||||
|
||||
/* Other compilers use integer division; this may be slower but is
|
||||
more portable. */
|
||||
#else
|
||||
# define xalloc_oversized(n, s) __xalloc_oversized (n, s)
|
||||
#endif
|
||||
|
||||
#endif /* !XALLOC_OVERSIZED_H_ */
|
||||
236
gnulib/lib/xstrtol.c
Normal file
236
gnulib/lib/xstrtol.c
Normal file
@@ -0,0 +1,236 @@
|
||||
/* A more useful interface to strtol.
|
||||
|
||||
Copyright (C) 1995-1996, 1998-2001, 2003-2007, 2009-2021 Free Software
|
||||
Foundation, Inc.
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program 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 General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program. If not, see <https://www.gnu.org/licenses/>. */
|
||||
|
||||
/* Written by Jim Meyering. */
|
||||
|
||||
#ifndef __strtol
|
||||
# define __strtol strtol
|
||||
# define __strtol_t long int
|
||||
# define __xstrtol xstrtol
|
||||
# define STRTOL_T_MINIMUM LONG_MIN
|
||||
# define STRTOL_T_MAXIMUM LONG_MAX
|
||||
#endif
|
||||
|
||||
#include <config.h>
|
||||
|
||||
#include "xstrtol.h"
|
||||
|
||||
/* Some pre-ANSI implementations (e.g. SunOS 4)
|
||||
need stderr defined if assertion checking is enabled. */
|
||||
#include <stdio.h>
|
||||
|
||||
#include <ctype.h>
|
||||
#include <errno.h>
|
||||
#include <limits.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
|
||||
#define TYPE_SIGNED(t) (! ((t) 0 < (t) -1))
|
||||
|
||||
static strtol_error
|
||||
bkm_scale (__strtol_t *x, int scale_factor)
|
||||
{
|
||||
if (TYPE_SIGNED (__strtol_t) && *x < STRTOL_T_MINIMUM / scale_factor)
|
||||
{
|
||||
*x = STRTOL_T_MINIMUM;
|
||||
return LONGINT_OVERFLOW;
|
||||
}
|
||||
if (STRTOL_T_MAXIMUM / scale_factor < *x)
|
||||
{
|
||||
*x = STRTOL_T_MAXIMUM;
|
||||
return LONGINT_OVERFLOW;
|
||||
}
|
||||
*x *= scale_factor;
|
||||
return LONGINT_OK;
|
||||
}
|
||||
|
||||
static strtol_error
|
||||
bkm_scale_by_power (__strtol_t *x, int base, int power)
|
||||
{
|
||||
strtol_error err = LONGINT_OK;
|
||||
while (power--)
|
||||
err |= bkm_scale (x, base);
|
||||
return err;
|
||||
}
|
||||
|
||||
/* FIXME: comment. */
|
||||
|
||||
strtol_error
|
||||
__xstrtol (const char *s, char **ptr, int strtol_base,
|
||||
__strtol_t *val, const char *valid_suffixes)
|
||||
{
|
||||
char *t_ptr;
|
||||
char **p;
|
||||
__strtol_t tmp;
|
||||
strtol_error err = LONGINT_OK;
|
||||
|
||||
assert (0 <= strtol_base && strtol_base <= 36);
|
||||
|
||||
p = (ptr ? ptr : &t_ptr);
|
||||
|
||||
errno = 0;
|
||||
|
||||
if (! TYPE_SIGNED (__strtol_t))
|
||||
{
|
||||
const char *q = s;
|
||||
unsigned char ch = *q;
|
||||
while (isspace (ch))
|
||||
ch = *++q;
|
||||
if (ch == '-')
|
||||
return LONGINT_INVALID;
|
||||
}
|
||||
|
||||
tmp = __strtol (s, p, strtol_base);
|
||||
|
||||
if (*p == s)
|
||||
{
|
||||
/* If there is no number but there is a valid suffix, assume the
|
||||
number is 1. The string is invalid otherwise. */
|
||||
if (valid_suffixes && **p && strchr (valid_suffixes, **p))
|
||||
tmp = 1;
|
||||
else
|
||||
return LONGINT_INVALID;
|
||||
}
|
||||
else if (errno != 0)
|
||||
{
|
||||
if (errno != ERANGE)
|
||||
return LONGINT_INVALID;
|
||||
err = LONGINT_OVERFLOW;
|
||||
}
|
||||
|
||||
/* Let valid_suffixes == NULL mean "allow any suffix". */
|
||||
/* FIXME: update all callers except the ones that allow suffixes
|
||||
after the number, changing last parameter NULL to "". */
|
||||
if (!valid_suffixes)
|
||||
{
|
||||
*val = tmp;
|
||||
return err;
|
||||
}
|
||||
|
||||
if (**p != '\0')
|
||||
{
|
||||
int base = 1024;
|
||||
int suffixes = 1;
|
||||
strtol_error overflow;
|
||||
|
||||
if (!strchr (valid_suffixes, **p))
|
||||
{
|
||||
*val = tmp;
|
||||
return err | LONGINT_INVALID_SUFFIX_CHAR;
|
||||
}
|
||||
|
||||
switch (**p)
|
||||
{
|
||||
case 'E': case 'G': case 'g': case 'k': case 'K': case 'M': case 'm':
|
||||
case 'P': case 'T': case 't': case 'Y': case 'Z':
|
||||
|
||||
/* The "valid suffix" '0' is a special flag meaning that
|
||||
an optional second suffix is allowed, which can change
|
||||
the base. A suffix "B" (e.g. "100MB") stands for a power
|
||||
of 1000, whereas a suffix "iB" (e.g. "100MiB") stands for
|
||||
a power of 1024. If no suffix (e.g. "100M"), assume
|
||||
power-of-1024. */
|
||||
|
||||
if (strchr (valid_suffixes, '0'))
|
||||
switch (p[0][1])
|
||||
{
|
||||
case 'i':
|
||||
if (p[0][2] == 'B')
|
||||
suffixes += 2;
|
||||
break;
|
||||
|
||||
case 'B':
|
||||
case 'D': /* 'D' is obsolescent */
|
||||
base = 1000;
|
||||
suffixes++;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
switch (**p)
|
||||
{
|
||||
case 'b':
|
||||
overflow = bkm_scale (&tmp, 512);
|
||||
break;
|
||||
|
||||
case 'B':
|
||||
/* This obsolescent first suffix is distinct from the 'B'
|
||||
second suffix above. E.g., 'tar -L 1000B' means change
|
||||
the tape after writing 1000 KiB of data. */
|
||||
overflow = bkm_scale (&tmp, 1024);
|
||||
break;
|
||||
|
||||
case 'c':
|
||||
overflow = LONGINT_OK;
|
||||
break;
|
||||
|
||||
case 'E': /* exa or exbi */
|
||||
overflow = bkm_scale_by_power (&tmp, base, 6);
|
||||
break;
|
||||
|
||||
case 'G': /* giga or gibi */
|
||||
case 'g': /* 'g' is undocumented; for compatibility only */
|
||||
overflow = bkm_scale_by_power (&tmp, base, 3);
|
||||
break;
|
||||
|
||||
case 'k': /* kilo */
|
||||
case 'K': /* kibi */
|
||||
overflow = bkm_scale_by_power (&tmp, base, 1);
|
||||
break;
|
||||
|
||||
case 'M': /* mega or mebi */
|
||||
case 'm': /* 'm' is undocumented; for compatibility only */
|
||||
overflow = bkm_scale_by_power (&tmp, base, 2);
|
||||
break;
|
||||
|
||||
case 'P': /* peta or pebi */
|
||||
overflow = bkm_scale_by_power (&tmp, base, 5);
|
||||
break;
|
||||
|
||||
case 'T': /* tera or tebi */
|
||||
case 't': /* 't' is undocumented; for compatibility only */
|
||||
overflow = bkm_scale_by_power (&tmp, base, 4);
|
||||
break;
|
||||
|
||||
case 'w':
|
||||
overflow = bkm_scale (&tmp, 2);
|
||||
break;
|
||||
|
||||
case 'Y': /* yotta or 2**80 */
|
||||
overflow = bkm_scale_by_power (&tmp, base, 8);
|
||||
break;
|
||||
|
||||
case 'Z': /* zetta or 2**70 */
|
||||
overflow = bkm_scale_by_power (&tmp, base, 7);
|
||||
break;
|
||||
|
||||
default:
|
||||
*val = tmp;
|
||||
return err | LONGINT_INVALID_SUFFIX_CHAR;
|
||||
}
|
||||
|
||||
err |= overflow;
|
||||
*p += suffixes;
|
||||
if (**p)
|
||||
err |= LONGINT_INVALID_SUFFIX_CHAR;
|
||||
}
|
||||
|
||||
*val = tmp;
|
||||
return err;
|
||||
}
|
||||
50
gnulib/lib/xstrtol.h
Normal file
50
gnulib/lib/xstrtol.h
Normal file
@@ -0,0 +1,50 @@
|
||||
/* A more useful interface to strtol.
|
||||
|
||||
Copyright (C) 1995-1996, 1998-1999, 2001-2004, 2006-2021 Free Software
|
||||
Foundation, Inc.
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program 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 General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program. If not, see <https://www.gnu.org/licenses/>. */
|
||||
|
||||
#ifndef XSTRTOL_H_
|
||||
# define XSTRTOL_H_ 1
|
||||
|
||||
# include <inttypes.h>
|
||||
|
||||
# ifndef _STRTOL_ERROR
|
||||
enum strtol_error
|
||||
{
|
||||
LONGINT_OK = 0,
|
||||
|
||||
/* These two values can be ORed together, to indicate that both
|
||||
errors occurred. */
|
||||
LONGINT_OVERFLOW = 1,
|
||||
LONGINT_INVALID_SUFFIX_CHAR = 2,
|
||||
|
||||
LONGINT_INVALID_SUFFIX_CHAR_WITH_OVERFLOW = (LONGINT_INVALID_SUFFIX_CHAR
|
||||
| LONGINT_OVERFLOW),
|
||||
LONGINT_INVALID = 4
|
||||
};
|
||||
typedef enum strtol_error strtol_error;
|
||||
# endif
|
||||
|
||||
# define _DECLARE_XSTRTOL(name, type) \
|
||||
strtol_error name (const char *, char **, int, type *, const char *);
|
||||
_DECLARE_XSTRTOL (xstrtol, long int)
|
||||
_DECLARE_XSTRTOL (xstrtoul, unsigned long int)
|
||||
_DECLARE_XSTRTOL (xstrtoll, long long int)
|
||||
_DECLARE_XSTRTOL (xstrtoull, unsigned long long int)
|
||||
_DECLARE_XSTRTOL (xstrtoimax, intmax_t)
|
||||
_DECLARE_XSTRTOL (xstrtoumax, uintmax_t)
|
||||
|
||||
#endif /* not XSTRTOL_H_ */
|
||||
10
gnulib/lib/xstrtoll.c
Normal file
10
gnulib/lib/xstrtoll.c
Normal file
@@ -0,0 +1,10 @@
|
||||
/* Note the license of this file is "GPL". It is used in the daemon
|
||||
* and in guestfish which have a compatible license.
|
||||
*/
|
||||
|
||||
#define __strtol strtoll
|
||||
#define __strtol_t long long int
|
||||
#define __xstrtol xstrtoll
|
||||
#define STRTOL_T_MINIMUM LLONG_MIN
|
||||
#define STRTOL_T_MAXIMUM LLONG_MAX
|
||||
#include "xstrtol.c"
|
||||
6
gnulib/lib/xstrtoul.c
Normal file
6
gnulib/lib/xstrtoul.c
Normal file
@@ -0,0 +1,6 @@
|
||||
#define __strtol strtoul
|
||||
#define __strtol_t unsigned long int
|
||||
#define __xstrtol xstrtoul
|
||||
#define STRTOL_T_MINIMUM 0
|
||||
#define STRTOL_T_MAXIMUM ULONG_MAX
|
||||
#include "xstrtol.c"
|
||||
6
gnulib/lib/xstrtoull.c
Normal file
6
gnulib/lib/xstrtoull.c
Normal file
@@ -0,0 +1,6 @@
|
||||
#define __strtol strtoull
|
||||
#define __strtol_t unsigned long long int
|
||||
#define __xstrtol xstrtoull
|
||||
#define STRTOL_T_MINIMUM 0
|
||||
#define STRTOL_T_MAXIMUM ULLONG_MAX
|
||||
#include "xstrtol.c"
|
||||
6
gnulib/lib/xstrtoumax.c
Normal file
6
gnulib/lib/xstrtoumax.c
Normal file
@@ -0,0 +1,6 @@
|
||||
#define __strtol strtoumax
|
||||
#define __strtol_t uintmax_t
|
||||
#define __xstrtol xstrtoumax
|
||||
#define STRTOL_T_MINIMUM 0
|
||||
#define STRTOL_T_MAXIMUM UINTMAX_MAX
|
||||
#include "xstrtol.c"
|
||||
251
m4/.gitignore
vendored
251
m4/.gitignore
vendored
@@ -1,251 +0,0 @@
|
||||
/00gnulib.m4
|
||||
/absolute-header.m4
|
||||
/accept4.m4
|
||||
/access.m4
|
||||
/alloca.m4
|
||||
/arpa_inet_h.m4
|
||||
/asm-underscore.m4
|
||||
/base64.m4
|
||||
/btowc.m4
|
||||
/builtin-expect.m4
|
||||
/byteswap.m4
|
||||
/chdir-long.m4
|
||||
/clock_time.m4
|
||||
/closedir.m4
|
||||
/close.m4
|
||||
/codeset.m4
|
||||
/creat.m4
|
||||
/ctype.m4
|
||||
/dirent_h.m4
|
||||
/dirfd.m4
|
||||
/double-slash-root.m4
|
||||
/d-type.m4
|
||||
/dup2.m4
|
||||
/dup.m4
|
||||
/eaccess.m4
|
||||
/eealloc.m4
|
||||
/environ.m4
|
||||
/errno_h.m4
|
||||
/error.m4
|
||||
/exponentd.m4
|
||||
/extensions.m4
|
||||
/extern-inline.m4
|
||||
/fatal-signal.m4
|
||||
/fchdir.m4
|
||||
/fcntl_h.m4
|
||||
/fcntl.m4
|
||||
/fcntl-o.m4
|
||||
/fdopen.m4
|
||||
/filenamecat.m4
|
||||
/findprog-in.m4
|
||||
/flexmember.m4
|
||||
/float_h.m4
|
||||
/fnmatch_h.m4
|
||||
/fnmatch.m4
|
||||
/fpending.m4
|
||||
/fpieee.m4
|
||||
/fstatat.m4
|
||||
/fstat.m4
|
||||
/ftruncate.m4
|
||||
/futimens.m4
|
||||
/getcwd.m4
|
||||
/getdelim.m4
|
||||
/getdtablesize.m4
|
||||
/getline.m4
|
||||
/getlogin.m4
|
||||
/getlogin_r.m4
|
||||
/getopt.m4
|
||||
/getpagesize.m4
|
||||
/getprogname.m4
|
||||
/getrandom.m4
|
||||
/gettime.m4
|
||||
/gettimeofday.m4
|
||||
/glob_h.m4
|
||||
/glob.m4
|
||||
/gnulib-common.m4
|
||||
/gnulib-comp.m4
|
||||
/gnulib-tool.m4
|
||||
/human.m4
|
||||
/include_next.m4
|
||||
/inet_pton.m4
|
||||
/__inline.m4
|
||||
/intlmacosx.m4
|
||||
/intl-thread-locale.m4
|
||||
/intmax_t.m4
|
||||
/inttostr.m4
|
||||
/inttypes_h.m4
|
||||
/inttypes.m4
|
||||
/ioctl.m4
|
||||
/isblank.m4
|
||||
/langinfo_h.m4
|
||||
/largefile.m4
|
||||
/lcmessage.m4
|
||||
/limits-h.m4
|
||||
/localcharset.m4
|
||||
/localeconv.m4
|
||||
/locale-fr.m4
|
||||
/locale_h.m4
|
||||
/locale-ja.m4
|
||||
/localename.m4
|
||||
/locale-tr.m4
|
||||
/locale-zh.m4
|
||||
/lock.m4
|
||||
/lseek.m4
|
||||
/lstat.m4
|
||||
/malloca.m4
|
||||
/malloc.m4
|
||||
/manywarnings-c++.m4
|
||||
/manywarnings.m4
|
||||
/math_h.m4
|
||||
/mbrtowc.m4
|
||||
/mbsinit.m4
|
||||
/mbsrtowcs.m4
|
||||
/mbstate_t.m4
|
||||
/mbtowc.m4
|
||||
/memchr.m4
|
||||
/memmem.m4
|
||||
/mempcpy.m4
|
||||
/memrchr.m4
|
||||
/minmax.m4
|
||||
/mkdir.m4
|
||||
/mkdtemp.m4
|
||||
/mkstemps.m4
|
||||
/mmap-anon.m4
|
||||
/mode_t.m4
|
||||
/msvc-inval.m4
|
||||
/msvc-nothrow.m4
|
||||
/multiarch.m4
|
||||
/musl.m4
|
||||
/nanosleep.m4
|
||||
/netdb_h.m4
|
||||
/netinet_in_h.m4
|
||||
/nocrash.m4
|
||||
/nonblocking.m4
|
||||
/off_t.m4
|
||||
/openat.m4
|
||||
/open-cloexec.m4
|
||||
/opendir.m4
|
||||
/open.m4
|
||||
/open-slash.m4
|
||||
/pathmax.m4
|
||||
/perror.m4
|
||||
/pid_t.m4
|
||||
/pipe2.m4
|
||||
/pipe.m4
|
||||
/posix_spawn.m4
|
||||
/pread.m4
|
||||
/printf.m4
|
||||
/priv-set.m4
|
||||
/pthread_h.m4
|
||||
/pthread_rwlock_rdlock.m4
|
||||
/pthread_sigmask.m4
|
||||
/pthread-thread.m4
|
||||
/putenv.m4
|
||||
/quotearg.m4
|
||||
/quote.m4
|
||||
/raise.m4
|
||||
/rawmemchr.m4
|
||||
/readdir.m4
|
||||
/readlinkat.m4
|
||||
/readlink.m4
|
||||
/read.m4
|
||||
/realloc.m4
|
||||
/rmdir.m4
|
||||
/safe-read.m4
|
||||
/safe-write.m4
|
||||
/save-cwd.m4
|
||||
/sched_h.m4
|
||||
/select.m4
|
||||
/semaphore.m4
|
||||
/setenv.m4
|
||||
/setlocale.m4
|
||||
/setlocale_null.m4
|
||||
/sh-filename.m4
|
||||
/sigaction.m4
|
||||
/sig_atomic_t.m4
|
||||
/signalblocking.m4
|
||||
/signal_h.m4
|
||||
/size_max.m4
|
||||
/sleep.m4
|
||||
/snprintf.m4
|
||||
/socketlib.m4
|
||||
/sockets.m4
|
||||
/socklen.m4
|
||||
/sockpfaf.m4
|
||||
/spawn_h.m4
|
||||
/ssize_t.m4
|
||||
/stat.m4
|
||||
/stat-time.m4
|
||||
/stdalign.m4
|
||||
/stdarg.m4
|
||||
/stdbool.m4
|
||||
/stddef_h.m4
|
||||
/std-gnu11.m4
|
||||
/stdint_h.m4
|
||||
/stdint.m4
|
||||
/stdio_h.m4
|
||||
/stdlib_h.m4
|
||||
/stpcpy.m4
|
||||
/strchrnul.m4
|
||||
/strdup.m4
|
||||
/strerror.m4
|
||||
/strerror_r.m4
|
||||
/string_h.m4
|
||||
/strndup.m4
|
||||
/strnlen.m4
|
||||
/strtoll.m4
|
||||
/strtoull.m4
|
||||
/strtoumax.m4
|
||||
/symlinkat.m4
|
||||
/symlink.m4
|
||||
/sys_ioctl_h.m4
|
||||
/sys_random_h.m4
|
||||
/sys_select_h.m4
|
||||
/sys_socket_h.m4
|
||||
/sys_stat_h.m4
|
||||
/sys_time_h.m4
|
||||
/sys_types_h.m4
|
||||
/sys_uio_h.m4
|
||||
/sys_wait_h.m4
|
||||
/tempname.m4
|
||||
/threadlib.m4
|
||||
/thread.m4
|
||||
/time_h.m4
|
||||
/timespec.m4
|
||||
/tls.m4
|
||||
/unistd_h.m4
|
||||
/unistd-safer.m4
|
||||
/unlinkat.m4
|
||||
/unlinkdir.m4
|
||||
/unlink.m4
|
||||
/usleep.m4
|
||||
/utimecmp.m4
|
||||
/utime_h.m4
|
||||
/utime.m4
|
||||
/utimensat.m4
|
||||
/utimens.m4
|
||||
/utimes.m4
|
||||
/vasnprintf.m4
|
||||
/vasprintf.m4
|
||||
/visibility.m4
|
||||
/vsnprintf.m4
|
||||
/waitpid.m4
|
||||
/wait-process.m4
|
||||
/warnings.m4
|
||||
/warn-on-use.m4
|
||||
/wchar_h.m4
|
||||
/wchar_t.m4
|
||||
/wcrtomb.m4
|
||||
/wctob.m4
|
||||
/wctomb.m4
|
||||
/wctype_h.m4
|
||||
/wint_t.m4
|
||||
/wmemchr.m4
|
||||
/wmempcpy.m4
|
||||
/write.m4
|
||||
/xalloc.m4
|
||||
/xsize.m4
|
||||
/xstrtol.m4
|
||||
/xvasprintf.m4
|
||||
/yield.m4
|
||||
/zzgnulib.m4
|
||||
131
m4/guestfs-c.m4
131
m4/guestfs-c.m4
@@ -24,115 +24,28 @@ AC_PROG_CC_STDC
|
||||
AC_PROG_INSTALL
|
||||
AC_PROG_CPP
|
||||
|
||||
AC_ARG_ENABLE([werror],
|
||||
[AS_HELP_STRING([--enable-werror],
|
||||
[turn GCC warnings into errors (for developers)])],
|
||||
[case $enableval in
|
||||
yes|no) ;;
|
||||
*) AC_MSG_ERROR([bad value $enableval for werror option]) ;;
|
||||
esac
|
||||
gl_gcc_werror=$enableval],
|
||||
[gl_gcc_werror=no]
|
||||
)
|
||||
|
||||
if test "$gl_gcc_werror" = yes; then
|
||||
gl_WARN_ADD([-Werror], [WERROR_CFLAGS])
|
||||
AC_SUBST([WERROR_CFLAGS])
|
||||
fi
|
||||
|
||||
dnl This, $nw, is the list of warnings we disable.
|
||||
nw=
|
||||
nw="$nw -Waggregate-return" # anachronistic
|
||||
nw="$nw -Wundef" # Warns on '#if GNULIB_FOO' etc in gnulib
|
||||
nw="$nw -Wtraditional" # Warns on #elif which we use often
|
||||
nw="$nw -Wsystem-headers" # Don't let system headers trigger warnings
|
||||
nw="$nw -Wpadded" # Our structs are not padded
|
||||
nw="$nw -Wvla" # Allow variable length arrays.
|
||||
nw="$nw -Wvla-larger-than=4031"
|
||||
nw="$nw -Winline" # inline functions in Python binding
|
||||
nw="$nw -Wshadow" # Not useful, as it applies to global vars
|
||||
nw="$nw -Wunsafe-loop-optimizations" # just a warning that an optimization
|
||||
# was not possible, safe to ignore
|
||||
nw="$nw -Wstack-protector" # Useless warning when stack protector
|
||||
# cannot being used in a function.
|
||||
nw="$nw -Wcast-align" # Useless warning on arm >= 7, intel
|
||||
nw="$nw -Wabi" # Broken in GCC 8.1.
|
||||
dnl things I might fix soon:
|
||||
nw="$nw -Wpacked" # Allow attribute((packed)) on structs
|
||||
nw="$nw -Wlong-long" # Allow long long since it's required
|
||||
# by Python, Ruby and xstrtoll.
|
||||
nw="$nw -Wsuggest-attribute=pure" # Don't suggest pure functions.
|
||||
nw="$nw -Wsuggest-attribute=const" # Don't suggest const functions.
|
||||
nw="$nw -Wsuggest-attribute=malloc" # Don't suggest malloc functions.
|
||||
nw="$nw -Wunsuffixed-float-constants" # Don't care about these.
|
||||
nw="$nw -Wswitch-default" # This warning is actively dangerous.
|
||||
nw="$nw -Woverlength-strings" # Who cares about stupid ISO C99 limit.
|
||||
|
||||
gl_MANYWARN_ALL_GCC([ws])
|
||||
gl_MANYWARN_COMPLEMENT([ws], [$ws], [$nw])
|
||||
for w in $ws; do
|
||||
gl_WARN_ADD([$w])
|
||||
done
|
||||
|
||||
dnl Normally we disable warnings in $nw above. However $nw only
|
||||
dnl filters out exact matching warning strings from a list inside
|
||||
dnl gnulib (see m4/manywarnings.m4). So we need to explicitly list a
|
||||
dnl few disabled warnings below.
|
||||
|
||||
dnl Unused parameters are not a bug.
|
||||
gl_WARN_ADD([-Wno-unused-parameter])
|
||||
|
||||
dnl Missing field initializers is not a bug in C.
|
||||
gl_WARN_ADD([-Wno-missing-field-initializers])
|
||||
|
||||
dnl Display the name of the warning option with the warning.
|
||||
gl_WARN_ADD([-fdiagnostics-show-option])
|
||||
|
||||
dnl Now some warnings we want to enable and/or customize ...
|
||||
|
||||
dnl Warn about large stack frames. This does not include alloca and
|
||||
dnl variable length arrays. Coverity warns about 10000 byte frames.
|
||||
gl_WARN_ADD([-Wframe-larger-than=6000])
|
||||
|
||||
dnl Warn about large stack frames, including estimates for alloca
|
||||
dnl and variable length arrays.
|
||||
gl_WARN_ADD([-Wstack-usage=10000])
|
||||
|
||||
dnl Warn about implicit fallthrough in case statements, but suppress
|
||||
dnl the warning if /*FALLTHROUGH*/ comment is used.
|
||||
gl_WARN_ADD([-Wimplicit-fallthrough=4])
|
||||
|
||||
dnl GCC level 2 gives incorrect warnings, so use level 1.
|
||||
gl_WARN_ADD([-Wformat-truncation=1])
|
||||
|
||||
dnl GCC 9 at level 2 gives apparently bogus errors when %.*s is used.
|
||||
gl_WARN_ADD([-Wformat-overflow=1])
|
||||
|
||||
dnl GCC < 11 gives warnings when disabling GCC 11 warnings.
|
||||
gl_WARN_ADD([-Wno-pragmas])
|
||||
|
||||
AC_SUBST([WARN_CFLAGS])
|
||||
|
||||
NO_SNV_CFLAGS=
|
||||
gl_COMPILER_OPTION_IF([-Wno-shift-negative-value],[
|
||||
NO_SNV_CFLAGS="-Wno-shift-negative-value"
|
||||
])
|
||||
AC_SUBST([NO_SNV_CFLAGS])
|
||||
|
||||
NO_UM_CFLAGS=
|
||||
gl_COMPILER_OPTION_IF([-Wno-unused-macros],[
|
||||
NO_UM_CFLAGS="-Wno-unused-macros"
|
||||
])
|
||||
AC_SUBST([NO_UM_CFLAGS])
|
||||
|
||||
AC_DEFINE([lint], [1], [Define to 1 if the compiler is checking for lint.])
|
||||
AC_DEFINE([GNULIB_PORTCHECK], [1], [Enable some gnulib portability checks.])
|
||||
|
||||
AC_C_PROTOTYPES
|
||||
test "x$U" != "x" && AC_MSG_ERROR([Compiler not ANSI compliant])
|
||||
|
||||
AM_PROG_CC_C_O
|
||||
|
||||
AC_ARG_ENABLE([werror],
|
||||
[AS_HELP_STRING([--enable-error],
|
||||
[turn on lots of GCC warnings (for developers)])],
|
||||
[case $enableval in
|
||||
yes|no) ;;
|
||||
*) AC_MSG_ERROR([bad value $enableval for werror option]) ;;
|
||||
esac
|
||||
gcc_warnings=$enableval],
|
||||
[gcc_warnings=no]
|
||||
)
|
||||
WARN_CFLAGS="-Wall"
|
||||
AC_SUBST([WARN_CFLAGS])
|
||||
if test "x$gcc_warnings" = "xyes"; then
|
||||
WERROR_CFLAGS="-Werror"
|
||||
fi
|
||||
AC_SUBST([WERROR_CFLAGS])
|
||||
|
||||
# Provide a global place to set CFLAGS. (Note that setting AM_CFLAGS
|
||||
# is no use because it doesn't override target_CFLAGS).
|
||||
#---
|
||||
@@ -205,16 +118,6 @@ resources when it runs.])])
|
||||
dnl restore CFLAGS
|
||||
CFLAGS="${acx_nbdkit_save_CFLAGS}"
|
||||
|
||||
dnl Should we run the gnulib tests?
|
||||
AC_MSG_CHECKING([if we should run the GNUlib tests])
|
||||
AC_ARG_ENABLE([gnulib-tests],
|
||||
[AS_HELP_STRING([--disable-gnulib-tests],
|
||||
[disable running GNU Portability library tests @<:@default=yes@:>@])],
|
||||
[ENABLE_GNULIB_TESTS="$enableval"],
|
||||
[ENABLE_GNULIB_TESTS=yes])
|
||||
AM_CONDITIONAL([ENABLE_GNULIB_TESTS],[test "x$ENABLE_GNULIB_TESTS" = "xyes"])
|
||||
AC_MSG_RESULT([$ENABLE_GNULIB_TESTS])
|
||||
|
||||
dnl Define this so that include/guestfs.h is included
|
||||
dnl instead of the possibly installed <guestfs.h>. This is
|
||||
dnl only needed when compiling libguestfs itself. It is
|
||||
|
||||
@@ -30,6 +30,7 @@
|
||||
#include <termios.h>
|
||||
#include <poll.h>
|
||||
#include <locale.h>
|
||||
#include <limits.h>
|
||||
#include <assert.h>
|
||||
#include <libintl.h>
|
||||
|
||||
@@ -37,7 +38,6 @@
|
||||
#include "getprogname.h"
|
||||
#include "ignore-value.h"
|
||||
#include "nonblocking.h"
|
||||
#include "xvasprintf.h"
|
||||
|
||||
#include "guestfs.h"
|
||||
#include "guestfs-utils.h"
|
||||
@@ -364,9 +364,12 @@ main (int argc, char *argv[])
|
||||
/* Kernel command line must include guestfs_rescue=1 (see
|
||||
* appliance/init) as well as other options.
|
||||
*/
|
||||
append_full = xasprintf ("guestfs_rescue=1%s%s",
|
||||
append ? " " : "",
|
||||
append ? append : "");
|
||||
if (asprintf (&append_full, "guestfs_rescue=1%s%s",
|
||||
append ? " " : "",
|
||||
append ? append : "") == -1) {
|
||||
perror ("asprintf");
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
if (guestfs_set_append (g, append_full) == -1)
|
||||
exit (EXIT_FAILURE);
|
||||
free (append_full);
|
||||
|
||||
Reference in New Issue
Block a user