aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--contrib/libarchive/NEWS2
-rw-r--r--contrib/libarchive/SECURITY.md2
-rwxr-xr-xcontrib/libarchive/build/ci/github_actions/install-macos-dependencies.sh3
-rw-r--r--contrib/libarchive/cat/bsdcat.c15
-rw-r--r--contrib/libarchive/cat/cmdline.c2
-rw-r--r--contrib/libarchive/cpio/cmdline.c2
-rw-r--r--contrib/libarchive/cpio/cpio.c14
-rw-r--r--contrib/libarchive/cpio/test/test_owner_parse.c2
-rw-r--r--contrib/libarchive/libarchive/archive.h4
-rw-r--r--contrib/libarchive/libarchive/archive_acl.c23
-rw-r--r--contrib/libarchive/libarchive/archive_check_magic.c9
-rw-r--r--contrib/libarchive/libarchive/archive_cryptor.c8
-rw-r--r--contrib/libarchive/libarchive/archive_cryptor_private.h11
-rw-r--r--contrib/libarchive/libarchive/archive_entry.h2
-rw-r--r--contrib/libarchive/libarchive/archive_entry_paths.32
-rw-r--r--contrib/libarchive/libarchive/archive_entry_stat.c6
-rw-r--r--contrib/libarchive/libarchive/archive_parse_date.c4
-rw-r--r--contrib/libarchive/libarchive/archive_platform.h10
-rw-r--r--contrib/libarchive/libarchive/archive_platform_stat.h45
-rw-r--r--contrib/libarchive/libarchive/archive_private.h1
-rw-r--r--contrib/libarchive/libarchive/archive_read.c7
-rw-r--r--contrib/libarchive/libarchive/archive_read_disk_entry_from_file.c12
-rw-r--r--contrib/libarchive/libarchive/archive_read_disk_posix.c157
-rw-r--r--contrib/libarchive/libarchive/archive_read_open_fd.c23
-rw-r--r--contrib/libarchive/libarchive/archive_read_open_file.c16
-rw-r--r--contrib/libarchive/libarchive/archive_read_open_filename.c31
-rw-r--r--contrib/libarchive/libarchive/archive_read_set_format.c32
-rw-r--r--contrib/libarchive/libarchive/archive_read_support_filter_program.c7
-rw-r--r--contrib/libarchive/libarchive/archive_read_support_format_7zip.c7
-rw-r--r--contrib/libarchive/libarchive/archive_read_support_format_mtree.c23
-rw-r--r--contrib/libarchive/libarchive/archive_read_support_format_rar.c8
-rw-r--r--contrib/libarchive/libarchive/archive_read_support_format_rar5.c66
-rw-r--r--contrib/libarchive/libarchive/archive_read_support_format_tar.c70
-rw-r--r--contrib/libarchive/libarchive/archive_read_support_format_warc.c2
-rw-r--r--contrib/libarchive/libarchive/archive_read_support_format_xar.c2
-rw-r--r--contrib/libarchive/libarchive/archive_read_support_format_zip.c4
-rw-r--r--contrib/libarchive/libarchive/archive_string.c5
-rw-r--r--contrib/libarchive/libarchive/archive_string_sprintf.c2
-rw-r--r--contrib/libarchive/libarchive/archive_util.c38
-rw-r--r--contrib/libarchive/libarchive/archive_write.c30
-rw-r--r--contrib/libarchive/libarchive/archive_write_add_filter_bzip2.c4
-rw-r--r--contrib/libarchive/libarchive/archive_write_add_filter_gzip.c55
-rw-r--r--contrib/libarchive/libarchive/archive_write_add_filter_program.c11
-rw-r--r--contrib/libarchive/libarchive/archive_write_add_filter_zstd.c2
-rw-r--r--contrib/libarchive/libarchive/archive_write_disk_posix.c16
-rw-r--r--contrib/libarchive/libarchive/archive_write_open_fd.c2
-rw-r--r--contrib/libarchive/libarchive/archive_write_open_file.c14
-rw-r--r--contrib/libarchive/libarchive/archive_write_open_filename.c3
-rw-r--r--contrib/libarchive/libarchive/archive_write_set_format_7zip.c2
-rw-r--r--contrib/libarchive/libarchive/archive_write_set_format_mtree.c19
-rw-r--r--contrib/libarchive/libarchive/archive_write_set_format_xar.c6
-rw-r--r--contrib/libarchive/libarchive/archive_write_set_format_zip.c25
-rw-r--r--contrib/libarchive/libarchive/filter_fork_posix.c37
-rw-r--r--contrib/libarchive/libarchive/test/test_acl_nfs4.c7
-rw-r--r--contrib/libarchive/libarchive/test/test_acl_posix1e.c5
-rw-r--r--contrib/libarchive/libarchive/test/test_archive_parse_date.c2
-rw-r--r--contrib/libarchive/libarchive/test/test_archive_string_conversion.c10
-rw-r--r--contrib/libarchive/libarchive/test/test_entry.c11
-rw-r--r--contrib/libarchive/libarchive/test/test_read_filter_gzip_recursive.c4
-rw-r--r--contrib/libarchive/libarchive/test/test_read_format_7zip.c81
-rw-r--r--contrib/libarchive/libarchive/test/test_read_format_rar5.c66
-rw-r--r--contrib/libarchive/libarchive/test/test_read_format_rar5_dirdata.rar.uu6
-rw-r--r--contrib/libarchive/libarchive/test/test_read_format_rar5_invalid_hash_valid_htime_exfld.rar.uu6
-rw-r--r--contrib/libarchive/libarchive/test/test_read_format_rar5_only_crypt_exfld.rar.uu7
-rw-r--r--contrib/libarchive/libarchive/test/test_read_format_rar5_unsupported_exfld.rar.uu6
-rw-r--r--contrib/libarchive/libarchive/test/test_read_format_tar_V_negative_size.c48
-rw-r--r--contrib/libarchive/libarchive/test/test_read_format_tar_V_negative_size.tar.uu20
-rw-r--r--contrib/libarchive/libarchive/test/test_read_set_format.c7
-rw-r--r--contrib/libarchive/libarchive/test/test_write_filter_bzip2.c29
-rw-r--r--contrib/libarchive/libarchive/test/test_write_filter_gzip.c12
-rw-r--r--contrib/libarchive/libarchive/test/test_write_filter_gzip_timestamp.c7
-rw-r--r--contrib/libarchive/libarchive_fe/lafe_err.c (renamed from contrib/libarchive/libarchive_fe/err.c)2
-rw-r--r--contrib/libarchive/libarchive_fe/lafe_err.h (renamed from contrib/libarchive/libarchive_fe/err.h)0
-rw-r--r--contrib/libarchive/libarchive_fe/line_reader.c2
-rw-r--r--contrib/libarchive/libarchive_fe/passphrase.c2
-rw-r--r--contrib/libarchive/tar/bsdtar.c7
-rw-r--r--contrib/libarchive/tar/bsdtar.h8
-rw-r--r--contrib/libarchive/tar/cmdline.c2
-rw-r--r--contrib/libarchive/tar/creation_set.c2
-rw-r--r--contrib/libarchive/tar/read.c2
-rw-r--r--contrib/libarchive/tar/subst.c2
-rw-r--r--contrib/libarchive/tar/test/test_crlf_mtree.c74
-rw-r--r--contrib/libarchive/tar/test/test_option_safe_writes.c5
-rw-r--r--contrib/libarchive/tar/util.c7
-rw-r--r--contrib/libarchive/tar/write.c29
-rw-r--r--contrib/libarchive/test_utils/test_common.h10
-rw-r--r--contrib/libarchive/test_utils/test_main.c156
-rw-r--r--contrib/libarchive/unzip/bsdunzip.c15
-rw-r--r--contrib/libarchive/unzip/cmdline.c2
-rw-r--r--contrib/libarchive/unzip/test/test_C.c4
-rw-r--r--contrib/libarchive/unzip/test/test_L.c4
-rw-r--r--contrib/libarchive/unzip/test/test_P_encryption.c12
-rw-r--r--contrib/libarchive/unzip/test/test_basic.c4
-rw-r--r--contrib/libarchive/unzip/test/test_d.c8
-rw-r--r--contrib/libarchive/unzip/test/test_doubledash.c4
-rw-r--r--contrib/libarchive/unzip/test/test_glob.c4
-rw-r--r--contrib/libarchive/unzip/test/test_j.c4
-rw-r--r--contrib/libarchive/unzip/test/test_n.c4
-rw-r--r--contrib/libarchive/unzip/test/test_o.c4
-rw-r--r--contrib/libarchive/unzip/test/test_p.c4
-rw-r--r--contrib/libarchive/unzip/test/test_q.c4
-rw-r--r--contrib/libarchive/unzip/test/test_singlefile.c4
-rw-r--r--contrib/libarchive/unzip/test/test_t.c4
-rw-r--r--contrib/libarchive/unzip/test/test_x.c12
-rw-r--r--contrib/llvm-project/clang/lib/Driver/ToolChains/FreeBSD.h5
-rw-r--r--lib/libarchive/tests/Makefile6
-rw-r--r--lib/libc/gen/getvfsbyname.33
-rw-r--r--lib/libc/sys/revoke.24
-rw-r--r--lib/libc/sys/write.220
-rw-r--r--sbin/mount/mount.83
-rw-r--r--share/man/man3/queue.36
-rw-r--r--share/man/man3/siginfo.32
-rw-r--r--share/man/man4/acpi_battery.44
-rw-r--r--share/man/man4/bce.42
-rw-r--r--share/man/man4/iwlwifi.42
-rw-r--r--share/man/man4/mac_do.42
-rw-r--r--share/man/man4/p9fs.42
-rw-r--r--share/man/man4/rights.43
-rw-r--r--share/man/man7/stats.73
-rw-r--r--share/man/man7/tuning.73
-rw-r--r--share/man/man9/insmntque.96
-rw-r--r--share/misc/bsd-family-tree16
-rw-r--r--share/mk/bsd.prog.mk6
-rw-r--r--sys/dev/e1000/e1000_osdep.h46
-rw-r--r--sys/dev/e1000/if_em.c83
-rw-r--r--sys/dev/ice/ice_drv_info.h3
-rw-r--r--sys/dev/ixl/if_ixl.c27
-rw-r--r--sys/dev/ixl/ixl.h1
-rw-r--r--sys/dev/ixl/ixl_pf_main.c110
-rw-r--r--sys/fs/nfsclient/nfs_clrpcops.c10
-rw-r--r--sys/geom/zero/g_zero.c4
-rw-r--r--sys/kern/vfs_syscalls.c2
-rw-r--r--sys/netinet/in_proto.c2
-rw-r--r--sys/netinet/tcp_subr.c2
-rw-r--r--sys/netinet/tcp_syncache.c16
-rw-r--r--sys/netinet/tcp_timer.c7
-rw-r--r--sys/netinet/udp_usrreq.c34
-rw-r--r--sys/netinet/udp_var.h1
-rw-r--r--sys/netpfil/ipfw/pmod/tcpmod.c25
-rw-r--r--sys/netpfil/pf/if_pfsync.c3
-rw-r--r--sys/netpfil/pf/pf_ioctl.c11
-rw-r--r--sys/x86/x86/local_apic.c9
-rw-r--r--tests/sys/netpfil/pf/ioctl/validation.c59
-rw-r--r--usr.bin/bsdcat/Makefile2
-rw-r--r--usr.bin/cpio/Makefile2
-rw-r--r--usr.bin/cpio/tests/Makefile2
-rw-r--r--usr.bin/netstat/inet.c37
-rw-r--r--usr.bin/netstat/main.c4
-rw-r--r--usr.bin/sockstat/sockstat.13
-rw-r--r--usr.bin/sockstat/sockstat.c19
-rw-r--r--usr.bin/tar/Makefile2
-rw-r--r--usr.bin/tar/tests/Makefile1
-rw-r--r--usr.bin/unzip/Makefile2
-rw-r--r--usr.bin/unzip/tests/Makefile2
154 files changed, 1590 insertions, 685 deletions
diff --git a/contrib/libarchive/NEWS b/contrib/libarchive/NEWS
index caca7d5cbdb9..f2dd4102fa04 100644
--- a/contrib/libarchive/NEWS
+++ b/contrib/libarchive/NEWS
@@ -1,3 +1,5 @@
+Oct 15, 2026: libarchive 3.8.2 released
+
Jun 01, 2026: libarchive 3.8.1 released
May 20, 2025: libarchive 3.8.0 released
diff --git a/contrib/libarchive/SECURITY.md b/contrib/libarchive/SECURITY.md
index 6ca188b603fe..f2f60e792a57 100644
--- a/contrib/libarchive/SECURITY.md
+++ b/contrib/libarchive/SECURITY.md
@@ -16,4 +16,4 @@ Please provide the following information in your report:
- How to reproduce the issue
This project is maintained by volunteers on a reasonable-effort basis. As such, we ask
-that you give me 90 days to work on a fix before public exposure.
+that you give us 90 days to work on a fix before public exposure.
diff --git a/contrib/libarchive/build/ci/github_actions/install-macos-dependencies.sh b/contrib/libarchive/build/ci/github_actions/install-macos-dependencies.sh
index 2aa4823fc3d0..b33aed5e5562 100755
--- a/contrib/libarchive/build/ci/github_actions/install-macos-dependencies.sh
+++ b/contrib/libarchive/build/ci/github_actions/install-macos-dependencies.sh
@@ -5,6 +5,9 @@ set -eux
#brew update > /dev/null
#brew upgrade > /dev/null
+# Workaround for cmake in local/pinned tap issue
+brew uninstall cmake
+
# This does an upgrade if the package is already installed
brew install \
autoconf \
diff --git a/contrib/libarchive/cat/bsdcat.c b/contrib/libarchive/cat/bsdcat.c
index 731621fa9b75..2e78870ae50e 100644
--- a/contrib/libarchive/cat/bsdcat.c
+++ b/contrib/libarchive/cat/bsdcat.c
@@ -7,6 +7,9 @@
#include "bsdcat_platform.h"
+#ifdef HAVE_SIGNAL_H
+#include <signal.h>
+#endif
#include <stdio.h>
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
@@ -22,7 +25,7 @@
#include <archive_entry.h>
#include "bsdcat.h"
-#include "err.h"
+#include "lafe_err.h"
#define BYTES_PER_BLOCK (20*512)
@@ -105,6 +108,16 @@ main(int argc, char **argv)
bsdcat = &bsdcat_storage;
memset(bsdcat, 0, sizeof(*bsdcat));
+#if defined(HAVE_SIGACTION) && defined(SIGCHLD)
+ { /* Do not ignore SIGCHLD. */
+ struct sigaction sa;
+ sa.sa_handler = SIG_DFL;
+ sigemptyset(&sa.sa_mask);
+ sa.sa_flags = 0;
+ sigaction(SIGCHLD, &sa, NULL);
+ }
+#endif
+
lafe_setprogname(*argv, "bsdcat");
bsdcat->argv = argv;
diff --git a/contrib/libarchive/cat/cmdline.c b/contrib/libarchive/cat/cmdline.c
index 8ecd74aa95e4..5a5fcaf0263f 100644
--- a/contrib/libarchive/cat/cmdline.c
+++ b/contrib/libarchive/cat/cmdline.c
@@ -22,7 +22,7 @@
#endif
#include "bsdcat.h"
-#include "err.h"
+#include "lafe_err.h"
/*
* Short options for bsdcat. Please keep this sorted.
diff --git a/contrib/libarchive/cpio/cmdline.c b/contrib/libarchive/cpio/cmdline.c
index c67519947dbc..db06c03c011d 100644
--- a/contrib/libarchive/cpio/cmdline.c
+++ b/contrib/libarchive/cpio/cmdline.c
@@ -26,7 +26,7 @@
#endif
#include "cpio.h"
-#include "err.h"
+#include "lafe_err.h"
/*
* Short options for cpio. Please keep this sorted.
diff --git a/contrib/libarchive/cpio/cpio.c b/contrib/libarchive/cpio/cpio.c
index 2bf1bfa2985a..262db510568b 100644
--- a/contrib/libarchive/cpio/cpio.c
+++ b/contrib/libarchive/cpio/cpio.c
@@ -60,7 +60,7 @@
#endif
#include "cpio.h"
-#include "err.h"
+#include "lafe_err.h"
#include "line_reader.h"
#include "passphrase.h"
@@ -124,13 +124,21 @@ main(int argc, char *argv[])
cpio->buff_size = sizeof(buff);
-#if defined(HAVE_SIGACTION) && defined(SIGPIPE)
- { /* Ignore SIGPIPE signals. */
+#if defined(HAVE_SIGACTION)
+ {
struct sigaction sa;
sigemptyset(&sa.sa_mask);
sa.sa_flags = 0;
+#ifdef SIGPIPE
+ /* Ignore SIGPIPE signals. */
sa.sa_handler = SIG_IGN;
sigaction(SIGPIPE, &sa, NULL);
+#endif
+#ifdef SIGCHLD
+ /* Do not ignore SIGCHLD. */
+ sa.sa_handler = SIG_DFL;
+ sigaction(SIGCHLD, &sa, NULL);
+#endif
}
#endif
diff --git a/contrib/libarchive/cpio/test/test_owner_parse.c b/contrib/libarchive/cpio/test/test_owner_parse.c
index dfc78ca77aec..bd68f21cec9b 100644
--- a/contrib/libarchive/cpio/test/test_owner_parse.c
+++ b/contrib/libarchive/cpio/test/test_owner_parse.c
@@ -7,7 +7,7 @@
#include "test.h"
#include "../cpio.h"
-#include "err.h"
+#include "lafe_err.h"
#if !defined(_WIN32)
#define ROOT "root"
diff --git a/contrib/libarchive/libarchive/archive.h b/contrib/libarchive/libarchive/archive.h
index 002190a24663..98d7674e18f1 100644
--- a/contrib/libarchive/libarchive/archive.h
+++ b/contrib/libarchive/libarchive/archive.h
@@ -34,7 +34,7 @@
* assert that ARCHIVE_VERSION_NUMBER >= 2012108.
*/
/* Note: Compiler will complain if this does not match archive_entry.h! */
-#define ARCHIVE_VERSION_NUMBER 3008001
+#define ARCHIVE_VERSION_NUMBER 3008002
#include <sys/stat.h>
#include <stddef.h> /* for wchar_t */
@@ -177,7 +177,7 @@ __LA_DECL int archive_version_number(void);
/*
* Textual name/version of the library, useful for version displays.
*/
-#define ARCHIVE_VERSION_ONLY_STRING "3.8.1"
+#define ARCHIVE_VERSION_ONLY_STRING "3.8.2"
#define ARCHIVE_VERSION_STRING "libarchive " ARCHIVE_VERSION_ONLY_STRING
__LA_DECL const char * archive_version_string(void);
diff --git a/contrib/libarchive/libarchive/archive_acl.c b/contrib/libarchive/libarchive/archive_acl.c
index 9e71f5ee5610..362e3308f43f 100644
--- a/contrib/libarchive/libarchive/archive_acl.c
+++ b/contrib/libarchive/libarchive/archive_acl.c
@@ -270,6 +270,19 @@ acl_new_entry(struct archive_acl *acl,
{
struct archive_acl_entry *ap, *aq;
+ /* Reject an invalid type */
+ switch (type) {
+ case ARCHIVE_ENTRY_ACL_TYPE_ACCESS:
+ case ARCHIVE_ENTRY_ACL_TYPE_DEFAULT:
+ case ARCHIVE_ENTRY_ACL_TYPE_ALLOW:
+ case ARCHIVE_ENTRY_ACL_TYPE_DENY:
+ case ARCHIVE_ENTRY_ACL_TYPE_AUDIT:
+ case ARCHIVE_ENTRY_ACL_TYPE_ALARM:
+ break;
+ default:
+ return (NULL);
+ }
+
/* Type argument must be a valid NFS4 or POSIX.1e type.
* The type must agree with anything already set and
* the permset must be compatible. */
@@ -822,6 +835,9 @@ append_entry_w(wchar_t **wp, const wchar_t *prefix, int type,
wname = NULL;
id = -1;
break;
+ default:
+ **wp = '\0';
+ break;
}
*wp += wcslen(*wp);
*(*wp)++ = L':';
@@ -878,6 +894,7 @@ append_entry_w(wchar_t **wp, const wchar_t *prefix, int type,
wcscpy(*wp, L"alarm");
break;
default:
+ *(*wp) = L'\0';
break;
}
*wp += wcslen(*wp);
@@ -1057,6 +1074,9 @@ append_entry(char **p, const char *prefix, int type,
name = NULL;
id = -1;
break;
+ default:
+ **p = '\0';
+ break;
}
*p += strlen(*p);
*(*p)++ = ':';
@@ -1112,6 +1132,9 @@ append_entry(char **p, const char *prefix, int type,
case ARCHIVE_ENTRY_ACL_TYPE_ALARM:
strcpy(*p, "alarm");
break;
+ default:
+ *(*p) = '\0';
+ break;
}
*p += strlen(*p);
}
diff --git a/contrib/libarchive/libarchive/archive_check_magic.c b/contrib/libarchive/libarchive/archive_check_magic.c
index d12f0c496e27..6b8e0c5595f4 100644
--- a/contrib/libarchive/libarchive/archive_check_magic.c
+++ b/contrib/libarchive/libarchive/archive_check_magic.c
@@ -30,6 +30,7 @@
#endif
#include <stdio.h>
+#include <errno.h>
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
@@ -54,8 +55,14 @@ errmsg(const char *m)
while (s > 0) {
written = write(2, m, s);
- if (written <= 0)
+ if (written == 0)
return;
+ if (written < 0)
+ {
+ if (errno == EINTR)
+ continue;
+ return;
+ }
m += written;
s -= written;
}
diff --git a/contrib/libarchive/libarchive/archive_cryptor.c b/contrib/libarchive/libarchive/archive_cryptor.c
index 1825af4dc510..9f03f9ca6dd0 100644
--- a/contrib/libarchive/libarchive/archive_cryptor.c
+++ b/contrib/libarchive/libarchive/archive_cryptor.c
@@ -151,7 +151,7 @@ pbkdf2_sha1(const char *pw, size_t pw_len, const uint8_t *salt,
(void)rounds; /* UNUSED */
(void)derived_key; /* UNUSED */
(void)derived_key_len; /* UNUSED */
- return -1; /* UNSUPPORTED */
+ return CRYPTOR_STUB_FUNCTION; /* UNSUPPORTED */
}
#endif
@@ -439,14 +439,14 @@ aes_ctr_init(archive_crypto_ctx *ctx, const uint8_t *key, size_t key_len)
(void)ctx; /* UNUSED */
(void)key; /* UNUSED */
(void)key_len; /* UNUSED */
- return -1;
+ return CRYPTOR_STUB_FUNCTION;
}
static int
aes_ctr_encrypt_counter(archive_crypto_ctx *ctx)
{
(void)ctx; /* UNUSED */
- return -1;
+ return CRYPTOR_STUB_FUNCTION;
}
static int
@@ -469,7 +469,7 @@ aes_ctr_update(archive_crypto_ctx *ctx, const uint8_t * const in,
(void)out; /* UNUSED */
(void)out_len; /* UNUSED */
aes_ctr_encrypt_counter(ctx); /* UNUSED */ /* Fix unused function warning */
- return -1;
+ return CRYPTOR_STUB_FUNCTION;
}
#else
diff --git a/contrib/libarchive/libarchive/archive_cryptor_private.h b/contrib/libarchive/libarchive/archive_cryptor_private.h
index 4b3c6c161433..1dbc5c17a01a 100644
--- a/contrib/libarchive/libarchive/archive_cryptor_private.h
+++ b/contrib/libarchive/libarchive/archive_cryptor_private.h
@@ -43,7 +43,7 @@ int __libarchive_cryptor_build_hack(void);
#ifdef __APPLE__
# include <AvailabilityMacros.h>
# if MAC_OS_X_VERSION_MAX_ALLOWED >= 1080
-# define ARCHIVE_CRYPTOR_USE_Apple_CommonCrypto
+# define ARCHIVE_CRYPTOR_USE_Apple_CommonCrypto 1
# endif
#endif
@@ -144,9 +144,15 @@ typedef struct {
#else
+#if defined(ARCHIVE_CRYPTO_MD5_WIN) ||\
+ defined(ARCHIVE_CRYPTO_SHA1_WIN) ||\
+ defined(ARCHIVE_CRYPTO_SHA256_WIN) ||\
+ defined(ARCHIVE_CRYPTO_SHA384_WIN) ||\
+ defined(ARCHIVE_CRYPTO_SHA512_WIN)
#if defined(_WIN32) && !defined(__CYGWIN__) && !(defined(HAVE_BCRYPT_H) && _WIN32_WINNT >= _WIN32_WINNT_VISTA)
#define ARCHIVE_CRYPTOR_USE_WINCRYPT 1
#endif
+#endif
#define AES_BLOCK_SIZE 16
#define AES_MAX_KEY_SIZE 32
@@ -172,6 +178,9 @@ typedef int archive_crypto_ctx;
#define archive_encrypto_aes_ctr_release(ctx) \
__archive_cryptor.encrypto_aes_ctr_release(ctx)
+/* Stub return value if no encryption support exists. */
+#define CRYPTOR_STUB_FUNCTION -2
+
/* Minimal interface to cryptographic functionality for internal use in
* libarchive */
struct archive_cryptor
diff --git a/contrib/libarchive/libarchive/archive_entry.h b/contrib/libarchive/libarchive/archive_entry.h
index 2b917b3fde8e..344f33bffac2 100644
--- a/contrib/libarchive/libarchive/archive_entry.h
+++ b/contrib/libarchive/libarchive/archive_entry.h
@@ -28,7 +28,7 @@
#define ARCHIVE_ENTRY_H_INCLUDED
/* Note: Compiler will complain if this does not match archive.h! */
-#define ARCHIVE_VERSION_NUMBER 3008001
+#define ARCHIVE_VERSION_NUMBER 3008002
/*
* Note: archive_entry.h is for use outside of libarchive; the
diff --git a/contrib/libarchive/libarchive/archive_entry_paths.3 b/contrib/libarchive/libarchive/archive_entry_paths.3
index 0f849c9ebb35..f739b172308d 100644
--- a/contrib/libarchive/libarchive/archive_entry_paths.3
+++ b/contrib/libarchive/libarchive/archive_entry_paths.3
@@ -64,7 +64,7 @@ Streaming Archive Library (libarchive, -larchive)
.Ft void
.Fn archive_entry_copy_hardlink "struct archive_entry *a" "const char *path"
.Ft void
-.Fn archive_entry_copy_hardlink_w "struct archive_entry *a "const wchar_t *path"
+.Fn archive_entry_copy_hardlink_w "struct archive_entry *a" "const wchar_t *path"
.Ft int
.Fn archive_entry_update_hardlink_utf8 "struct archive_entry *a" "const char *path"
.Ft void
diff --git a/contrib/libarchive/libarchive/archive_entry_stat.c b/contrib/libarchive/libarchive/archive_entry_stat.c
index c4906838ed0f..345d3d29b2f2 100644
--- a/contrib/libarchive/libarchive/archive_entry_stat.c
+++ b/contrib/libarchive/libarchive/archive_entry_stat.c
@@ -38,6 +38,7 @@
const struct stat *
archive_entry_stat(struct archive_entry *entry)
{
+ int64_t size;
struct stat *st;
if (entry->stat == NULL) {
entry->stat = calloc(1, sizeof(*st));
@@ -74,7 +75,10 @@ archive_entry_stat(struct archive_entry *entry)
st->st_ino = (ino_t)archive_entry_ino64(entry);
st->st_nlink = archive_entry_nlink(entry);
st->st_rdev = archive_entry_rdev(entry);
- st->st_size = (off_t)archive_entry_size(entry);
+ size = archive_entry_size(entry);
+ st->st_size = (off_t)size;
+ if (st->st_size < 0 || (int64_t)st->st_size != size)
+ st->st_size = 0;
st->st_mode = archive_entry_mode(entry);
/*
diff --git a/contrib/libarchive/libarchive/archive_parse_date.c b/contrib/libarchive/libarchive/archive_parse_date.c
index cda0b11a555f..d9e968387d34 100644
--- a/contrib/libarchive/libarchive/archive_parse_date.c
+++ b/contrib/libarchive/libarchive/archive_parse_date.c
@@ -703,9 +703,7 @@ Convert(time_t Month, time_t Day, time_t Year,
Year += 1900;
DaysInMonth[1] = Year % 4 == 0 && (Year % 100 != 0 || Year % 400 == 0)
? 29 : 28;
- /* Checking for 2038 bogusly assumes that time_t is 32 bits. But
- I'm too lazy to try to check for time_t overflow in another way. */
- if (Year < EPOCH || Year >= 2038
+ if (Year < EPOCH || (sizeof(time_t) <= 4 && Year >= 2038)
|| Month < 1 || Month > 12
/* Lint fluff: "conversion from long may lose accuracy" */
|| Day < 1 || Day > DaysInMonth[(int)--Month]
diff --git a/contrib/libarchive/libarchive/archive_platform.h b/contrib/libarchive/libarchive/archive_platform.h
index f30df1104c83..33dc5582b7ed 100644
--- a/contrib/libarchive/libarchive/archive_platform.h
+++ b/contrib/libarchive/libarchive/archive_platform.h
@@ -183,16 +183,6 @@
#define CAN_RESTORE_METADATA_FD
#endif
-/*
- * glibc 2.24 deprecates readdir_r
- * bionic c deprecates readdir_r too
- */
-#if defined(HAVE_READDIR_R) && (!defined(__GLIBC__) || !defined(__GLIBC_MINOR__) || __GLIBC__ < 2 || (__GLIBC__ == 2 && __GLIBC_MINOR__ < 24)) && (!defined(__ANDROID__))
-#define USE_READDIR_R 1
-#else
-#undef USE_READDIR_R
-#endif
-
/* Set up defaults for internal error codes. */
#ifndef ARCHIVE_ERRNO_FILE_FORMAT
#if HAVE_EFTYPE
diff --git a/contrib/libarchive/libarchive/archive_platform_stat.h b/contrib/libarchive/libarchive/archive_platform_stat.h
new file mode 100644
index 000000000000..5432b2f6433a
--- /dev/null
+++ b/contrib/libarchive/libarchive/archive_platform_stat.h
@@ -0,0 +1,45 @@
+/*-
+ * SPDX-License-Identifier: BSD-2-Clause
+ *
+ * Copyright (c) 2025 Tobias Stoeckmann
+ * All rights reserved.
+ */
+
+/* !!ONLY FOR USE INTERNALLY TO LIBARCHIVE!! */
+
+#ifndef ARCHIVE_PLATFORM_STAT_H_INCLUDED
+#define ARCHIVE_PLATFORM_STAT_H_INCLUDED
+
+#ifndef __LIBARCHIVE_BUILD
+#error This header is only to be used internally to libarchive.
+#endif
+
+#if defined(_WIN32) && !defined(__CYGWIN__)
+/* We use _lseeki64() on Windows. */
+typedef int64_t la_seek_t;
+
+struct la_seek_stat {
+ int64_t st_mtime;
+ ino_t st_ino;
+ unsigned short st_mode;
+ uint32_t st_nlink;
+ gid_t st_gid;
+ la_seek_t st_size;
+ uid_t st_uid;
+ dev_t st_dev;
+ dev_t st_rdev;
+};
+typedef struct la_seek_stat la_seek_stat_t;
+
+#define la_seek_fstat(fd, st) __la_seek_fstat((fd), (st))
+#define la_seek_stat(fd, st) __la_seek_stat((fd), (st))
+
+#else
+typedef off_t la_seek_t;
+typedef struct stat la_seek_stat_t;
+
+#define la_seek_fstat(fd, st) fstat((fd), (st))
+#define la_seek_stat(fd, st) stat((fd), (st))
+#endif
+
+#endif /* !ARCHIVE_PLATFORM_STAT_H_INCLUDED */
diff --git a/contrib/libarchive/libarchive/archive_private.h b/contrib/libarchive/libarchive/archive_private.h
index 050fc63c0b2e..3a926c6886ad 100644
--- a/contrib/libarchive/libarchive/archive_private.h
+++ b/contrib/libarchive/libarchive/archive_private.h
@@ -158,6 +158,7 @@ int __archive_check_magic(struct archive *, unsigned int magic,
__LA_NORETURN void __archive_errx(int retvalue, const char *msg);
void __archive_ensure_cloexec_flag(int fd);
+int __archive_get_tempdir(struct archive_string *);
int __archive_mktemp(const char *tmpdir);
#if defined(_WIN32) && !defined(__CYGWIN__)
int __archive_mkstemp(wchar_t *templates);
diff --git a/contrib/libarchive/libarchive/archive_read.c b/contrib/libarchive/libarchive/archive_read.c
index 50db87017706..c9b9d5981516 100644
--- a/contrib/libarchive/libarchive/archive_read.c
+++ b/contrib/libarchive/libarchive/archive_read.c
@@ -575,8 +575,7 @@ choose_filters(struct archive_read *a)
return (ARCHIVE_OK);
}
- filter
- = calloc(1, sizeof(*filter));
+ filter = calloc(1, sizeof(*filter));
if (filter == NULL)
return (ARCHIVE_FATAL);
filter->bidder = best_bidder;
@@ -834,7 +833,9 @@ archive_read_data(struct archive *_a, void *buff, size_t s)
r = archive_read_data_block(a, &read_buf,
&a->read_data_remaining, &a->read_data_offset);
a->read_data_block = read_buf;
- if (r == ARCHIVE_EOF)
+ if (r == ARCHIVE_EOF &&
+ a->read_data_offset == a->read_data_output_offset &&
+ a->read_data_remaining == 0)
return (bytes_read);
/*
* Error codes are all negative, so the status
diff --git a/contrib/libarchive/libarchive/archive_read_disk_entry_from_file.c b/contrib/libarchive/libarchive/archive_read_disk_entry_from_file.c
index 19d049770b78..42af4034b07e 100644
--- a/contrib/libarchive/libarchive/archive_read_disk_entry_from_file.c
+++ b/contrib/libarchive/libarchive/archive_read_disk_entry_from_file.c
@@ -338,7 +338,7 @@ setup_mac_metadata(struct archive_read_disk *a,
int ret = ARCHIVE_OK;
void *buff = NULL;
int have_attrs;
- const char *name, *tempdir;
+ const char *name;
struct archive_string tempfile;
(void)fd; /* UNUSED */
@@ -357,13 +357,11 @@ setup_mac_metadata(struct archive_read_disk *a,
if (have_attrs == 0)
return (ARCHIVE_OK);
- tempdir = NULL;
- if (issetugid() == 0)
- tempdir = getenv("TMPDIR");
- if (tempdir == NULL)
- tempdir = _PATH_TMP;
archive_string_init(&tempfile);
- archive_strcpy(&tempfile, tempdir);
+ if (__archive_get_tempdir(&tempfile) != ARCHIVE_OK) {
+ ret = ARCHIVE_WARN;
+ goto cleanup;
+ }
archive_strcat(&tempfile, "tar.md.XXXXXX");
tempfd = mkstemp(tempfile.s);
if (tempfd < 0) {
diff --git a/contrib/libarchive/libarchive/archive_read_disk_posix.c b/contrib/libarchive/libarchive/archive_read_disk_posix.c
index a7a98e9cb1cd..54a8e66188f8 100644
--- a/contrib/libarchive/libarchive/archive_read_disk_posix.c
+++ b/contrib/libarchive/libarchive/archive_read_disk_posix.c
@@ -168,9 +168,6 @@ struct filesystem {
int synthetic;
int remote;
int noatime;
-#if defined(USE_READDIR_R)
- size_t name_max;
-#endif
long incr_xfer_size;
long max_xfer_size;
long min_xfer_size;
@@ -203,10 +200,6 @@ struct tree {
DIR *d;
#define INVALID_DIR_HANDLE NULL
struct dirent *de;
-#if defined(USE_READDIR_R)
- struct dirent *dirent;
- size_t dirent_allocated;
-#endif
int flags;
int visit_type;
/* Error code from last failed operation. */
@@ -869,7 +862,7 @@ next_entry(struct archive_read_disk *a, struct tree *t,
tree_enter_initial_dir(t);
return (ARCHIVE_FATAL);
case TREE_ERROR_DIR:
- archive_set_error(&a->archive, ARCHIVE_ERRNO_MISC,
+ archive_set_error(&a->archive, t->tree_errno,
"%s: Couldn't visit directory",
tree_current_path(t));
tree_enter_initial_dir(t);
@@ -1578,9 +1571,6 @@ setup_current_filesystem(struct archive_read_disk *a)
# endif
#endif
int r, xr = 0;
-#if !defined(HAVE_STRUCT_STATFS_F_NAMEMAX)
- long nm;
-#endif
t->current_filesystem->synthetic = -1;
t->current_filesystem->remote = -1;
@@ -1647,35 +1637,6 @@ setup_current_filesystem(struct archive_read_disk *a)
#endif
t->current_filesystem->noatime = 0;
-#if defined(USE_READDIR_R)
- /* Set maximum filename length. */
-#if defined(HAVE_STRUCT_STATFS_F_NAMEMAX)
- t->current_filesystem->name_max = sfs.f_namemax;
-#else
-# if defined(_PC_NAME_MAX)
- /* Mac OS X does not have f_namemax in struct statfs. */
- if (tree_current_is_symblic_link_target(t)) {
- if (tree_enter_working_dir(t) != 0) {
- archive_set_error(&a->archive, errno, "fchdir failed");
- return (ARCHIVE_FAILED);
- }
- nm = pathconf(tree_current_access_path(t), _PC_NAME_MAX);
- } else
- nm = fpathconf(tree_current_dir_fd(t), _PC_NAME_MAX);
-# else
- nm = -1;
-# endif
- if (nm == -1)
- t->current_filesystem->name_max = NAME_MAX;
- else
- t->current_filesystem->name_max = nm;
-#endif
- if (t->current_filesystem->name_max == 0) {
- archive_set_error(&a->archive, ARCHIVE_ERRNO_MISC,
- "Cannot determine name_max");
- return (ARCHIVE_FAILED);
- }
-#endif /* USE_READDIR_R */
return (ARCHIVE_OK);
}
@@ -1863,19 +1824,6 @@ setup_current_filesystem(struct archive_read_disk *a)
#endif
t->current_filesystem->noatime = 0;
-#if defined(USE_READDIR_R)
- /* Set maximum filename length. */
-#if defined(HAVE_STATVFS)
- t->current_filesystem->name_max = svfs.f_namemax;
-#else
- t->current_filesystem->name_max = sfs.f_namelen;
-#endif
- if (t->current_filesystem->name_max == 0) {
- archive_set_error(&a->archive, ARCHIVE_ERRNO_MISC,
- "Cannot determine name_max");
- return (ARCHIVE_FAILED);
- }
-#endif
return (ARCHIVE_OK);
}
@@ -1953,15 +1901,6 @@ setup_current_filesystem(struct archive_read_disk *a)
#endif
t->current_filesystem->noatime = 0;
-#if defined(USE_READDIR_R)
- /* Set maximum filename length. */
- t->current_filesystem->name_max = svfs.f_namemax;
- if (t->current_filesystem->name_max == 0) {
- archive_set_error(&a->archive, ARCHIVE_ERRNO_MISC,
- "Cannot determine name_max");
- return (ARCHIVE_FAILED);
- }
-#endif
return (ARCHIVE_OK);
}
@@ -1975,9 +1914,6 @@ static int
setup_current_filesystem(struct archive_read_disk *a)
{
struct tree *t = a->tree;
-#if defined(_PC_NAME_MAX) && defined(USE_READDIR_R)
- long nm;
-#endif
t->current_filesystem->synthetic = -1;/* Not supported */
t->current_filesystem->remote = -1;/* Not supported */
t->current_filesystem->noatime = 0;
@@ -1987,40 +1923,6 @@ setup_current_filesystem(struct archive_read_disk *a)
t->current_filesystem->min_xfer_size = -1;
t->current_filesystem->incr_xfer_size = -1;
-#if defined(USE_READDIR_R)
- /* Set maximum filename length. */
-# if defined(_PC_NAME_MAX)
- if (tree_current_is_symblic_link_target(t)) {
- if (tree_enter_working_dir(t) != 0) {
- archive_set_error(&a->archive, errno, "fchdir failed");
- return (ARCHIVE_FAILED);
- }
- nm = pathconf(tree_current_access_path(t), _PC_NAME_MAX);
- } else
- nm = fpathconf(tree_current_dir_fd(t), _PC_NAME_MAX);
- if (nm == -1)
-# endif /* _PC_NAME_MAX */
- /*
- * Some systems (HP-UX or others?) incorrectly defined
- * NAME_MAX macro to be a smaller value.
- */
-# if defined(NAME_MAX) && NAME_MAX >= 255
- t->current_filesystem->name_max = NAME_MAX;
-# else
- /* No way to get a trusted value of maximum filename
- * length. */
- t->current_filesystem->name_max = PATH_MAX;
-# endif /* NAME_MAX */
-# if defined(_PC_NAME_MAX)
- else
- t->current_filesystem->name_max = nm;
-# endif /* _PC_NAME_MAX */
- if (t->current_filesystem->name_max == 0) {
- archive_set_error(&a->archive, ARCHIVE_ERRNO_MISC,
- "Cannot determine name_max");
- return (ARCHIVE_FAILED);
- }
-#endif /* USE_READDIR_R */
return (ARCHIVE_OK);
}
@@ -2112,8 +2014,11 @@ tree_dup(int fd)
}
#endif /* F_DUPFD_CLOEXEC */
new_fd = dup(fd);
- __archive_ensure_cloexec_flag(new_fd);
- return (new_fd);
+ if (new_fd != -1) {
+ __archive_ensure_cloexec_flag(new_fd);
+ return (new_fd);
+ }
+ return (-1);
}
/*
@@ -2235,11 +2140,16 @@ tree_reopen(struct tree *t, const char *path, int restore_time)
* so try again for execute. The consequences of not opening this are
* unhelpful and unnecessary errors later.
*/
- if (t->initial_dir_fd < 0)
+ if (t->initial_dir_fd < 0) {
t->initial_dir_fd = open(".", o_flag | O_CLOEXEC);
+ if (t->initial_dir_fd < 0)
+ return NULL;
+ }
#endif
__archive_ensure_cloexec_flag(t->initial_dir_fd);
t->working_dir_fd = tree_dup(t->initial_dir_fd);
+ if (t->working_dir_fd < 0)
+ return NULL;
return (t);
}
@@ -2449,12 +2359,11 @@ tree_dir_next_posix(struct tree *t)
size_t namelen;
if (t->d == NULL) {
-#if defined(USE_READDIR_R)
- size_t dirent_size;
-#endif
#if defined(HAVE_FDOPENDIR)
- t->d = fdopendir(tree_dup(t->working_dir_fd));
+ int fd = tree_dup(t->working_dir_fd);
+ if (fd != -1)
+ t->d = fdopendir(fd);
#else /* HAVE_FDOPENDIR */
if (tree_enter_working_dir(t) == 0) {
t->d = opendir(".");
@@ -2470,45 +2379,12 @@ tree_dir_next_posix(struct tree *t)
t->visit_type = r != 0 ? r : TREE_ERROR_DIR;
return (t->visit_type);
}
-#if defined(USE_READDIR_R)
- dirent_size = offsetof(struct dirent, d_name) +
- t->filesystem_table[t->current->filesystem_id].name_max + 1;
- if (t->dirent == NULL || t->dirent_allocated < dirent_size) {
- free(t->dirent);
- t->dirent = malloc(dirent_size);
- if (t->dirent == NULL) {
- closedir(t->d);
- t->d = INVALID_DIR_HANDLE;
- (void)tree_ascend(t);
- tree_pop(t);
- t->tree_errno = ENOMEM;
- t->visit_type = TREE_ERROR_DIR;
- return (t->visit_type);
- }
- t->dirent_allocated = dirent_size;
- }
-#endif /* USE_READDIR_R */
}
for (;;) {
errno = 0;
-#if defined(USE_READDIR_R)
- r = readdir_r(t->d, t->dirent, &t->de);
-#ifdef _AIX
- /* Note: According to the man page, return value 9 indicates
- * that the readdir_r was not successful and the error code
- * is set to the global errno variable. And then if the end
- * of directory entries was reached, the return value is 9
- * and the third parameter is set to NULL and errno is
- * unchanged. */
- if (r == 9)
- r = errno;
-#endif /* _AIX */
- if (r != 0 || t->de == NULL) {
-#else
t->de = readdir(t->d);
if (t->de == NULL) {
r = errno;
-#endif
closedir(t->d);
t->d = INVALID_DIR_HANDLE;
if (r != 0) {
@@ -2747,9 +2623,6 @@ tree_free(struct tree *t)
if (t == NULL)
return;
archive_string_free(&t->path);
-#if defined(USE_READDIR_R)
- free(t->dirent);
-#endif
free(t->sparse_list);
for (i = 0; i < t->max_filesystem_id; i++)
free(t->filesystem_table[i].allocation_ptr);
diff --git a/contrib/libarchive/libarchive/archive_read_open_fd.c b/contrib/libarchive/libarchive/archive_read_open_fd.c
index dc7c9e52c6f6..c85a62a3e2d7 100644
--- a/contrib/libarchive/libarchive/archive_read_open_fd.c
+++ b/contrib/libarchive/libarchive/archive_read_open_fd.c
@@ -48,6 +48,7 @@
#endif
#include "archive.h"
+#include "archive_platform_stat.h"
struct read_fd_data {
int fd;
@@ -65,12 +66,12 @@ static int64_t file_skip(struct archive *, void *, int64_t request);
int
archive_read_open_fd(struct archive *a, int fd, size_t block_size)
{
- struct stat st;
+ la_seek_stat_t st;
struct read_fd_data *mine;
void *b;
archive_clear_error(a);
- if (fstat(fd, &st) != 0) {
+ if (la_seek_fstat(fd, &st) != 0) {
archive_set_error(a, errno, "Can't stat fd %d", fd);
return (ARCHIVE_FATAL);
}
@@ -133,7 +134,7 @@ static int64_t
file_skip(struct archive *a, void *client_data, int64_t request)
{
struct read_fd_data *mine = (struct read_fd_data *)client_data;
- off_t skip = (off_t)request;
+ la_seek_t skip = (la_seek_t)request;
int64_t old_offset, new_offset;
int skip_bits = sizeof(skip) * 8 - 1; /* off_t is a signed type. */
@@ -149,7 +150,8 @@ file_skip(struct archive *a, void *client_data, int64_t request)
}
/* Reduce 'skip' to the next smallest multiple of block_size */
- skip = (off_t)(((int64_t)skip / mine->block_size) * mine->block_size);
+ skip = (la_seek_t)(((int64_t)skip / mine->block_size) * mine->block_size);
+
if (skip == 0)
return (0);
@@ -185,27 +187,28 @@ static int64_t
file_seek(struct archive *a, void *client_data, int64_t request, int whence)
{
struct read_fd_data *mine = (struct read_fd_data *)client_data;
- off_t seek = (off_t)request;
+ la_seek_t seek = (la_seek_t)request;
int64_t r;
int seek_bits = sizeof(seek) * 8 - 1; /* off_t is a signed type. */
/* We use off_t here because lseek() is declared that way. */
- /* Reduce a request that would overflow the 'seek' variable. */
+ /* Do not perform a seek which cannot be fulfilled. */
if (sizeof(request) > sizeof(seek)) {
const int64_t max_seek =
(((int64_t)1 << (seek_bits - 1)) - 1) * 2 + 1;
const int64_t min_seek = ~max_seek;
- if (request > max_seek)
- seek = (off_t)max_seek;
- else if (request < min_seek)
- seek = (off_t)min_seek;
+ if (request < min_seek || request > max_seek) {
+ errno = EOVERFLOW;
+ goto err;
+ }
}
r = lseek(mine->fd, seek, whence);
if (r >= 0)
return r;
+err:
if (errno == ESPIPE) {
archive_set_error(a, errno,
"A file descriptor(%d) is not seekable(PIPE)", mine->fd);
diff --git a/contrib/libarchive/libarchive/archive_read_open_file.c b/contrib/libarchive/libarchive/archive_read_open_file.c
index 742923abbee9..6ca2ff191aa8 100644
--- a/contrib/libarchive/libarchive/archive_read_open_file.c
+++ b/contrib/libarchive/libarchive/archive_read_open_file.c
@@ -48,6 +48,7 @@
#endif
#include "archive.h"
+#include "archive_platform_stat.h"
struct read_FILE_data {
FILE *f;
@@ -65,7 +66,7 @@ static int64_t FILE_skip(struct archive *, void *, int64_t);
int
archive_read_open_FILE(struct archive *a, FILE *f)
{
- struct stat st;
+ la_seek_stat_t st;
struct read_FILE_data *mine;
size_t block_size = 128 * 1024;
void *b;
@@ -88,7 +89,7 @@ archive_read_open_FILE(struct archive *a, FILE *f)
* streams that don't support fileno()). As a result, fileno()
* should be used cautiously.)
*/
- if (fstat(fileno(mine->f), &st) == 0 && S_ISREG(st.st_mode)) {
+ if (la_seek_fstat(fileno(mine->f), &st) == 0 && S_ISREG(st.st_mode)) {
archive_read_extract_set_skip_file(a, st.st_dev, st.st_ino);
/* Enable the seek optimization only for regular files. */
mine->can_skip = 1;
@@ -205,15 +206,15 @@ FILE_seek(struct archive *a, void *client_data, int64_t request, int whence)
int seek_bits = sizeof(seek) * 8 - 1;
(void)a; /* UNUSED */
- /* Reduce a request that would overflow the 'seek' variable. */
+ /* Do not perform a seek which cannot be fulfilled. */
if (sizeof(request) > sizeof(seek)) {
const int64_t max_seek =
(((int64_t)1 << (seek_bits - 1)) - 1) * 2 + 1;
const int64_t min_seek = ~max_seek;
- if (request > max_seek)
- seek = max_seek;
- else if (request < min_seek)
- seek = min_seek;
+ if (request < min_seek || request > max_seek) {
+ errno = EOVERFLOW;
+ goto err;
+ }
}
#ifdef __ANDROID__
@@ -236,6 +237,7 @@ FILE_seek(struct archive *a, void *client_data, int64_t request, int whence)
}
#endif
/* If we arrive here, the input is corrupted or truncated so fail. */
+err:
archive_set_error(a, errno, "Error seeking in FILE* pointer");
return (ARCHIVE_FATAL);
}
diff --git a/contrib/libarchive/libarchive/archive_read_open_filename.c b/contrib/libarchive/libarchive/archive_read_open_filename.c
index 5f5b3f1f7259..a910eefcbfd2 100644
--- a/contrib/libarchive/libarchive/archive_read_open_filename.c
+++ b/contrib/libarchive/libarchive/archive_read_open_filename.c
@@ -59,6 +59,7 @@
#endif
#include "archive.h"
+#include "archive_platform_stat.h"
#include "archive_private.h"
#include "archive_string.h"
@@ -136,8 +137,10 @@ archive_read_open_filenames(struct archive *a, const char **filenames,
mine->filename_type = FNT_STDIN;
} else
mine->filename_type = FNT_MBS;
- if (archive_read_append_callback_data(a, mine) != (ARCHIVE_OK))
+ if (archive_read_append_callback_data(a, mine) != (ARCHIVE_OK)) {
+ free(mine);
return (ARCHIVE_FATAL);
+ }
if (filenames == NULL)
break;
filename = *(filenames++);
@@ -216,8 +219,10 @@ archive_read_open_filenames_w(struct archive *a, const wchar_t **wfilenames,
archive_string_free(&fn);
#endif
}
- if (archive_read_append_callback_data(a, mine) != (ARCHIVE_OK))
+ if (archive_read_append_callback_data(a, mine) != (ARCHIVE_OK)) {
+ free(mine);
return (ARCHIVE_FATAL);
+ }
if (wfilenames == NULL)
break;
wfilename = *(wfilenames++);
@@ -248,7 +253,7 @@ archive_read_open_filename_w(struct archive *a, const wchar_t *wfilename,
static int
file_open(struct archive *a, void *client_data)
{
- struct stat st;
+ la_seek_stat_t st;
struct read_file_data *mine = (struct read_file_data *)client_data;
void *buffer;
const char *filename = NULL;
@@ -313,7 +318,7 @@ file_open(struct archive *a, void *client_data)
goto fail;
#endif
}
- if (fstat(fd, &st) != 0) {
+ if (la_seek_fstat(fd, &st) != 0) {
#if defined(_WIN32) && !defined(__CYGWIN__)
if (mine->filename_type == FNT_WCS)
archive_set_error(a, errno, "Can't stat '%ls'",
@@ -482,10 +487,11 @@ file_skip_lseek(struct archive *a, void *client_data, int64_t request)
struct read_file_data *mine = (struct read_file_data *)client_data;
#if defined(_WIN32) && !defined(__CYGWIN__)
/* We use _lseeki64() on Windows. */
- int64_t old_offset, new_offset, skip = request;
+ int64_t old_offset, new_offset;
#else
- off_t old_offset, new_offset, skip = (off_t)request;
+ off_t old_offset, new_offset;
#endif
+ la_seek_t skip = (la_seek_t)request;
int skip_bits = sizeof(skip) * 8 - 1;
/* We use off_t here because lseek() is declared that way. */
@@ -552,21 +558,21 @@ static int64_t
file_seek(struct archive *a, void *client_data, int64_t request, int whence)
{
struct read_file_data *mine = (struct read_file_data *)client_data;
- off_t seek = (off_t)request;
+ la_seek_t seek = (la_seek_t)request;
int64_t r;
int seek_bits = sizeof(seek) * 8 - 1;
/* We use off_t here because lseek() is declared that way. */
- /* Reduce a request that would overflow the 'seek' variable. */
+ /* Do not perform a seek which cannot be fulfilled. */
if (sizeof(request) > sizeof(seek)) {
const int64_t max_seek =
(((int64_t)1 << (seek_bits - 1)) - 1) * 2 + 1;
const int64_t min_seek = ~max_seek;
- if (request > max_seek)
- seek = (off_t)max_seek;
- else if (request < min_seek)
- seek = (off_t)min_seek;
+ if (request < min_seek || request > max_seek) {
+ errno = EOVERFLOW;
+ goto err;
+ }
}
r = lseek(mine->fd, seek, whence);
@@ -574,6 +580,7 @@ file_seek(struct archive *a, void *client_data, int64_t request, int whence)
return r;
/* If the input is corrupted or truncated, fail. */
+err:
if (mine->filename_type == FNT_STDIN)
archive_set_error(a, errno, "Error seeking in stdin");
else if (mine->filename_type == FNT_MBS)
diff --git a/contrib/libarchive/libarchive/archive_read_set_format.c b/contrib/libarchive/libarchive/archive_read_set_format.c
index c74361b20c13..552ab12d2f92 100644
--- a/contrib/libarchive/libarchive/archive_read_set_format.c
+++ b/contrib/libarchive/libarchive/archive_read_set_format.c
@@ -37,7 +37,7 @@ int
archive_read_set_format(struct archive *_a, int code)
{
int r1, r2, slots, i;
- char str[10];
+ const char *str;
struct archive_read *a = (struct archive_read *)_a;
if ((r1 = archive_read_support_format_by_code(_a, code)) < (ARCHIVE_OK))
@@ -49,49 +49,49 @@ archive_read_set_format(struct archive *_a, int code)
switch (code & ARCHIVE_FORMAT_BASE_MASK)
{
case ARCHIVE_FORMAT_7ZIP:
- strcpy(str, "7zip");
+ str = "7zip";
break;
case ARCHIVE_FORMAT_AR:
- strcpy(str, "ar");
+ str = "ar";
break;
case ARCHIVE_FORMAT_CAB:
- strcpy(str, "cab");
+ str = "cab";
break;
case ARCHIVE_FORMAT_CPIO:
- strcpy(str, "cpio");
+ str = "cpio";
break;
case ARCHIVE_FORMAT_EMPTY:
- strcpy(str, "empty");
+ str = "empty";
break;
case ARCHIVE_FORMAT_ISO9660:
- strcpy(str, "iso9660");
+ str = "iso9660";
break;
case ARCHIVE_FORMAT_LHA:
- strcpy(str, "lha");
+ str = "lha";
break;
case ARCHIVE_FORMAT_MTREE:
- strcpy(str, "mtree");
+ str = "mtree";
break;
case ARCHIVE_FORMAT_RAR:
- strcpy(str, "rar");
+ str = "rar";
break;
case ARCHIVE_FORMAT_RAR_V5:
- strcpy(str, "rar5");
+ str = "rar5";
break;
case ARCHIVE_FORMAT_RAW:
- strcpy(str, "raw");
+ str = "raw";
break;
case ARCHIVE_FORMAT_TAR:
- strcpy(str, "tar");
+ str = "tar";
break;
case ARCHIVE_FORMAT_WARC:
- strcpy(str, "warc");
+ str = "warc";
break;
case ARCHIVE_FORMAT_XAR:
- strcpy(str, "xar");
+ str = "xar";
break;
case ARCHIVE_FORMAT_ZIP:
- strcpy(str, "zip");
+ str = "zip";
break;
default:
archive_set_error(&a->archive, ARCHIVE_ERRNO_PROGRAMMER,
diff --git a/contrib/libarchive/libarchive/archive_read_support_filter_program.c b/contrib/libarchive/libarchive/archive_read_support_filter_program.c
index 9e825223b26c..2c8e45302d8e 100644
--- a/contrib/libarchive/libarchive/archive_read_support_filter_program.c
+++ b/contrib/libarchive/libarchive/archive_read_support_filter_program.c
@@ -110,7 +110,7 @@ struct program_filter {
pid_t child;
#endif
int exit_status;
- int waitpid_return;
+ pid_t waitpid_return;
int child_stdin, child_stdout;
char *out_buf;
@@ -242,16 +242,13 @@ child_stop(struct archive_read_filter *self, struct program_filter *state)
state->waitpid_return
= waitpid(state->child, &state->exit_status, 0);
} while (state->waitpid_return == -1 && errno == EINTR);
-#if defined(_WIN32) && !defined(__CYGWIN__)
- CloseHandle(state->child);
-#endif
state->child = 0;
}
if (state->waitpid_return < 0) {
/* waitpid() failed? This is ugly. */
archive_set_error(&self->archive->archive, ARCHIVE_ERRNO_MISC,
- "Child process exited badly");
+ "Error closing child process");
return (ARCHIVE_WARN);
}
diff --git a/contrib/libarchive/libarchive/archive_read_support_format_7zip.c b/contrib/libarchive/libarchive/archive_read_support_format_7zip.c
index f273f84be521..595462733104 100644
--- a/contrib/libarchive/libarchive/archive_read_support_format_7zip.c
+++ b/contrib/libarchive/libarchive/archive_read_support_format_7zip.c
@@ -80,7 +80,7 @@
/*
* ELF format
*/
-#define ELF_HDR_MIN_LEN 0x34
+#define ELF_HDR_MIN_LEN 0x3f
#define ELF_HDR_EI_CLASS_OFFSET 0x04
#define ELF_HDR_EI_DATA_OFFSET 0x05
@@ -811,6 +811,8 @@ find_elf_data_sec(struct archive_read *a)
strtab_size = (*dec32)(
h + e_shstrndx * e_shentsize + 0x14);
}
+ if (strtab_size < 6 || strtab_size > SIZE_MAX)
+ break;
/*
* Read the STRTAB section to find the .data offset
@@ -1391,7 +1393,8 @@ init_decompression(struct archive_read *a, struct _7zip *zip,
* size to liblzma when using lzma_raw_decoder() liblzma
* could correctly deal with BCJ+LZMA. But unfortunately
* there is no way to do that.
- * Discussion about this can be found at XZ Utils forum.
+ *
+ * Reference: https://web.archive.org/web/20240405171610/https://www.mail-archive.com/xz-devel@tukaani.org/msg00373.html
*/
if (coder2 != NULL) {
zip->codec2 = coder2->codec;
diff --git a/contrib/libarchive/libarchive/archive_read_support_format_mtree.c b/contrib/libarchive/libarchive/archive_read_support_format_mtree.c
index ba0e49de2408..ded13bee79a3 100644
--- a/contrib/libarchive/libarchive/archive_read_support_format_mtree.c
+++ b/contrib/libarchive/libarchive/archive_read_support_format_mtree.c
@@ -51,6 +51,7 @@
#include "archive.h"
#include "archive_entry.h"
#include "archive_entry_private.h"
+#include "archive_platform_stat.h"
#include "archive_private.h"
#include "archive_rb.h"
#include "archive_read_private.h"
@@ -1073,6 +1074,8 @@ read_mtree(struct archive_read *a, struct mtree *mtree)
/* Non-printable characters are not allowed */
for (s = p;s < p + len - 1; s++) {
if (!isprint((unsigned char)*s) && *s != '\t') {
+ archive_set_error(&a->archive, ARCHIVE_ERRNO_FILE_FORMAT,
+ "Non-printable character 0x%02X", (unsigned char)(*s));
r = ARCHIVE_FATAL;
break;
}
@@ -1175,7 +1178,7 @@ parse_file(struct archive_read *a, struct archive_entry *entry,
struct mtree *mtree, struct mtree_entry *mentry, int *use_next)
{
const char *path;
- struct stat st_storage, *st;
+ la_seek_stat_t st_storage, *st;
struct mtree_entry *mp;
struct archive_entry *sparse_entry;
int r = ARCHIVE_OK, r1, parsed_kws;
@@ -1251,7 +1254,7 @@ parse_file(struct archive_read *a, struct archive_entry *entry,
archive_entry_filetype(entry) == AE_IFDIR) {
mtree->fd = open(path, O_RDONLY | O_BINARY | O_CLOEXEC);
__archive_ensure_cloexec_flag(mtree->fd);
- if (mtree->fd == -1 && (
+ if (mtree->fd < 0 && (
#if defined(_WIN32) && !defined(__CYGWIN__)
/*
* On Windows, attempting to open a file with an
@@ -1270,7 +1273,7 @@ parse_file(struct archive_read *a, struct archive_entry *entry,
st = &st_storage;
if (mtree->fd >= 0) {
- if (fstat(mtree->fd, st) == -1) {
+ if (la_seek_fstat(mtree->fd, st) == -1) {
archive_set_error(&a->archive, errno,
"Could not fstat %s", path);
r = ARCHIVE_WARN;
@@ -1283,7 +1286,7 @@ parse_file(struct archive_read *a, struct archive_entry *entry,
#ifdef HAVE_LSTAT
else if (lstat(path, st) == -1)
#else
- else if (la_stat(path, st) == -1)
+ else if (la_seek_stat(path, st) == -1)
#endif
{
st = NULL;
@@ -2130,6 +2133,13 @@ readline(struct archive_read *a, struct mtree *mtree, char **start,
for (u = mtree->line.s + find_off; *u; ++u) {
if (u[0] == '\n') {
/* Ends with unescaped newline. */
+ /* Check if preceded by '\r' for CRLF handling */
+ if (u > mtree->line.s && u[-1] == '\r') {
+ /* CRLF ending - remove the '\r' */
+ u[-1] = '\n';
+ u[0] = '\0';
+ total_size--;
+ }
*start = mtree->line.s;
return total_size;
} else if (u[0] == '#') {
@@ -2144,6 +2154,11 @@ readline(struct archive_read *a, struct mtree *mtree, char **start,
total_size -= 2;
mtree->line.s[total_size] = '\0';
break;
+ } else if (u[1] == '\r' && u[2] == '\n') {
+ /* Trim escaped CRLF. */
+ total_size -= 3;
+ mtree->line.s[total_size] = '\0';
+ break;
} else if (u[1] != '\0') {
/* Skip the two-char escape sequence */
++u;
diff --git a/contrib/libarchive/libarchive/archive_read_support_format_rar.c b/contrib/libarchive/libarchive/archive_read_support_format_rar.c
index 923ae5c65e17..9b401c00ba34 100644
--- a/contrib/libarchive/libarchive/archive_read_support_format_rar.c
+++ b/contrib/libarchive/libarchive/archive_read_support_format_rar.c
@@ -1117,8 +1117,6 @@ archive_read_format_rar_read_data(struct archive_read *a, const void **buff,
if (rar->entry_eof || rar->offset_seek >= rar->unp_size) {
*size = 0;
*offset = rar->offset;
- if (*offset < rar->unp_size)
- *offset = rar->unp_size;
return (ARCHIVE_EOF);
}
@@ -1455,7 +1453,7 @@ read_header(struct archive_read *a, struct archive_entry *entry,
return (ARCHIVE_FATAL);
#endif
}
- /* If no CRC error, Go on parsing File Header. */
+ /* If no CRC error, go on parsing File Header. */
p = h;
endp = p + header_size - 7;
memcpy(&file_header, p, sizeof(file_header));
@@ -2368,8 +2366,8 @@ parse_codes(struct archive_read *a)
return (ARCHIVE_FATAL);
}
- /* Make sure ppmd7_contest is freed before Ppmd7_Construct
- * because reading a broken file cause this abnormal sequence. */
+ /* Make sure ppmd7_context is freed before Ppmd7_Construct
+ * because reading a broken file causes this abnormal sequence. */
__archive_ppmd7_functions.Ppmd7_Free(&rar->ppmd7_context);
rar->bytein.a = a;
diff --git a/contrib/libarchive/libarchive/archive_read_support_format_rar5.c b/contrib/libarchive/libarchive/archive_read_support_format_rar5.c
index 48dde0c2e814..17e501e02e9f 100644
--- a/contrib/libarchive/libarchive/archive_read_support_format_rar5.c
+++ b/contrib/libarchive/libarchive/archive_read_support_format_rar5.c
@@ -1619,10 +1619,13 @@ static int process_head_file_extra(struct archive_read* a,
{
uint64_t extra_field_size;
uint64_t extra_field_id = 0;
- int ret = ARCHIVE_FATAL;
uint64_t var_size;
while(extra_data_size > 0) {
+ /* Make sure we won't fail if the file declares only unsupported
+ attributes. */
+ int ret = ARCHIVE_OK;
+
if(!read_var(a, &extra_field_size, &var_size))
return ARCHIVE_EOF;
@@ -1675,12 +1678,53 @@ static int process_head_file_extra(struct archive_read* a,
if (ARCHIVE_OK != consume(a, extra_field_size)) {
return ARCHIVE_EOF;
}
+
+ /* Don't fail on unsupported attribute -- we've handled it
+ by skipping over it. */
+ ret = ARCHIVE_OK;
+ }
+
+ if (ret != ARCHIVE_OK) {
+ /* Forward any errors signalled by the attribute parsing
+ functions. */
+ return ret;
}
}
- if(ret != ARCHIVE_OK) {
- /* Attribute not implemented. */
- return ret;
+ if (extra_data_size != 0) {
+ /* We didn't skip everything, or we skipped too much; either way,
+ there's an error in this parsing function. */
+
+ archive_set_error(&a->archive, ARCHIVE_ERRNO_PROGRAMMER,
+ "unsupported structure of file header extra data");
+ return ARCHIVE_FATAL;
+ }
+
+ return ARCHIVE_OK;
+}
+
+static int file_entry_sanity_checks(struct archive_read* a,
+ size_t block_flags, uint8_t is_dir, uint64_t unpacked_size,
+ size_t packed_size)
+{
+ if (is_dir) {
+ const int declares_data_size =
+ (int) (unpacked_size != 0 || packed_size != 0);
+
+ /* FILE entries for directories still declare HFL_DATA in block flags,
+ even though attaching data to such blocks doesn't make much sense. */
+ if (declares_data_size) {
+ archive_set_error(&a->archive, ARCHIVE_ERRNO_FILE_FORMAT,
+ "directory entries cannot have any data");
+ return ARCHIVE_FATAL;
+ }
+ } else {
+ const int declares_hfl_data = (int) ((block_flags & HFL_DATA) != 0);
+ if (!declares_hfl_data) {
+ archive_set_error(&a->archive, ARCHIVE_ERRNO_FILE_FORMAT,
+ "no data found in file/service block");
+ return ARCHIVE_FATAL;
+ }
}
return ARCHIVE_OK;
@@ -1701,6 +1745,7 @@ static int process_head_file(struct archive_read* a, struct rar5* rar,
int c_method = 0, c_version = 0;
char name_utf8_buf[MAX_NAME_IN_BYTES];
const uint8_t* p;
+ int sanity_ret;
enum FILE_FLAGS {
DIRECTORY = 0x0001, UTIME = 0x0002, CRC32 = 0x0004,
@@ -1744,10 +1789,6 @@ static int process_head_file(struct archive_read* a, struct rar5* rar,
rar->file.bytes_remaining = data_size;
} else {
rar->file.bytes_remaining = 0;
-
- archive_set_error(&a->archive, ARCHIVE_ERRNO_FILE_FORMAT,
- "no data found in file/service block");
- return ARCHIVE_FATAL;
}
if(!read_var_sized(a, &file_flags, NULL))
@@ -1764,6 +1805,13 @@ static int process_head_file(struct archive_read* a, struct rar5* rar,
rar->file.dir = (uint8_t) ((file_flags & DIRECTORY) > 0);
+ sanity_ret = file_entry_sanity_checks(a, block_flags, rar->file.dir,
+ unpacked_size, data_size);
+
+ if (sanity_ret != ARCHIVE_OK) {
+ return sanity_ret;
+ }
+
if(!read_var_sized(a, &file_attr, NULL))
return ARCHIVE_EOF;
@@ -4163,7 +4211,7 @@ static int rar5_read_data(struct archive_read *a, const void **buff,
* it's impossible to perform any decompression. */
archive_set_error(&a->archive, ARCHIVE_ERRNO_FILE_FORMAT,
"Can't decompress an entry marked as a directory");
- return ARCHIVE_FAILED;
+ return ARCHIVE_FATAL;
}
if(!rar->skip_mode && (rar->cstate.last_write_ptr > rar->file.unpacked_size)) {
diff --git a/contrib/libarchive/libarchive/archive_read_support_format_tar.c b/contrib/libarchive/libarchive/archive_read_support_format_tar.c
index 0c87bc6d732f..eeb2c725f6eb 100644
--- a/contrib/libarchive/libarchive/archive_read_support_format_tar.c
+++ b/contrib/libarchive/libarchive/archive_read_support_format_tar.c
@@ -233,7 +233,7 @@ static int tar_read_header(struct archive_read *, struct tar *,
struct archive_entry *, int64_t *);
static int tohex(int c);
static char *url_decode(const char *, size_t);
-static void tar_flush_unconsumed(struct archive_read *, int64_t *);
+static int tar_flush_unconsumed(struct archive_read *, int64_t *);
/* Sanity limits: These numbers should be low enough to
* prevent a maliciously-crafted archive from forcing us to
@@ -477,7 +477,7 @@ archive_read_format_tar_options(struct archive_read *a,
* how much unconsumed data we have floating around, and to consume
* anything outstanding since we're going to do read_aheads
*/
-static void
+static int
tar_flush_unconsumed(struct archive_read *a, int64_t *unconsumed)
{
if (*unconsumed) {
@@ -490,9 +490,13 @@ tar_flush_unconsumed(struct archive_read *a, int64_t *unconsumed)
memset(data, 0xff, *unconsumed);
}
*/
- __archive_read_consume(a, *unconsumed);
+ int64_t consumed = __archive_read_consume(a, *unconsumed);
+ if (consumed != *unconsumed) {
+ return (ARCHIVE_FATAL);
+ }
*unconsumed = 0;
}
+ return (ARCHIVE_OK);
}
/*
@@ -750,7 +754,9 @@ tar_read_header(struct archive_read *a, struct tar *tar,
/* Find the next valid header record. */
while (1) {
- tar_flush_unconsumed(a, unconsumed);
+ if (tar_flush_unconsumed(a, unconsumed) != ARCHIVE_OK) {
+ return (ARCHIVE_FATAL);
+ }
/* Read 512-byte header record */
h = __archive_read_ahead(a, 512, &bytes);
@@ -796,7 +802,9 @@ tar_read_header(struct archive_read *a, struct tar *tar,
/* This is NOT a null block, so it must be a valid header. */
if (!checksum(a, h)) {
- tar_flush_unconsumed(a, unconsumed);
+ if (tar_flush_unconsumed(a, unconsumed) != ARCHIVE_OK) {
+ return (ARCHIVE_FATAL);
+ }
archive_set_error(&a->archive, EINVAL,
"Damaged tar archive (bad header checksum)");
/* If we've read some critical information (pax headers, etc)
@@ -1236,7 +1244,7 @@ header_volume(struct archive_read *a, struct tar *tar,
header = (const struct archive_entry_header_ustar *)h;
size = tar_atol(header->size, sizeof(header->size));
- if (size > (int64_t)pathname_limit) {
+ if (size < 0 || size > (int64_t)pathname_limit) {
return (ARCHIVE_FATAL);
}
to_consume = ((size + 511) & ~511);
@@ -1255,13 +1263,15 @@ read_bytes_to_string(struct archive_read *a,
const void *src;
/* Fail if we can't make our buffer big enough. */
- if (archive_string_ensure(as, (size_t)size+1) == NULL) {
+ if (archive_string_ensure(as, size + 1) == NULL) {
archive_set_error(&a->archive, ENOMEM,
"No memory");
return (ARCHIVE_FATAL);
}
- tar_flush_unconsumed(a, unconsumed);
+ if (tar_flush_unconsumed(a, unconsumed) != ARCHIVE_OK) {
+ return (ARCHIVE_FATAL);
+ }
/* Read the body into the string. */
src = __archive_read_ahead(a, size, NULL);
@@ -1272,9 +1282,9 @@ read_bytes_to_string(struct archive_read *a,
*unconsumed = 0;
return (ARCHIVE_FATAL);
}
- memcpy(as->s, src, (size_t)size);
+ memcpy(as->s, src, size);
as->s[size] = '\0';
- as->length = (size_t)size;
+ as->length = size;
*unconsumed += size;
return (ARCHIVE_OK);
}
@@ -1715,7 +1725,9 @@ read_mac_metadata_blob(struct archive_read *a,
* Q: Is the above idea really possible? Even
* when there are GNU or pax extension entries?
*/
- tar_flush_unconsumed(a, unconsumed);
+ if (tar_flush_unconsumed(a, unconsumed) != ARCHIVE_OK) {
+ return (ARCHIVE_FATAL);
+ }
data = __archive_read_ahead(a, msize, NULL);
if (data == NULL) {
archive_set_error(&a->archive, EINVAL,
@@ -1900,7 +1912,9 @@ header_pax_extension(struct archive_read *a, struct tar *tar,
(long long)ext_size, (long long)ext_size_limit);
return (ARCHIVE_WARN);
}
- tar_flush_unconsumed(a, unconsumed);
+ if (tar_flush_unconsumed(a, unconsumed) != ARCHIVE_OK) {
+ return (ARCHIVE_FATAL);
+ }
/* Parse the size/name of each pax attribute in the body */
archive_string_init(&attr_name);
@@ -1994,7 +2008,9 @@ header_pax_extension(struct archive_read *a, struct tar *tar,
/* Consume size, name, and `=` */
*unconsumed += p - attr_start;
- tar_flush_unconsumed(a, unconsumed);
+ if (tar_flush_unconsumed(a, unconsumed) != ARCHIVE_OK) {
+ return (ARCHIVE_FATAL);
+ }
if (value_length == 0) {
archive_set_error(&a->archive, EINVAL,
@@ -2017,7 +2033,9 @@ header_pax_extension(struct archive_read *a, struct tar *tar,
err = err_combine(err, r);
/* Consume the `\n` that follows the pax attribute value. */
- tar_flush_unconsumed(a, unconsumed);
+ if (tar_flush_unconsumed(a, unconsumed) != ARCHIVE_OK) {
+ return (ARCHIVE_FATAL);
+ }
p = __archive_read_ahead(a, 1, &did_read);
if (p == NULL) {
archive_set_error(&a->archive, EINVAL,
@@ -2033,7 +2051,9 @@ header_pax_extension(struct archive_read *a, struct tar *tar,
}
ext_size -= 1;
*unconsumed += 1;
- tar_flush_unconsumed(a, unconsumed);
+ if (tar_flush_unconsumed(a, unconsumed) != ARCHIVE_OK) {
+ return (ARCHIVE_FATAL);
+ }
}
*unconsumed += ext_size + ext_padding;
@@ -2290,7 +2310,9 @@ pax_attribute_read_number(struct archive_read *a, size_t value_length, int64_t *
archive_string_init(&as);
r = read_bytes_to_string(a, &as, value_length, &unconsumed);
- tar_flush_unconsumed(a, &unconsumed);
+ if (tar_flush_unconsumed(a, &unconsumed) != ARCHIVE_OK) {
+ return (ARCHIVE_FATAL);
+ }
if (r < ARCHIVE_OK) {
archive_string_free(&as);
*result = 0;
@@ -2940,7 +2962,9 @@ header_gnutar(struct archive_read *a, struct tar *tar,
/* Copy filename over (to ensure null termination). */
header = (const struct archive_entry_header_gnutar *)h;
const char *existing_pathname = archive_entry_pathname(entry);
- if (existing_pathname == NULL || existing_pathname[0] == '\0') {
+ const wchar_t *existing_wcs_pathname = archive_entry_pathname_w(entry);
+ if ((existing_pathname == NULL || existing_pathname[0] == '\0')
+ && (existing_wcs_pathname == NULL || existing_wcs_pathname[0] == L'\0')) {
if (archive_entry_copy_pathname_l(entry,
header->name, sizeof(header->name), tar->sconv) != 0) {
err = set_conversion_failed_error(a, tar->sconv, "Pathname");
@@ -3093,7 +3117,9 @@ gnu_sparse_old_read(struct archive_read *a, struct tar *tar,
return (ARCHIVE_OK);
do {
- tar_flush_unconsumed(a, unconsumed);
+ if (tar_flush_unconsumed(a, unconsumed) != ARCHIVE_OK) {
+ return (ARCHIVE_FATAL);
+ }
data = __archive_read_ahead(a, 512, &bytes_read);
if (data == NULL) {
archive_set_error(&a->archive, ARCHIVE_ERRNO_FILE_FORMAT,
@@ -3283,7 +3309,9 @@ gnu_sparse_10_read(struct archive_read *a, struct tar *tar, int64_t *unconsumed)
return (ARCHIVE_FATAL);
}
/* Skip rest of block... */
- tar_flush_unconsumed(a, unconsumed);
+ if (tar_flush_unconsumed(a, unconsumed) != ARCHIVE_OK) {
+ return (ARCHIVE_FATAL);
+ }
bytes_read = tar->entry_bytes_remaining - remaining;
to_skip = 0x1ff & -bytes_read;
/* Fail if tar->entry_bytes_remaing would get negative */
@@ -3509,7 +3537,9 @@ readline(struct archive_read *a, struct tar *tar, const char **start,
const char *s;
void *p;
- tar_flush_unconsumed(a, unconsumed);
+ if (tar_flush_unconsumed(a, unconsumed) != ARCHIVE_OK) {
+ return (ARCHIVE_FATAL);
+ }
t = __archive_read_ahead(a, 1, &bytes_read);
if (bytes_read <= 0 || t == NULL)
diff --git a/contrib/libarchive/libarchive/archive_read_support_format_warc.c b/contrib/libarchive/libarchive/archive_read_support_format_warc.c
index 696f959c341d..d8f188cf0b44 100644
--- a/contrib/libarchive/libarchive/archive_read_support_format_warc.c
+++ b/contrib/libarchive/libarchive/archive_read_support_format_warc.c
@@ -405,7 +405,7 @@ _warc_read(struct archive_read *a, const void **buf, size_t *bsz, int64_t *off)
/* it's our lucky day, no work, we can leave early */
*buf = NULL;
*bsz = 0U;
- *off = w->cntoff + 4U/*for \r\n\r\n separator*/;
+ *off = w->cntoff;
w->unconsumed = 0U;
return (ARCHIVE_EOF);
}
diff --git a/contrib/libarchive/libarchive/archive_read_support_format_xar.c b/contrib/libarchive/libarchive/archive_read_support_format_xar.c
index b4e1192ef771..36b5ab3ae04c 100644
--- a/contrib/libarchive/libarchive/archive_read_support_format_xar.c
+++ b/contrib/libarchive/libarchive/archive_read_support_format_xar.c
@@ -930,7 +930,7 @@ xar_read_data(struct archive_read *a,
abort_read_data:
*buff = NULL;
*size = 0;
- *offset = xar->total;
+ *offset = (int64_t)xar->entry_total;
return (r);
}
diff --git a/contrib/libarchive/libarchive/archive_read_support_format_zip.c b/contrib/libarchive/libarchive/archive_read_support_format_zip.c
index daf51933d687..9abd55709e3f 100644
--- a/contrib/libarchive/libarchive/archive_read_support_format_zip.c
+++ b/contrib/libarchive/libarchive/archive_read_support_format_zip.c
@@ -3015,8 +3015,8 @@ init_WinZip_AES_decryption(struct archive_read *a)
p, salt_len, 1000, derived_key, key_len * 2 + 2);
if (r != 0) {
archive_set_error(&a->archive, ARCHIVE_ERRNO_MISC,
- "Decryption is unsupported due to lack of "
- "crypto library");
+ r == CRYPTOR_STUB_FUNCTION ? "Decryption is unsupported due "
+ "to lack of crypto library" : "Failed to process passphrase");
return (ARCHIVE_FAILED);
}
diff --git a/contrib/libarchive/libarchive/archive_string.c b/contrib/libarchive/libarchive/archive_string.c
index 7437715f9122..3bb978335eb8 100644
--- a/contrib/libarchive/libarchive/archive_string.c
+++ b/contrib/libarchive/libarchive/archive_string.c
@@ -2015,7 +2015,7 @@ archive_strncat_l(struct archive_string *as, const void *_p, size_t n,
/* We must allocate memory even if there is no data for conversion
* or copy. This simulates archive_string_append behavior. */
if (length == 0) {
- int tn = 1;
+ size_t tn = 1;
if (sc != NULL && (sc->flag & SCONV_TO_UTF16))
tn = 2;
if (archive_string_ensure(as, as->length + tn) == NULL)
@@ -2752,7 +2752,8 @@ archive_string_append_unicode(struct archive_string *as, const void *_p,
char *p, *endp;
uint32_t uc;
size_t w;
- int n, ret = 0, ts, tm;
+ size_t ts, tm;
+ int n, ret = 0;
int (*parse)(uint32_t *, const char *, size_t);
size_t (*unparse)(char *, size_t, uint32_t);
diff --git a/contrib/libarchive/libarchive/archive_string_sprintf.c b/contrib/libarchive/libarchive/archive_string_sprintf.c
index 1c5910e0b2d3..69b0cdcd83d5 100644
--- a/contrib/libarchive/libarchive/archive_string_sprintf.c
+++ b/contrib/libarchive/libarchive/archive_string_sprintf.c
@@ -146,7 +146,7 @@ archive_string_vsprintf(struct archive_string *as, const char *fmt,
case 'z': s = va_arg(ap, ssize_t); break;
default: s = va_arg(ap, int); break;
}
- append_int(as, s, 10);
+ append_int(as, s, 10);
break;
case 's':
switch(long_flag) {
diff --git a/contrib/libarchive/libarchive/archive_util.c b/contrib/libarchive/libarchive/archive_util.c
index 900abd0c3c62..d048bbc94650 100644
--- a/contrib/libarchive/libarchive/archive_util.c
+++ b/contrib/libarchive/libarchive/archive_util.c
@@ -445,11 +445,39 @@ __archive_mkstemp(wchar_t *template)
#else
static int
-get_tempdir(struct archive_string *temppath)
+__archive_issetugid(void)
{
- const char *tmp;
+#ifdef HAVE_ISSETUGID
+ return (issetugid());
+#elif HAVE_GETRESUID
+ uid_t ruid, euid, suid;
+ gid_t rgid, egid, sgid;
+ if (getresuid(&ruid, &euid, &suid) != 0)
+ return (-1);
+ if (ruid != euid || ruid != suid)
+ return (1);
+ if (getresgid(&ruid, &egid, &sgid) != 0)
+ return (-1);
+ if (rgid != egid || rgid != sgid)
+ return (1);
+#elif HAVE_GETEUID
+ if (geteuid() != getuid())
+ return (1);
+#if HAVE_GETEGID
+ if (getegid() != getgid())
+ return (1);
+#endif
+#endif
+ return (0);
+}
+
+int
+__archive_get_tempdir(struct archive_string *temppath)
+{
+ const char *tmp = NULL;
- tmp = getenv("TMPDIR");
+ if (__archive_issetugid() == 0)
+ tmp = getenv("TMPDIR");
if (tmp == NULL)
#ifdef _PATH_TMP
tmp = _PATH_TMP;
@@ -476,7 +504,7 @@ __archive_mktemp(const char *tmpdir)
archive_string_init(&temp_name);
if (tmpdir == NULL) {
- if (get_tempdir(&temp_name) != ARCHIVE_OK)
+ if (__archive_get_tempdir(&temp_name) != ARCHIVE_OK)
goto exit_tmpfile;
} else {
archive_strcpy(&temp_name, tmpdir);
@@ -538,7 +566,7 @@ __archive_mktempx(const char *tmpdir, char *template)
if (template == NULL) {
archive_string_init(&temp_name);
if (tmpdir == NULL) {
- if (get_tempdir(&temp_name) != ARCHIVE_OK)
+ if (__archive_get_tempdir(&temp_name) != ARCHIVE_OK)
goto exit_tmpfile;
} else
archive_strcpy(&temp_name, tmpdir);
diff --git a/contrib/libarchive/libarchive/archive_write.c b/contrib/libarchive/libarchive/archive_write.c
index a8e7b63b5bfe..9b9cb196f0f9 100644
--- a/contrib/libarchive/libarchive/archive_write.c
+++ b/contrib/libarchive/libarchive/archive_write.c
@@ -360,7 +360,6 @@ archive_write_client_open(struct archive_write_filter *f)
struct archive_none *state;
void *buffer;
size_t buffer_size;
- int ret;
f->bytes_per_block = archive_write_get_bytes_per_block(f->archive);
f->bytes_in_last_block =
@@ -385,13 +384,7 @@ archive_write_client_open(struct archive_write_filter *f)
if (a->client_opener == NULL)
return (ARCHIVE_OK);
- ret = a->client_opener(f->archive, a->client_data);
- if (ret != ARCHIVE_OK) {
- free(state->buffer);
- free(state);
- f->data = NULL;
- }
- return (ret);
+ return (a->client_opener(f->archive, a->client_data));
}
static int
@@ -480,6 +473,7 @@ static int
archive_write_client_free(struct archive_write_filter *f)
{
struct archive_write *a = (struct archive_write *)f->archive;
+ struct archive_none *state = (struct archive_none *)f->data;
if (a->client_freer)
(*a->client_freer)(&a->archive, a->client_data);
@@ -492,6 +486,13 @@ archive_write_client_free(struct archive_write_filter *f)
a->passphrase = NULL;
}
+ /* Free state. */
+ if (state != NULL) {
+ free(state->buffer);
+ free(state);
+ f->data = NULL;
+ }
+
return (ARCHIVE_OK);
}
@@ -548,8 +549,6 @@ archive_write_client_close(struct archive_write_filter *f)
}
if (a->client_closer)
(*a->client_closer)(&a->archive, a->client_data);
- free(state->buffer);
- free(state);
/* Clear the close handler myself not to be called again. */
f->state = ARCHIVE_WRITE_FILTER_STATE_CLOSED;
@@ -807,7 +806,10 @@ _archive_write_finish_entry(struct archive *_a)
if (a->archive.state & ARCHIVE_STATE_DATA
&& a->format_finish_entry != NULL)
ret = (a->format_finish_entry)(a);
- a->archive.state = ARCHIVE_STATE_HEADER;
+ if (ret == ARCHIVE_FATAL)
+ a->archive.state = ARCHIVE_STATE_FATAL;
+ else
+ a->archive.state = ARCHIVE_STATE_HEADER;
return (ret);
}
@@ -819,6 +821,7 @@ _archive_write_data(struct archive *_a, const void *buff, size_t s)
{
struct archive_write *a = (struct archive_write *)_a;
const size_t max_write = INT_MAX;
+ int ret;
archive_check_magic(&a->archive, ARCHIVE_WRITE_MAGIC,
ARCHIVE_STATE_DATA, "archive_write_data");
@@ -826,7 +829,10 @@ _archive_write_data(struct archive *_a, const void *buff, size_t s)
if (s > max_write)
s = max_write;
archive_clear_error(&a->archive);
- return ((a->format_write_data)(a, buff, s));
+ ret = (a->format_write_data)(a, buff, s);
+ if (ret == ARCHIVE_FATAL)
+ a->archive.state = ARCHIVE_STATE_FATAL;
+ return (ret);
}
static struct archive_write_filter *
diff --git a/contrib/libarchive/libarchive/archive_write_add_filter_bzip2.c b/contrib/libarchive/libarchive/archive_write_add_filter_bzip2.c
index 0726f08936ec..2434528d5133 100644
--- a/contrib/libarchive/libarchive/archive_write_add_filter_bzip2.c
+++ b/contrib/libarchive/libarchive/archive_write_add_filter_bzip2.c
@@ -281,6 +281,10 @@ static int
archive_compressor_bzip2_free(struct archive_write_filter *f)
{
struct private_data *data = (struct private_data *)f->data;
+
+ /* May already have been called, but not necessarily. */
+ (void)BZ2_bzCompressEnd(&(data->stream));
+
free(data->compressed);
free(data);
f->data = NULL;
diff --git a/contrib/libarchive/libarchive/archive_write_add_filter_gzip.c b/contrib/libarchive/libarchive/archive_write_add_filter_gzip.c
index 5ef43c1936ed..b09e669b753d 100644
--- a/contrib/libarchive/libarchive/archive_write_add_filter_gzip.c
+++ b/contrib/libarchive/libarchive/archive_write_add_filter_gzip.c
@@ -191,7 +191,8 @@ static int
archive_compressor_gzip_open(struct archive_write_filter *f)
{
struct private_data *data = (struct private_data *)f->data;
- int ret;
+ int ret = ARCHIVE_OK;
+ int init_success;
if (data->compressed == NULL) {
size_t bs = 65536, bpb;
@@ -221,44 +222,66 @@ archive_compressor_gzip_open(struct archive_write_filter *f)
data->compressed[0] = 0x1f; /* GZip signature bytes */
data->compressed[1] = 0x8b;
data->compressed[2] = 0x08; /* "Deflate" compression */
- data->compressed[3] = data->original_filename == NULL ? 0 : 0x8;
+ data->compressed[3] = 0x00; /* Flags */
if (data->timestamp >= 0) {
time_t t = time(NULL);
data->compressed[4] = (uint8_t)(t)&0xff; /* Timestamp */
data->compressed[5] = (uint8_t)(t>>8)&0xff;
data->compressed[6] = (uint8_t)(t>>16)&0xff;
data->compressed[7] = (uint8_t)(t>>24)&0xff;
- } else
+ } else {
memset(&data->compressed[4], 0, 4);
- if (data->compression_level == 9)
- data->compressed[8] = 2;
- else if(data->compression_level == 1)
- data->compressed[8] = 4;
- else
- data->compressed[8] = 0;
+ }
+ if (data->compression_level == 9) {
+ data->compressed[8] = 2;
+ } else if(data->compression_level == 1) {
+ data->compressed[8] = 4;
+ } else {
+ data->compressed[8] = 0;
+ }
data->compressed[9] = 3; /* OS=Unix */
data->stream.next_out += 10;
data->stream.avail_out -= 10;
if (data->original_filename != NULL) {
- strcpy((char*)data->compressed + 10, data->original_filename);
- data->stream.next_out += strlen(data->original_filename) + 1;
- data->stream.avail_out -= strlen(data->original_filename) + 1;
+ /* Limit "original filename" to 32k or the
+ * remaining space in the buffer, whichever is smaller.
+ */
+ int ofn_length = strlen(data->original_filename);
+ int ofn_max_length = 32768;
+ int ofn_space_available = data->compressed
+ + data->compressed_buffer_size
+ - data->stream.next_out
+ - 1;
+ if (ofn_max_length > ofn_space_available) {
+ ofn_max_length = ofn_space_available;
+ }
+ if (ofn_length < ofn_max_length) {
+ data->compressed[3] |= 0x8;
+ strcpy((char*)data->compressed + 10,
+ data->original_filename);
+ data->stream.next_out += ofn_length + 1;
+ data->stream.avail_out -= ofn_length + 1;
+ } else {
+ archive_set_error(f->archive, ARCHIVE_ERRNO_MISC,
+ "Gzip 'Original Filename' ignored because it is too long");
+ ret = ARCHIVE_WARN;
+ }
}
f->write = archive_compressor_gzip_write;
/* Initialize compression library. */
- ret = deflateInit2(&(data->stream),
+ init_success = deflateInit2(&(data->stream),
data->compression_level,
Z_DEFLATED,
-15 /* < 0 to suppress zlib header */,
8,
Z_DEFAULT_STRATEGY);
- if (ret == Z_OK) {
+ if (init_success == Z_OK) {
f->data = data;
- return (ARCHIVE_OK);
+ return (ret);
}
/* Library setup failed: clean up. */
@@ -266,7 +289,7 @@ archive_compressor_gzip_open(struct archive_write_filter *f)
"initializing compression library");
/* Override the error message if we know what really went wrong. */
- switch (ret) {
+ switch (init_success) {
case Z_STREAM_ERROR:
archive_set_error(f->archive, ARCHIVE_ERRNO_MISC,
"Internal error initializing "
diff --git a/contrib/libarchive/libarchive/archive_write_add_filter_program.c b/contrib/libarchive/libarchive/archive_write_add_filter_program.c
index c661cc7f412f..f12db3373883 100644
--- a/contrib/libarchive/libarchive/archive_write_add_filter_program.c
+++ b/contrib/libarchive/libarchive/archive_write_add_filter_program.c
@@ -330,6 +330,7 @@ __archive_write_program_close(struct archive_write_filter *f,
struct archive_write_program_data *data)
{
int ret, status;
+ pid_t pid;
ssize_t bytes_read;
if (data->child == 0)
@@ -373,14 +374,12 @@ cleanup:
close(data->child_stdin);
if (data->child_stdout != -1)
close(data->child_stdout);
- while (waitpid(data->child, &status, 0) == -1 && errno == EINTR)
- continue;
-#if defined(_WIN32) && !defined(__CYGWIN__)
- CloseHandle(data->child);
-#endif
+ do {
+ pid = waitpid(data->child, &status, 0);
+ } while (pid == -1 && errno == EINTR);
data->child = 0;
- if (status != 0) {
+ if (pid < 0 || status != 0) {
archive_set_error(f->archive, EIO,
"Error closing program: %s", data->program_name);
ret = ARCHIVE_FATAL;
diff --git a/contrib/libarchive/libarchive/archive_write_add_filter_zstd.c b/contrib/libarchive/libarchive/archive_write_add_filter_zstd.c
index c0a6e5a37a66..d4752c247157 100644
--- a/contrib/libarchive/libarchive/archive_write_add_filter_zstd.c
+++ b/contrib/libarchive/libarchive/archive_write_add_filter_zstd.c
@@ -391,6 +391,8 @@ archive_compressor_zstd_open(struct archive_write_filter *f)
ZSTD_CCtx_setParameter(data->cstream, ZSTD_c_nbWorkers, data->threads);
+ ZSTD_CCtx_setParameter(data->cstream, ZSTD_c_checksumFlag, 1);
+
#if ZSTD_VERSION_NUMBER >= MINVER_LONG
ZSTD_CCtx_setParameter(data->cstream, ZSTD_c_windowLog, data->long_distance);
#endif
diff --git a/contrib/libarchive/libarchive/archive_write_disk_posix.c b/contrib/libarchive/libarchive/archive_write_disk_posix.c
index 1bbfd7a3d779..aeb27e1270ad 100644
--- a/contrib/libarchive/libarchive/archive_write_disk_posix.c
+++ b/contrib/libarchive/libarchive/archive_write_disk_posix.c
@@ -2204,7 +2204,7 @@ restore_entry(struct archive_write_disk *a)
(void)clear_nochange_fflags(a);
if ((a->flags & ARCHIVE_EXTRACT_SAFE_WRITES) &&
- S_ISREG(a->st.st_mode)) {
+ S_ISREG(a->mode)) {
/* Use a temporary file to extract */
if ((a->fd = la_mktemp(a)) == -1) {
archive_set_error(&a->archive, errno,
@@ -2559,9 +2559,9 @@ _archive_write_disk_close(struct archive *_a)
* for directories. For other file types
* we need to verify via fstat() or lstat()
*/
- if (fd == -1 || p->filetype != AE_IFDIR) {
+ if (fd < 0 || p->filetype != AE_IFDIR) {
#if HAVE_FSTAT
- if (fd > 0 && (
+ if (fd >= 0 && (
fstat(fd, &st) != 0 ||
la_verify_filetype(st.st_mode,
p->filetype) == 0)) {
@@ -3930,10 +3930,14 @@ clear_nochange_fflags(struct archive_write_disk *a)
#ifdef UF_APPEND
| UF_APPEND
#endif
-#ifdef EXT2_APPEND_FL
+#if defined(FS_APPEND_FL)
+ | FS_APPEND_FL
+#elif defined(EXT2_APPEND_FL)
| EXT2_APPEND_FL
#endif
-#ifdef EXT2_IMMUTABLE_FL
+#if defined(FS_IMMUTABLE_FL)
+ | FS_IMMUTABLE_FL
+#elif defined(EXT2_IMMUTABLE_FL)
| EXT2_IMMUTABLE_FL
#endif
;
@@ -4437,7 +4441,7 @@ fixup_appledouble(struct archive_write_disk *a, const char *pathname)
*/
fd = open(pathname, O_RDONLY | O_BINARY | O_CLOEXEC);
__archive_ensure_cloexec_flag(fd);
- if (fd == -1) {
+ if (fd < 0) {
archive_set_error(&a->archive, errno,
"Failed to open a restoring file");
ret = ARCHIVE_WARN;
diff --git a/contrib/libarchive/libarchive/archive_write_open_fd.c b/contrib/libarchive/libarchive/archive_write_open_fd.c
index 8a3f68d0699d..ba034ed92f8a 100644
--- a/contrib/libarchive/libarchive/archive_write_open_fd.c
+++ b/contrib/libarchive/libarchive/archive_write_open_fd.c
@@ -122,7 +122,7 @@ file_write(struct archive *a, void *client_data, const void *buff, size_t length
mine = (struct write_fd_data *)client_data;
for (;;) {
bytesWritten = write(mine->fd, buff, length);
- if (bytesWritten <= 0) {
+ if (bytesWritten < 0) {
if (errno == EINTR)
continue;
archive_set_error(a, errno, "Write error");
diff --git a/contrib/libarchive/libarchive/archive_write_open_file.c b/contrib/libarchive/libarchive/archive_write_open_file.c
index 4c6ebfb2269d..0b310f3da83b 100644
--- a/contrib/libarchive/libarchive/archive_write_open_file.c
+++ b/contrib/libarchive/libarchive/archive_write_open_file.c
@@ -85,16 +85,12 @@ file_write(struct archive *a, void *client_data, const void *buff, size_t length
size_t bytesWritten;
mine = client_data;
- for (;;) {
- bytesWritten = fwrite(buff, 1, length, mine->f);
- if (bytesWritten <= 0) {
- if (errno == EINTR)
- continue;
- archive_set_error(a, errno, "Write error");
- return (-1);
- }
- return (bytesWritten);
+ bytesWritten = fwrite(buff, 1, length, mine->f);
+ if (bytesWritten != length) {
+ archive_set_error(a, errno, "Write error");
+ return (-1);
}
+ return (bytesWritten);
}
static int
diff --git a/contrib/libarchive/libarchive/archive_write_open_filename.c b/contrib/libarchive/libarchive/archive_write_open_filename.c
index 34209426558c..7d0f9bde1dbb 100644
--- a/contrib/libarchive/libarchive/archive_write_open_filename.c
+++ b/contrib/libarchive/libarchive/archive_write_open_filename.c
@@ -108,6 +108,7 @@ open_filename(struct archive *a, int mbs_fn, const void *filename)
else
r = archive_mstring_copy_wcs(&mine->filename, filename);
if (r < 0) {
+ free(mine);
if (errno == ENOMEM) {
archive_set_error(a, ENOMEM, "No memory");
return (ARCHIVE_FATAL);
@@ -227,7 +228,7 @@ file_write(struct archive *a, void *client_data, const void *buff,
mine = (struct write_file_data *)client_data;
for (;;) {
bytesWritten = write(mine->fd, buff, length);
- if (bytesWritten <= 0) {
+ if (bytesWritten < 0) {
if (errno == EINTR)
continue;
archive_set_error(a, errno, "Write error");
diff --git a/contrib/libarchive/libarchive/archive_write_set_format_7zip.c b/contrib/libarchive/libarchive/archive_write_set_format_7zip.c
index c2bce5975a46..175285da13be 100644
--- a/contrib/libarchive/libarchive/archive_write_set_format_7zip.c
+++ b/contrib/libarchive/libarchive/archive_write_set_format_7zip.c
@@ -686,7 +686,7 @@ write_to_temp(struct archive_write *a, const void *buff, size_t s)
ws = write(zip->temp_fd, p, s);
if (ws < 0) {
archive_set_error(&(a->archive), errno,
- "fwrite function failed");
+ "write function failed");
return (ARCHIVE_FATAL);
}
s -= ws;
diff --git a/contrib/libarchive/libarchive/archive_write_set_format_mtree.c b/contrib/libarchive/libarchive/archive_write_set_format_mtree.c
index 02fbb2d2f555..8131574c8da2 100644
--- a/contrib/libarchive/libarchive/archive_write_set_format_mtree.c
+++ b/contrib/libarchive/libarchive/archive_write_set_format_mtree.c
@@ -1927,7 +1927,7 @@ mtree_entry_setup_filenames(struct archive_write *a, struct mtree_entry *file,
}
/*
- * Find out the position which points the last position of
+ * Find out the position which points to the last position of
* path separator('/').
*/
slash = NULL;
@@ -2024,7 +2024,7 @@ mtree_entry_add_child_tail(struct mtree_entry *parent,
}
/*
- * Find a entry from a parent entry with the name.
+ * Find an entry from a parent entry with given name.
*/
static struct mtree_entry *
mtree_entry_find_child(struct mtree_entry *parent, const char *child_name)
@@ -2148,10 +2148,10 @@ mtree_entry_tree_add(struct archive_write *a, struct mtree_entry **filep)
/* Find next sub directory. */
if (!np->dir_info) {
- /* NOT Directory! */
+ /* NOT a directory! */
archive_set_error(&a->archive,
ARCHIVE_ERRNO_MISC,
- "`%s' is not directory, we cannot insert `%s' ",
+ "`%s' is not a directory, we cannot insert `%s' ",
np->pathname.s, file->pathname.s);
return (ARCHIVE_FAILED);
}
@@ -2243,10 +2243,7 @@ mtree_entry_tree_add(struct archive_write *a, struct mtree_entry **filep)
}
same_entry:
- /*
- * We have already has the entry the filename of which is
- * the same.
- */
+ /* We already have an entry with same filename. */
r = mtree_entry_exchange_same_entry(a, np, file);
if (r < ARCHIVE_WARN)
return (r);
@@ -2264,13 +2261,13 @@ mtree_entry_exchange_same_entry(struct archive_write *a, struct mtree_entry *np,
if ((np->mode & AE_IFMT) != (file->mode & AE_IFMT)) {
archive_set_error(&a->archive, ARCHIVE_ERRNO_MISC,
- "Found duplicate entries `%s' and its file type is "
- "different",
+ "Found duplicate entries for `%s' with "
+ "differing file types.",
np->pathname.s);
return (ARCHIVE_FAILED);
}
- /* Update the existent mtree entry's attributes by the new one's. */
+ /* Update the existing mtree entry's attributes by the new one's. */
archive_string_empty(&np->symlink);
archive_string_concat(&np->symlink, &file->symlink);
archive_string_empty(&np->uname);
diff --git a/contrib/libarchive/libarchive/archive_write_set_format_xar.c b/contrib/libarchive/libarchive/archive_write_set_format_xar.c
index 3775e9f5819a..9921f1032be5 100644
--- a/contrib/libarchive/libarchive/archive_write_set_format_xar.c
+++ b/contrib/libarchive/libarchive/archive_write_set_format_xar.c
@@ -689,7 +689,7 @@ write_to_temp(struct archive_write *a, const void *buff, size_t s)
ws = write(xar->temp_fd, p, s);
if (ws < 0) {
archive_set_error(&(a->archive), errno,
- "fwrite function failed");
+ "write function failed");
return (ARCHIVE_FATAL);
}
s -= ws;
@@ -3418,8 +3418,8 @@ static int
xml_writer_get_final_content_and_length(struct xml_writer *ctx,
const char **out, size_t *size)
{
- *out = (const char*)ctx->bp->content;
- *size = (size_t)ctx->bp->use;
+ *out = (const char*)xmlBufferContent(ctx->bp);
+ *size = (size_t)xmlBufferLength(ctx->bp);
return (0);
}
diff --git a/contrib/libarchive/libarchive/archive_write_set_format_zip.c b/contrib/libarchive/libarchive/archive_write_set_format_zip.c
index 3630b9f2b3a3..19121b519148 100644
--- a/contrib/libarchive/libarchive/archive_write_set_format_zip.c
+++ b/contrib/libarchive/libarchive/archive_write_set_format_zip.c
@@ -1856,7 +1856,10 @@ archive_write_zip_finish_entry(struct archive_write *a)
}
ret = __archive_write_output(a, zip->buf, remainder);
if (ret != ARCHIVE_OK)
+ {
+ deflateEnd(&zip->stream.deflate);
return (ret);
+ }
zip->entry_compressed_written += remainder;
zip->written_bytes += remainder;
zip->stream.deflate.next_out = zip->buf;
@@ -1898,7 +1901,10 @@ archive_write_zip_finish_entry(struct archive_write *a)
}
ret = __archive_write_output(a, zip->buf, remainder);
if (ret != ARCHIVE_OK)
+ {
+ BZ2_bzCompressEnd(&zip->stream.bzip2);
return (ret);
+ }
zip->entry_compressed_written += remainder;
zip->written_bytes += remainder;
zip->stream.bzip2.next_out = (char*)zip->buf;
@@ -1940,13 +1946,17 @@ archive_write_zip_finish_entry(struct archive_write *a)
}
ret = __archive_write_output(a, zip->buf, remainder);
if (ret != ARCHIVE_OK)
+ {
+ ZSTD_freeCStream(zip->stream.zstd.context);
return (ret);
+ }
zip->entry_compressed_written += remainder;
zip->written_bytes += remainder;
- zip->stream.zstd.out.dst = zip->buf;
if (zip->stream.zstd.out.pos != zip->stream.zstd.out.size)
finishing = 0;
+ zip->stream.zstd.out.dst = zip->buf;
zip->stream.zstd.out.size = zip->len_buf;
+ zip->stream.zstd.out.pos = 0;
} while (finishing);
ZSTD_freeCStream(zip->stream.zstd.context);
break;
@@ -1984,7 +1994,10 @@ archive_write_zip_finish_entry(struct archive_write *a)
}
ret = __archive_write_output(a, zip->buf, remainder);
if (ret != ARCHIVE_OK)
+ {
+ lzma_end(&zip->stream.lzma.context);
return (ret);
+ }
zip->entry_compressed_written += remainder;
zip->written_bytes += remainder;
zip->stream.lzma.context.next_out = zip->buf;
@@ -2434,13 +2447,19 @@ init_winzip_aes_encryption(struct archive_write *a)
"Can't generate random number for encryption");
return (ARCHIVE_FATAL);
}
- archive_pbkdf2_sha1(passphrase, strlen(passphrase),
+ ret = archive_pbkdf2_sha1(passphrase, strlen(passphrase),
salt, salt_len, 1000, derived_key, key_len * 2 + 2);
+ if (ret != 0) {
+ archive_set_error(&a->archive, ARCHIVE_ERRNO_MISC,
+ ret == CRYPTOR_STUB_FUNCTION ? "Encryption is unsupported due to "
+ "lack of crypto library" : "Failed to process passphrase");
+ return (ARCHIVE_FAILED);
+ }
ret = archive_encrypto_aes_ctr_init(&zip->cctx, derived_key, key_len);
if (ret != 0) {
archive_set_error(&a->archive, ARCHIVE_ERRNO_MISC,
- "Decryption is unsupported due to lack of crypto library");
+ "Failed to initialize AES CTR mode");
return (ARCHIVE_FAILED);
}
ret = archive_hmac_sha1_init(&zip->hctx, derived_key + key_len,
diff --git a/contrib/libarchive/libarchive/filter_fork_posix.c b/contrib/libarchive/libarchive/filter_fork_posix.c
index c895c08e59b3..7c48519336ff 100644
--- a/contrib/libarchive/libarchive/filter_fork_posix.c
+++ b/contrib/libarchive/libarchive/filter_fork_posix.c
@@ -1,6 +1,6 @@
/*-
* Copyright (c) 2007 Joerg Sonnenberger
- * Copyright (c) 2012 Michihiro NAKAJIMA
+ * Copyright (c) 2012 Michihiro NAKAJIMA
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -76,7 +76,15 @@ __archive_create_child(const char *cmd, int *child_stdin, int *child_stdout,
{
pid_t child = -1;
int stdin_pipe[2], stdout_pipe[2], tmp;
+
+#if !defined(POSIX_SPAWN_CLOEXEC_DEFAULT) && \
+ (HAVE_FORK || HAVE_VFORK) && \
+ (HAVE_CLOSEFROM || HAVE_CLOSE_RANGE || defined(_SC_OPEN_MAX))
+#undef HAVE_POSIX_SPAWNP
+#endif
+
#if HAVE_POSIX_SPAWNP
+ posix_spawnattr_t attr;
posix_spawn_file_actions_t actions;
int r;
#endif
@@ -107,11 +115,21 @@ __archive_create_child(const char *cmd, int *child_stdin, int *child_stdout,
#if HAVE_POSIX_SPAWNP
- r = posix_spawn_file_actions_init(&actions);
+ r = posix_spawnattr_init(&attr);
if (r != 0) {
errno = r;
goto stdout_opened;
}
+ r = posix_spawn_file_actions_init(&actions);
+ if (r != 0) {
+ errno = r;
+ goto attr_inited;
+ }
+#ifdef POSIX_SPAWN_CLOEXEC_DEFAULT
+ r = posix_spawnattr_setflags(&attr, POSIX_SPAWN_CLOEXEC_DEFAULT);
+ if (r != 0)
+ goto actions_inited;
+#endif
r = posix_spawn_file_actions_addclose(&actions, stdin_pipe[1]);
if (r != 0)
goto actions_inited;
@@ -136,11 +154,12 @@ __archive_create_child(const char *cmd, int *child_stdin, int *child_stdout,
if (r != 0)
goto actions_inited;
}
- r = posix_spawnp(&child, cmdline->path, &actions, NULL,
+ r = posix_spawnp(&child, cmdline->path, &actions, &attr,
cmdline->argv, NULL);
if (r != 0)
goto actions_inited;
posix_spawn_file_actions_destroy(&actions);
+ posix_spawnattr_destroy(&attr);
#else /* HAVE_POSIX_SPAWNP */
@@ -162,6 +181,16 @@ __archive_create_child(const char *cmd, int *child_stdin, int *child_stdout,
_exit(254);
if (stdout_pipe[1] != 1 /* stdout */)
close(stdout_pipe[1]);
+
+#if HAVE_CLOSEFROM
+ closefrom(3);
+#elif HAVE_CLOSE_RANGE
+ close_range(3, ~0U, 0);
+#elif defined(_SC_OPEN_MAX)
+ for (int i = sysconf(_SC_OPEN_MAX); i > 3;)
+ close(--i);
+#endif
+
execvp(cmdline->path, cmdline->argv);
_exit(254);
}
@@ -183,6 +212,8 @@ __archive_create_child(const char *cmd, int *child_stdin, int *child_stdout,
actions_inited:
errno = r;
posix_spawn_file_actions_destroy(&actions);
+attr_inited:
+ posix_spawnattr_destroy(&attr);
#endif
stdout_opened:
close(stdout_pipe[0]);
diff --git a/contrib/libarchive/libarchive/test/test_acl_nfs4.c b/contrib/libarchive/libarchive/test/test_acl_nfs4.c
index 98d39689df69..050c0a063654 100644
--- a/contrib/libarchive/libarchive/test/test_acl_nfs4.c
+++ b/contrib/libarchive/libarchive/test/test_acl_nfs4.c
@@ -145,6 +145,13 @@ static struct archive_test_acl_t acls_bad[] = {
ARCHIVE_ENTRY_ACL_EVERYONE, -1, "" },
{ ARCHIVE_ENTRY_ACL_TYPE_ALLOW, ARCHIVE_ENTRY_ACL_WRITE,
ARCHIVE_ENTRY_ACL_EVERYONE, -1, "" },
+
+ /* Multiple types */
+ { ARCHIVE_ENTRY_ACL_TYPE_ALLOW | ARCHIVE_ENTRY_ACL_TYPE_AUDIT,
+ ARCHIVE_ENTRY_ACL_EXECUTE,
+ ARCHIVE_ENTRY_ACL_EVERYONE, -1, "" },
+ { ARCHIVE_ENTRY_ACL_TYPE_NFS4, ARCHIVE_ENTRY_ACL_EXECUTE,
+ ARCHIVE_ENTRY_ACL_EVERYONE, -1, "" },
};
DEFINE_TEST(test_acl_nfs4)
diff --git a/contrib/libarchive/libarchive/test/test_acl_posix1e.c b/contrib/libarchive/libarchive/test/test_acl_posix1e.c
index 025ef6afd102..f9b6ffeb6ab7 100644
--- a/contrib/libarchive/libarchive/test/test_acl_posix1e.c
+++ b/contrib/libarchive/libarchive/test/test_acl_posix1e.c
@@ -94,6 +94,11 @@ static struct archive_test_acl_t acls_nfs4[] = {
{ ARCHIVE_ENTRY_ACL_TYPE_ACCESS,
ARCHIVE_ENTRY_ACL_READ | ARCHIVE_ENTRY_ACL_ENTRY_FILE_INHERIT,
ARCHIVE_ENTRY_ACL_USER_OBJ, -1, "" },
+
+ /* Invalid type codes */
+ { ARCHIVE_ENTRY_ACL_TYPE_ACCESS | ARCHIVE_ENTRY_ACL_TYPE_DEFAULT,
+ ARCHIVE_ENTRY_ACL_READ,
+ ARCHIVE_ENTRY_ACL_GROUP_OBJ, -1, "" },
};
DEFINE_TEST(test_acl_posix1e)
diff --git a/contrib/libarchive/libarchive/test/test_archive_parse_date.c b/contrib/libarchive/libarchive/test/test_archive_parse_date.c
index 0a70971b1da6..5251b3393999 100644
--- a/contrib/libarchive/libarchive/test/test_archive_parse_date.c
+++ b/contrib/libarchive/libarchive/test/test_archive_parse_date.c
@@ -39,6 +39,8 @@ DEFINE_TEST(test_archive_parse_date)
assertEqualInt(get_date(now, "Jan 1, 1970 UTC"), 0);
assertEqualInt(get_date(now, "7:12:18-0530 4 May 1983"), 420900138);
assertEqualInt(get_date(now, "2004/01/29 513 mest"), 1075345980);
+ assertEqualInt(get_date(now, "2038-06-01 00:01:02 UTC"),
+ sizeof(time_t) <= 4 ? -1 : 2158963262);
assertEqualInt(get_date(now, "99/02/17 7pm utc"), 919278000);
assertEqualInt(get_date(now, "02/17/99 7:11am est"), 919253460);
assertEqualInt(get_date(now, "now - 2 hours"),
diff --git a/contrib/libarchive/libarchive/test/test_archive_string_conversion.c b/contrib/libarchive/libarchive/test/test_archive_string_conversion.c
index 12976f3e70ec..055bddc75068 100644
--- a/contrib/libarchive/libarchive/test/test_archive_string_conversion.c
+++ b/contrib/libarchive/libarchive/test/test_archive_string_conversion.c
@@ -991,6 +991,7 @@ DEFINE_TEST(test_archive_string_update_utf8_koi8)
static const char koi8_string[] = "\xD0\xD2\xC9";
static const wchar_t wcs_string[] = L"\U0000043f\U00000440\U00000438";
struct archive_mstring mstr;
+ struct archive *a;
int r;
memset(&mstr, 0, sizeof(mstr));
@@ -999,6 +1000,15 @@ DEFINE_TEST(test_archive_string_update_utf8_koi8)
skipping("KOI8-R locale not available on this system.");
return;
}
+ a = archive_write_new();
+ assertEqualInt(ARCHIVE_OK, archive_write_set_format_pax(a));
+ if (archive_write_set_options(a, "hdrcharset=UTF-8") != ARCHIVE_OK) {
+ skipping("This system cannot convert character-set"
+ " from KOI8-R to UTF-8.");
+ archive_write_free(a);
+ return;
+ }
+ archive_write_free(a);
r = archive_mstring_update_utf8(NULL, &mstr, utf8_string);
diff --git a/contrib/libarchive/libarchive/test/test_entry.c b/contrib/libarchive/libarchive/test/test_entry.c
index 9b21b83ecdfb..cff9c5c86efc 100644
--- a/contrib/libarchive/libarchive/test/test_entry.c
+++ b/contrib/libarchive/libarchive/test/test_entry.c
@@ -880,6 +880,17 @@ DEFINE_TEST(test_entry)
if (pst == NULL)
return;
assertEqualInt(pst->st_uid, 22);
+
+ /* Check behavior with large sizes. */
+ archive_entry_set_size(e, INT64_MAX - 1);
+ assert((pst = archive_entry_stat(e)) != NULL);
+ if (pst == NULL)
+ return;
+ if (sizeof(pst->st_size) < sizeof(int64_t))
+ assertEqualInt(pst->st_size, 0);
+ else
+ assertEqualInt(pst->st_size, INT64_MAX - 1);
+
/* We don't need to check high-res fields here. */
/*
diff --git a/contrib/libarchive/libarchive/test/test_read_filter_gzip_recursive.c b/contrib/libarchive/libarchive/test/test_read_filter_gzip_recursive.c
index 0042a0511d5a..51b614b6c023 100644
--- a/contrib/libarchive/libarchive/test/test_read_filter_gzip_recursive.c
+++ b/contrib/libarchive/libarchive/test/test_read_filter_gzip_recursive.c
@@ -29,8 +29,8 @@ DEFINE_TEST(test_read_filter_gzip_recursive)
const char *name = "test_read_filter_gzip_recursive.gz";
struct archive *a;
- if (!canGzip()) {
- skipping("gzip not available");
+ if (archive_zlib_version() == NULL) {
+ skipping("zlib not available");
return;
}
diff --git a/contrib/libarchive/libarchive/test/test_read_format_7zip.c b/contrib/libarchive/libarchive/test/test_read_format_7zip.c
index ad10ef06bbc5..3236fee2c9d3 100644
--- a/contrib/libarchive/libarchive/test/test_read_format_7zip.c
+++ b/contrib/libarchive/libarchive/test/test_read_format_7zip.c
@@ -1285,19 +1285,26 @@ DEFINE_TEST(test_read_format_7zip_sfx_pe)
const char test_txt[] = "123";
int size = sizeof(test_txt) - 1;
- extract_reference_file(reffile);
assert((a = archive_read_new()) != NULL);
- assertA(0 == archive_read_support_filter_all(a));
- assertA(0 == archive_read_support_format_all(a));
- assertA(0 == archive_read_open_filename(a, reffile, bs));
- assertA(0 == archive_read_next_header(a, &ae));
- assertEqualString("test.txt.txt", archive_entry_pathname(ae));
+ if (ARCHIVE_OK != archive_read_support_filter_lzma(a)) {
+ skipping(
+ "7zip:lzma decoding is not supported on this platform");
+ } else {
+ extract_reference_file(reffile);
+ assertA(0 == archive_read_support_filter_all(a));
+ assertA(0 == archive_read_support_format_all(a));
+ assertA(0 == archive_read_open_filename(a, reffile, bs));
- assertA(size == archive_read_data(a, buff, size));
- assertEqualMem(buff, test_txt, size);
+ assertA(0 == archive_read_next_header(a, &ae));
+ assertEqualString("test.txt.txt", archive_entry_pathname(ae));
+
+ assertA(size == archive_read_data(a, buff, size));
+ assertEqualMem(buff, test_txt, size);
+
+ assertEqualIntA(a, ARCHIVE_OK, archive_read_close(a));
+ }
- assertEqualIntA(a, ARCHIVE_OK, archive_read_close(a));
assertEqualInt(ARCHIVE_OK, archive_read_free(a));
}
@@ -1316,19 +1323,26 @@ DEFINE_TEST(test_read_format_7zip_sfx_modified_pe)
const char test_txt[] = "123";
int size = sizeof(test_txt) - 1;
- extract_reference_file(reffile);
assert((a = archive_read_new()) != NULL);
- assertA(0 == archive_read_support_filter_all(a));
- assertA(0 == archive_read_support_format_all(a));
- assertA(0 == archive_read_open_filename(a, reffile, bs));
- assertA(0 == archive_read_next_header(a, &ae));
- assertEqualString("test.txt.txt", archive_entry_pathname(ae));
+ if (ARCHIVE_OK != archive_read_support_filter_lzma(a)) {
+ skipping(
+ "7zip:lzma decoding is not supported on this platform");
+ } else {
+ extract_reference_file(reffile);
+ assertA(0 == archive_read_support_filter_all(a));
+ assertA(0 == archive_read_support_format_all(a));
+ assertA(0 == archive_read_open_filename(a, reffile, bs));
+
+ assertA(0 == archive_read_next_header(a, &ae));
+ assertEqualString("test.txt.txt", archive_entry_pathname(ae));
+
+ assertA(size == archive_read_data(a, buff, size));
+ assertEqualMem(buff, test_txt, size);
- assertA(size == archive_read_data(a, buff, size));
- assertEqualMem(buff, test_txt, size);
+ assertEqualIntA(a, ARCHIVE_OK, archive_read_close(a));
+ }
- assertEqualIntA(a, ARCHIVE_OK, archive_read_close(a));
assertEqualInt(ARCHIVE_OK, archive_read_free(a));
}
@@ -1346,20 +1360,27 @@ DEFINE_TEST(test_read_format_7zip_sfx_elf)
const char test_txt[] = "123";
int size = sizeof(test_txt) - 1;
- extract_reference_file(reffile);
assert((a = archive_read_new()) != NULL);
- assertA(0 == archive_read_support_filter_all(a));
- assertA(0 == archive_read_support_format_all(a));
- assertA(0 == archive_read_open_filename(a, reffile, bs));
- assertA(0 == archive_read_next_header(a, &ae));
- assertEqualString("test.txt.txt", archive_entry_pathname(ae));
+ if (ARCHIVE_OK != archive_read_support_filter_lzma(a)) {
+ skipping(
+ "7zip:lzma decoding is not supported on this platform");
+ } else {
+ extract_reference_file(reffile);
+ assertA(0 == archive_read_support_filter_all(a));
+ assertA(0 == archive_read_support_format_all(a));
+ assertA(0 == archive_read_open_filename(a, reffile, bs));
+
+ assertA(0 == archive_read_next_header(a, &ae));
+ assertEqualString("test.txt.txt", archive_entry_pathname(ae));
- assertA(size == archive_read_data(a, buff, size));
- assertEqualMem(buff, test_txt, size);
+ assertA(size == archive_read_data(a, buff, size));
+ assertEqualMem(buff, test_txt, size);
- assertEqualIntA(a, ARCHIVE_OK, archive_read_close(a));
- assertEqualInt(ARCHIVE_OK, archive_read_free(a));
+ assertEqualIntA(a, ARCHIVE_OK, archive_read_close(a));
+ }
+
+ assertEqualInt(ARCHIVE_OK, archive_read_free(a));
}
DEFINE_TEST(test_read_format_7zip_extract_second)
@@ -1597,9 +1618,9 @@ DEFINE_TEST(test_read_format_7zip_lzma2_powerpc)
assert((a = archive_read_new()) != NULL);
- if (ARCHIVE_OK != archive_read_support_filter_gzip(a)) {
+ if (ARCHIVE_OK != archive_read_support_filter_lzma(a)) {
skipping(
- "7zip:deflate decoding is not supported on this platform");
+ "7zip:lzma decoding is not supported on this platform");
} else {
test_powerpc_filter("test_read_format_7zip_lzma2_powerpc.7z");
}
diff --git a/contrib/libarchive/libarchive/test/test_read_format_rar5.c b/contrib/libarchive/libarchive/test/test_read_format_rar5.c
index fd233277bc1b..6ab0d236a1ed 100644
--- a/contrib/libarchive/libarchive/test/test_read_format_rar5.c
+++ b/contrib/libarchive/libarchive/test/test_read_format_rar5.c
@@ -1111,6 +1111,18 @@ DEFINE_TEST(test_read_format_rar5_nonempty_dir_stream)
EPILOGUE();
}
+DEFINE_TEST(test_read_format_rar5_nonempty_dir_data)
+{
+ PROLOGUE("test_read_format_rar5_dirdata.rar");
+
+ /* This archive is invalid. It declares a directory entry with nonzero
+ data size. */
+
+ assertA(archive_read_next_header(a, &ae) == ARCHIVE_FATAL);
+
+ EPILOGUE();
+}
+
DEFINE_TEST(test_read_format_rar5_fileattr)
{
unsigned long set, clear, flag;
@@ -1428,3 +1440,57 @@ DEFINE_TEST(test_read_format_rar5_data_ready_pointer_leak)
EPILOGUE();
}
+
+DEFINE_TEST(test_read_format_rar5_only_crypt_exfld)
+{
+ /* GH #2711 */
+
+ char buf[4096];
+ PROLOGUE("test_read_format_rar5_only_crypt_exfld.rar");
+
+ /* The reader should allow iteration through files, but should fail
+ during data extraction. */
+
+ assertA(archive_read_next_header(a, &ae) == ARCHIVE_OK);
+ assertA(archive_read_data(a, buf, sizeof(buf)) == ARCHIVE_FATAL);
+
+ /* The reader should also provide a valid error message. */
+ assertA(archive_error_string(a) != NULL);
+
+ EPILOGUE();
+}
+
+DEFINE_TEST(test_read_format_rar5_only_unsupported_exfld)
+{
+ /* GH #2711 */
+
+ char buf[4096];
+ PROLOGUE("test_read_format_rar5_unsupported_exfld.rar");
+
+ /* The reader should allow iteration through files, and it should
+ succeed with data extraction. */
+
+ assertA(archive_read_next_header(a, &ae) == ARCHIVE_OK);
+
+ /* 48 is the expected number of bytes that should be extracted */
+ assertA(archive_read_data(a, buf, sizeof(buf)) == 48);
+
+ EPILOGUE();
+}
+
+DEFINE_TEST(test_read_format_rar5_invalidhash_and_validhtime_exfld)
+{
+ /* GH #2711 */
+
+ char buf[4096];
+ PROLOGUE("test_read_format_rar5_invalid_hash_valid_htime_exfld.rar");
+
+ /* The reader should report an error when trying to process this data.
+ Returning EOF here means that the reader has failed to identify
+ malformed structure. */
+
+ assertA(archive_read_next_header(a, &ae) < 0);
+ assertA(archive_read_data(a, buf, sizeof(buf)) < 0);
+
+ EPILOGUE();
+}
diff --git a/contrib/libarchive/libarchive/test/test_read_format_rar5_dirdata.rar.uu b/contrib/libarchive/libarchive/test/test_read_format_rar5_dirdata.rar.uu
new file mode 100644
index 000000000000..c7928f344a80
--- /dev/null
+++ b/contrib/libarchive/libarchive/test/test_read_format_rar5_dirdata.rar.uu
@@ -0,0 +1,6 @@
+begin 644 -
+M4F%R(1H'`0`BD'[;,`$%,#8P`0&`@("``B?GD;$U`@(+@X``"_C5%:2#``(`
+M`#"``S`P,#`P,#`P,#!);S#6KA',@]:N$?*IN;YV[8"1S>?4^`,#`R,#`P,#
+-`P,#1)'C@XX*4`O.^P``
+`
+end
diff --git a/contrib/libarchive/libarchive/test/test_read_format_rar5_invalid_hash_valid_htime_exfld.rar.uu b/contrib/libarchive/libarchive/test/test_read_format_rar5_invalid_hash_valid_htime_exfld.rar.uu
new file mode 100644
index 000000000000..399acd814ae4
--- /dev/null
+++ b/contrib/libarchive/libarchive/test/test_read_format_rar5_invalid_hash_valid_htime_exfld.rar.uu
@@ -0,0 +1,6 @@
+begin 644 -
+M4F%R(1H'`0`SDK7E"@$%!@`%`0&`@`#^T/5L)`(###$$,>V#`D840I@``0AF
+M:6QE+G1X=`@"OX0]``$"`P(#`&EN=F%L:60@2$%32"!E>'1R82P@86YD(&QA
+>=&5R(&$@=F%L:60@2%1)344@97AT<F$@/=^&`@4$
+`
+end
diff --git a/contrib/libarchive/libarchive/test/test_read_format_rar5_only_crypt_exfld.rar.uu b/contrib/libarchive/libarchive/test/test_read_format_rar5_only_crypt_exfld.rar.uu
new file mode 100644
index 000000000000..4f9faf350c11
--- /dev/null
+++ b/contrib/libarchive/libarchive/test/test_read_format_rar5_only_crypt_exfld.rar.uu
@@ -0,0 +1,7 @@
+begin 644 -
+M4F%R(1H'`0`SDK7E"@$%!@`%`0&`@`"!0_"Y/0(#)2X$+NV#`IB>)!,``0AF
+M:6QE+G1X="0!```&``````````````````````````````````````````!R
+M87(U('-T;W)E9"!F:6QE('=I=&@@;VYL>2!A($-265!4(&5X=')A(&9I96QD
+'(#W?A@(%!```
+`
+end
diff --git a/contrib/libarchive/libarchive/test/test_read_format_rar5_unsupported_exfld.rar.uu b/contrib/libarchive/libarchive/test/test_read_format_rar5_unsupported_exfld.rar.uu
new file mode 100644
index 000000000000..16b456bf4873
--- /dev/null
+++ b/contrib/libarchive/libarchive/test/test_read_format_rar5_unsupported_exfld.rar.uu
@@ -0,0 +1,6 @@
+begin 644 -
+M4F%R(1H'`0`SDK7E"@$%!@`%`0&`@`#>[JDS)@(##C`$,.V#`BX6Z[0``0AF
+M:6QE+G1X=`W_____#WA6-!(`````<F%R-2!S=&]R960@9FEL92!W:71H(&%N
+?('5N<W5P<&]R=&5D(&5X=')A(&9I96QD(#W?A@(%!```
+`
+end
diff --git a/contrib/libarchive/libarchive/test/test_read_format_tar_V_negative_size.c b/contrib/libarchive/libarchive/test/test_read_format_tar_V_negative_size.c
new file mode 100644
index 000000000000..d110553acfaf
--- /dev/null
+++ b/contrib/libarchive/libarchive/test/test_read_format_tar_V_negative_size.c
@@ -0,0 +1,48 @@
+/*-
+ * Copyright (c) 2025 Tim Kientzle
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR(S) ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR(S) BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+#include "test.h"
+
+DEFINE_TEST(test_read_format_tar_V_negative_size)
+{
+ /*
+ * An archive that contains a `V` volume header with a negative body size
+ *
+ * This used to lead to an infinite loop: the tar reader would "advance"
+ * by the size of the body to skip it, which would in this case end up
+ * reversing back to the beginning of the same header.
+ */
+ struct archive_entry *ae;
+ struct archive *a;
+ const char *refname = "test_read_format_tar_V_negative_size.tar";
+
+ extract_reference_file(refname);
+ assert((a = archive_read_new()) != NULL);
+ assertEqualInt(ARCHIVE_OK, archive_read_support_filter_all(a));
+ assertEqualInt(ARCHIVE_OK, archive_read_support_format_all(a));
+ assertEqualIntA(a, ARCHIVE_OK, archive_read_open_filename(a, refname, 10240));
+ assertEqualIntA(a, ARCHIVE_FATAL, archive_read_next_header(a, &ae));
+ assertEqualIntA(a, ARCHIVE_OK, archive_read_close(a));
+ assertEqualInt(ARCHIVE_OK, archive_read_free(a));
+}
diff --git a/contrib/libarchive/libarchive/test/test_read_format_tar_V_negative_size.tar.uu b/contrib/libarchive/libarchive/test/test_read_format_tar_V_negative_size.tar.uu
new file mode 100644
index 000000000000..230d710c8f8f
--- /dev/null
+++ b/contrib/libarchive/libarchive/test/test_read_format_tar_V_negative_size.tar.uu
@@ -0,0 +1,20 @@
+Tar archive with a single `V` header that has a negative size.
+This used to result in an infinite loop -- the tar reader would
+"advance" by the size of the header, which in this case just backed
+up to re-read the same header again.
+
+begin 644 test_read_format_tar_V_negative_size.tar
+M`#(VXP```````````````````-Z;@"E&LOX^\@````````````!7````'```
+M````````````````````````````````````````````````````````````
+M``````````````````````````````````````````#___\````````@````
+M````````````````````````````5H%ZL#X]SH\-``":SN#[C4;Z5OOW-&']
+M?HHQ%WRG?Z$Q>^E#_1.OY96VEI*Z<U[)$TR502_;F$;9FU"/F'!`V:0`````
+M`````````````````````````````````````````````````````0``````
+M````````````````````````````````````````````````````````````
+M`````````````````````````````0``````````````````````````````
+M````````````````````````````````````````````````````````````
+M````````````````````````````````````````````````````````````
+M````````````````````````````````````````````````````````````
+1````````````````````````
+`
+end
diff --git a/contrib/libarchive/libarchive/test/test_read_set_format.c b/contrib/libarchive/libarchive/test/test_read_set_format.c
index c760de0056d3..615dd8ae8022 100644
--- a/contrib/libarchive/libarchive/test/test_read_set_format.c
+++ b/contrib/libarchive/libarchive/test/test_read_set_format.c
@@ -138,7 +138,10 @@ DEFINE_TEST(test_read_append_filter)
assertEqualInt(ARCHIVE_OK, archive_read_free(a));
return;
}
- assertEqualIntA(a, ARCHIVE_OK, r);
+ if (r == ARCHIVE_WARN && canGzip())
+ assertEqualString(archive_error_string(a), "Using external gzip program");
+ else
+ assertEqualIntA(a, ARCHIVE_OK, r);
assertEqualInt(ARCHIVE_OK,
archive_read_open_memory(a, archive, sizeof(archive)));
assertEqualInt(ARCHIVE_OK, archive_read_next_header(a, &ae));
@@ -210,7 +213,7 @@ DEFINE_TEST(test_read_append_filter_wrong_program)
/*
* If we have "bunzip2 -q", try using that.
*/
- if (!canRunCommand("bunzip2 -h")) {
+ if (!canRunCommand("bunzip2 -h", NULL)) {
skipping("Can't run bunzip2 program on this platform");
return;
}
diff --git a/contrib/libarchive/libarchive/test/test_write_filter_bzip2.c b/contrib/libarchive/libarchive/test/test_write_filter_bzip2.c
index 20ca0d9a7b22..7b2e4f857a75 100644
--- a/contrib/libarchive/libarchive/test/test_write_filter_bzip2.c
+++ b/contrib/libarchive/libarchive/test/test_write_filter_bzip2.c
@@ -268,6 +268,35 @@ DEFINE_TEST(test_write_filter_bzip2)
assertEqualInt(ARCHIVE_OK, archive_write_free(a));
/*
+ * Test behavior after a fatal error (triggered by giving
+ * archive_write_open_memory() a very small buffer).
+ */
+ if (!use_prog) {
+ used1 = 0;
+ assert((a = archive_write_new()) != NULL);
+ assertEqualIntA(a, ARCHIVE_OK,
+ archive_write_set_format_ustar(a));
+ assertEqualIntA(a, ARCHIVE_OK,
+ archive_write_add_filter_bzip2(a));
+ assertEqualIntA(a, ARCHIVE_OK,
+ archive_write_open_memory(a, buff, 100, &used1));
+ assert((ae = archive_entry_new()) != NULL);
+ archive_entry_set_filetype(ae, AE_IFREG);
+ archive_entry_set_size(ae, 4000000);
+ archive_entry_copy_pathname(ae, "file");
+ assertEqualIntA(a, ARCHIVE_OK,
+ archive_write_header(a, ae));
+ for (i = 0; i < 1000000; i++) {
+ r = archive_write_data(a, &i, 4);
+ if (r == ARCHIVE_FATAL)
+ break;
+ }
+ assertEqualIntA(a, ARCHIVE_FATAL, r);
+ archive_entry_free(ae);
+ assertEqualInt(ARCHIVE_OK, archive_write_free(a));
+ }
+
+ /*
* Clean up.
*/
free(data);
diff --git a/contrib/libarchive/libarchive/test/test_write_filter_gzip.c b/contrib/libarchive/libarchive/test/test_write_filter_gzip.c
index 8fbdbed09744..a6681d7618b1 100644
--- a/contrib/libarchive/libarchive/test/test_write_filter_gzip.c
+++ b/contrib/libarchive/libarchive/test/test_write_filter_gzip.c
@@ -166,9 +166,15 @@ DEFINE_TEST(test_write_filter_gzip)
assertEqualInt(rbuff[0], 0x1f);
assertEqualInt(rbuff[1], 0x8b);
assertEqualInt(rbuff[2], 0x08);
- assertEqualInt(rbuff[3], 0x08);
- assertEqualInt(rbuff[8], 2); /* RFC 1952 flag for compression level 9 */
- assertEqualString((const char*)rbuff+10, "testorgfilename");
+ /* RFC 1952 flag for compression level 9 */
+ assertEqualInt(rbuff[8], 2);
+ /* External gzip program might not save filename */
+ if (!use_prog || rbuff[3] == 0x08) {
+ assertEqualInt(rbuff[3], 0x08);
+ assertEqualString((const char*)rbuff+10, "testorgfilename");
+ } else {
+ assertEqualInt(rbuff[3], 0x00);
+ }
/* Curiously, this test fails; the test data above compresses
* better at default compression than at level 9. */
diff --git a/contrib/libarchive/libarchive/test/test_write_filter_gzip_timestamp.c b/contrib/libarchive/libarchive/test/test_write_filter_gzip_timestamp.c
index a148f818dcec..d0496b025b64 100644
--- a/contrib/libarchive/libarchive/test/test_write_filter_gzip_timestamp.c
+++ b/contrib/libarchive/libarchive/test/test_write_filter_gzip_timestamp.c
@@ -81,8 +81,11 @@ DEFINE_TEST(test_write_filter_gzip_timestamp)
archive_entry_free(ae);
assertEqualIntA(a, ARCHIVE_OK, archive_write_close(a));
assertEqualInt(ARCHIVE_OK, archive_write_free(a));
- failure("Timestamp should be recorded");
- assert(memcmp(buff + 4, "\x00\x00\x00\x00", 4) != 0);
+ /* External gzip program might not save timestamp */
+ if (!use_prog) {
+ failure("Timestamp should be recorded");
+ assert(memcmp(buff + 4, "\x00\x00\x00\x00", 4) != 0);
+ }
/* Test2: set "gzip:!timestamp" option. */
assert((a = archive_write_new()) != NULL);
diff --git a/contrib/libarchive/libarchive_fe/err.c b/contrib/libarchive/libarchive_fe/lafe_err.c
index f6dcf44af347..b108b9b1fea7 100644
--- a/contrib/libarchive/libarchive_fe/err.c
+++ b/contrib/libarchive/libarchive_fe/lafe_err.c
@@ -36,7 +36,7 @@
#include <string.h>
#endif
-#include "err.h"
+#include "lafe_err.h"
static void lafe_vwarnc(int, const char *, va_list) __LA_PRINTFLIKE(2, 0);
diff --git a/contrib/libarchive/libarchive_fe/err.h b/contrib/libarchive/libarchive_fe/lafe_err.h
index f4a66350a669..f4a66350a669 100644
--- a/contrib/libarchive/libarchive_fe/err.h
+++ b/contrib/libarchive/libarchive_fe/lafe_err.h
diff --git a/contrib/libarchive/libarchive_fe/line_reader.c b/contrib/libarchive/libarchive_fe/line_reader.c
index 7f0429ece3cf..0af9db53c0a2 100644
--- a/contrib/libarchive/libarchive_fe/line_reader.c
+++ b/contrib/libarchive/libarchive_fe/line_reader.c
@@ -31,7 +31,7 @@
#include <stdlib.h>
#include <string.h>
-#include "err.h"
+#include "lafe_err.h"
#include "line_reader.h"
#if defined(_WIN32) && !defined(__CYGWIN__) && !defined(__BORLANDC__)
diff --git a/contrib/libarchive/libarchive_fe/passphrase.c b/contrib/libarchive/libarchive_fe/passphrase.c
index 527ad2d63654..1b7a50453664 100644
--- a/contrib/libarchive/libarchive_fe/passphrase.c
+++ b/contrib/libarchive/libarchive_fe/passphrase.c
@@ -61,7 +61,7 @@
#include <readpassphrase.h>
#endif
-#include "err.h"
+#include "lafe_err.h"
#include "passphrase.h"
#ifndef HAVE_READPASSPHRASE
diff --git a/contrib/libarchive/tar/bsdtar.c b/contrib/libarchive/tar/bsdtar.c
index 53ac135f0129..92e86fd6bd94 100644
--- a/contrib/libarchive/tar/bsdtar.c
+++ b/contrib/libarchive/tar/bsdtar.c
@@ -55,7 +55,7 @@
#endif
#include "bsdtar.h"
-#include "err.h"
+#include "lafe_err.h"
#if ARCHIVE_VERSION_NUMBER < 4000000 && !defined(_PATH_DEFTAPE)
// Libarchive 4.0 and later will NOT define _PATH_DEFTAPE
@@ -183,6 +183,11 @@ main(int argc, char **argv)
sa.sa_handler = SIG_IGN;
sigaction(SIGPIPE, &sa, NULL);
#endif
+#ifdef SIGCHLD
+ /* Do not ignore SIGCHLD. */
+ sa.sa_handler = SIG_DFL;
+ sigaction(SIGCHLD, &sa, NULL);
+#endif
}
#endif
diff --git a/contrib/libarchive/tar/bsdtar.h b/contrib/libarchive/tar/bsdtar.h
index 45dfeed7dce3..782d36d6f756 100644
--- a/contrib/libarchive/tar/bsdtar.h
+++ b/contrib/libarchive/tar/bsdtar.h
@@ -16,6 +16,12 @@
#define ENV_WRITER_OPTIONS "TAR_WRITER_OPTIONS"
#define IGNORE_WRONG_MODULE_NAME "__ignore_wrong_module_name__,"
+#if defined(_MSC_VER ) && (_MSC_VER < 1927 ) /* Check if compiler pre-dated Visual Studio 2019 Release 16.8 */
+#define ARCHIVE_RESTRICT
+#else
+#define ARCHIVE_RESTRICT restrict
+#endif
+
struct creation_set;
/*
* The internal state for the "bsdtar" program.
@@ -188,7 +194,7 @@ int edit_pathname(struct bsdtar *, struct archive_entry *);
void edit_mtime(struct bsdtar *, struct archive_entry *);
int need_report(void);
int pathcmp(const char *a, const char *b);
-void safe_fprintf(FILE * restrict, const char * restrict fmt, ...) __LA_PRINTF(2, 3);
+void safe_fprintf(FILE * ARCHIVE_RESTRICT, const char * ARCHIVE_RESTRICT fmt, ...) __LA_PRINTF(2, 3);
void set_chdir(struct bsdtar *, const char *newdir);
const char *tar_i64toa(int64_t);
void tar_mode_c(struct bsdtar *bsdtar);
diff --git a/contrib/libarchive/tar/cmdline.c b/contrib/libarchive/tar/cmdline.c
index c766c1a52dbb..309be312c948 100644
--- a/contrib/libarchive/tar/cmdline.c
+++ b/contrib/libarchive/tar/cmdline.c
@@ -22,7 +22,7 @@
#endif
#include "bsdtar.h"
-#include "err.h"
+#include "lafe_err.h"
/*
* Short options for tar. Please keep this sorted.
diff --git a/contrib/libarchive/tar/creation_set.c b/contrib/libarchive/tar/creation_set.c
index 6883090418b0..51f803354a5d 100644
--- a/contrib/libarchive/tar/creation_set.c
+++ b/contrib/libarchive/tar/creation_set.c
@@ -15,7 +15,7 @@
#endif
#include "bsdtar.h"
-#include "err.h"
+#include "lafe_err.h"
struct creation_set {
char *create_format;
diff --git a/contrib/libarchive/tar/read.c b/contrib/libarchive/tar/read.c
index 8563fe714f9a..7cbcfb19ff0a 100644
--- a/contrib/libarchive/tar/read.c
+++ b/contrib/libarchive/tar/read.c
@@ -57,7 +57,7 @@
#endif
#include "bsdtar.h"
-#include "err.h"
+#include "lafe_err.h"
struct progress_data {
struct bsdtar *bsdtar;
diff --git a/contrib/libarchive/tar/subst.c b/contrib/libarchive/tar/subst.c
index 5546b5f93b12..a5d644dc5a70 100644
--- a/contrib/libarchive/tar/subst.c
+++ b/contrib/libarchive/tar/subst.c
@@ -25,7 +25,7 @@
#define REG_BASIC 0
#endif
-#include "err.h"
+#include "lafe_err.h"
struct subst_rule {
struct subst_rule *next;
diff --git a/contrib/libarchive/tar/test/test_crlf_mtree.c b/contrib/libarchive/tar/test/test_crlf_mtree.c
new file mode 100644
index 000000000000..5ef8811369c1
--- /dev/null
+++ b/contrib/libarchive/tar/test/test_crlf_mtree.c
@@ -0,0 +1,74 @@
+/*-
+ * SPDX-License-Identifier: BSD-2-Clause
+ *
+ * Copyright (c) 2018 The FreeBSD Foundation
+ * All rights reserved.
+ *
+ * This software was developed by Arshan Khanifar <arshankhanifar@gmail.com>
+ * under sponsorship from the FreeBSD Foundation.
+ */
+#include "test.h"
+
+DEFINE_TEST(test_crlf_mtree)
+{
+ char *p0;
+ size_t s;
+ int r;
+ p0 = NULL;
+ char *content = "#mtree\r\n"
+ "f type=file uname=\\\r\n"
+ "root gname=root mode=0755 content=bar/foo\r\n"
+ "g type=file uname=root gname=root mode=0755 content=bar/goo\r\n";
+ char *filename = "output.tar";
+#if defined(_WIN32) && !defined(__CYGWIN__)
+ char *p;
+#endif
+
+ /* an absolute path to mtree file */
+ char *mtree_file = "/METALOG.mtree";
+ char *absolute_path = malloc(strlen(testworkdir) + strlen(mtree_file) + 1);
+ strcpy(absolute_path, testworkdir);
+ strcat(absolute_path, mtree_file );
+
+ /* Create an archive using an mtree file. */
+ assertMakeFile(absolute_path, 0777, content);
+ assertMakeDir("bar", 0775);
+ assertMakeFile("bar/foo", 0777, "abc");
+ assertMakeFile("bar/goo", 0777, "abc");
+
+#if defined(_WIN32) && !defined(__CYGWIN__)
+ p = absolute_path;
+ while(*p != '\0') {
+ if (*p == '/')
+ *p = '\\';
+ p++;
+ }
+
+ r = systemf("%s -cf %s @%s >step1.out 2>step1.err", testprog, filename, absolute_path);
+ failure("Error invoking %s -cf %s -C bar @%s", testprog, filename, absolute_path);
+#else
+ r = systemf("%s -cf %s \"@%s\" >step1.out 2>step1.err", testprog, filename, absolute_path);
+ failure("Error invoking %s -cf %s -C bar \"@%s\"", testprog, filename, absolute_path);
+#endif
+
+ assertEqualInt(r, 0);
+ assertEmptyFile("step1.out");
+ assertEmptyFile("step1.err");
+
+ /* Do validation of the constructed archive. */
+
+ p0 = slurpfile(&s, "output.tar");
+ if (!assert(p0 != NULL))
+ goto done;
+ if (!assert(s >= 2048))
+ goto done;
+ assertEqualMem(p0 + 0, "f", 2);
+ assertEqualMem(p0 + 512, "abc", 4);
+ assertEqualMem(p0 + 1024, "g", 2);
+ assertEqualMem(p0 + 1536, "abc", 4);
+done:
+ free(p0);
+ free(absolute_path);
+}
+
+
diff --git a/contrib/libarchive/tar/test/test_option_safe_writes.c b/contrib/libarchive/tar/test/test_option_safe_writes.c
index b88479bc5f35..d30b9a745927 100644
--- a/contrib/libarchive/tar/test/test_option_safe_writes.c
+++ b/contrib/libarchive/tar/test/test_option_safe_writes.c
@@ -16,11 +16,12 @@ DEFINE_TEST(test_option_safe_writes)
assertMakeFile("d", 0644, "c");
assertMakeFile("fs", 0644, "d");
assertMakeFile("ds", 0644, "e");
+ assertMakeDir("fd", 0755);
assertEqualInt(0, chdir(".."));
/* Tar files up */
assertEqualInt(0,
- systemf("%s -c -C in -f t.tar f fh d fs ds "
+ systemf("%s -c -C in -f t.tar f fh d fs ds fd "
">pack.out 2>pack.err", testprog));
/* Verify that nothing went to stdout or stderr. */
@@ -32,6 +33,7 @@ DEFINE_TEST(test_option_safe_writes)
assertEqualInt(0, chdir("out"));
assertMakeFile("f", 0644, "a");
assertMakeHardlink("fh", "f");
+ assertMakeFile("fd", 0644, "b");
assertMakeDir("d", 0755);
if (canSymlink()) {
assertMakeSymlink("fs", "f", 0);
@@ -55,4 +57,5 @@ DEFINE_TEST(test_option_safe_writes)
assertTextFileContents("c","d");
assertTextFileContents("d","fs");
assertTextFileContents("e","ds");
+ assertIsDir("fd", 0755);
}
diff --git a/contrib/libarchive/tar/util.c b/contrib/libarchive/tar/util.c
index c99f67797562..fc5e15cb039f 100644
--- a/contrib/libarchive/tar/util.c
+++ b/contrib/libarchive/tar/util.c
@@ -41,7 +41,7 @@
#endif
#include "bsdtar.h"
-#include "err.h"
+#include "lafe_err.h"
#include "passphrase.h"
static size_t bsdtar_expand_char(char *, size_t, size_t, char);
@@ -682,6 +682,7 @@ list_item_verbose(struct bsdtar *bsdtar, FILE *out, struct archive_entry *entry)
{
char tmp[100];
size_t w;
+ size_t sw;
const char *p;
const char *fmt;
time_t tim;
@@ -769,8 +770,8 @@ list_item_verbose(struct bsdtar *bsdtar, FILE *out, struct archive_entry *entry)
ltime = localtime(&tim);
#endif
if (ltime)
- strftime(tmp, sizeof(tmp), fmt, ltime);
- else
+ sw = strftime(tmp, sizeof(tmp), fmt, ltime);
+ if (!ltime || !sw)
sprintf(tmp, "-- -- ----");
fprintf(out, " %s ", tmp);
safe_fprintf(out, "%s", archive_entry_pathname(entry));
diff --git a/contrib/libarchive/tar/write.c b/contrib/libarchive/tar/write.c
index 21984e980ebd..9e6c97b580b7 100644
--- a/contrib/libarchive/tar/write.c
+++ b/contrib/libarchive/tar/write.c
@@ -58,7 +58,7 @@
#endif
#include "bsdtar.h"
-#include "err.h"
+#include "lafe_err.h"
#include "line_reader.h"
#ifndef O_BINARY
@@ -111,7 +111,32 @@ seek_file(int fd, int64_t offset, int whence)
return (SetFilePointerEx((HANDLE)_get_osfhandle(fd),
distance, NULL, FILE_BEGIN) ? 1 : -1);
}
-#define open _open
+
+static int
+_open_wrap_sopen(char const *const path, int const oflag, ...)
+{
+ va_list ap;
+ int r, pmode;
+
+ pmode = 0;
+ if (oflag & _O_CREAT)
+ {
+ va_start(ap, oflag);
+ pmode = va_arg(ap, int);
+ va_end(ap);
+ }
+
+ _sopen_s(&r, path, oflag, _SH_DENYNO, pmode & 0600);
+ if (r < 0)
+ {
+ /* _sopen_s populates errno */
+ return -1;
+ }
+
+ return r;
+}
+
+#define open _open_wrap_sopen
#define close _close
#define read _read
#ifdef lseek
diff --git a/contrib/libarchive/test_utils/test_common.h b/contrib/libarchive/test_utils/test_common.h
index 064f0a6ec241..a9df300e3be8 100644
--- a/contrib/libarchive/test_utils/test_common.h
+++ b/contrib/libarchive/test_utils/test_common.h
@@ -340,8 +340,14 @@ int canGrzip(void);
/* Return true if this platform can run the "gzip" program. */
int canGzip(void);
-/* Return true if this platform can run the specified command. */
-int canRunCommand(const char *);
+/* Return true if this platform can run the specified command.
+ *
+ * Result can be optionally cached with `*tested`:
+ * - 0 if not tested yet
+ * - <0 if already tested negative
+ * - >0 if already tested positive
+ */
+int canRunCommand(const char *cmd, int *tested);
/* Return true if this platform can run the "lrzip" program. */
int canLrzip(void);
diff --git a/contrib/libarchive/test_utils/test_main.c b/contrib/libarchive/test_utils/test_main.c
index fe330e5a052e..f4d443060d88 100644
--- a/contrib/libarchive/test_utils/test_main.c
+++ b/contrib/libarchive/test_utils/test_main.c
@@ -2523,167 +2523,77 @@ static const char *redirectArgs = ">NUL 2>NUL"; /* Win32 cmd.exe */
#else
static const char *redirectArgs = ">/dev/null 2>/dev/null"; /* POSIX 'sh' */
#endif
+
/*
- * Can this platform run the bzip2 program?
+ * Can this platform run the specified command?
*/
int
-canBzip2(void)
+canRunCommand(const char *cmd, int *tested)
{
- static int tested = 0, value = 0;
- if (!tested) {
- tested = 1;
- if (systemf("bzip2 --help %s", redirectArgs) == 0)
- value = 1;
- }
- return (value);
+ int value = tested ? *tested : 0;
+ if (!value) {
+ value = systemf("%s %s", cmd, redirectArgs) ? -1 : +1;
+ if (tested)
+ *tested = value;
+ }
+ return (value > 0);
}
+#define CAN_RUN_FUNC(Program, Command) \
+ int can##Program(void) { \
+ static int tested = 0; \
+ return canRunCommand((Command), &tested); \
+ }
+
+/*
+ * Can this platform run the bzip2 program?
+ */
+CAN_RUN_FUNC(Bzip2, "bzip2 --help")
+
/*
* Can this platform run the grzip program?
*/
-int
-canGrzip(void)
-{
- static int tested = 0, value = 0;
- if (!tested) {
- tested = 1;
- if (systemf("grzip -V %s", redirectArgs) == 0)
- value = 1;
- }
- return (value);
-}
+CAN_RUN_FUNC(Grzip, "grzip -V")
/*
* Can this platform run the gzip program?
*/
-int
-canGzip(void)
-{
- static int tested = 0, value = 0;
- if (!tested) {
- tested = 1;
- if (systemf("gzip --help %s", redirectArgs) == 0)
- value = 1;
- }
- return (value);
-}
+CAN_RUN_FUNC(Gzip, "gzip --help")
/*
* Can this platform run the lrzip program?
*/
-int
-canRunCommand(const char *cmd)
-{
- static int tested = 0, value = 0;
- if (!tested) {
- tested = 1;
- if (systemf("%s %s", cmd, redirectArgs) == 0)
- value = 1;
- }
- return (value);
-}
-
-int
-canLrzip(void)
-{
- static int tested = 0, value = 0;
- if (!tested) {
- tested = 1;
- if (systemf("lrzip -V %s", redirectArgs) == 0)
- value = 1;
- }
- return (value);
-}
+CAN_RUN_FUNC(Lrzip, "lrzip -V")
/*
* Can this platform run the lz4 program?
*/
-int
-canLz4(void)
-{
- static int tested = 0, value = 0;
- if (!tested) {
- tested = 1;
- if (systemf("lz4 --help %s", redirectArgs) == 0)
- value = 1;
- }
- return (value);
-}
+CAN_RUN_FUNC(Lz4, "lz4 --help")
/*
* Can this platform run the zstd program?
*/
-int
-canZstd(void)
-{
- static int tested = 0, value = 0;
- if (!tested) {
- tested = 1;
- if (systemf("zstd --help %s", redirectArgs) == 0)
- value = 1;
- }
- return (value);
-}
+CAN_RUN_FUNC(Zstd, "zstd --help")
/*
* Can this platform run the lzip program?
*/
-int
-canLzip(void)
-{
- static int tested = 0, value = 0;
- if (!tested) {
- tested = 1;
- if (systemf("lzip --help %s", redirectArgs) == 0)
- value = 1;
- }
- return (value);
-}
+CAN_RUN_FUNC(Lzip, "lzip --help")
/*
* Can this platform run the lzma program?
*/
-int
-canLzma(void)
-{
- static int tested = 0, value = 0;
- if (!tested) {
- tested = 1;
- if (systemf("lzma --help %s", redirectArgs) == 0)
- value = 1;
- }
- return (value);
-}
+CAN_RUN_FUNC(Lzma, "lzma --help")
/*
* Can this platform run the lzop program?
*/
-int
-canLzop(void)
-{
- static int tested = 0, value = 0;
- if (!tested) {
- tested = 1;
- if (systemf("lzop --help %s", redirectArgs) == 0)
- value = 1;
- }
- return (value);
-}
+CAN_RUN_FUNC(Lzop, "lzop --help")
/*
* Can this platform run the xz program?
*/
-int
-canXz(void)
-{
- static int tested = 0, value = 0;
- if (!tested) {
- tested = 1;
- if (systemf("xz --help %s", redirectArgs) == 0)
- value = 1;
- }
- return (value);
-}
+CAN_RUN_FUNC(Xz, "xz --help")
/*
* Can this filesystem handle nodump flags.
@@ -4184,6 +4094,9 @@ main(int argc, char **argv)
if (testprogfile == NULL)
{
tmp2_len = strlen(testprogdir) + 1 + strlen(PROGRAM) + 1;
+#if defined(_WIN32) && !defined(__CYGWIN__)
+ tmp2_len += 4;
+#endif
if ((tmp2 = malloc(tmp2_len)) == NULL)
{
fprintf(stderr, "ERROR: Out of memory.");
@@ -4192,6 +4105,9 @@ main(int argc, char **argv)
strncpy(tmp2, testprogdir, tmp2_len);
strncat(tmp2, "/", tmp2_len);
strncat(tmp2, PROGRAM, tmp2_len);
+#if defined(_WIN32) && !defined(__CYGWIN__)
+ strncat(tmp2, ".exe", tmp2_len);
+#endif
testprogfile = tmp2;
}
diff --git a/contrib/libarchive/unzip/bsdunzip.c b/contrib/libarchive/unzip/bsdunzip.c
index 621afbeb9d6a..1b520e841690 100644
--- a/contrib/libarchive/unzip/bsdunzip.c
+++ b/contrib/libarchive/unzip/bsdunzip.c
@@ -29,6 +29,9 @@
#ifdef HAVE_LOCALE_H
#include <locale.h>
#endif
+#ifdef HAVE_SIGNAL_H
+#include <signal.h>
+#endif
#ifdef HAVE_STDARG_H
#include <stdarg.h>
#endif
@@ -54,7 +57,7 @@
#include "bsdunzip.h"
#include "passphrase.h"
-#include "err.h"
+#include "lafe_err.h"
/* command-line options */
static int a_opt; /* convert EOL */
@@ -1187,6 +1190,16 @@ main(int argc, char *argv[])
const char *zipfile;
int nopts;
+#if defined(HAVE_SIGACTION) && defined(SIGCHLD)
+ { /* Do not ignore SIGCHLD. */
+ struct sigaction sa;
+ sa.sa_handler = SIG_DFL;
+ sigemptyset(&sa.sa_mask);
+ sa.sa_flags = 0;
+ sigaction(SIGCHLD, &sa, NULL);
+ }
+#endif
+
lafe_setprogname(*argv, "bsdunzip");
#if HAVE_SETLOCALE
diff --git a/contrib/libarchive/unzip/cmdline.c b/contrib/libarchive/unzip/cmdline.c
index 8afddedd5ead..8e6eedd2321c 100644
--- a/contrib/libarchive/unzip/cmdline.c
+++ b/contrib/libarchive/unzip/cmdline.c
@@ -21,7 +21,7 @@
#endif
#include "bsdunzip.h"
-#include "err.h"
+#include "lafe_err.h"
/*
* Short options for bsdunzip. Please keep this sorted.
diff --git a/contrib/libarchive/unzip/test/test_C.c b/contrib/libarchive/unzip/test/test_C.c
index 66835c8406f3..d386bd61e85d 100644
--- a/contrib/libarchive/unzip/test/test_C.c
+++ b/contrib/libarchive/unzip/test/test_C.c
@@ -9,6 +9,7 @@
/* Test C arg - match case-insensitive */
DEFINE_TEST(test_C)
{
+#ifdef HAVE_LIBZ
const char *reffile = "test_basic.zip";
int r;
@@ -19,4 +20,7 @@ DEFINE_TEST(test_C)
assertEmptyFile("test.err");
assertTextFileContents("contents CAPS\n", "test_basic/CAPS");
+#else
+ skipping("zlib not available");
+#endif
}
diff --git a/contrib/libarchive/unzip/test/test_L.c b/contrib/libarchive/unzip/test/test_L.c
index 5b004d5d5707..85b43f592542 100644
--- a/contrib/libarchive/unzip/test/test_L.c
+++ b/contrib/libarchive/unzip/test/test_L.c
@@ -9,6 +9,7 @@
/* Test L arg - make names lowercase */
DEFINE_TEST(test_L)
{
+#ifdef HAVE_LIBZ
const char *reffile = "test_basic.zip";
int r;
@@ -22,4 +23,7 @@ DEFINE_TEST(test_L)
assertTextFileContents("contents b\n", "test_basic/b");
assertTextFileContents("contents c\n", "test_basic/c");
assertTextFileContents("contents CAPS\n", "test_basic/caps");
+#else
+ skipping("zlib not available");
+#endif
}
diff --git a/contrib/libarchive/unzip/test/test_P_encryption.c b/contrib/libarchive/unzip/test/test_P_encryption.c
index e2cf3cda0ebd..ed08a068811b 100644
--- a/contrib/libarchive/unzip/test/test_P_encryption.c
+++ b/contrib/libarchive/unzip/test/test_P_encryption.c
@@ -14,9 +14,13 @@ DEFINE_TEST(test_P_encryption)
extract_reference_file(reffile);
r = systemf("%s -P password %s >test.out 2>test.err", testprog, reffile);
- assertEqualInt(0, r);
- assertNonEmptyFile("test.out");
- assertEmptyFile("test.err");
+ if (r == 256) {
+ assertTextFileContents("unzip: Decryption is unsupported due to lack of crypto library\n", "test.err");
+ } else {
+ assertEqualInt(0, r);
+ assertNonEmptyFile("test.out");
+ assertEmptyFile("test.err");
- assertTextFileContents("plaintext\n", "encrypted/file.txt");
+ assertTextFileContents("plaintext\n", "encrypted/file.txt");
+ }
}
diff --git a/contrib/libarchive/unzip/test/test_basic.c b/contrib/libarchive/unzip/test/test_basic.c
index 1f37dcd416a3..3a884aa30e5d 100644
--- a/contrib/libarchive/unzip/test/test_basic.c
+++ b/contrib/libarchive/unzip/test/test_basic.c
@@ -9,6 +9,7 @@
/* This test just does a basic zip decompression */
DEFINE_TEST(test_basic)
{
+#ifdef HAVE_LIBZ
const char *reffile = "test_basic.zip";
int r;
@@ -22,4 +23,7 @@ DEFINE_TEST(test_basic)
assertTextFileContents("contents b\n", "test_basic/b");
assertTextFileContents("contents c\n", "test_basic/c");
assertTextFileContents("contents CAPS\n", "test_basic/CAPS");
+#else
+ skipping("zlib not available");
+#endif
}
diff --git a/contrib/libarchive/unzip/test/test_d.c b/contrib/libarchive/unzip/test/test_d.c
index ea67246207f2..cd7c3dfd97ad 100644
--- a/contrib/libarchive/unzip/test/test_d.c
+++ b/contrib/libarchive/unzip/test/test_d.c
@@ -9,6 +9,7 @@
/* Test d arg - extract to target dir - before zipfile argument */
DEFINE_TEST(test_d_before_zipfile)
{
+#ifdef HAVE_LIBZ
const char *reffile = "test_basic.zip";
int r;
@@ -22,11 +23,15 @@ DEFINE_TEST(test_d_before_zipfile)
assertTextFileContents("contents b\n", "foobar/test_basic/b");
assertTextFileContents("contents c\n", "foobar/test_basic/c");
assertTextFileContents("contents CAPS\n", "foobar/test_basic/CAPS");
+#else
+ skipping("zlib not available");
+#endif
}
/* Test d arg - extract to target dir - after zipfile argument */
DEFINE_TEST(test_d_after_zipfile)
{
+#ifdef HAVE_LIBZ
const char *reffile = "test_basic.zip";
int r;
@@ -40,4 +45,7 @@ DEFINE_TEST(test_d_after_zipfile)
assertTextFileContents("contents b\n", "foobar/test_basic/b");
assertTextFileContents("contents c\n", "foobar/test_basic/c");
assertTextFileContents("contents CAPS\n", "foobar/test_basic/CAPS");
+#else
+ skipping("zlib not available");
+#endif
}
diff --git a/contrib/libarchive/unzip/test/test_doubledash.c b/contrib/libarchive/unzip/test/test_doubledash.c
index 4467213dbb89..db0445ec3c24 100644
--- a/contrib/libarchive/unzip/test/test_doubledash.c
+++ b/contrib/libarchive/unzip/test/test_doubledash.c
@@ -9,6 +9,7 @@
/* Test double dash arg - swallow "--" and use next argument as file name */
DEFINE_TEST(test_doubledash)
{
+#ifdef HAVE_LIBZ
const char *reffile = "test_basic.zip";
int r;
@@ -22,4 +23,7 @@ DEFINE_TEST(test_doubledash)
assertTextFileContents("contents b\n", "test_basic/b");
assertTextFileContents("contents c\n", "test_basic/c");
assertTextFileContents("contents CAPS\n", "test_basic/CAPS");
+#else
+ skipping("zlib not available");
+#endif
}
diff --git a/contrib/libarchive/unzip/test/test_glob.c b/contrib/libarchive/unzip/test/test_glob.c
index b53aa16fd85c..589ff1c55ef3 100644
--- a/contrib/libarchive/unzip/test/test_glob.c
+++ b/contrib/libarchive/unzip/test/test_glob.c
@@ -9,6 +9,7 @@
/* Test that the glob works */
DEFINE_TEST(test_glob)
{
+#ifdef HAVE_LIBZ
const char *reffile = "test_basic.zip";
int r;
@@ -22,4 +23,7 @@ DEFINE_TEST(test_glob)
assertTextFileContents("contents b\n", "test_basic/b");
assertFileNotExists("test_basic/c");
assertFileNotExists("test_basic/CAPS");
+#else
+ skipping("zlib not available");
+#endif
}
diff --git a/contrib/libarchive/unzip/test/test_j.c b/contrib/libarchive/unzip/test/test_j.c
index b87229f42e25..1fba8ca207ec 100644
--- a/contrib/libarchive/unzip/test/test_j.c
+++ b/contrib/libarchive/unzip/test/test_j.c
@@ -9,6 +9,7 @@
/* Test j arg - don't make directories */
DEFINE_TEST(test_j)
{
+#ifdef HAVE_LIBZ
const char *reffile = "test_basic.zip";
int r;
@@ -22,4 +23,7 @@ DEFINE_TEST(test_j)
assertTextFileContents("contents b\n", "b");
assertTextFileContents("contents c\n", "c");
assertTextFileContents("contents CAPS\n", "CAPS");
+#else
+ skipping("zlib not available");
+#endif
}
diff --git a/contrib/libarchive/unzip/test/test_n.c b/contrib/libarchive/unzip/test/test_n.c
index bb75c5d7696d..a13623ce23df 100644
--- a/contrib/libarchive/unzip/test/test_n.c
+++ b/contrib/libarchive/unzip/test/test_n.c
@@ -9,6 +9,7 @@
/* Test n arg - don't overwrite existing files */
DEFINE_TEST(test_n)
{
+#ifdef HAVE_LIBZ
const char *reffile = "test_basic.zip";
int r;
@@ -26,4 +27,7 @@ DEFINE_TEST(test_n)
assertTextFileContents("orig b\n", "test_basic/b");
assertTextFileContents("contents c\n", "test_basic/c");
assertTextFileContents("contents CAPS\n", "test_basic/CAPS");
+#else
+ skipping("zlib not available");
+#endif
}
diff --git a/contrib/libarchive/unzip/test/test_o.c b/contrib/libarchive/unzip/test/test_o.c
index 64f946774440..8c48348c41a4 100644
--- a/contrib/libarchive/unzip/test/test_o.c
+++ b/contrib/libarchive/unzip/test/test_o.c
@@ -9,6 +9,7 @@
/* Test o arg - overwrite existing files */
DEFINE_TEST(test_o)
{
+#ifdef HAVE_LIBZ
const char *reffile = "test_basic.zip";
int r;
@@ -25,4 +26,7 @@ DEFINE_TEST(test_o)
assertTextFileContents("contents b\n", "test_basic/b");
assertTextFileContents("contents c\n", "test_basic/c");
assertTextFileContents("contents CAPS\n", "test_basic/CAPS");
+#else
+ skipping("zlib not available");
+#endif
}
diff --git a/contrib/libarchive/unzip/test/test_p.c b/contrib/libarchive/unzip/test/test_p.c
index 8bfffbe5dc39..13a7765463ec 100644
--- a/contrib/libarchive/unzip/test/test_p.c
+++ b/contrib/libarchive/unzip/test/test_p.c
@@ -9,6 +9,7 @@
/* Test p arg - Print to stdout */
DEFINE_TEST(test_p)
{
+#ifdef HAVE_LIBZ
const char *reffile = "test_basic.zip";
int r;
@@ -17,4 +18,7 @@ DEFINE_TEST(test_p)
assertEqualInt(0, r);
assertTextFileContents("contents a\ncontents b\ncontents c\ncontents CAPS\n", "test.out");
assertEmptyFile("test.err");
+#else
+ skipping("zlib not available");
+#endif
}
diff --git a/contrib/libarchive/unzip/test/test_q.c b/contrib/libarchive/unzip/test/test_q.c
index 13222a483992..0579e8028d76 100644
--- a/contrib/libarchive/unzip/test/test_q.c
+++ b/contrib/libarchive/unzip/test/test_q.c
@@ -9,6 +9,7 @@
/* Test q arg - Quiet */
DEFINE_TEST(test_q)
{
+#ifdef HAVE_LIBZ
const char *reffile = "test_basic.zip";
int r;
@@ -22,4 +23,7 @@ DEFINE_TEST(test_q)
assertTextFileContents("contents b\n", "test_basic/b");
assertTextFileContents("contents c\n", "test_basic/c");
assertTextFileContents("contents CAPS\n", "test_basic/CAPS");
+#else
+ skipping("zlib not available");
+#endif
}
diff --git a/contrib/libarchive/unzip/test/test_singlefile.c b/contrib/libarchive/unzip/test/test_singlefile.c
index a72811f046d9..a5a35ecacc4d 100644
--- a/contrib/libarchive/unzip/test/test_singlefile.c
+++ b/contrib/libarchive/unzip/test/test_singlefile.c
@@ -9,6 +9,7 @@
/* Ensure single-file zips work */
DEFINE_TEST(test_singlefile)
{
+#ifdef HAVE_LIBZ
const char *reffile = "test_singlefile.zip";
int r;
@@ -19,4 +20,7 @@ DEFINE_TEST(test_singlefile)
assertEmptyFile("test.err");
assertTextFileContents("hello\n", "file.txt");
+#else
+ skipping("zlib not available");
+#endif
}
diff --git a/contrib/libarchive/unzip/test/test_t.c b/contrib/libarchive/unzip/test/test_t.c
index 55a516fc636f..7565830915c3 100644
--- a/contrib/libarchive/unzip/test/test_t.c
+++ b/contrib/libarchive/unzip/test/test_t.c
@@ -9,6 +9,7 @@
/* Test t arg - Test zip contents */
DEFINE_TEST(test_t)
{
+#ifdef HAVE_LIBZ
const char *reffile = "test_basic.zip";
int r;
@@ -17,4 +18,7 @@ DEFINE_TEST(test_t)
assertEqualInt(0, r);
assertNonEmptyFile("test.out");
assertEmptyFile("test.err");
+#else
+ skipping("zlib not available");
+#endif
}
diff --git a/contrib/libarchive/unzip/test/test_x.c b/contrib/libarchive/unzip/test/test_x.c
index 959beb1950df..43a2085dc5b2 100644
--- a/contrib/libarchive/unzip/test/test_x.c
+++ b/contrib/libarchive/unzip/test/test_x.c
@@ -9,6 +9,7 @@
/* Test x arg with single exclude path */
DEFINE_TEST(test_x_single)
{
+#ifdef HAVE_LIBZ
const char *reffile = "test_basic.zip";
int r;
@@ -22,11 +23,15 @@ DEFINE_TEST(test_x_single)
assertTextFileContents("contents b\n", "test_basic/b");
assertFileNotExists("test_basic/c");
assertTextFileContents("contents CAPS\n", "test_basic/CAPS");
+#else
+ skipping("zlib not available");
+#endif
}
/* Test x arg with multiple exclude paths */
DEFINE_TEST(test_x_multiple)
{
+#ifdef HAVE_LIBZ
const char *reffile = "test_basic.zip";
int r;
@@ -40,11 +45,15 @@ DEFINE_TEST(test_x_multiple)
assertFileNotExists("test_basic/b");
assertFileNotExists("test_basic/c");
assertTextFileContents("contents CAPS\n", "test_basic/CAPS");
+#else
+ skipping("zlib not available");
+#endif
}
/* Test x arg with multiple exclude paths and a d arg afterwards */
DEFINE_TEST(test_x_multiple_with_d)
{
+#ifdef HAVE_LIBZ
const char *reffile = "test_basic.zip";
int r;
@@ -58,4 +67,7 @@ DEFINE_TEST(test_x_multiple_with_d)
assertFileNotExists("foobar/test_basic/b");
assertFileNotExists("foobar/test_basic/c");
assertTextFileContents("contents CAPS\n", "foobar/test_basic/CAPS");
+#else
+ skipping("zlib not available");
+#endif
}
diff --git a/contrib/llvm-project/clang/lib/Driver/ToolChains/FreeBSD.h b/contrib/llvm-project/clang/lib/Driver/ToolChains/FreeBSD.h
index 7d090ba682b3..7ab63905ed4f 100644
--- a/contrib/llvm-project/clang/lib/Driver/ToolChains/FreeBSD.h
+++ b/contrib/llvm-project/clang/lib/Driver/ToolChains/FreeBSD.h
@@ -78,11 +78,6 @@ public:
void AddHIPIncludeArgs(const llvm::opt::ArgList &DriverArgs,
llvm::opt::ArgStringList &CC1Args) const override;
- bool IsAArch64OutlineAtomicsDefault(
- const llvm::opt::ArgList &Args) const override {
- return true;
- }
-
UnwindTableLevel
getDefaultUnwindTableLevel(const llvm::opt::ArgList &Args) const override;
bool isPIEDefault(const llvm::opt::ArgList &Args) const override;
diff --git a/lib/libarchive/tests/Makefile b/lib/libarchive/tests/Makefile
index 07c5fe24dd30..930250d974c5 100644
--- a/lib/libarchive/tests/Makefile
+++ b/lib/libarchive/tests/Makefile
@@ -185,6 +185,7 @@ TESTS_SRCS= \
test_read_format_rar_overflow.c \
test_read_format_raw.c \
test_read_format_tar.c \
+ test_read_format_tar_V_negative_size.c \
test_read_format_tar_concatenated.c \
test_read_format_tar_empty_filename.c \
test_read_format_tar_empty_pax.c \
@@ -607,6 +608,7 @@ ${PACKAGE}FILES+= test_read_format_rar5_decode_number_out_of_bounds_read.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_different_solid_window_size.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_different_window_size.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_different_winsize_on_merge.rar.uu
+${PACKAGE}FILES+= test_read_format_rar5_dirdata.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_distance_overflow.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_encrypted.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_encrypted_filenames.rar.uu
@@ -616,6 +618,7 @@ ${PACKAGE}FILES+= test_read_format_rar5_extra_field_version.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_fileattr.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_hardlink.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_invalid_dict_reference.rar.uu
+${PACKAGE}FILES+= test_read_format_rar5_invalid_hash_valid_htime_exfld.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_leftshift1.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_leftshift2.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_multiarchive.part01.rar.uu
@@ -633,6 +636,7 @@ ${PACKAGE}FILES+= test_read_format_rar5_multiarchive_solid.part04.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_multiple_files.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_multiple_files_solid.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_nonempty_dir_stream.rar.uu
+${PACKAGE}FILES+= test_read_format_rar5_only_crypt_exfld.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_owner.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_readtables_overflow.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_sfx.exe.uu
@@ -642,12 +646,14 @@ ${PACKAGE}FILES+= test_read_format_rar5_stored_manyfiles.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_symlink.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_truncated_huff.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_unicode.rar.uu
+${PACKAGE}FILES+= test_read_format_rar5_unsupported_exfld.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_win32.rar.uu
${PACKAGE}FILES+= test_read_format_rar5_window_buf_and_size_desync.rar.uu
${PACKAGE}FILES+= test_read_format_raw.bufr.uu
${PACKAGE}FILES+= test_read_format_raw.data.Z.uu
${PACKAGE}FILES+= test_read_format_raw.data.gz.uu
${PACKAGE}FILES+= test_read_format_raw.data.uu
+${PACKAGE}FILES+= test_read_format_tar_V_negative_size.tar.uu
${PACKAGE}FILES+= test_read_format_tar_concatenated.tar.uu
${PACKAGE}FILES+= test_read_format_tar_empty_filename.tar.uu
${PACKAGE}FILES+= test_read_format_tar_empty_with_gnulabel.tar.uu
diff --git a/lib/libc/gen/getvfsbyname.3 b/lib/libc/gen/getvfsbyname.3
index 9365d043a1fc..19fa12419353 100644
--- a/lib/libc/gen/getvfsbyname.3
+++ b/lib/libc/gen/getvfsbyname.3
@@ -27,7 +27,7 @@
.\"
.\" @(#)kvm_getvfsbyname.3 8.3 (Berkeley) 5/4/95
.\"
-.Dd August 16, 2018
+.Dd October 28, 2025
.Dt GETVFSBYNAME 3
.Os
.Sh NAME
@@ -104,6 +104,7 @@ argument
specifies a file system that is unknown or not configured in the kernel.
.El
.Sh SEE ALSO
+.Xr lsvfs 1 ,
.Xr jail 2 ,
.Xr mount 2 ,
.Xr sysctl 3 ,
diff --git a/lib/libc/sys/revoke.2 b/lib/libc/sys/revoke.2
index dc92512d3129..db0c8a85558b 100644
--- a/lib/libc/sys/revoke.2
+++ b/lib/libc/sys/revoke.2
@@ -30,7 +30,7 @@
.\"
.\" @(#)revoke.2 8.1 (Berkeley) 6/4/93
.\"
-.Dd January 25, 2016
+.Dd October 24, 2025
.Dt REVOKE 2
.Os
.Sh NAME
@@ -64,7 +64,7 @@ using a special close method which does not block.
Access to a file may be revoked only by its owner or the super user.
The
.Fn revoke
-system call is currently supported only for block and character special
+system call is currently supported only for character special
device files.
It is normally used to prepare a terminal device for a new login session,
preventing any access by a previous user of the terminal.
diff --git a/lib/libc/sys/write.2 b/lib/libc/sys/write.2
index adf60aa91d7a..2f0a9d034038 100644
--- a/lib/libc/sys/write.2
+++ b/lib/libc/sys/write.2
@@ -134,6 +134,26 @@ and
may write fewer bytes than requested;
the return value must be noted,
and the remainder of the operation should be retried when possible.
+.Sh ATOMICITY OF WRITES
+When operating on regular files on local file systems, the effects of
+.Fn write
+are atomic.
+As required by the POSIX standard,
+the
+.Fn read ,
+.Fn write ,
+and
+.Fn ftruncate
+functions and their variations are atomic with respect to
+each other on the file data and metadata for regular files.
+See for instance
+.St -p1003.1-2024
+Volume 2, Section 2.9.7 for more information.
+.Pp
+.Fx
+implements the requirement by taking
+a read/write range lock on the file byte range
+affected by the corresponding function.
.Sh RETURN VALUES
Upon successful completion the number of bytes which were written
is returned.
diff --git a/sbin/mount/mount.8 b/sbin/mount/mount.8
index 0adc5ffc228b..1e5440fbc846 100644
--- a/sbin/mount/mount.8
+++ b/sbin/mount/mount.8
@@ -25,7 +25,7 @@
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
.\" SUCH DAMAGE.
.\"
-.Dd November 19, 2024
+.Dd October 28, 2025
.Dt MOUNT 8
.Os
.Sh NAME
@@ -563,6 +563,7 @@ support for a particular file system might be provided either on a static
.Xr kldload 8 ) .
.Sh SEE ALSO
.Xr getfacl 1 ,
+.Xr lsvfs 1 ,
.Xr setfacl 1 ,
.Xr nmount 2 ,
.Xr acl 3 ,
diff --git a/share/man/man3/queue.3 b/share/man/man3/queue.3
index aef4944e3847..dd466cf20a0b 100644
--- a/share/man/man3/queue.3
+++ b/share/man/man3/queue.3
@@ -1422,13 +1422,13 @@ while in userland builds it prints the diagnostic message on
.Dv stderr
and then calls
.Fn abort .
-These behaviors can be overriden by defining a custom
+These behaviors can be overridden by defining a custom
.Fn QMD_PANIC
macro before first inclusion of
.In sys/queue.h .
The diagnostic messages automatically include the source file, line and function
-where the failing check occured.
-This behavior can be overriden by defining a custom
+where the failing check occurred.
+This behavior can be overridden by defining a custom
.Fn QMD_ASSERT
macro before first inclusion of
.In sys/queue.h .
diff --git a/share/man/man3/siginfo.3 b/share/man/man3/siginfo.3
index f57cf5f7d706..59e3ecf8f3e8 100644
--- a/share/man/man3/siginfo.3
+++ b/share/man/man3/siginfo.3
@@ -224,7 +224,7 @@ raised by a hardware watchpoint exception may report the data address that
triggered the watchpoint in
.Va si_addr .
.Pp
-Sychronous signals set
+Synchronous signals set
.Va si_trapno
to a machine-dependent trap number.
.Pp
diff --git a/share/man/man4/acpi_battery.4 b/share/man/man4/acpi_battery.4
index 3707cd125678..49fed625ea31 100644
--- a/share/man/man4/acpi_battery.4
+++ b/share/man/man4/acpi_battery.4
@@ -158,8 +158,8 @@ Typically this will decrease every charging cycle.
.It btech
Battery technology:
.Bl -tag -width indent
-.It 0x00000000 Primary cell Pq non-rechargable
-.It 0x00000001 Secondary cell Pq rechargable
+.It 0x00000000 Primary cell Pq non-rechargeable
+.It 0x00000001 Secondary cell Pq rechargeable
.El
.It Va dvol
Design voltage in mV,
diff --git a/share/man/man4/bce.4 b/share/man/man4/bce.4
index ab979f371b66..aab9eaebd505 100644
--- a/share/man/man4/bce.4
+++ b/share/man/man4/bce.4
@@ -240,7 +240,7 @@ Values from 0-256 are valid.
A value of 0 disables this status block update (default 6).
.It Va hw.bce.tx_ticks
Time in microsecond ticks to wait before a status block
-update is generated due to TX activitiy.
+update is generated due to TX activity.
Values from 0-100 are valid.
A value of 0 disables this status block update.
Cannot be set to 0 if hw.bce.tx_quick_cons_trip is also 0
diff --git a/share/man/man4/iwlwifi.4 b/share/man/man4/iwlwifi.4
index 4a251f239a55..05a0ee6ecacf 100644
--- a/share/man/man4/iwlwifi.4
+++ b/share/man/man4/iwlwifi.4
@@ -284,7 +284,7 @@ module parameters and are mapped automatically by
.Sy linuxkpi .
They were not adjusted so that they stay consistent with upstream
Linux, e.g., for documentation available and problem investigations.
-This left their names inconsistent between themselves and incosistent to
+This left their names inconsistent between themselves and inconsistent to
.Fx
style.
.Pp
diff --git a/share/man/man4/mac_do.4 b/share/man/man4/mac_do.4
index 39bfafd95474..d02932070e25 100644
--- a/share/man/man4/mac_do.4
+++ b/share/man/man4/mac_do.4
@@ -246,7 +246,7 @@ nor contradictory ones.
In practice, no two clauses may display the same ID except for group IDs but
only if, each time the same ID appears, it does so with a different flag, or no
flags only once.
-Additionally, the specified flags in multiple occurences must not be
+Additionally, the specified flags in multiple occurrences must not be
contradictory.
For example, the same group ID appearing with both
.Ql +
diff --git a/share/man/man4/p9fs.4 b/share/man/man4/p9fs.4
index 04f27abd2545..a49053d461d4 100644
--- a/share/man/man4/p9fs.4
+++ b/share/man/man4/p9fs.4
@@ -96,7 +96,7 @@ may not work correctly.
If
.Nm
is the root filesystem,
-it is recommented to use with
+it is recommended to use with
.Xr tmpfs 5
to ensure that temporary files created in
.Pa /tmp
diff --git a/share/man/man4/rights.4 b/share/man/man4/rights.4
index 2d44a1060006..6669f75e1674 100644
--- a/share/man/man4/rights.4
+++ b/share/man/man4/rights.4
@@ -276,7 +276,8 @@ Permit
and
.Xr openat 2
with
-.Dv O_FSYNC
+.Dv O_DSYNC ,
+.Dv O_FSYNC ,
or
.Dv O_SYNC
flag.
diff --git a/share/man/man7/stats.7 b/share/man/man7/stats.7
index 715db70e118b..0b57d525522c 100644
--- a/share/man/man7/stats.7
+++ b/share/man/man7/stats.7
@@ -24,7 +24,7 @@
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
.\" SUCH DAMAGE.
.\"
-.Dd April 22, 2021
+.Dd October 28, 2025
.Dt STATS 7
.Os
.Sh NAME
@@ -100,6 +100,7 @@ Report ZFS I/O statistics
.Xr stat 1 ,
.Xr systat 1 ,
.Xr intro 7 ,
+.Xr tuning 7 ,
.Xr ctlstat 8 ,
.Xr gstat 8 ,
.Xr ibstat 8 ,
diff --git a/share/man/man7/tuning.7 b/share/man/man7/tuning.7
index f04500d0f0dc..8da4b55b9d4f 100644
--- a/share/man/man7/tuning.7
+++ b/share/man/man7/tuning.7
@@ -22,7 +22,7 @@
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
.\" SUCH DAMAGE.
.\"
-.Dd November 17, 2023
+.Dd October 28, 2025
.Dt TUNING 7
.Os
.Sh NAME
@@ -702,6 +702,7 @@ over services you export from your box (web services, email).
.Xr firewall 7 ,
.Xr hier 7 ,
.Xr ports 7 ,
+.Xr stats 7 ,
.Xr boot 8 ,
.Xr bsdinstall 8 ,
.Xr ccdconfig 8 ,
diff --git a/share/man/man9/insmntque.9 b/share/man/man9/insmntque.9
index 869d8767632b..33ba697b10b9 100644
--- a/share/man/man9/insmntque.9
+++ b/share/man/man9/insmntque.9
@@ -24,7 +24,7 @@
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
.\" DAMAGE.
.\"
-.Dd January 29, 2022
+.Dd October 24, 2025
.Dt INSMNTQUE 9
.Os
.Sh NAME
@@ -56,7 +56,7 @@ The vnode must be exclusively locked.
.Pp
On failure,
.Fn insmntque
-resets vnode' operation vector to the vector of
+resets vnode's operations vector to the vector of
.Xr deadfs 9 ,
clears
.Va v_data ,
@@ -71,7 +71,7 @@ failure is needed, the
function may be used instead.
It does not do any cleanup following a failure, leaving all
the work to the caller.
-In particular, the operation vector
+In particular, the operations vector
.Va v_op
and
.Va v_data
diff --git a/share/misc/bsd-family-tree b/share/misc/bsd-family-tree
index 94455bbde628..d36c64259569 100644
--- a/share/misc/bsd-family-tree
+++ b/share/misc/bsd-family-tree
@@ -479,9 +479,9 @@ FreeBSD 5.2 | | | |
| | | | | DragonFly 6.4.1
| | | | | DragonFly 6.4.2
| FreeBSD | | | |
- | 14.3 | | | |
+ | 14.3 | | OpenBSD 7.8 |
| | | | |
-FreeBSD 15 -current | NetBSD -current OpenBSD -current DragonFly -current
+FreeBSD 16 -current | NetBSD -current OpenBSD -current DragonFly -current
| | | | |
v v v v v
@@ -926,6 +926,7 @@ OpenBSD 7.7 2025-04-28 [OBD]
DragonFly 6.4.1 2025-04-30 [DFB]
DragonFly 6.4.2 2025-05-09 [DFB]
FreeBSD 14.3 2025-06-10 [FBD]
+OpenBSD 7.8 2025-10-22 [OBD]
Bibliography
------------------------
@@ -981,6 +982,15 @@ URL: https://web.archive.org/web/20090427195917/http://ezine.daemonnews.org/2001
("what are the differences between FreeBSD, NetBSD, and OpenBSD?")
+End-of-Life (EOL)
+-----------------
+The FreeBSD family tree shows when a release was published.
+If you would like to know when the support ends, just look at
+https://www.freebsd.org/security/#sup and
+https://www.freebsd.org/security/unsupported
+For other operating systems, see https://endoflife.date
+
+
Acknowledgments
---------------
@@ -990,5 +1000,5 @@ original BSD announcements from Usenet or tapes.
Steven M. Schultz for providing 2.8BSD, 2.10BSD, 2.11BSD manual pages.
--
-Copyright (c) 1997-2024 Wolfram Schneider <wosch@FreeBSD.org>
+Copyright (c) 1997-2025 Wolfram Schneider <wosch@FreeBSD.org>
URL: https://cgit.freebsd.org/src/tree/share/misc/bsd-family-tree
diff --git a/share/mk/bsd.prog.mk b/share/mk/bsd.prog.mk
index fa15370a82c6..1c32a442aac9 100644
--- a/share/mk/bsd.prog.mk
+++ b/share/mk/bsd.prog.mk
@@ -49,9 +49,11 @@ CXXFLAGS+= -mretpoline
LDFLAGS+= -Wl,-zretpolineplt
.endif
.else
+.if !defined(_NO_INCLUDE_COMPILERMK)
.warning Retpoline requested but not supported by compiler or linker
.endif
.endif
+.endif
# LLD sensibly defaults to -znoexecstack, so do the same for BFD
LDFLAGS.bfd+= -Wl,-znoexecstack
@@ -65,16 +67,20 @@ CFLAGS+= -enable-trivial-auto-var-init-zero-knowing-it-will-be-removed-from-clan
CXXFLAGS+= -enable-trivial-auto-var-init-zero-knowing-it-will-be-removed-from-clang
.endif
.else
+.if !defined(_NO_INCLUDE_COMPILERMK)
.warning InitAll (zeros) requested but not supported by compiler
.endif
+.endif
.elif ${MK_INIT_ALL_PATTERN} == "yes"
.if ${COMPILER_FEATURES:Minit-all}
CFLAGS+= -ftrivial-auto-var-init=pattern
CXXFLAGS+= -ftrivial-auto-var-init=pattern
.else
+.if !defined(_NO_INCLUDE_COMPILERMK)
.warning InitAll (pattern) requested but not supported by compiler
.endif
.endif
+.endif
# bsd.sanitizer.mk is not installed, so don't require it (e.g. for ports).
.sinclude "bsd.sanitizer.mk"
diff --git a/sys/dev/e1000/e1000_osdep.h b/sys/dev/e1000/e1000_osdep.h
index 893979025f01..ba1c8a16fad1 100644
--- a/sys/dev/e1000/e1000_osdep.h
+++ b/sys/dev/e1000/e1000_osdep.h
@@ -152,6 +152,9 @@ struct e1000_osdep
{
bus_space_tag_t mem_bus_space_tag;
bus_space_handle_t mem_bus_space_handle;
+#ifdef INVARIANTS
+ bus_size_t mem_bus_space_size;
+#endif
bus_space_tag_t io_bus_space_tag;
bus_space_handle_t io_bus_space_handle;
bus_space_tag_t flash_bus_space_tag;
@@ -175,27 +178,44 @@ struct e1000_osdep
bus_space_write_4(((struct e1000_osdep *)(hw)->back)->mem_bus_space_tag, \
((struct e1000_osdep *)(hw)->back)->mem_bus_space_handle, offset, value)
+static __inline uint32_t
+e1000_rd32(struct e1000_osdep *osdep, uint32_t reg)
+{
+
+ KASSERT(reg < osdep->mem_bus_space_size,
+ ("e1000: register offset %#jx too large (max is %#jx)",
+ (uintmax_t)reg, (uintmax_t)osdep->mem_bus_space_size));
+
+ return (bus_space_read_4(osdep->mem_bus_space_tag,
+ osdep->mem_bus_space_handle, reg));
+}
+
+
+static __inline void
+e1000_wr32(struct e1000_osdep *osdep, uint32_t reg, uint32_t value)
+{
+
+ KASSERT(reg < osdep->mem_bus_space_size,
+ ("e1000: register offset %#jx too large (max is %#jx)",
+ (uintmax_t)reg, (uintmax_t)osdep->mem_bus_space_size));
+
+ bus_space_write_4(osdep->mem_bus_space_tag,
+ osdep->mem_bus_space_handle, reg, value);
+}
+
/* Register READ/WRITE macros */
-#define E1000_READ_REG(hw, reg) \
- bus_space_read_4(((struct e1000_osdep *)(hw)->back)->mem_bus_space_tag, \
- ((struct e1000_osdep *)(hw)->back)->mem_bus_space_handle, \
- E1000_REGISTER(hw, reg))
+#define E1000_READ_REG(hw, reg) \
+ e1000_rd32((hw)->back, E1000_REGISTER(hw, reg))
#define E1000_WRITE_REG(hw, reg, value) \
- bus_space_write_4(((struct e1000_osdep *)(hw)->back)->mem_bus_space_tag, \
- ((struct e1000_osdep *)(hw)->back)->mem_bus_space_handle, \
- E1000_REGISTER(hw, reg), value)
+ e1000_wr32((hw)->back, E1000_REGISTER(hw, reg), value)
#define E1000_READ_REG_ARRAY(hw, reg, index) \
- bus_space_read_4(((struct e1000_osdep *)(hw)->back)->mem_bus_space_tag, \
- ((struct e1000_osdep *)(hw)->back)->mem_bus_space_handle, \
- E1000_REGISTER(hw, reg) + ((index)<< 2))
+ e1000_rd32((hw)->back, E1000_REGISTER(hw, reg) + ((index) << 2))
#define E1000_WRITE_REG_ARRAY(hw, reg, index, value) \
- bus_space_write_4(((struct e1000_osdep *)(hw)->back)->mem_bus_space_tag, \
- ((struct e1000_osdep *)(hw)->back)->mem_bus_space_handle, \
- E1000_REGISTER(hw, reg) + ((index)<< 2), value)
+ e1000_wr32((hw)->back, E1000_REGISTER(hw, reg) + ((index) << 2), value)
#define E1000_READ_REG_ARRAY_DWORD E1000_READ_REG_ARRAY
#define E1000_WRITE_REG_ARRAY_DWORD E1000_WRITE_REG_ARRAY
diff --git a/sys/dev/e1000/if_em.c b/sys/dev/e1000/if_em.c
index f0ef6051fab1..9040949b36c7 100644
--- a/sys/dev/e1000/if_em.c
+++ b/sys/dev/e1000/if_em.c
@@ -1575,7 +1575,7 @@ em_if_init(if_ctx_t ctx)
E1000_WRITE_REG(&sc->hw, E1000_VET, ETHERTYPE_VLAN);
/* Clear bad data from Rx FIFOs */
- if (sc->hw.mac.type >= igb_mac_min)
+ if (sc->hw.mac.type >= igb_mac_min && !sc->vf_ifp)
e1000_rx_fifo_flush_base(&sc->hw);
/* Configure for OS presence */
@@ -1595,7 +1595,9 @@ em_if_init(if_ctx_t ctx)
/* Don't lose promiscuous settings */
em_if_set_promisc(ctx, if_getflags(ifp));
- e1000_clear_hw_cntrs_base_generic(&sc->hw);
+
+ if (sc->hw.mac.ops.clear_hw_cntrs != NULL)
+ sc->hw.mac.ops.clear_hw_cntrs(&sc->hw);
/* MSI-X configuration for 82574 */
if (sc->hw.mac.type == e1000_82574) {
@@ -2374,7 +2376,7 @@ em_if_stop(if_ctx_t ctx)
em_flush_desc_rings(sc);
e1000_reset_hw(&sc->hw);
- if (sc->hw.mac.type >= e1000_82544)
+ if (sc->hw.mac.type >= e1000_82544 && !sc->vf_ifp)
E1000_WRITE_REG(&sc->hw, E1000_WUFC, 0);
e1000_led_off(&sc->hw);
@@ -2433,6 +2435,9 @@ em_allocate_pci_resources(if_ctx_t ctx)
}
sc->osdep.mem_bus_space_tag = rman_get_bustag(sc->memory);
sc->osdep.mem_bus_space_handle = rman_get_bushandle(sc->memory);
+#ifdef INVARIANTS
+ sc->osdep.mem_bus_space_size = rman_get_size(sc->memory);
+#endif
sc->hw.hw_addr = (u8 *)&sc->osdep.mem_bus_space_handle;
/* Only older adapters use IO mapping */
@@ -3284,11 +3289,13 @@ em_reset(if_ctx_t ctx)
/* Issue a global reset */
e1000_reset_hw(hw);
- if (hw->mac.type >= igb_mac_min) {
- E1000_WRITE_REG(hw, E1000_WUC, 0);
- } else {
- E1000_WRITE_REG(hw, E1000_WUFC, 0);
- em_disable_aspm(sc);
+ if (!sc->vf_ifp) {
+ if (hw->mac.type >= igb_mac_min) {
+ E1000_WRITE_REG(hw, E1000_WUC, 0);
+ } else {
+ E1000_WRITE_REG(hw, E1000_WUFC, 0);
+ em_disable_aspm(sc);
+ }
}
if (sc->flags & IGB_MEDIA_RESET) {
e1000_setup_init_funcs(hw, true);
@@ -3838,7 +3845,7 @@ em_initialize_receive_unit(if_ctx_t ctx)
sc->rx_int_delay.value);
}
- if (hw->mac.type >= em_mac_min) {
+ if (hw->mac.type >= em_mac_min && !sc->vf_ifp) {
uint32_t rfctl;
/* Use extended rx descriptor formats */
rfctl = E1000_READ_REG(hw, E1000_RFCTL);
@@ -3858,33 +3865,38 @@ em_initialize_receive_unit(if_ctx_t ctx)
E1000_WRITE_REG(hw, E1000_RFCTL, rfctl);
}
- /* Set up L3 and L4 csum Rx descriptor offloads */
- rxcsum = E1000_READ_REG(hw, E1000_RXCSUM);
- if (if_getcapenable(ifp) & IFCAP_RXCSUM) {
- rxcsum |= E1000_RXCSUM_TUOFL | E1000_RXCSUM_IPOFL;
- if (hw->mac.type > e1000_82575)
- rxcsum |= E1000_RXCSUM_CRCOFL;
- else if (hw->mac.type < em_mac_min &&
- if_getcapenable(ifp) & IFCAP_HWCSUM_IPV6)
- rxcsum |= E1000_RXCSUM_IPV6OFL;
- } else {
- rxcsum &= ~(E1000_RXCSUM_IPOFL | E1000_RXCSUM_TUOFL);
- if (hw->mac.type > e1000_82575)
- rxcsum &= ~E1000_RXCSUM_CRCOFL;
- else if (hw->mac.type < em_mac_min)
- rxcsum &= ~E1000_RXCSUM_IPV6OFL;
- }
+ /*
+ * Set up L3 and L4 csum Rx descriptor offloads only on Physical
+ * Functions. Virtual Functions have no access to this register.
+ */
+ if (!sc->vf_ifp) {
+ rxcsum = E1000_READ_REG(hw, E1000_RXCSUM);
+ if (if_getcapenable(ifp) & IFCAP_RXCSUM) {
+ rxcsum |= E1000_RXCSUM_TUOFL | E1000_RXCSUM_IPOFL;
+ if (hw->mac.type > e1000_82575)
+ rxcsum |= E1000_RXCSUM_CRCOFL;
+ else if (hw->mac.type < em_mac_min &&
+ if_getcapenable(ifp) & IFCAP_HWCSUM_IPV6)
+ rxcsum |= E1000_RXCSUM_IPV6OFL;
+ } else {
+ rxcsum &= ~(E1000_RXCSUM_IPOFL | E1000_RXCSUM_TUOFL);
+ if (hw->mac.type > e1000_82575)
+ rxcsum &= ~E1000_RXCSUM_CRCOFL;
+ else if (hw->mac.type < em_mac_min)
+ rxcsum &= ~E1000_RXCSUM_IPV6OFL;
+ }
- if (sc->rx_num_queues > 1) {
- /* RSS hash needed in the Rx descriptor */
- rxcsum |= E1000_RXCSUM_PCSD;
+ if (sc->rx_num_queues > 1) {
+ /* RSS hash needed in the Rx descriptor */
+ rxcsum |= E1000_RXCSUM_PCSD;
- if (hw->mac.type >= igb_mac_min)
- igb_initialize_rss_mapping(sc);
- else
- em_initialize_rss_mapping(sc);
+ if (hw->mac.type >= igb_mac_min)
+ igb_initialize_rss_mapping(sc);
+ else
+ em_initialize_rss_mapping(sc);
+ }
+ E1000_WRITE_REG(hw, E1000_RXCSUM, rxcsum);
}
- E1000_WRITE_REG(hw, E1000_RXCSUM, rxcsum);
for (i = 0, que = sc->rx_queues; i < sc->rx_num_queues; i++, que++) {
struct rx_ring *rxr = &que->rxr;
@@ -4392,6 +4404,8 @@ em_get_wakeup(if_ctx_t ctx)
switch (sc->hw.mac.type) {
case e1000_82542:
case e1000_82543:
+ case e1000_vfadapt:
+ case e1000_vfadapt_i350:
break;
case e1000_82544:
e1000_read_nvm(&sc->hw,
@@ -4437,8 +4451,6 @@ em_get_wakeup(if_ctx_t ctx)
case e1000_i354:
case e1000_i210:
case e1000_i211:
- case e1000_vfadapt:
- case e1000_vfadapt_i350:
apme_mask = E1000_WUC_APME;
sc->has_amt = true;
eeprom_data = E1000_READ_REG(&sc->hw, E1000_WUC);
@@ -4494,7 +4506,6 @@ em_get_wakeup(if_ctx_t ctx)
global_quad_port_a = 0;
break;
}
- return;
}
diff --git a/sys/dev/ice/ice_drv_info.h b/sys/dev/ice/ice_drv_info.h
index 46965f4124bc..abb11bdb5fd9 100644
--- a/sys/dev/ice/ice_drv_info.h
+++ b/sys/dev/ice/ice_drv_info.h
@@ -238,6 +238,9 @@ static const pci_vendor_info_t ice_vendor_info_array[] = {
ICE_INTEL_VENDOR_ID, 0x0001, 0,
"Intel(R) Ethernet Network Adapter E835-XXV-2 for OCP 3.0"),
PVIDV_OEM(ICE_INTEL_VENDOR_ID, ICE_DEV_ID_E835CC_SFP,
+ ICE_INTEL_VENDOR_ID, 0x0002, 0,
+ "Intel(R) Ethernet Network Adapter E835-XXV-4"),
+ PVIDV_OEM(ICE_INTEL_VENDOR_ID, ICE_DEV_ID_E835CC_SFP,
ICE_INTEL_VENDOR_ID, 0x0003, 0,
"Intel(R) Ethernet Network Adapter E835-XXV-2"),
PVIDV_OEM(ICE_INTEL_VENDOR_ID, ICE_DEV_ID_E835CC_SFP,
diff --git a/sys/dev/ixl/if_ixl.c b/sys/dev/ixl/if_ixl.c
index 43c3af056b67..aa2e69ea0b5a 100644
--- a/sys/dev/ixl/if_ixl.c
+++ b/sys/dev/ixl/if_ixl.c
@@ -1480,17 +1480,33 @@ ixl_if_multi_set(if_ctx_t ctx)
struct ixl_pf *pf = iflib_get_softc(ctx);
struct ixl_vsi *vsi = &pf->vsi;
struct i40e_hw *hw = vsi->hw;
+ enum i40e_status_code status;
int mcnt;
+ if_t ifp = iflib_get_ifp(ctx);
IOCTL_DEBUGOUT("ixl_if_multi_set: begin");
/* Delete filters for removed multicast addresses */
ixl_del_multi(vsi, false);
- mcnt = min(if_llmaddr_count(iflib_get_ifp(ctx)), MAX_MULTICAST_ADDR);
+ mcnt = min(if_llmaddr_count(ifp), MAX_MULTICAST_ADDR);
if (__predict_false(mcnt == MAX_MULTICAST_ADDR)) {
- i40e_aq_set_vsi_multicast_promiscuous(hw,
+ /* Check if promisc mode is already enabled, if yes return */
+ if (vsi->flags & IXL_FLAGS_MC_PROMISC)
+ return;
+
+ status = i40e_aq_set_vsi_multicast_promiscuous(hw,
vsi->seid, TRUE, NULL);
+ if (status != I40E_SUCCESS)
+ if_printf(ifp, "Failed to enable multicast promiscuous "
+ "mode, status: %s\n", i40e_stat_str(hw, status));
+ else {
+ if_printf(ifp, "Enabled multicast promiscuous mode\n");
+
+ /* Set the flag to track promiscuous mode */
+ vsi->flags |= IXL_FLAGS_MC_PROMISC;
+ }
+ /* Delete all existing MC filters */
ixl_del_multi(vsi, true);
return;
}
@@ -1693,6 +1709,13 @@ ixl_if_promisc_set(if_ctx_t ctx, int flags)
return (err);
err = i40e_aq_set_vsi_multicast_promiscuous(hw,
vsi->seid, multi, NULL);
+
+ /* Update the multicast promiscuous flag based on the new state */
+ if (multi)
+ vsi->flags |= IXL_FLAGS_MC_PROMISC;
+ else
+ vsi->flags &= ~IXL_FLAGS_MC_PROMISC;
+
return (err);
}
diff --git a/sys/dev/ixl/ixl.h b/sys/dev/ixl/ixl.h
index f45354d29300..69925a131b35 100644
--- a/sys/dev/ixl/ixl.h
+++ b/sys/dev/ixl/ixl.h
@@ -202,6 +202,7 @@
#define IXL_FLAGS_KEEP_TSO6 (1 << 1)
#define IXL_FLAGS_USES_MSIX (1 << 2)
#define IXL_FLAGS_IS_VF (1 << 3)
+#define IXL_FLAGS_MC_PROMISC (1 << 4)
#define IXL_VSI_IS_PF(v) ((v->flags & IXL_FLAGS_IS_VF) == 0)
#define IXL_VSI_IS_VF(v) ((v->flags & IXL_FLAGS_IS_VF) != 0)
diff --git a/sys/dev/ixl/ixl_pf_main.c b/sys/dev/ixl/ixl_pf_main.c
index 4f384e7191af..99851af61cfe 100644
--- a/sys/dev/ixl/ixl_pf_main.c
+++ b/sys/dev/ixl/ixl_pf_main.c
@@ -592,24 +592,29 @@ ixl_add_maddr(void *arg, struct sockaddr_dl *sdl, u_int cnt)
* Routines for multicast and vlan filter management.
*
*********************************************************************/
+
+/**
+ * ixl_add_multi - Add multicast filters to the hardware
+ * @vsi: The VSI structure
+ *
+ * In case number of multicast filters in the IFP exceeds 127 entries,
+ * multicast promiscuous mode will be enabled and the filters will be removed
+ * from the hardware
+ */
void
ixl_add_multi(struct ixl_vsi *vsi)
{
if_t ifp = vsi->ifp;
- struct i40e_hw *hw = vsi->hw;
int mcnt = 0;
struct ixl_add_maddr_arg cb_arg;
IOCTL_DEBUGOUT("ixl_add_multi: begin");
- mcnt = if_llmaddr_count(ifp);
- if (__predict_false(mcnt >= MAX_MULTICAST_ADDR)) {
- i40e_aq_set_vsi_multicast_promiscuous(hw,
- vsi->seid, TRUE, NULL);
- /* delete all existing MC filters */
- ixl_del_multi(vsi, true);
- return;
- }
+ /*
+ * There is no need to check if the number of multicast addresses
+ * exceeds the MAX_MULTICAST_ADDR threshold and set promiscuous mode
+ * here, as all callers already handle this case.
+ */
cb_arg.vsi = vsi;
LIST_INIT(&cb_arg.to_add);
@@ -632,30 +637,103 @@ ixl_match_maddr(void *arg, struct sockaddr_dl *sdl, u_int cnt)
return (0);
}
+/**
+ * ixl_dis_multi_promisc - Disable multicast promiscuous mode
+ * @vsi: The VSI structure
+ * @vsi_mcnt: Number of multicast filters in the VSI
+ *
+ * Disable multicast promiscuous mode based on number of entries in the IFP
+ * and the VSI, then re-add multicast filters.
+ *
+ */
+static void
+ixl_dis_multi_promisc(struct ixl_vsi *vsi, int vsi_mcnt)
+{
+ struct ifnet *ifp = vsi->ifp;
+ struct i40e_hw *hw = vsi->hw;
+ int ifp_mcnt = 0;
+ enum i40e_status_code status;
+
+ /*
+ * Check if multicast promiscuous mode was actually enabled.
+ * If promiscuous mode was not enabled, don't attempt to disable it.
+ * Also, don't disable if IFF_PROMISC or IFF_ALLMULTI is set.
+ */
+ if (!(vsi->flags & IXL_FLAGS_MC_PROMISC) ||
+ (if_getflags(ifp) & (IFF_PROMISC | IFF_ALLMULTI)))
+ return;
+
+ ifp_mcnt = if_llmaddr_count(ifp);
+ /*
+ * Equal lists or empty ifp list mean the list has not been changed
+ * and in such case avoid disabling multicast promiscuous mode as it
+ * was not previously enabled. Case where multicast promiscuous mode has
+ * been enabled is when vsi_mcnt == 0 && ifp_mcnt > 0.
+ */
+ if (ifp_mcnt == vsi_mcnt || ifp_mcnt == 0 ||
+ ifp_mcnt >= MAX_MULTICAST_ADDR)
+ return;
+
+ status = i40e_aq_set_vsi_multicast_promiscuous(hw, vsi->seid,
+ FALSE, NULL);
+ if (status != I40E_SUCCESS) {
+ if_printf(ifp, "Failed to disable multicast promiscuous "
+ "mode, status: %s\n", i40e_stat_str(hw, status));
+
+ return;
+ }
+
+ /* Clear the flag since promiscuous mode is now disabled */
+ vsi->flags &= ~IXL_FLAGS_MC_PROMISC;
+ if_printf(ifp, "Disabled multicast promiscuous mode\n");
+
+ ixl_add_multi(vsi);
+}
+
+/**
+ * ixl_del_multi - Delete multicast filters from the hardware
+ * @vsi: The VSI structure
+ * @all: Bool to determine if all the multicast filters should be removed
+ *
+ * In case number of multicast filters in the IFP drops to 127 entries,
+ * multicast promiscuous mode will be disabled and the filters will be reapplied
+ * to the hardware.
+ */
void
ixl_del_multi(struct ixl_vsi *vsi, bool all)
{
- struct ixl_ftl_head to_del;
+ int to_del_cnt = 0, vsi_mcnt = 0;
if_t ifp = vsi->ifp;
struct ixl_mac_filter *f, *fn;
- int mcnt = 0;
+ struct ixl_ftl_head to_del;
IOCTL_DEBUGOUT("ixl_del_multi: begin");
LIST_INIT(&to_del);
/* Search for removed multicast addresses */
LIST_FOREACH_SAFE(f, &vsi->ftl, ftle, fn) {
- if ((f->flags & IXL_FILTER_MC) == 0 ||
- (!all && (if_foreach_llmaddr(ifp, ixl_match_maddr, f) == 0)))
+ if ((f->flags & IXL_FILTER_MC) == 0)
+ continue;
+
+ /* Count all the multicast filters in the VSI for comparison */
+ vsi_mcnt++;
+
+ if (!all && if_foreach_llmaddr(ifp, ixl_match_maddr, f) != 0)
continue;
LIST_REMOVE(f, ftle);
LIST_INSERT_HEAD(&to_del, f, ftle);
- mcnt++;
+ to_del_cnt++;
}
- if (mcnt > 0)
- ixl_del_hw_filters(vsi, &to_del, mcnt);
+ if (to_del_cnt > 0) {
+ ixl_del_hw_filters(vsi, &to_del, to_del_cnt);
+ return;
+ }
+
+ ixl_dis_multi_promisc(vsi, vsi_mcnt);
+
+ IOCTL_DEBUGOUT("ixl_del_multi: end");
}
void
diff --git a/sys/fs/nfsclient/nfs_clrpcops.c b/sys/fs/nfsclient/nfs_clrpcops.c
index c5483623a9a5..387c5465618a 100644
--- a/sys/fs/nfsclient/nfs_clrpcops.c
+++ b/sys/fs/nfsclient/nfs_clrpcops.c
@@ -5157,7 +5157,7 @@ nfsrpc_getdirpath(struct nfsmount *nmp, u_char *dirpath, struct ucred *cred,
struct nfsrv_descript nfsd;
struct nfsrv_descript *nd = &nfsd;
u_char *cp, *cp2, *fhp;
- int error, cnt, len, setnil;
+ int error, cnt, i, len, setnil;
u_int32_t *opcntp;
nfscl_reqstart(nd, NFSPROC_PUTROOTFH, nmp, NULL, 0, &opcntp, NULL, 0,
@@ -5198,8 +5198,12 @@ nfsrpc_getdirpath(struct nfsmount *nmp, u_char *dirpath, struct ucred *cred,
if (error)
return (error);
if (nd->nd_repstat == 0) {
- NFSM_DISSECT(tl, u_int32_t *, (3 + 2 * cnt) * NFSX_UNSIGNED);
- tl += (2 + 2 * cnt);
+ NFSM_DISSECT(tl, uint32_t *, 3 * NFSX_UNSIGNED);
+ tl += 2;
+ for (i = 0; i < cnt; i++) {
+ NFSM_DISSECT(tl, uint32_t *, 2 * NFSX_UNSIGNED);
+ tl++;
+ }
if ((len = fxdr_unsigned(int, *tl)) <= 0 ||
len > NFSX_FHMAX) {
nd->nd_repstat = NFSERR_BADXDR;
diff --git a/sys/geom/zero/g_zero.c b/sys/geom/zero/g_zero.c
index 66cc884fab56..be31cc794cb5 100644
--- a/sys/geom/zero/g_zero.c
+++ b/sys/geom/zero/g_zero.c
@@ -47,11 +47,11 @@ static SYSCTL_NODE(_kern_geom, OID_AUTO, zero, CTLFLAG_RW | CTLFLAG_MPSAFE, 0,
"GEOM_ZERO stuff");
static int g_zero_clear = 1;
SYSCTL_PROC(_kern_geom_zero, OID_AUTO, clear,
- CTLTYPE_INT | CTLFLAG_RW | CTLFLAG_MPSAFE, &g_zero_clear, 0,
+ CTLTYPE_INT | CTLFLAG_RWTUN | CTLFLAG_MPSAFE, &g_zero_clear, 0,
g_zero_clear_sysctl, "I",
"Clear read data buffer");
static int g_zero_byte = 0;
-SYSCTL_INT(_kern_geom_zero, OID_AUTO, byte, CTLFLAG_RW, &g_zero_byte, 0,
+SYSCTL_INT(_kern_geom_zero, OID_AUTO, byte, CTLFLAG_RWTUN, &g_zero_byte, 0,
"Byte (octet) value to clear the buffers with");
static struct g_provider *gpp;
diff --git a/sys/kern/vfs_syscalls.c b/sys/kern/vfs_syscalls.c
index 9c5c5b9dfa80..99f9e129f4cd 100644
--- a/sys/kern/vfs_syscalls.c
+++ b/sys/kern/vfs_syscalls.c
@@ -1074,7 +1074,7 @@ flags_to_rights(int flags, cap_rights_t *rightsp)
if (flags & O_TRUNC)
cap_rights_set_one(rightsp, CAP_FTRUNCATE);
- if (flags & (O_SYNC | O_FSYNC))
+ if (flags & (O_SYNC | O_FSYNC | O_DSYNC))
cap_rights_set_one(rightsp, CAP_FSYNC);
if (flags & (O_EXLOCK | O_SHLOCK))
diff --git a/sys/netinet/in_proto.c b/sys/netinet/in_proto.c
index e534fdd77635..129dc1cfe892 100644
--- a/sys/netinet/in_proto.c
+++ b/sys/netinet/in_proto.c
@@ -110,6 +110,8 @@ SYSCTL_NODE(_net_inet, IPPROTO_ICMP, icmp, CTLFLAG_RW | CTLFLAG_MPSAFE, 0,
"ICMP");
SYSCTL_NODE(_net_inet, IPPROTO_UDP, udp, CTLFLAG_RW | CTLFLAG_MPSAFE, 0,
"UDP");
+SYSCTL_NODE(_net_inet, IPPROTO_UDPLITE, udplite, CTLFLAG_RW | CTLFLAG_MPSAFE, 0,
+ "UDP-Lite");
SYSCTL_NODE(_net_inet, IPPROTO_TCP, tcp, CTLFLAG_RW | CTLFLAG_MPSAFE, 0,
"TCP");
#if defined(SCTP) || defined(SCTP_SUPPORT)
diff --git a/sys/netinet/tcp_subr.c b/sys/netinet/tcp_subr.c
index 6829d2a743f2..81b378f496c9 100644
--- a/sys/netinet/tcp_subr.c
+++ b/sys/netinet/tcp_subr.c
@@ -654,7 +654,7 @@ tcp_recv_udp_tunneled_packet(struct mbuf *m, int off, struct inpcb *inp,
}
}
m->m_pkthdr.tcp_tun_port = port = uh->uh_sport;
- bcopy(th, uh, m->m_len - off);
+ bcopy(th, uh, m->m_len - off - sizeof(struct udphdr));
m->m_len -= sizeof(struct udphdr);
m->m_pkthdr.len -= sizeof(struct udphdr);
/*
diff --git a/sys/netinet/tcp_syncache.c b/sys/netinet/tcp_syncache.c
index 077c3a5f6ef3..713f6a35ad45 100644
--- a/sys/netinet/tcp_syncache.c
+++ b/sys/netinet/tcp_syncache.c
@@ -1175,7 +1175,7 @@ syncache_expand(struct in_conninfo *inc, struct tcpopt *to, struct tcphdr *th,
/*
* If listening socket requested TCP digests, check that
* received ACK has signature and it is correct.
- * If not, drop the ACK and leave sc entry in th cache,
+ * If not, drop the ACK and leave sc entry in the cache,
* because SYN was received with correct signature.
*/
if (sc->sc_flags & SCF_SIGNATURE) {
@@ -1387,6 +1387,7 @@ syncache_add(struct in_conninfo *inc, struct tcpopt *to, struct tcphdr *th,
struct tcpcb *tp;
struct socket *rv = NULL;
struct syncache *sc = NULL;
+ struct ucred *cred;
struct syncache_head *sch;
struct mbuf *ipopts = NULL;
u_int ltflags;
@@ -1415,6 +1416,7 @@ syncache_add(struct in_conninfo *inc, struct tcpopt *to, struct tcphdr *th,
*/
KASSERT(SOLISTENING(so), ("%s: %p not listening", __func__, so));
tp = sototcpcb(so);
+ cred = V_tcp_syncache.see_other ? NULL : crhold(so->so_cred);
#ifdef INET6
if (inc->inc_flags & INC_ISIPV6) {
@@ -1643,16 +1645,16 @@ syncache_add(struct in_conninfo *inc, struct tcpopt *to, struct tcphdr *th,
/*
* sc_cred is only used in syncache_pcblist() to list TCP endpoints in
* TCPS_SYN_RECEIVED state when V_tcp_syncache.see_other is false.
- * Therefore, store the credentials and take a reference count only
- * when needed:
+ * Therefore, store the credentials only when needed:
* - sc is allocated from the zone and not using the on stack instance.
* - the sysctl variable net.inet.tcp.syncache.see_other is false.
* The reference count is decremented when a zone allocated sc is
* freed in syncache_free().
*/
- if (sc != &scs && !V_tcp_syncache.see_other)
- sc->sc_cred = crhold(so->so_cred);
- else
+ if (sc != &scs && !V_tcp_syncache.see_other) {
+ sc->sc_cred = cred;
+ cred = NULL;
+ } else
sc->sc_cred = NULL;
sc->sc_port = port;
sc->sc_ipopts = ipopts;
@@ -1790,6 +1792,8 @@ donenoprobe:
tcp_fastopen_decrement_counter(tfo_pending);
tfo_expanded:
+ if (cred != NULL)
+ crfree(cred);
if (sc == NULL || sc == &scs) {
#ifdef MAC
mac_syncache_destroy(&maclabel);
diff --git a/sys/netinet/tcp_timer.c b/sys/netinet/tcp_timer.c
index 65a9fbc84ff7..1c687e94bb4a 100644
--- a/sys/netinet/tcp_timer.c
+++ b/sys/netinet/tcp_timer.c
@@ -515,9 +515,12 @@ tcp_timer_persist(struct tcpcb *tp)
if (progdrop || (tp->t_rxtshift >= V_tcp_retries &&
(ticks - tp->t_rcvtime >= tcp_maxpersistidle ||
ticks - tp->t_rcvtime >= TCP_REXMTVAL(tp) * tcp_totbackoff))) {
- if (!progdrop)
+ if (progdrop) {
+ tcp_log_end_status(tp, TCP_EI_STATUS_PROGRESS);
+ } else {
TCPSTAT_INC(tcps_persistdrop);
- tcp_log_end_status(tp, TCP_EI_STATUS_PERSIST_MAX);
+ tcp_log_end_status(tp, TCP_EI_STATUS_PERSIST_MAX);
+ }
goto dropit;
}
/*
diff --git a/sys/netinet/udp_usrreq.c b/sys/netinet/udp_usrreq.c
index 88df8f8d38fc..a1000dadf583 100644
--- a/sys/netinet/udp_usrreq.c
+++ b/sys/netinet/udp_usrreq.c
@@ -852,6 +852,11 @@ SYSCTL_PROC(_net_inet_udp, UDPCTL_PCBLIST, pcblist,
udp_pcblist, "S,xinpcb",
"List of active UDP sockets");
+SYSCTL_PROC(_net_inet_udplite, OID_AUTO, pcblist,
+ CTLTYPE_OPAQUE | CTLFLAG_RD | CTLFLAG_MPSAFE, NULL, IPPROTO_UDPLITE,
+ udp_pcblist, "S,xinpcb",
+ "List of active UDP-Lite sockets");
+
#ifdef INET
static int
udp_getcred(SYSCTL_HANDLER_ARGS)
@@ -1141,7 +1146,19 @@ udp_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr,
else
INP_RLOCK(inp);
NET_EPOCH_ENTER(et);
+#ifdef INET6
+ if ((flags & PRUS_IPV6) != 0) {
+ if ((inp->in6p_outputopts != NULL) &&
+ (inp->in6p_outputopts->ip6po_tclass != -1))
+ tos = (u_char)inp->in6p_outputopts->ip6po_tclass;
+ else
+ tos = 0;
+ } else {
+ tos = inp->inp_ip_tos;
+ }
+#else
tos = inp->inp_ip_tos;
+#endif
if (control != NULL) {
/*
* XXX: Currently, we assume all the optional information is
@@ -1165,6 +1182,23 @@ udp_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr,
error = udp_v4mapped_pktinfo(cm, &src, inp, flags);
if (error != 0)
break;
+ if (((flags & PRUS_IPV6) != 0) &&
+ (cm->cmsg_level == IPPROTO_IPV6) &&
+ (cm->cmsg_type == IPV6_TCLASS)) {
+ int tclass;
+
+ if (cm->cmsg_len != CMSG_LEN(sizeof(int))) {
+ error = EINVAL;
+ break;
+ }
+ tclass = *(int *)CMSG_DATA(cm);
+ if (tclass < -1 || tclass > 255) {
+ error = EINVAL;
+ break;
+ }
+ if (tclass != -1)
+ tos = (u_char)tclass;
+ }
#endif
if (cm->cmsg_level != IPPROTO_IP)
continue;
diff --git a/sys/netinet/udp_var.h b/sys/netinet/udp_var.h
index 51272e7c9349..569b7b8d5240 100644
--- a/sys/netinet/udp_var.h
+++ b/sys/netinet/udp_var.h
@@ -141,6 +141,7 @@ void kmod_udpstat_inc(int statnum);
kmod_udpstat_inc(offsetof(struct udpstat, name) / sizeof(uint64_t))
SYSCTL_DECL(_net_inet_udp);
+SYSCTL_DECL(_net_inet_udplite);
VNET_DECLARE(struct inpcbinfo, udbinfo);
VNET_DECLARE(struct inpcbinfo, ulitecbinfo);
diff --git a/sys/netpfil/ipfw/pmod/tcpmod.c b/sys/netpfil/ipfw/pmod/tcpmod.c
index d7400f4fd5ed..138fefe22a98 100644
--- a/sys/netpfil/ipfw/pmod/tcpmod.c
+++ b/sys/netpfil/ipfw/pmod/tcpmod.c
@@ -58,7 +58,8 @@ VNET_DEFINE_STATIC(uint16_t, tcpmod_setmss_eid) = 0;
#define V_tcpmod_setmss_eid VNET(tcpmod_setmss_eid)
static int
-tcpmod_setmss(struct mbuf **mp, struct tcphdr *tcp, int tlen, uint16_t mss)
+tcpmod_setmss(struct mbuf **mp, struct tcphdr *tcp, int tlen, uint16_t mss,
+ int *done)
{
struct mbuf *m;
u_char *cp;
@@ -73,8 +74,10 @@ tcpmod_setmss(struct mbuf **mp, struct tcphdr *tcp, int tlen, uint16_t mss)
* TCP header with options.
*/
*mp = m = m_pullup(m, m->m_pkthdr.len);
- if (m == NULL)
+ if (m == NULL) {
+ *done = 1;
return (ret);
+ }
}
/* Parse TCP options. */
for (tlen -= sizeof(struct tcphdr), cp = (u_char *)(tcp + 1);
@@ -115,7 +118,7 @@ tcpmod_setmss(struct mbuf **mp, struct tcphdr *tcp, int tlen, uint16_t mss)
#ifdef INET6
static int
-tcpmod_ipv6_setmss(struct mbuf **mp, uint16_t mss)
+tcpmod_ipv6_setmss(struct mbuf **mp, uint16_t mss, int *done)
{
struct ip6_hdr *ip6;
struct ip6_hbh *hbh;
@@ -143,13 +146,13 @@ tcpmod_ipv6_setmss(struct mbuf **mp, uint16_t mss)
/* We must have TCP options and enough data in a packet. */
if (hlen <= sizeof(struct tcphdr) || hlen > plen)
return (IP_FW_DENY);
- return (tcpmod_setmss(mp, tcp, hlen, mss));
+ return (tcpmod_setmss(mp, tcp, hlen, mss, done));
}
#endif /* INET6 */
#ifdef INET
static int
-tcpmod_ipv4_setmss(struct mbuf **mp, uint16_t mss)
+tcpmod_ipv4_setmss(struct mbuf **mp, uint16_t mss, int *done)
{
struct tcphdr *tcp;
struct ip *ip;
@@ -163,7 +166,7 @@ tcpmod_ipv4_setmss(struct mbuf **mp, uint16_t mss)
/* We must have TCP options and enough data in a packet. */
if (hlen <= sizeof(struct tcphdr) || hlen > plen)
return (IP_FW_DENY);
- return (tcpmod_setmss(mp, tcp, hlen, mss));
+ return (tcpmod_setmss(mp, tcp, hlen, mss, done));
}
#endif /* INET */
@@ -207,19 +210,23 @@ ipfw_tcpmod(struct ip_fw_chain *chain, struct ip_fw_args *args,
switch (args->f_id.addr_type) {
#ifdef INET
case 4:
- ret = tcpmod_ipv4_setmss(&args->m, htons(icmd->arg1));
+ ret = tcpmod_ipv4_setmss(&args->m, htons(icmd->arg1),
+ done);
break;
#endif
#ifdef INET6
case 6:
- ret = tcpmod_ipv6_setmss(&args->m, htons(icmd->arg1));
+ ret = tcpmod_ipv6_setmss(&args->m, htons(icmd->arg1),
+ done);
break;
#endif
}
/*
* We return zero in both @ret and @done on success, and ipfw_chk()
* will update rule counters. Otherwise a packet will not be matched
- * by rule.
+ * by rule. We passed @done around above in case we hit a fatal error
+ * somewhere, we'll return non-zero but signal that rule processing
+ * cannot succeed.
*/
return (ret);
}
diff --git a/sys/netpfil/pf/if_pfsync.c b/sys/netpfil/pf/if_pfsync.c
index 8c080b472653..2a5cb0612d36 100644
--- a/sys/netpfil/pf/if_pfsync.c
+++ b/sys/netpfil/pf/if_pfsync.c
@@ -530,6 +530,9 @@ pfsync_state_import(union pfsync_state_union *sp, int flags, int msg_version)
PF_RULES_RASSERT();
+ if (strnlen(sp->pfs_1301.ifname, IFNAMSIZ) == IFNAMSIZ)
+ return (EINVAL);
+
if (sp->pfs_1301.creatorid == 0) {
if (V_pf_status.debug >= PF_DEBUG_MISC)
printf("%s: invalid creator id: %08x\n", __func__,
diff --git a/sys/netpfil/pf/pf_ioctl.c b/sys/netpfil/pf/pf_ioctl.c
index d95f36d06ee3..cf53ea638095 100644
--- a/sys/netpfil/pf/pf_ioctl.c
+++ b/sys/netpfil/pf/pf_ioctl.c
@@ -4645,6 +4645,17 @@ DIOCCHANGEADDR_error:
error = ENODEV;
break;
}
+ if (strnlen(io->pfrio_table.pfrt_anchor, MAXPATHLEN)
+ == MAXPATHLEN) {
+ error = EINVAL;
+ goto fail;
+ }
+ if (strnlen(io->pfrio_table.pfrt_name, PF_TABLE_NAME_SIZE)
+ == PF_TABLE_NAME_SIZE) {
+ error = EINVAL;
+ goto fail;
+ }
+
PF_RULES_WLOCK();
error = pfr_clr_tables(&io->pfrio_table, &io->pfrio_ndel,
io->pfrio_flags | PFR_FLAG_USERIOCTL);
diff --git a/sys/x86/x86/local_apic.c b/sys/x86/x86/local_apic.c
index 6a913883cc5c..bf05855439bc 100644
--- a/sys/x86/x86/local_apic.c
+++ b/sys/x86/x86/local_apic.c
@@ -371,9 +371,12 @@ lvt_mode_impl(struct lapic *la, struct lvt *lvt, u_int pin, uint32_t value)
case APIC_LVT_DM_SMI:
case APIC_LVT_DM_INIT:
case APIC_LVT_DM_EXTINT:
- if (!lvt->lvt_edgetrigger && bootverbose) {
- printf("lapic%u: Forcing LINT%u to edge trigger\n",
- la->la_id, pin);
+ if (!lvt->lvt_edgetrigger) {
+ if (bootverbose) {
+ printf(
+ "lapic%u: Forcing LINT%u to edge trigger\n",
+ la->la_id, pin);
+ }
value &= ~APIC_LVT_TM;
}
/* Use a vector of 0. */
diff --git a/tests/sys/netpfil/pf/ioctl/validation.c b/tests/sys/netpfil/pf/ioctl/validation.c
index 1ce8999dcb91..651e6837acd7 100644
--- a/tests/sys/netpfil/pf/ioctl/validation.c
+++ b/tests/sys/netpfil/pf/ioctl/validation.c
@@ -32,6 +32,7 @@
#include <net/if.h>
#include <net/pfvar.h>
+#include <errno.h>
#include <fcntl.h>
#include <stdio.h>
@@ -192,6 +193,38 @@ ATF_TC_CLEANUP(gettables, tc)
COMMON_CLEANUP();
}
+ATF_TC_WITH_CLEANUP(clrtables);
+ATF_TC_HEAD(clrtables, tc)
+{
+ atf_tc_set_md_var(tc, "require.user", "root");
+ atf_tc_set_md_var(tc, "require.kmods", "pf");
+}
+
+ATF_TC_BODY(clrtables, tc)
+{
+ struct pfioc_table io;
+ struct pfr_table tbl;
+ int flags;
+
+ COMMON_HEAD();
+
+ flags = 0;
+
+ memset(&io, '/', sizeof(io));
+ io.pfrio_flags = flags;
+ io.pfrio_buffer = &tbl;
+ io.pfrio_esize = 0;
+ io.pfrio_size = 1;
+
+ if (ioctl(dev, DIOCRCLRTABLES, &io) == 0)
+ atf_tc_fail("Request with unterminated anchor name succeeded");
+}
+
+ATF_TC_CLEANUP(clrtables, tc)
+{
+ COMMON_CLEANUP();
+}
+
ATF_TC_WITH_CLEANUP(gettstats);
ATF_TC_HEAD(gettstats, tc)
{
@@ -894,11 +927,36 @@ ATF_TC_CLEANUP(rpool_mtx2, tc)
}
+ATF_TC_WITH_CLEANUP(addstate);
+ATF_TC_HEAD(addstate, tc)
+{
+ atf_tc_set_md_var(tc, "require.user", "root");
+ atf_tc_set_md_var(tc, "require.kmods", "pfsync");
+}
+
+ATF_TC_BODY(addstate, tc)
+{
+ struct pfioc_state st;
+
+ COMMON_HEAD();
+
+ memset(&st, 'a', sizeof(st));
+ st.state.timeout = PFTM_TCP_FIRST_PACKET;
+
+ ATF_CHECK_ERRNO(EINVAL, ioctl(dev, DIOCADDSTATE, &st) == -1);
+}
+
+ATF_TC_CLEANUP(addstate, tc)
+{
+ COMMON_CLEANUP();
+}
+
ATF_TP_ADD_TCS(tp)
{
ATF_TP_ADD_TC(tp, addtables);
ATF_TP_ADD_TC(tp, deltables);
ATF_TP_ADD_TC(tp, gettables);
+ ATF_TP_ADD_TC(tp, clrtables);
ATF_TP_ADD_TC(tp, getastats);
ATF_TP_ADD_TC(tp, gettstats);
ATF_TP_ADD_TC(tp, clrtstats);
@@ -918,6 +976,7 @@ ATF_TP_ADD_TCS(tp)
ATF_TP_ADD_TC(tp, tag);
ATF_TP_ADD_TC(tp, rpool_mtx);
ATF_TP_ADD_TC(tp, rpool_mtx2);
+ ATF_TP_ADD_TC(tp, addstate);
return (atf_no_error());
}
diff --git a/usr.bin/bsdcat/Makefile b/usr.bin/bsdcat/Makefile
index 8e730e634ea6..0377a4c48f5f 100644
--- a/usr.bin/bsdcat/Makefile
+++ b/usr.bin/bsdcat/Makefile
@@ -12,7 +12,7 @@ BSDCAT_VERSION_STRING!= sed -n '/define.*ARCHIVE_VERSION_ONLY_STRING/{s,[^0-9.],
SRCS= bsdcat.c cmdline.c
.PATH: ${_LIBARCHIVEDIR}/libarchive_fe
-SRCS+= err.c
+SRCS+= lafe_err.c
CFLAGS+= -DBSDCAT_VERSION_STRING=\"${BSDCAT_VERSION_STRING}\"
CFLAGS+= -DPLATFORM_CONFIG_H=\"${_LIBARCHIVECONFDIR}/config_freebsd.h\"
diff --git a/usr.bin/cpio/Makefile b/usr.bin/cpio/Makefile
index b52c9645ebb5..a52a12ea361b 100644
--- a/usr.bin/cpio/Makefile
+++ b/usr.bin/cpio/Makefile
@@ -12,7 +12,7 @@ BSDCPIO_VERSION_STRING!= sed -n '/define.*ARCHIVE_VERSION_ONLY_STRING/{s,[^0-9.]
SRCS= cpio.c cmdline.c
.PATH: ${_LIBARCHIVEDIR}/libarchive_fe
-SRCS+= err.c line_reader.c passphrase.c
+SRCS+= lafe_err.c line_reader.c passphrase.c
CFLAGS+= -DBSDCPIO_VERSION_STRING=\"${BSDCPIO_VERSION_STRING}\"
CFLAGS+= -DPLATFORM_CONFIG_H=\"${_LIBARCHIVECONFDIR}/config_freebsd.h\"
diff --git a/usr.bin/cpio/tests/Makefile b/usr.bin/cpio/tests/Makefile
index d99b1c37e226..e06f7fc34de3 100644
--- a/usr.bin/cpio/tests/Makefile
+++ b/usr.bin/cpio/tests/Makefile
@@ -27,7 +27,7 @@ CFLAGS.test_utils.c+= -Wno-cast-align
CPIO_SRCS= cmdline.c
.PATH: ${_LIBARCHIVEDIR}/libarchive_fe
-CPIO_SRCS+= err.c
+CPIO_SRCS+= lafe_err.c
.PATH: ${_LIBARCHIVEDIR}/cpio/test
TESTS_SRCS= \
diff --git a/usr.bin/netstat/inet.c b/usr.bin/netstat/inet.c
index 363224d5f913..898158ce288a 100644
--- a/usr.bin/netstat/inet.c
+++ b/usr.bin/netstat/inet.c
@@ -90,7 +90,7 @@ static void inetprint(const char *, struct in_addr *, int, const char *, int,
const int);
#endif
#ifdef INET6
-static int udp_done, tcp_done, sdp_done;
+static int udp_done, udplite_done, tcp_done, sdp_done;
#endif /* INET6 */
static int
@@ -107,6 +107,9 @@ pcblist_sysctl(int proto, const char *name, char **bufp)
case IPPROTO_UDP:
mibvar = "net.inet.udp.pcblist";
break;
+ case IPPROTO_UDPLITE:
+ mibvar = "net.inet.udplite.pcblist";
+ break;
default:
mibvar = "net.inet.raw.pcblist";
break;
@@ -229,11 +232,18 @@ protopr(u_long off, const char *name, int af1, int proto)
udp_done = 1;
#endif
break;
+ case IPPROTO_UDPLITE:
+#ifdef INET6
+ if (udplite_done != 0)
+ return;
+ else
+ udplite_done = 1;
+#endif
+ break;
}
if (!pcblist_sysctl(proto, name, &buf))
return;
-
if (istcp && (cflag || Cflag)) {
fnamelen = strlen("Stack");
cnamelen = strlen("CC");
@@ -325,18 +335,18 @@ protopr(u_long off, const char *name, int af1, int proto)
"Proto", "Listen", "Local Address");
else if (Tflag)
xo_emit((Aflag && !Wflag) ?
- "{T:/%-5.5s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-18.18s} {T:/%s}" :
+ "{T:/%-9.9s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-18.18s} {T:/%s}" :
((!Wflag || af1 == AF_INET) ?
- "{T:/%-5.5s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-22.22s} {T:/%s}" :
- "{T:/%-5.5s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-45.45s} {T:/%s}"),
+ "{T:/%-9.9s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-22.22s} {T:/%s}" :
+ "{T:/%-9.9s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-45.45s} {T:/%s}"),
"Proto", "Rexmit", "OOORcv", "0-win",
"Local Address", "Foreign Address");
else {
xo_emit((Aflag && !Wflag) ?
- "{T:/%-5.5s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-18.18s} {T:/%-18.18s}" :
+ "{T:/%-9.9s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-18.18s} {T:/%-18.18s}" :
((!Wflag || af1 == AF_INET) ?
- "{T:/%-5.5s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-22.22s} {T:/%-22.22s}" :
- "{T:/%-5.5s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-45.45s} {T:/%-45.45s}"),
+ "{T:/%-9.9s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-22.22s} {T:/%-22.22s}" :
+ "{T:/%-9.9s} {T:/%-6.6s} {T:/%-6.6s} {T:/%-45.45s} {T:/%-45.45s}"),
"Proto", "Recv-Q", "Send-Q",
"Local Address", "Foreign Address");
if (!xflag && !Rflag)
@@ -389,9 +399,14 @@ protopr(u_long off, const char *name, int af1, int proto)
vchar = ((inp->inp_vflag & INP_IPV4) != 0) ?
"4" : "";
if (istcp && (tp->t_flags & TF_TOE) != 0)
- xo_emit("{:protocol/%-3.3s%-2.2s/%s%s} ", "toe", vchar);
- else
- xo_emit("{:protocol/%-3.3s%-2.2s/%s%s} ", name, vchar);
+ xo_emit("{:protocol/%-3.3s%-6.6s/%s%s} ", "toe", vchar);
+ else {
+ int len;
+
+ len = max (2, 9 - strlen(name));
+ xo_emit("{:protocol/%.7s%-*.*s/%s%s} ", name, len, len,
+ vchar);
+ }
if (Lflag) {
char buf1[33];
diff --git a/usr.bin/netstat/main.c b/usr.bin/netstat/main.c
index 481284cb88a6..a60d951c8d39 100644
--- a/usr.bin/netstat/main.c
+++ b/usr.bin/netstat/main.c
@@ -96,6 +96,8 @@ static struct protox {
tcp_stats, NULL, "tcp", 1, IPPROTO_TCP },
{ -1 , N_UDPSTAT, 1, protopr,
udp_stats, NULL, "udp", 1, IPPROTO_UDP },
+ { -1, -1, 1, protopr,
+ NULL, NULL, "udplite", 1, IPPROTO_UDPLITE },
#ifdef SCTP
{ -1, N_SCTPSTAT, 1, sctp_protopr,
sctp_stats, NULL, "sctp", 1, IPPROTO_SCTP },
@@ -142,6 +144,8 @@ static struct protox ip6protox[] = {
tcp_stats, NULL, "tcp", 1, IPPROTO_TCP },
{ -1 , N_UDPSTAT, 1, protopr,
udp_stats, NULL, "udp", 1, IPPROTO_UDP },
+ { -1, -1, 1, protopr,
+ NULL, NULL, "udplite", 1, IPPROTO_UDPLITE },
{ -1 , N_IP6STAT, 1, protopr,
ip6_stats, ip6_ifstats, "ip6", 1, IPPROTO_RAW },
{ -1 , N_ICMP6STAT, 1, protopr,
diff --git a/usr.bin/sockstat/sockstat.1 b/usr.bin/sockstat/sockstat.1
index eba4b1c4aed5..abd83f049703 100644
--- a/usr.bin/sockstat/sockstat.1
+++ b/usr.bin/sockstat/sockstat.1
@@ -25,7 +25,7 @@
.\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
.\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
.\"
-.Dd October 7, 2025
+.Dd October 9, 2025
.Dt SOCKSTAT 1
.Os
.Sh NAME
@@ -194,6 +194,7 @@ is specified (only for SCTP or TCP).
The path state if
.Fl s
is specified (only for SCTP).
+This column is only shown when there is at least one path state to show.
.It Li CONN STATE
The connection state if
.Fl s
diff --git a/usr.bin/sockstat/sockstat.c b/usr.bin/sockstat/sockstat.c
index 4548eb8a0b11..587647e5950f 100644
--- a/usr.bin/sockstat/sockstat.c
+++ b/usr.bin/sockstat/sockstat.c
@@ -99,11 +99,13 @@ static int opt_U; /* Show remote UDP encapsulation port number */
static int opt_u; /* Show Unix domain sockets */
static int opt_v; /* Verbose mode */
static int opt_w; /* Wide print area for addresses */
+static bool show_path_state = false;
/*
* Default protocols to use if no -P was defined.
*/
-static const char *default_protos[] = {"sctp", "tcp", "udp", "divert" };
+static const char *default_protos[] = {"sctp", "tcp", "udp", "udplite",
+ "divert" };
static size_t default_numprotos = nitems(default_protos);
static int *protos; /* protocols to use */
@@ -519,6 +521,7 @@ gather_sctp(void)
((xinpcb->flags & SCTP_PCB_FLAGS_UDPTYPE) ||
(xstcb->last == 1))) {
RB_INSERT(socks_t, &socks, sock);
+ show_path_state = true;
} else {
free_socket(sock);
}
@@ -684,6 +687,10 @@ gather_inet(int proto)
varname = "net.inet.udp.pcblist";
protoname = "udp";
break;
+ case IPPROTO_UDPLITE:
+ varname = "net.inet.udplite.pcblist";
+ protoname = "udplite";
+ break;
case IPPROTO_DIVERT:
varname = "net.inet.divert.pcblist";
protoname = "div";
@@ -732,6 +739,7 @@ gather_inet(int proto)
protoname = xtp->t_flags & TF_TOE ? "toe" : "tcp";
break;
case IPPROTO_UDP:
+ case IPPROTO_UDPLITE:
case IPPROTO_DIVERT:
xip = (struct xinpcb *)xig;
if (!check_ksize(xip->xi_len, struct xinpcb))
@@ -1159,7 +1167,7 @@ displaysock(struct sock *s, int pos)
faddr = s->faddr;
first = 1;
while (laddr != NULL || faddr != NULL) {
- offset = 37;
+ offset = 40;
while (pos < offset)
pos += xprintf(" ");
switch (s->family) {
@@ -1296,7 +1304,7 @@ displaysock(struct sock *s, int pos)
}
offset += 7;
}
- if (opt_s) {
+ if (opt_s && show_path_state) {
if (faddr != NULL &&
s->proto == IPPROTO_SCTP &&
s->state != SCTP_CLOSED &&
@@ -1387,7 +1395,7 @@ display(void)
int n, pos;
if (opt_q != 1) {
- printf("%-8s %-10s %-5s %-3s %-6s %-*s %-*s",
+ printf("%-8s %-10s %-5s %-3s %-9s %-*s %-*s",
"USER", "COMMAND", "PID", "FD", "PROTO",
opt_w ? 45 : 21, "LOCAL ADDRESS",
opt_w ? 45 : 21, "FOREIGN ADDRESS");
@@ -1401,7 +1409,8 @@ display(void)
if (opt_U)
printf(" %-6s", "ENCAPS");
if (opt_s) {
- printf(" %-12s", "PATH STATE");
+ if (show_path_state)
+ printf(" %-12s", "PATH STATE");
printf(" %-12s", "CONN STATE");
}
if (opt_b)
diff --git a/usr.bin/tar/Makefile b/usr.bin/tar/Makefile
index 9260315fb30b..8b0d3e4a6cf0 100644
--- a/usr.bin/tar/Makefile
+++ b/usr.bin/tar/Makefile
@@ -17,7 +17,7 @@ SRCS= bsdtar.c \
write.c
.PATH: ${_LIBARCHIVEDIR}/libarchive_fe
-SRCS+= err.c \
+SRCS+= lafe_err.c \
line_reader.c \
passphrase.c
diff --git a/usr.bin/tar/tests/Makefile b/usr.bin/tar/tests/Makefile
index 34f87cb65ea2..fe3dd3e8e6ed 100644
--- a/usr.bin/tar/tests/Makefile
+++ b/usr.bin/tar/tests/Makefile
@@ -28,6 +28,7 @@ TESTS_SRCS= \
test_0.c \
test_basic.c \
test_copy.c \
+ test_crlf_mtree.c \
test_empty_mtree.c \
test_extract_tar_bz2.c \
test_extract_tar_grz.c \
diff --git a/usr.bin/unzip/Makefile b/usr.bin/unzip/Makefile
index 7193ab58b5a3..b14122f93ae6 100644
--- a/usr.bin/unzip/Makefile
+++ b/usr.bin/unzip/Makefile
@@ -13,7 +13,7 @@ BSDUNZIP_VERSION_STRING!= sed -n '/define.*ARCHIVE_VERSION_ONLY_STRING/{s,[^0-9.
SRCS= bsdunzip.c
.PATH: ${_LIBARCHIVEDIR}/libarchive_fe
-SRCS+= cmdline.c err.c passphrase.c
+SRCS+= cmdline.c lafe_err.c passphrase.c
CFLAGS+= -DBSDUNZIP_VERSION_STRING=\"${BSDUNZIP_VERSION_STRING}\"
CFLAGS+= -DPLATFORM_CONFIG_H=\"${_LIBARCHIVECONFDIR}/config_freebsd.h\"
diff --git a/usr.bin/unzip/tests/Makefile b/usr.bin/unzip/tests/Makefile
index 85fc4b88cd78..fd5254a55912 100644
--- a/usr.bin/unzip/tests/Makefile
+++ b/usr.bin/unzip/tests/Makefile
@@ -24,7 +24,7 @@ CFLAGS+= -I${_LIBARCHIVEDIR}/libarchive_fe -I${_LIBARCHIVEDIR}/test_utils
CFLAGS.test_utils.c+= -Wno-cast-align
.PATH: ${_LIBARCHIVEDIR}/libarchive_fe
-UNZIP_SRCS+= err.c
+UNZIP_SRCS+= lafe_err.c
.PATH: ${_LIBARCHIVEDIR}/unzip/test
TESTS_SRCS= \