浏览代码

Merge branch 'master' into dev

Source commit: e5442e4fe0d6b40ed9f87809361d6d759859b76e
Martin Prikryl 1 周之前
父节点
当前提交
43fefabab0
共有 50 个文件被更改,包括 2693 次插入953 次删除
  1. 7 7
      libs/expat/CMake.README
  2. 20 25
      libs/expat/CMakeLists.txt
  3. 133 2
      libs/expat/Changes
  4. 1 0
      libs/expat/ConfigureChecks.cmake
  5. 4 3
      libs/expat/Makefile.am
  6. 63 65
      libs/expat/Makefile.in
  7. 4 4
      libs/expat/README.md
  8. 305 136
      libs/expat/aclocal.m4
  9. 0 0
      libs/expat/cmake/autotools/expat__linux.cmake.in
  10. 107 0
      libs/expat/cmake/autotools/expat__macos.cmake.in
  11. 107 0
      libs/expat/cmake/autotools/expat__windows.cmake.in
  12. 352 158
      libs/expat/configure
  13. 17 7
      libs/expat/configure.ac
  14. 20 9
      libs/expat/doc/Makefile.in
  15. 134 12
      libs/expat/doc/reference.html
  16. 23 7
      libs/expat/doc/xmlwf.1
  17. 21 7
      libs/expat/doc/xmlwf.xml
  18. 21 14
      libs/expat/examples/Makefile.in
  19. 9 9
      libs/expat/expat_config.h
  20. 12 12
      libs/expat/expat_config.h.cmake
  21. 6 6
      libs/expat/expat_config.h.in
  22. 4 2
      libs/expat/fuzz/xml_lpm_fuzzer.cpp
  23. 12 8
      libs/expat/fuzz/xml_parse_fuzzer.c
  24. 14 10
      libs/expat/fuzz/xml_parsebuffer_fuzzer.c
  25. 28 21
      libs/expat/lib/Makefile.in
  26. 39 25
      libs/expat/lib/expat.h
  27. 62 61
      libs/expat/lib/expat_external.h
  28. 14 0
      libs/expat/lib/internal.h
  29. 3 0
      libs/expat/lib/libexpat.def.cmake
  30. 478 94
      libs/expat/lib/xmlparse.c
  31. 15 21
      libs/expat/lib/xmlrole.h
  32. 2 2
      libs/expat/lib/xmltok.c
  33. 113 113
      libs/expat/lib/xmltok.h
  34. 68 31
      libs/expat/tests/Makefile.in
  35. 239 3
      libs/expat/tests/alloc_tests.c
  36. 6 2
      libs/expat/tests/basic_tests.c
  37. 21 14
      libs/expat/tests/benchmark/Makefile.in
  38. 10 1
      libs/expat/tests/common.c
  39. 15 14
      libs/expat/tests/handlers.c
  40. 1 2
      libs/expat/tests/minicheck.h
  41. 98 3
      libs/expat/tests/misc_tests.c
  42. 8 3
      libs/expat/tests/nsalloc_tests.c
  43. 2 2
      libs/expat/win32/README.txt
  44. 2 2
      libs/expat/win32/build_expat_iss.bat
  45. 1 1
      libs/expat/win32/expat.iss
  46. 22 15
      libs/expat/xmlwf/Makefile.in
  47. 3 3
      libs/expat/xmlwf/unixfilemap.c
  48. 16 9
      libs/expat/xmlwf/xmlfile.c
  49. 17 4
      libs/expat/xmlwf/xmlwf.c
  50. 14 4
      libs/expat/xmlwf/xmlwf_helpgen.py

+ 7 - 7
libs/expat/CMake.README

@@ -3,25 +3,25 @@
 The cmake based buildsystem for expat works on Windows (cygwin, mingw, Visual
 Studio) and should work on all other platform cmake supports.
 
-Assuming ~/expat-2.7.1 is the source directory of expat, add a subdirectory
+Assuming ~/expat-2.7.3 is the source directory of expat, add a subdirectory
 build and change into that directory:
-~/expat-2.7.1$ mkdir build && cd build
-~/expat-2.7.1/build$
+~/expat-2.7.3$ mkdir build && cd build
+~/expat-2.7.3/build$
 
 From that directory, call cmake first, then call make, make test and
 make install in the usual way:
-~/expat-2.7.1/build$ cmake ..
+~/expat-2.7.3/build$ cmake ..
 -- The C compiler identification is GNU
 -- The CXX compiler identification is GNU
 ....
 -- Configuring done
 -- Generating done
--- Build files have been written to: /home/patrick/expat-2.7.1/build
+-- Build files have been written to: /home/patrick/expat-2.7.3/build
 
 If you want to specify the install location for your files, append
 -DCMAKE_INSTALL_PREFIX=/your/install/path to the cmake call.
 
-~/expat-2.7.1/build$ make && make test && make install
+~/expat-2.7.3/build$ make && make test && make install
 Scanning dependencies of target expat
 [  5%] Building C object CMakeFiles/expat.dir/lib/xmlparse.c.o
 [ 11%] Building C object CMakeFiles/expat.dir/lib/xmlrole.c.o
@@ -36,7 +36,7 @@ Visual Studio Command Prompt or when using mingw, you must open a cmd.exe and
 make sure that gcc can be called. On Windows, you also might want to specify a
 special Generator for CMake:
 for Visual Studio builds do:
-cmake .. -G "Visual Studio 16 2019" && msbuild /m expat.sln
+cmake .. -G "Visual Studio 17 2022" && msbuild /m expat.sln
 for mingw builds do:
 cmake .. -G "MinGW Makefiles" -DCMAKE_INSTALL_PREFIX=D:\expat-install
     && gmake && gmake install

+ 20 - 25
libs/expat/CMakeLists.txt

@@ -35,11 +35,11 @@
 # Unlike most of Expat,
 # this file is copyrighted under the BSD-license for buildsystem files of KDE.
 
-cmake_minimum_required(VERSION 3.13.0)
+cmake_minimum_required(VERSION 3.15.0)
 
 project(expat
     VERSION
-        2.7.1
+        2.7.3
     LANGUAGES
         C
 )
@@ -118,9 +118,8 @@ macro(expat_shy_set var default cache type desc)
 
     if(DEFINED ${var})
         # NOTE: The idea is to (ideally) only add to the cache if
-        #       there is no cache entry, yet.  "if(DEFINED CACHE{var})"
-        #       requires CMake >=3.14.
-        if(CMAKE_VERSION VERSION_GREATER_EQUAL "3.14" AND NOT DEFINED "CACHE{${var}}")
+        #       there is no cache entry, yet.
+        if(NOT DEFINED "CACHE{${var}}")
             set("${var}" "${${var}}" CACHE "${type}" "${desc}")
         endif()
     else()
@@ -206,8 +205,8 @@ if(MSVC)
     # - https://sourceforge.net/p/predef/wiki/Compilers/
     # - https://en.wikipedia.org/wiki/Microsoft_Visual_Studio#History
     set(_EXPAT_MSVC_REQUIRED_INT 1800)  # i.e. 12.0/2013/1800; see PR #426
-    set(_EXPAT_MSVC_SUPPORTED_INT 1920)
-    set(_EXPAT_MSVC_SUPPORTED_DISPLAY "Visual Studio 16.0/2019/${_EXPAT_MSVC_SUPPORTED_INT}")
+    set(_EXPAT_MSVC_SUPPORTED_INT 1930)
+    set(_EXPAT_MSVC_SUPPORTED_DISPLAY "Visual Studio 17.0/2022/${_EXPAT_MSVC_SUPPORTED_INT}")
 
     if(MSVC_VERSION VERSION_LESS ${_EXPAT_MSVC_SUPPORTED_INT})
         if(MSVC_VERSION VERSION_LESS ${_EXPAT_MSVC_REQUIRED_INT})
@@ -344,22 +343,16 @@ set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${EXTRA_COMPILE_FLAGS}")
 set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${EXTRA_COMPILE_FLAGS}")
 
 if (MSVC)
+    cmake_policy(GET CMP0091 _policy_cmp0091_behavior)
+    if (NOT _policy_cmp0091_behavior STREQUAL NEW)
+        message(SEND_ERROR "Policy CMP0091 behavior is '${_policy_cmp0091_behavior}' rather than 'NEW', mis-compilation detected.")
+    endif()
+
+    message(STATUS "-- Using static CRT ${EXPAT_MSVC_STATIC_CRT}")
     if (EXPAT_MSVC_STATIC_CRT)
-        message("-- Using static CRT ${EXPAT_MSVC_STATIC_CRT}")
-        foreach(flag_var
-                CMAKE_CXX_FLAGS_${_EXPAT_BUILD_TYPE_UPPER}
-                CMAKE_CXX_FLAGS_DEBUG
-                CMAKE_CXX_FLAGS_RELEASE
-                CMAKE_CXX_FLAGS_MINSIZEREL
-                CMAKE_CXX_FLAGS_RELWITHDEBINFO
-                CMAKE_C_FLAGS_${_EXPAT_BUILD_TYPE_UPPER}
-                CMAKE_C_FLAGS_DEBUG
-                CMAKE_C_FLAGS_RELEASE
-                CMAKE_C_FLAGS_MINSIZEREL
-                CMAKE_C_FLAGS_RELWITHDEBINFO
-                )
-            string(REPLACE "/MD" "/MT" ${flag_var} "${${flag_var}}")
-        endforeach()
+        set(CMAKE_MSVC_RUNTIME_LIBRARY "MultiThreaded$<$<CONFIG:Debug>:Debug>")  # .. without suffix "DLL": static
+    else()
+        set(CMAKE_MSVC_RUNTIME_LIBRARY "MultiThreaded$<$<CONFIG:Debug>:Debug>DLL")  # i.e. CMake default behavior: shared
     endif()
 endif()
 
@@ -471,9 +464,9 @@ foreach(build_type_upper
     set_property(TARGET expat PROPERTY ${build_type_upper}_POSTFIX ${EXPAT_${build_type_upper}_POSTFIX})
 endforeach()
 
-set(LIBCURRENT 11)  # sync
-set(LIBREVISION 2)  # with
-set(LIBAGE 10)      # configure.ac!
+set(LIBCURRENT 12)  # sync
+set(LIBREVISION 1)  # with
+set(LIBAGE 11)      # configure.ac!
 math(EXPR LIBCURRENT_MINUS_AGE "${LIBCURRENT} - ${LIBAGE}")
 
 if(NOT WIN32)
@@ -976,6 +969,8 @@ get_property(_EXPAT_GENERATOR_IS_MULTI_CONFIG GLOBAL PROPERTY GENERATOR_IS_MULTI
 
 message(STATUS "===========================================================================")
 message(STATUS "")
+message(STATUS "CMake version in use ......... ${CMAKE_VERSION}")
+message(STATUS "")
 message(STATUS "Configuration")
 message(STATUS "  Generator .................. ${CMAKE_GENERATOR}")
 if(_EXPAT_GENERATOR_IS_MULTI_CONFIG)

+ 133 - 2
libs/expat/Changes

@@ -15,12 +15,16 @@
 !!   ClusterFuzz findings with few-days-max response times in communication  !!
 !!   in order to (1) have a sound fix ready before the end of a 90 days      !!
 !!   grace period and (2) in a sustainable manner,                           !!
-!! - helping CPython Expat bindings with supporting Expat's billion laughs   !!
+!! - helping CPython Expat bindings with supporting Expat's amplification    !!
 !!   attack protection API (https://github.com/python/cpython/issues/90949): !!
+!!   - XML_SetAllocTrackerActivationThreshold                                !!
+!!   - XML_SetAllocTrackerMaximumAmplification                               !!
 !!   - XML_SetBillionLaughsAttackProtectionActivationThreshold               !!
 !!   - XML_SetBillionLaughsAttackProtectionMaximumAmplification              !!
 !! - helping Perl's XML::Parser Expat bindings with supporting Expat's       !!
 !!   security API (https://github.com/cpan-authors/XML-Parser/issues/102):   !!
+!!   - XML_SetAllocTrackerActivationThreshold                                !!
+!!   - XML_SetAllocTrackerMaximumAmplification                               !!
 !!   - XML_SetBillionLaughsAttackProtectionActivationThreshold               !!
 !!   - XML_SetBillionLaughsAttackProtectionMaximumAmplification              !!
 !!   - XML_SetReparseDeferralEnabled                                         !!
@@ -37,6 +41,133 @@
 !! THANK YOU!                        Sebastian Pipping -- Berlin, 2024-03-09 !!
 !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
 
+Release 2.7.3 Wed September 24 2025
+        Security fixes:
+     #1046 #1048  Fix alignment of internal allocations for some non-amd64
+                    architectures (e.g. sparc32); fixes up on the fix to
+                    CVE-2025-59375 from #1034 (of Expat 2.7.2 and related
+                    backports)
+           #1059  Fix a class of false positives where input should have been
+                    rejected with error XML_ERROR_ASYNC_ENTITY; regression from
+                    CVE-2024-8176 fix pull request #973 (of Expat 2.7.0 and
+                    related backports). Please check the added unit tests for
+                    example documents.
+
+        Other changes:
+           #1043  Prove and regression-proof absence of integer overflow
+                    from function expat_realloc
+           #1062  Remove "harmless" cast that truncated a size_t to unsigned
+           #1049  Autotools: Remove "ln -s" discovery
+           #1054  docs: Be consistent with use of floating point around
+                    XML_SetAllocTrackerMaximumAmplification
+           #1056  docs: Make it explicit that XML_GetCurrentColumnNumber
+                    starts at 0
+           #1057  docs: Better integrate the effect of the activation
+                    thresholds
+           #1058  docs: Fix an in-comment typo in expat.h
+           #1045  docs: Fix a typo in README.md
+           #1041  docs: Improve change log of release 2.7.2
+           #1053  xmlwf: Resolve use of functions XML_GetErrorLineNumber
+                    and XML_GetErrorColumnNumber
+           #1032  Windows: Normalize .bat files to CRLF line endings
+     #1060 #1061  Version info bumped from 12:0:11 (libexpat*.so.1.11.0)
+                    to 12:1:11 (libexpat*.so.1.11.1); see https://verbump.de/
+                    for what these numbers do
+
+        Infrastructure:
+     #1047 #1050  CI: Cleanup UndefinedBehaviorSanitizer fatality
+           #1044  CI|Linux: Stop aborting at first job failure
+           #1052  CI|FreeBSD: Upgrade to FreeBSD 15.0
+           #1039  CI|FreeBSD: Do not install CMake meta-package
+
+        Special thanks to:
+            Bénédikt Tran
+            Berkay Eren Ürün
+            Daniel Engberg
+            Hanno Böck
+            Matthew Fernandez
+            Rolf Eike Beer
+            Sam James
+            Tim Bray
+                 and
+            Clang/GCC UndefinedBehaviorSanitizer
+            OSS-Fuzz / ClusterFuzz
+            Z3 Theorem Prover
+
+Release 2.7.2 Tue September 16 2025
+        Security fixes:
+     #1018 #1034  CVE-2025-59375 -- Disallow use of disproportional amounts of
+                    dynamic memory from within an Expat parser (e.g. previously
+                    a ~250 KiB sized document was able to cause allocation of
+                    ~800 MiB from the heap, i.e. an "amplification" of factor
+                    ~3,300); once a threshold (that defaults to 64 MiB) is
+                    reached, a maximum amplification factor (that defaults to
+                    100.0) is enforced, and violating documents are rejected
+                    with an out-of-memory error.
+                    There are two new API functions to fine-tune this new
+                    behavior:
+                      - XML_SetAllocTrackerActivationThreshold
+                      - XML_SetAllocTrackerMaximumAmplification .
+                    If you ever need to increase these defaults for non-attack
+                    XML payload, please file a bug report with libexpat.
+                      There is also a new environment variable
+                    EXPAT_MALLOC_DEBUG=(0|1|2) to control the verbosity
+                    of allocations debugging at runtime, disabled by default.
+                      Known impact is (reliable and easy) denial of service:
+                    CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:N/A:H/E:H/RL:O/RC:C
+                    (Base Score: 7.5, Temporal Score: 7.2)
+                    Please note that a layer of compression around XML can
+                    significantly reduce the minimum attack payload size.
+                      Distributors intending to backport (or cherry-pick) the
+                    fix need to copy 99% of the related pull request, not just
+                    the "lib: Implement tracking of dynamic memory allocations"
+                    commit, to not end up with a state that literally does both
+                    too much and too little at the same time. Appending ".diff"
+                    to the pull request URL could be of help.
+
+        Other changes:
+     #1008 #1017  Autotools|macOS: Sync CMake templates with CMake 3.31
+           #1007  CMake: Drop support for CMake <3.15
+           #1004  CMake: Fix off_t detection for -Werror
+           #1007  CMake|Windows: Fix -DEXPAT_MSVC_STATIC_CRT=ON
+           #1013  Windows: Drop support for Visual Studio <=16.0/2019
+           #1026  xmlwf: Mention supported environment variables in
+                    --help output
+           #1024  xmlwf: Fix (internal) help generator
+           #1034  docs: Promote the contract to call function
+                    XML_FreeContentModel when registering a custom
+                    element declaration handler (via a call to function
+                    XML_SetElementDeclHandler)
+           #1027  docs: Add missing <p>..</p> wrap
+            #994  docs: Drop AppVeyor badge
+           #1000  tests: Fix portable_strndup
+           #1036  Drop casts around malloc/free/realloc that C99 does not need
+           #1010  Replace empty for loops with while loops
+           #1011  Add const with internal XmlInitUnknownEncodingNS
+       #14 #1037  Drop an OpenVMS support leftover
+      #999 #1001  Address more clang-tidy warnings
+     #1030 #1038  Version info bumped from 11:2:10 (libexpat*.so.1.10.2)
+                    to 12:0:11 (libexpat*.so.1.11.0); see https://verbump.de/
+                    for what these numbers do
+
+        Infrastructure:
+           #1003  CI: Cover compilation on FreeBSD
+     #1009 #1035  CI: Upgrade Clang from 19 to 21
+           #1031  CI: Make calling Cppcheck without --suppress=objectIndex
+                    and --suppress=unknownMacro possible
+           #1013  CI|Windows: Get off of deprecated image "windows-2019"
+  #1008 #1017 ..
+     #1023 #1025  CI: Adapt to breaking changes in GitHub Actions
+
+        Special thanks to:
+            Alexander Bluhm
+            Neil Pang
+            Theo Buehler
+                 and
+            GNU Time
+            OSS-Fuzz / ClusterFuzz
+            Perl XML::Parser
+
 Release 2.7.1 Thu March 27 2025
         Bug fixes:
        #980 #989  Restore event pointer behavior from Expat 2.6.4
@@ -54,7 +185,7 @@ Release 2.7.1 Thu March 27 2025
        #983 #984  Fix printf format specifiers for 32bit Emscripten
             #992  docs: Promote OpenSSF Best Practices self-certification
             #978  tests/benchmark: Resolve mistaken double close
-            #986  Address compiler warnings
+            #986  Address Frama-C warnings
        #990 #993  Version info bumped from 11:1:10 (libexpat*.so.1.10.1)
                     to 11:2:10 (libexpat*.so.1.10.2); see https://verbump.de/
                     for what these numbers do

+ 1 - 0
libs/expat/ConfigureChecks.cmake

@@ -50,6 +50,7 @@ if(HAVE_SYS_TYPES_H)
         #include <sys/types.h>
         int main(void) {
             const off_t offset = -123;
+            (void)offset;
             return 0;
         }"
         HAVE_OFF_T)

+ 4 - 3
libs/expat/Makefile.am

@@ -58,10 +58,8 @@ pkgconfig_DATA = expat.pc
 pkgconfigdir = $(libdir)/pkgconfig
 
 
-dist_cmake_DATA = \
-    cmake/autotools/expat.cmake
-
 nodist_cmake_DATA = \
+    cmake/autotools/expat.cmake \
     cmake/autotools/expat-config-version.cmake \
     cmake/autotools/expat-noconfig.cmake \
     cmake/expat-config.cmake
@@ -70,6 +68,9 @@ cmakedir = $(libdir)/cmake/expat-@PACKAGE_VERSION@
 
 
 _EXTRA_DIST_CMAKE = \
+    cmake/autotools/expat__linux.cmake.in \
+    cmake/autotools/expat__macos.cmake.in \
+    cmake/autotools/expat__windows.cmake.in \
     cmake/autotools/expat-noconfig__linux.cmake.in \
     cmake/autotools/expat-noconfig__macos.cmake.in \
     cmake/autotools/expat-noconfig__windows.cmake.in \

+ 63 - 65
libs/expat/Makefile.in

@@ -1,7 +1,7 @@
-# Makefile.in generated by automake 1.16.5 from Makefile.am.
+# Makefile.in generated by automake 1.18.1 from Makefile.am.
 # @configure_input@
 
-# Copyright (C) 1994-2021 Free Software Foundation, Inc.
+# Copyright (C) 1994-2025 Free Software Foundation, Inc.
 
 # This Makefile.in is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -105,6 +105,8 @@ am__make_running_with_option = \
   test $$has_opt = yes
 am__make_dryrun = (target_option=n; $(am__make_running_with_option))
 am__make_keepgoing = (target_option=k; $(am__make_running_with_option))
+am__rm_f = rm -f $(am__rm_f_notfound)
+am__rm_rf = rm -rf $(am__rm_f_notfound)
 pkgdatadir = $(datadir)/@PACKAGE@
 pkgincludedir = $(includedir)/@PACKAGE@
 pkglibdir = $(libdir)/@PACKAGE@
@@ -145,12 +147,13 @@ am__aclocal_m4_deps = $(top_srcdir)/m4/libtool.m4 \
 am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \
 	$(ACLOCAL_M4)
 DIST_COMMON = $(srcdir)/Makefile.am $(top_srcdir)/configure \
-	$(am__configure_deps) $(dist_cmake_DATA) $(am__DIST_COMMON)
+	$(am__configure_deps) $(am__DIST_COMMON)
 am__CONFIG_DISTCLEAN_FILES = config.status config.cache config.log \
  configure.lineno config.status.lineno
 mkinstalldirs = $(install_sh) -d
 CONFIG_HEADER = expat_config.h
 CONFIG_CLEAN_FILES = expat.pc cmake/expat-config.cmake \
+	cmake/autotools/expat.cmake \
 	cmake/autotools/expat-config-version.cmake \
 	cmake/autotools/expat-noconfig.cmake run.sh
 CONFIG_CLEAN_VPATH_FILES =
@@ -203,14 +206,12 @@ am__base_list = \
   sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \
   sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g'
 am__uninstall_files_from_dir = { \
-  test -z "$$files" \
-    || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \
-    || { echo " ( cd '$$dir' && rm -f" $$files ")"; \
-         $(am__cd) "$$dir" && rm -f $$files; }; \
+  { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \
+  || { echo " ( cd '$$dir' && rm -f" $$files ")"; \
+       $(am__cd) "$$dir" && echo $$files | $(am__xargs_n) 40 $(am__rm_f); }; \
   }
-am__installdirs = "$(DESTDIR)$(cmakedir)" "$(DESTDIR)$(cmakedir)" \
-	"$(DESTDIR)$(pkgconfigdir)"
-DATA = $(dist_cmake_DATA) $(nodist_cmake_DATA) $(pkgconfig_DATA)
+am__installdirs = "$(DESTDIR)$(cmakedir)" "$(DESTDIR)$(pkgconfigdir)"
+DATA = $(nodist_cmake_DATA) $(pkgconfig_DATA)
 RECURSIVE_CLEAN_TARGETS = mostlyclean-recursive clean-recursive	\
   distclean-recursive maintainer-clean-recursive
 am__recursive_targets = \
@@ -256,8 +257,8 @@ distdir = $(PACKAGE)-$(VERSION)
 top_distdir = $(distdir)
 am__remove_distdir = \
   if test -d "$(distdir)"; then \
-    find "$(distdir)" -type d ! -perm -200 -exec chmod u+w {} ';' \
-      && rm -rf "$(distdir)" \
+    find "$(distdir)" -type d ! -perm -700 -exec chmod u+rwx {} ';' \
+      ; rm -rf "$(distdir)" \
       || { sleep 5 && rm -rf "$(distdir)"; }; \
   else :; fi
 am__post_remove_distdir = $(am__remove_distdir)
@@ -288,14 +289,16 @@ am__relativize = \
   reldir="$$dir2"
 DIST_ARCHIVES = $(distdir).tar.gz $(distdir).tar.bz2 $(distdir).tar.lz \
 	$(distdir).tar.xz
-GZIP_ENV = --best
+GZIP_ENV = -9
 DIST_TARGETS = dist-lzip dist-xz dist-bzip2 dist-gzip
 # Exists only to be overridden by the user if desired.
 AM_DISTCHECK_DVI_TARGET = dvi
 distuninstallcheck_listfiles = find . -type f -print
 am__distuninstallcheck_listfiles = $(distuninstallcheck_listfiles) \
   | sed 's|^\./|$(prefix)/|' | grep -v '$(infodir)/dir$$'
-distcleancheck_listfiles = find . -type f -print
+distcleancheck_listfiles = \
+  find . \( -type f -a \! \
+            \( -name .nfs* -o -name .smb* -o -name .__afs* \) \) -print
 ACLOCAL = @ACLOCAL@
 AMTAR = @AMTAR@
 AM_CFLAGS = @AM_CFLAGS@
@@ -403,8 +406,10 @@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@
 am__include = @am__include@
 am__leading_dot = @am__leading_dot@
 am__quote = @am__quote@
+am__rm_f_notfound = @am__rm_f_notfound@
 am__tar = @am__tar@
 am__untar = @am__untar@
+am__xargs_n = @am__xargs_n@
 bindir = @bindir@
 build = @build@
 build_alias = @build_alias@
@@ -458,16 +463,17 @@ LIBTOOLFLAGS = --verbose
 SUBDIRS = lib $(am__append_1) $(am__append_2) $(am__append_3)
 pkgconfig_DATA = expat.pc
 pkgconfigdir = $(libdir)/pkgconfig
-dist_cmake_DATA = \
-    cmake/autotools/expat.cmake
-
 nodist_cmake_DATA = \
+    cmake/autotools/expat.cmake \
     cmake/autotools/expat-config-version.cmake \
     cmake/autotools/expat-noconfig.cmake \
     cmake/expat-config.cmake
 
 cmakedir = $(libdir)/cmake/expat-@PACKAGE_VERSION@
 _EXTRA_DIST_CMAKE = \
+    cmake/autotools/expat__linux.cmake.in \
+    cmake/autotools/expat__macos.cmake.in \
+    cmake/autotools/expat__windows.cmake.in \
     cmake/autotools/expat-noconfig__linux.cmake.in \
     cmake/autotools/expat-noconfig__macos.cmake.in \
     cmake/autotools/expat-noconfig__windows.cmake.in \
@@ -552,12 +558,12 @@ expat_config.h: stamp-h1
 	@test -f $@ || $(MAKE) $(AM_MAKEFLAGS) stamp-h1
 
 stamp-h1: $(srcdir)/expat_config.h.in $(top_builddir)/config.status
-	@rm -f stamp-h1
-	cd $(top_builddir) && $(SHELL) ./config.status expat_config.h
+	$(AM_V_at)rm -f stamp-h1
+	$(AM_V_GEN)cd $(top_builddir) && $(SHELL) ./config.status expat_config.h
 $(srcdir)/expat_config.h.in: @MAINTAINER_MODE_TRUE@ $(am__configure_deps) 
-	($(am__cd) $(top_srcdir) && $(AUTOHEADER))
-	rm -f stamp-h1
-	touch $@
+	$(AM_V_GEN)($(am__cd) $(top_srcdir) && $(AUTOHEADER))
+	$(AM_V_at)rm -f stamp-h1
+	$(AM_V_at)touch $@
 
 distclean-hdr:
 	-rm -f expat_config.h stamp-h1
@@ -565,6 +571,8 @@ expat.pc: $(top_builddir)/config.status $(srcdir)/expat.pc.in
 	cd $(top_builddir) && $(SHELL) ./config.status $@
 cmake/expat-config.cmake: $(top_builddir)/config.status $(top_srcdir)/cmake/expat-config.cmake.in
 	cd $(top_builddir) && $(SHELL) ./config.status $@
+cmake/autotools/expat.cmake: $(top_builddir)/config.status 
+	cd $(top_builddir) && $(SHELL) ./config.status $@
 cmake/autotools/expat-config-version.cmake: $(top_builddir)/config.status $(top_srcdir)/cmake/autotools/expat-config-version.cmake.in
 	cd $(top_builddir) && $(SHELL) ./config.status $@
 cmake/autotools/expat-noconfig.cmake: $(top_builddir)/config.status 
@@ -580,27 +588,6 @@ clean-libtool:
 
 distclean-libtool:
 	-rm -f libtool config.lt
-install-dist_cmakeDATA: $(dist_cmake_DATA)
-	@$(NORMAL_INSTALL)
-	@list='$(dist_cmake_DATA)'; test -n "$(cmakedir)" || list=; \
-	if test -n "$$list"; then \
-	  echo " $(MKDIR_P) '$(DESTDIR)$(cmakedir)'"; \
-	  $(MKDIR_P) "$(DESTDIR)$(cmakedir)" || exit 1; \
-	fi; \
-	for p in $$list; do \
-	  if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \
-	  echo "$$d$$p"; \
-	done | $(am__base_list) | \
-	while read files; do \
-	  echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(cmakedir)'"; \
-	  $(INSTALL_DATA) $$files "$(DESTDIR)$(cmakedir)" || exit $$?; \
-	done
-
-uninstall-dist_cmakeDATA:
-	@$(NORMAL_UNINSTALL)
-	@list='$(dist_cmake_DATA)'; test -n "$(cmakedir)" || list=; \
-	files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \
-	dir='$(DESTDIR)$(cmakedir)'; $(am__uninstall_files_from_dir)
 install-nodist_cmakeDATA: $(nodist_cmake_DATA)
 	@$(NORMAL_INSTALL)
 	@list='$(nodist_cmake_DATA)'; test -n "$(cmakedir)" || list=; \
@@ -749,12 +736,13 @@ cscopelist-am: $(am__tagged_files)
 distclean-tags:
 	-rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags
 	-rm -f cscope.out cscope.in.out cscope.po.out cscope.files
+
 distdir: $(BUILT_SOURCES)
 	$(MAKE) $(AM_MAKEFLAGS) distdir-am
 
 distdir-am: $(DISTFILES)
 	$(am__remove_distdir)
-	test -d "$(distdir)" || mkdir "$(distdir)"
+	$(AM_V_at)$(MKDIR_P) "$(distdir)"
 	@srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \
 	topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \
 	list='$(DISTFILES)'; \
@@ -822,6 +810,10 @@ dist-gzip: distdir
 dist-bzip2: distdir
 	tardir=$(distdir) && $(am__tar) | BZIP2=$${BZIP2--9} bzip2 -c >$(distdir).tar.bz2
 	$(am__post_remove_distdir)
+
+dist-bzip3: distdir
+	tardir=$(distdir) && $(am__tar) | bzip3 -c >$(distdir).tar.bz3
+	$(am__post_remove_distdir)
 dist-lzip: distdir
 	tardir=$(distdir) && $(am__tar) | lzip -c $${LZIP_OPT--9} >$(distdir).tar.lz
 	$(am__post_remove_distdir)
@@ -862,9 +854,11 @@ dist dist-all:
 distcheck: dist
 	case '$(DIST_ARCHIVES)' in \
 	*.tar.gz*) \
-	  eval GZIP= gzip $(GZIP_ENV) -dc $(distdir).tar.gz | $(am__untar) ;;\
+	  eval GZIP= gzip -dc $(distdir).tar.gz | $(am__untar) ;;\
 	*.tar.bz2*) \
 	  bzip2 -dc $(distdir).tar.bz2 | $(am__untar) ;;\
+	*.tar.bz3*) \
+	  bzip3 -dc $(distdir).tar.bz3 | $(am__untar) ;;\
 	*.tar.lz*) \
 	  lzip -dc $(distdir).tar.lz | $(am__untar) ;;\
 	*.tar.xz*) \
@@ -872,7 +866,7 @@ distcheck: dist
 	*.tar.Z*) \
 	  uncompress -c $(distdir).tar.Z | $(am__untar) ;;\
 	*.shar.gz*) \
-	  eval GZIP= gzip $(GZIP_ENV) -dc $(distdir).shar.gz | unshar ;;\
+	  eval GZIP= gzip -dc $(distdir).shar.gz | unshar ;;\
 	*.zip*) \
 	  unzip $(distdir).zip ;;\
 	*.tar.zst*) \
@@ -948,7 +942,7 @@ check: check-recursive
 all-am: Makefile $(DATA) expat_config.h
 installdirs: installdirs-recursive
 installdirs-am:
-	for dir in "$(DESTDIR)$(cmakedir)" "$(DESTDIR)$(cmakedir)" "$(DESTDIR)$(pkgconfigdir)"; do \
+	for dir in "$(DESTDIR)$(cmakedir)" "$(DESTDIR)$(pkgconfigdir)"; do \
 	  test -z "$$dir" || $(MKDIR_P) "$$dir"; \
 	done
 install: install-recursive
@@ -975,8 +969,8 @@ mostlyclean-generic:
 clean-generic:
 
 distclean-generic:
-	-test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
-	-test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES)
+	-$(am__rm_f) $(CONFIG_CLEAN_FILES)
+	-test . = "$(srcdir)" || $(am__rm_f) $(CONFIG_CLEAN_VPATH_FILES)
 
 maintainer-clean-generic:
 	@echo "This command is intended for maintainers to use"
@@ -1003,8 +997,7 @@ info: info-recursive
 
 info-am:
 
-install-data-am: install-dist_cmakeDATA install-nodist_cmakeDATA \
-	install-pkgconfigDATA
+install-data-am: install-nodist_cmakeDATA install-pkgconfigDATA
 
 install-dvi: install-dvi-recursive
 
@@ -1050,29 +1043,27 @@ ps: ps-recursive
 
 ps-am:
 
-uninstall-am: uninstall-dist_cmakeDATA uninstall-nodist_cmakeDATA \
-	uninstall-pkgconfigDATA
+uninstall-am: uninstall-nodist_cmakeDATA uninstall-pkgconfigDATA
 
 .MAKE: $(am__recursive_targets) all install-am install-strip
 
 .PHONY: $(am__recursive_targets) CTAGS GTAGS TAGS all all-am \
 	am--refresh check check-am clean clean-cscope clean-generic \
 	clean-libtool cscope cscopelist-am ctags ctags-am dist \
-	dist-all dist-bzip2 dist-gzip dist-lzip dist-shar dist-tarZ \
-	dist-xz dist-zip dist-zstd distcheck distclean \
+	dist-all dist-bzip2 dist-bzip3 dist-gzip dist-lzip dist-shar \
+	dist-tarZ dist-xz dist-zip dist-zstd distcheck distclean \
 	distclean-generic distclean-hdr distclean-libtool \
 	distclean-tags distcleancheck distdir distuninstallcheck dvi \
 	dvi-am html html-am info info-am install install-am \
-	install-data install-data-am install-dist_cmakeDATA \
-	install-dvi install-dvi-am install-exec install-exec-am \
-	install-html install-html-am install-info install-info-am \
-	install-man install-nodist_cmakeDATA install-pdf \
-	install-pdf-am install-pkgconfigDATA install-ps install-ps-am \
-	install-strip installcheck installcheck-am installdirs \
-	installdirs-am maintainer-clean maintainer-clean-generic \
-	mostlyclean mostlyclean-generic mostlyclean-libtool pdf pdf-am \
-	ps ps-am tags tags-am uninstall uninstall-am \
-	uninstall-dist_cmakeDATA uninstall-nodist_cmakeDATA \
+	install-data install-data-am install-dvi install-dvi-am \
+	install-exec install-exec-am install-html install-html-am \
+	install-info install-info-am install-man \
+	install-nodist_cmakeDATA install-pdf install-pdf-am \
+	install-pkgconfigDATA install-ps install-ps-am install-strip \
+	installcheck installcheck-am installdirs installdirs-am \
+	maintainer-clean maintainer-clean-generic mostlyclean \
+	mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \
+	tags tags-am uninstall uninstall-am uninstall-nodist_cmakeDATA \
 	uninstall-pkgconfigDATA
 
 .PRECIOUS: Makefile
@@ -1149,3 +1140,10 @@ qa:
 # Tell versions [3.59,3.63) of GNU make to not export all variables.
 # Otherwise a system limit (for SysV at least) may be exceeded.
 .NOEXPORT:
+
+# Tell GNU make to disable its built-in pattern rules.
+%:: %,v
+%:: RCS/%,v
+%:: RCS/%
+%:: s.%
+%:: SCCS/s.%

+ 4 - 4
libs/expat/README.md

@@ -1,5 +1,4 @@
 [![Run Linux CI tasks](https://github.com/libexpat/libexpat/actions/workflows/linux.yml/badge.svg)](https://github.com/libexpat/libexpat/actions/workflows/linux.yml)
-[![AppVeyor Build Status](https://ci.appveyor.com/api/projects/status/github/libexpat/libexpat?svg=true)](https://ci.appveyor.com/project/libexpat/libexpat)
 [![Packaging status](https://repology.org/badge/tiny-repos/expat.svg)](https://repology.org/metapackage/expat/versions)
 [![Downloads SourceForge](https://img.shields.io/sourceforge/dt/expat?label=Downloads%20SourceForge)](https://sourceforge.net/projects/expat/files/)
 [![Downloads GitHub](https://img.shields.io/github/downloads/libexpat/libexpat/total?label=Downloads%20GitHub)](https://github.com/libexpat/libexpat/releases)
@@ -12,7 +11,7 @@
 > at the top of the `Changes` file.
 
 
-# Expat, Release 2.7.1
+# Expat, Release 2.7.3
 
 This is Expat, a C99 library for parsing
 [XML 1.0 Fourth Edition](https://www.w3.org/TR/2006/REC-xml-20060816/), started by
@@ -27,7 +26,8 @@ Expat supports the following C99 compilers:
 
 - GNU GCC >=4.5 (for use from C) or GNU GCC >=4.8.1 (for use from C++)
 - LLVM Clang >=3.5
-- Microsoft Visual Studio >=16.0/2019 (rolling `${today} minus 5 years`)
+- Microsoft Visual Studio >=17.0/2022
+  (the oldest version supported by the [official GitHub Actions Windows images](https://github.com/actions/runner-images))
 
 Windows users can use the
 [`expat-win32bin-*.*.*.{exe,zip}` download](https://github.com/libexpat/libexpat/releases),
@@ -120,7 +120,7 @@ project(hello VERSION 1.0.0)
 FetchContent_Declare(
     expat
     GIT_REPOSITORY https://github.com/libexpat/libexpat/
-    GIT_TAG        000000000_GIT_COMMIT_SHA1_HERE_000000000  # i.e. Git tag R_0_Y_Z
+    GIT_TAG        000000000_GIT_COMMIT_SHA1_HERE_000000000  # i.e. Git tag R_X_Y_Z
     SOURCE_SUBDIR  expat/
 )
 

+ 305 - 136
libs/expat/aclocal.m4

@@ -1,6 +1,6 @@
-# generated automatically by aclocal 1.16.5 -*- Autoconf -*-
+# generated automatically by aclocal 1.18.1 -*- Autoconf -*-
 
-# Copyright (C) 1996-2021 Free Software Foundation, Inc.
+# Copyright (C) 1996-2025 Free Software Foundation, Inc.
 
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -14,13 +14,13 @@
 m4_ifndef([AC_CONFIG_MACRO_DIRS], [m4_defun([_AM_CONFIG_MACRO_DIRS], [])m4_defun([AC_CONFIG_MACRO_DIRS], [_AM_CONFIG_MACRO_DIRS($@)])])
 m4_ifndef([AC_AUTOCONF_VERSION],
   [m4_copy([m4_PACKAGE_VERSION], [AC_AUTOCONF_VERSION])])dnl
-m4_if(m4_defn([AC_AUTOCONF_VERSION]), [2.71],,
-[m4_warning([this file was generated for autoconf 2.71.
+m4_if(m4_defn([AC_AUTOCONF_VERSION]), [2.72],,
+[m4_warning([this file was generated for autoconf 2.72.
 You have another version of autoconf.  It may work, but is not guaranteed to.
 If you have problems, you may need to regenerate the build system entirely.
 To do so, use the procedure documented by the package, typically 'autoreconf'.])])
 
-# Copyright (C) 2002-2021 Free Software Foundation, Inc.
+# Copyright (C) 2002-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -32,10 +32,10 @@ To do so, use the procedure documented by the package, typically 'autoreconf'.])
 # generated from the m4 files accompanying Automake X.Y.
 # (This private macro should not be called outside this file.)
 AC_DEFUN([AM_AUTOMAKE_VERSION],
-[am__api_version='1.16'
+[am__api_version='1.18'
 dnl Some users find AM_AUTOMAKE_VERSION and mistake it for a way to
 dnl require some minimum version.  Point them to the right macro.
-m4_if([$1], [1.16.5], [],
+m4_if([$1], [1.18.1], [],
       [AC_FATAL([Do not call $0, use AM_INIT_AUTOMAKE([$1]).])])dnl
 ])
 
@@ -51,12 +51,12 @@ m4_define([_AM_AUTOCONF_VERSION], [])
 # Call AM_AUTOMAKE_VERSION and AM_AUTOMAKE_VERSION so they can be traced.
 # This function is AC_REQUIREd by AM_INIT_AUTOMAKE.
 AC_DEFUN([AM_SET_CURRENT_AUTOMAKE_VERSION],
-[AM_AUTOMAKE_VERSION([1.16.5])dnl
+[AM_AUTOMAKE_VERSION([1.18.1])dnl
 m4_ifndef([AC_AUTOCONF_VERSION],
   [m4_copy([m4_PACKAGE_VERSION], [AC_AUTOCONF_VERSION])])dnl
 _AM_AUTOCONF_VERSION(m4_defn([AC_AUTOCONF_VERSION]))])
 
-# Copyright (C) 2011-2021 Free Software Foundation, Inc.
+# Copyright (C) 2011-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -70,16 +70,18 @@ _AM_AUTOCONF_VERSION(m4_defn([AC_AUTOCONF_VERSION]))])
 AC_DEFUN([AM_PROG_AR],
 [AC_BEFORE([$0], [LT_INIT])dnl
 AC_BEFORE([$0], [AC_PROG_LIBTOOL])dnl
+AC_BEFORE([$0], [AC_PROG_AR])dnl
 AC_REQUIRE([AM_AUX_DIR_EXPAND])dnl
 AC_REQUIRE_AUX_FILE([ar-lib])dnl
 AC_CHECK_TOOLS([AR], [ar lib "link -lib"], [false])
 : ${AR=ar}
+: ${ARFLAGS=cr}
 
 AC_CACHE_CHECK([the archiver ($AR) interface], [am_cv_ar_interface],
   [AC_LANG_PUSH([C])
    am_cv_ar_interface=ar
    AC_COMPILE_IFELSE([AC_LANG_SOURCE([[int some_variable = 0;]])],
-     [am_ar_try='$AR cru libconftest.a conftest.$ac_objext >&AS_MESSAGE_LOG_FD'
+     [am_ar_try='$AR $ARFLAGS libconftest.a conftest.$ac_objext >&AS_MESSAGE_LOG_FD'
       AC_TRY_EVAL([am_ar_try])
       if test "$ac_status" -eq 0; then
         am_cv_ar_interface=ar
@@ -118,7 +120,7 @@ AC_SUBST([AR])dnl
 
 # AM_AUX_DIR_EXPAND                                         -*- Autoconf -*-
 
-# Copyright (C) 2001-2021 Free Software Foundation, Inc.
+# Copyright (C) 2001-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -170,7 +172,7 @@ am_aux_dir=`cd "$ac_aux_dir" && pwd`
 
 # AM_CONDITIONAL                                            -*- Autoconf -*-
 
-# Copyright (C) 1997-2021 Free Software Foundation, Inc.
+# Copyright (C) 1997-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -201,7 +203,7 @@ AC_CONFIG_COMMANDS_PRE(
 Usually this means the macro was only invoked conditionally.]])
 fi])])
 
-# Copyright (C) 1999-2021 Free Software Foundation, Inc.
+# Copyright (C) 1999-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -333,7 +335,7 @@ AC_CACHE_CHECK([dependency style of $depcc],
       # icc doesn't choke on unknown options, it will just issue warnings
       # or remarks (even with -Werror).  So we grep stderr for any message
       # that says an option was ignored or not supported.
-      # When given -MP, icc 7.0 and 7.1 complain thusly:
+      # When given -MP, icc 7.0 and 7.1 complain thus:
       #   icc: Command line warning: ignoring option '-M'; no argument required
       # The diagnosis changed in icc 8.0:
       #   icc: Command line remark: option '-MP' not supported
@@ -392,7 +394,7 @@ _AM_SUBST_NOTMAKE([am__nodep])dnl
 
 # Generate code to set up dependency tracking.              -*- Autoconf -*-
 
-# Copyright (C) 1999-2021 Free Software Foundation, Inc.
+# Copyright (C) 1999-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -460,7 +462,7 @@ AC_DEFUN([AM_OUTPUT_DEPENDENCY_COMMANDS],
 
 # Do all the work for Automake.                             -*- Autoconf -*-
 
-# Copyright (C) 1996-2021 Free Software Foundation, Inc.
+# Copyright (C) 1996-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -560,8 +562,9 @@ AC_REQUIRE([AC_PROG_AWK])dnl
 AC_REQUIRE([AC_PROG_MAKE_SET])dnl
 AC_REQUIRE([AM_SET_LEADING_DOT])dnl
 _AM_IF_OPTION([tar-ustar], [_AM_PROG_TAR([ustar])],
-	      [_AM_IF_OPTION([tar-pax], [_AM_PROG_TAR([pax])],
-			     [_AM_PROG_TAR([v7])])])
+  [_AM_IF_OPTION([tar-pax], [_AM_PROG_TAR([pax])],
+    [_AM_IF_OPTION([tar-v7], [_AM_PROG_TAR([v7])],
+      [_AM_PROG_TAR([ustar])])])])
 _AM_IF_OPTION([no-dependencies],,
 [AC_PROVIDE_IFELSE([AC_PROG_CC],
 		  [_AM_DEPENDENCIES([CC])],
@@ -594,7 +597,7 @@ if test -z "$CSCOPE"; then
 fi
 AC_SUBST([CSCOPE])
 
-AC_REQUIRE([AM_SILENT_RULES])dnl
+AC_REQUIRE([_AM_SILENT_RULES])dnl
 dnl The testsuite driver may need to know about EXEEXT, so add the
 dnl 'am__EXEEXT' conditional if _AM_COMPILER_EXEEXT was seen.  This
 dnl macro is hooked onto _AC_COMPILER_EXEEXT early, see below.
@@ -602,47 +605,9 @@ AC_CONFIG_COMMANDS_PRE(dnl
 [m4_provide_if([_AM_COMPILER_EXEEXT],
   [AM_CONDITIONAL([am__EXEEXT], [test -n "$EXEEXT"])])])dnl
 
-# POSIX will say in a future version that running "rm -f" with no argument
-# is OK; and we want to be able to make that assumption in our Makefile
-# recipes.  So use an aggressive probe to check that the usage we want is
-# actually supported "in the wild" to an acceptable degree.
-# See automake bug#10828.
-# To make any issue more visible, cause the running configure to be aborted
-# by default if the 'rm' program in use doesn't match our expectations; the
-# user can still override this though.
-if rm -f && rm -fr && rm -rf; then : OK; else
-  cat >&2 <<'END'
-Oops!
-
-Your 'rm' program seems unable to run without file operands specified
-on the command line, even when the '-f' option is present.  This is contrary
-to the behaviour of most rm programs out there, and not conforming with
-the upcoming POSIX standard: <http://austingroupbugs.net/view.php?id=542>
-
-Please tell [email protected] about your system, including the value
-of your $PATH and any error possibly output before this message.  This
-can help us improve future automake versions.
+AC_REQUIRE([_AM_PROG_RM_F])
+AC_REQUIRE([_AM_PROG_XARGS_N])
 
-END
-  if test x"$ACCEPT_INFERIOR_RM_PROGRAM" = x"yes"; then
-    echo 'Configuration will proceed anyway, since you have set the' >&2
-    echo 'ACCEPT_INFERIOR_RM_PROGRAM variable to "yes"' >&2
-    echo >&2
-  else
-    cat >&2 <<'END'
-Aborting the configuration process, to ensure you take notice of the issue.
-
-You can download and install GNU coreutils to get an 'rm' implementation
-that behaves properly: <https://www.gnu.org/software/coreutils/>.
-
-If you want to complete the configuration process using your problematic
-'rm' anyway, export the environment variable ACCEPT_INFERIOR_RM_PROGRAM
-to "yes", and re-run configure.
-
-END
-    AC_MSG_ERROR([Your 'rm' program is bad, sorry.])
-  fi
-fi
 dnl The trailing newline in this macro's definition is deliberate, for
 dnl backward compatibility and to allow trailing 'dnl'-style comments
 dnl after the AM_INIT_AUTOMAKE invocation. See automake bug#16841.
@@ -675,7 +640,7 @@ for _am_header in $config_headers :; do
 done
 echo "timestamp for $_am_arg" >`AS_DIRNAME(["$_am_arg"])`/stamp-h[]$_am_stamp_count])
 
-# Copyright (C) 2001-2021 Free Software Foundation, Inc.
+# Copyright (C) 2001-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -696,7 +661,7 @@ if test x"${install_sh+set}" != xset; then
 fi
 AC_SUBST([install_sh])])
 
-# Copyright (C) 2003-2021 Free Software Foundation, Inc.
+# Copyright (C) 2003-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -718,7 +683,7 @@ AC_SUBST([am__leading_dot])])
 # Add --enable-maintainer-mode option to configure.         -*- Autoconf -*-
 # From Jim Meyering
 
-# Copyright (C) 1996-2021 Free Software Foundation, Inc.
+# Copyright (C) 1996-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -753,7 +718,7 @@ AC_MSG_CHECKING([whether to enable maintainer-specific portions of Makefiles])
 
 # Check to see how 'make' treats includes.	            -*- Autoconf -*-
 
-# Copyright (C) 2001-2021 Free Software Foundation, Inc.
+# Copyright (C) 2001-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -796,7 +761,7 @@ AC_SUBST([am__quote])])
 
 # Fake the existence of programs that GNU maintainers use.  -*- Autoconf -*-
 
-# Copyright (C) 1997-2021 Free Software Foundation, Inc.
+# Copyright (C) 1997-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -830,7 +795,7 @@ fi
 
 # Helper functions for option handling.                     -*- Autoconf -*-
 
-# Copyright (C) 2001-2021 Free Software Foundation, Inc.
+# Copyright (C) 2001-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -859,7 +824,7 @@ AC_DEFUN([_AM_SET_OPTIONS],
 AC_DEFUN([_AM_IF_OPTION],
 [m4_ifset(_AM_MANGLE_OPTION([$1]), [$2], [$3])])
 
-# Copyright (C) 1999-2021 Free Software Foundation, Inc.
+# Copyright (C) 1999-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -891,7 +856,10 @@ AC_CACHE_CHECK(
       break
     fi
   done
-  rm -f core conftest*
+  # aligned with autoconf, so not including core; see bug#72225.
+  rm -f -r a.out a.exe b.out conftest.$ac_ext conftest.$ac_objext \
+    conftest.dSYM conftest1.$ac_ext conftest1.$ac_objext conftest1.dSYM \
+    conftest2.$ac_ext conftest2.$ac_objext conftest2.dSYM
   unset am_i])
 if test "$am_cv_prog_cc_c_o" != yes; then
    # Losing compiler, so override with the script.
@@ -906,7 +874,23 @@ AC_LANG_POP([C])])
 # For backward compatibility.
 AC_DEFUN_ONCE([AM_PROG_CC_C_O], [AC_REQUIRE([AC_PROG_CC])])
 
-# Copyright (C) 2001-2021 Free Software Foundation, Inc.
+# Copyright (C) 2022-2025 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# _AM_PROG_RM_F
+# ---------------
+# Check whether 'rm -f' without any arguments works.
+# https://bugs.gnu.org/10828
+AC_DEFUN([_AM_PROG_RM_F],
+[am__rm_f_notfound=
+AS_IF([(rm -f && rm -fr && rm -rf) 2>/dev/null], [], [am__rm_f_notfound='""'])
+AC_SUBST(am__rm_f_notfound)
+])
+
+# Copyright (C) 2001-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -925,26 +909,181 @@ AC_DEFUN([AM_RUN_LOG],
 
 # Check to make sure that the build environment is sane.    -*- Autoconf -*-
 
-# Copyright (C) 1996-2021 Free Software Foundation, Inc.
+# Copyright (C) 1996-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
 # with or without modifications, as long as this notice is preserved.
 
+# _AM_SLEEP_FRACTIONAL_SECONDS
+# ----------------------------
+AC_DEFUN([_AM_SLEEP_FRACTIONAL_SECONDS], [dnl
+AC_CACHE_CHECK([whether sleep supports fractional seconds],
+               am_cv_sleep_fractional_seconds, [dnl
+AS_IF([sleep 0.001 2>/dev/null], [am_cv_sleep_fractional_seconds=yes],
+                                 [am_cv_sleep_fractional_seconds=no])
+])])
+
+# _AM_FILESYSTEM_TIMESTAMP_RESOLUTION
+# -----------------------------------
+# Determine the filesystem's resolution for file modification
+# timestamps.  The coarsest we know of is FAT, with a resolution
+# of only two seconds, even with the most recent "exFAT" extensions.
+# The finest (e.g. ext4 with large inodes, XFS, ZFS) is one
+# nanosecond, matching clock_gettime.  However, it is probably not
+# possible to delay execution of a shell script for less than one
+# millisecond, due to process creation overhead and scheduling
+# granularity, so we don't check for anything finer than that. (See below.)
+AC_DEFUN([_AM_FILESYSTEM_TIMESTAMP_RESOLUTION], [dnl
+AC_REQUIRE([_AM_SLEEP_FRACTIONAL_SECONDS])
+AC_CACHE_CHECK([filesystem timestamp resolution],
+               am_cv_filesystem_timestamp_resolution, [dnl
+# Default to the worst case.
+am_cv_filesystem_timestamp_resolution=2
+
+# Only try to go finer than 1 sec if sleep can do it.
+# Don't try 1 sec, because if 0.01 sec and 0.1 sec don't work,
+# - 1 sec is not much of a win compared to 2 sec, and
+# - it takes 2 seconds to perform the test whether 1 sec works.
+# 
+# Instead, just use the default 2s on platforms that have 1s resolution,
+# accept the extra 1s delay when using $sleep in the Automake tests, in
+# exchange for not incurring the 2s delay for running the test for all
+# packages.
+#
+am_try_resolutions=
+if test "$am_cv_sleep_fractional_seconds" = yes; then
+  # Even a millisecond often causes a bunch of false positives,
+  # so just try a hundredth of a second. The time saved between .001 and
+  # .01 is not terribly consequential.
+  am_try_resolutions="0.01 0.1 $am_try_resolutions"
+fi
+
+# In order to catch current-generation FAT out, we must *modify* files
+# that already exist; the *creation* timestamp is finer.  Use names
+# that make ls -t sort them differently when they have equal
+# timestamps than when they have distinct timestamps, keeping
+# in mind that ls -t prints the *newest* file first.
+rm -f conftest.ts?
+: > conftest.ts1
+: > conftest.ts2
+: > conftest.ts3
+
+# Make sure ls -t actually works.  Do 'set' in a subshell so we don't
+# clobber the current shell's arguments. (Outer-level square brackets
+# are removed by m4; they're present so that m4 does not expand
+# <dollar><star>; be careful, easy to get confused.)
+if (
+     set X `[ls -t conftest.ts[12]]` &&
+     {
+       test "$[]*" != "X conftest.ts1 conftest.ts2" ||
+       test "$[]*" != "X conftest.ts2 conftest.ts1";
+     }
+); then :; else
+  # If neither matched, then we have a broken ls.  This can happen
+  # if, for instance, CONFIG_SHELL is bash and it inherits a
+  # broken ls alias from the environment.  This has actually
+  # happened.  Such a system could not be considered "sane".
+  _AS_ECHO_UNQUOTED(
+    ["Bad output from ls -t: \"`[ls -t conftest.ts[12]]`\""],
+    [AS_MESSAGE_LOG_FD])
+  AC_MSG_FAILURE([ls -t produces unexpected output.
+Make sure there is not a broken ls alias in your environment.])
+fi
+
+for am_try_res in $am_try_resolutions; do
+  # Any one fine-grained sleep might happen to cross the boundary
+  # between two values of a coarser actual resolution, but if we do
+  # two fine-grained sleeps in a row, at least one of them will fall
+  # entirely within a coarse interval.
+  echo alpha > conftest.ts1
+  sleep $am_try_res
+  echo beta > conftest.ts2
+  sleep $am_try_res
+  echo gamma > conftest.ts3
+
+  # We assume that 'ls -t' will make use of high-resolution
+  # timestamps if the operating system supports them at all.
+  if (set X `ls -t conftest.ts?` &&
+      test "$[]2" = conftest.ts3 &&
+      test "$[]3" = conftest.ts2 &&
+      test "$[]4" = conftest.ts1); then
+    #
+    # Ok, ls -t worked. If we're at a resolution of 1 second, we're done,
+    # because we don't need to test make.
+    make_ok=true
+    if test $am_try_res != 1; then
+      # But if we've succeeded so far with a subsecond resolution, we
+      # have one more thing to check: make. It can happen that
+      # everything else supports the subsecond mtimes, but make doesn't;
+      # notably on macOS, which ships make 3.81 from 2006 (the last one
+      # released under GPLv2). https://bugs.gnu.org/68808
+      # 
+      # We test $MAKE if it is defined in the environment, else "make".
+      # It might get overridden later, but our hope is that in practice
+      # it does not matter: it is the system "make" which is (by far)
+      # the most likely to be broken, whereas if the user overrides it,
+      # probably they did so with a better, or at least not worse, make.
+      # https://lists.gnu.org/archive/html/automake/2024-06/msg00051.html
+      #
+      # Create a Makefile (real tab character here):
+      rm -f conftest.mk
+      echo 'conftest.ts1: conftest.ts2' >conftest.mk
+      echo '	touch conftest.ts2' >>conftest.mk
+      #
+      # Now, running
+      #   touch conftest.ts1; touch conftest.ts2; make
+      # should touch ts1 because ts2 is newer. This could happen by luck,
+      # but most often, it will fail if make's support is insufficient. So
+      # test for several consecutive successes.
+      #
+      # (We reuse conftest.ts[12] because we still want to modify existing
+      # files, not create new ones, per above.)
+      n=0
+      make=${MAKE-make}
+      until test $n -eq 3; do
+        echo one > conftest.ts1
+        sleep $am_try_res
+        echo two > conftest.ts2 # ts2 should now be newer than ts1
+        if $make -f conftest.mk | grep 'up to date' >/dev/null; then
+          make_ok=false
+          break # out of $n loop
+        fi
+        n=`expr $n + 1`
+      done
+    fi
+    #
+    if $make_ok; then
+      # Everything we know to check worked out, so call this resolution good.
+      am_cv_filesystem_timestamp_resolution=$am_try_res
+      break # out of $am_try_res loop
+    fi
+    # Otherwise, we'll go on to check the next resolution.
+  fi
+done
+rm -f conftest.ts?
+# (end _am_filesystem_timestamp_resolution)
+])])
+
 # AM_SANITY_CHECK
 # ---------------
 AC_DEFUN([AM_SANITY_CHECK],
-[AC_MSG_CHECKING([whether build environment is sane])
+[AC_REQUIRE([_AM_FILESYSTEM_TIMESTAMP_RESOLUTION])
+# This check should not be cached, as it may vary across builds of
+# different projects.
+AC_MSG_CHECKING([whether build environment is sane])
 # Reject unsafe characters in $srcdir or the absolute working directory
 # name.  Accept space and tab only in the latter.
 am_lf='
 '
 case `pwd` in
   *[[\\\"\#\$\&\'\`$am_lf]]*)
+    AC_MSG_RESULT([no])
     AC_MSG_ERROR([unsafe absolute working directory name]);;
 esac
 case $srcdir in
   *[[\\\"\#\$\&\'\`$am_lf\ \	]]*)
+    AC_MSG_RESULT([no])
     AC_MSG_ERROR([unsafe srcdir value: '$srcdir']);;
 esac
 
@@ -953,49 +1092,40 @@ esac
 # symlink; some systems play weird games with the mod time of symlinks
 # (eg FreeBSD returns the mod time of the symlink's containing
 # directory).
-if (
-   am_has_slept=no
-   for am_try in 1 2; do
-     echo "timestamp, slept: $am_has_slept" > conftest.file
-     set X `ls -Lt "$srcdir/configure" conftest.file 2> /dev/null`
-     if test "$[*]" = "X"; then
-	# -L didn't work.
-	set X `ls -t "$srcdir/configure" conftest.file`
-     fi
-     if test "$[*]" != "X $srcdir/configure conftest.file" \
-	&& test "$[*]" != "X conftest.file $srcdir/configure"; then
-
-	# If neither matched, then we have a broken ls.  This can happen
-	# if, for instance, CONFIG_SHELL is bash and it inherits a
-	# broken ls alias from the environment.  This has actually
-	# happened.  Such a system could not be considered "sane".
-	AC_MSG_ERROR([ls -t appears to fail.  Make sure there is not a broken
-  alias in your environment])
-     fi
-     if test "$[2]" = conftest.file || test $am_try -eq 2; then
-       break
-     fi
-     # Just in case.
-     sleep 1
-     am_has_slept=yes
-   done
-   test "$[2]" = conftest.file
-   )
-then
-   # Ok.
-   :
-else
-   AC_MSG_ERROR([newly created file is older than distributed files!
+am_build_env_is_sane=no
+am_has_slept=no
+rm -f conftest.file
+for am_try in 1 2; do
+  echo "timestamp, slept: $am_has_slept" > conftest.file
+  if (
+    set X `ls -Lt "$srcdir/configure" conftest.file 2> /dev/null`
+    if test "$[]*" = "X"; then
+      # -L didn't work.
+      set X `ls -t "$srcdir/configure" conftest.file`
+    fi
+    test "$[]2" = conftest.file
+  ); then
+    am_build_env_is_sane=yes
+    break
+  fi
+  # Just in case.
+  sleep "$am_cv_filesystem_timestamp_resolution"
+  am_has_slept=yes
+done
+
+AC_MSG_RESULT([$am_build_env_is_sane])
+if test "$am_build_env_is_sane" = no; then
+  AC_MSG_ERROR([newly created file is older than distributed files!
 Check your system clock])
 fi
-AC_MSG_RESULT([yes])
+
 # If we didn't sleep, we still need to ensure time stamps of config.status and
 # generated files are strictly newer.
 am_sleep_pid=
-if grep 'slept: no' conftest.file >/dev/null 2>&1; then
-  ( sleep 1 ) &
+AS_IF([test -e conftest.file || grep 'slept: no' conftest.file >/dev/null 2>&1],, [dnl
+  ( sleep "$am_cv_filesystem_timestamp_resolution" ) &
   am_sleep_pid=$!
-fi
+])
 AC_CONFIG_COMMANDS_PRE(
   [AC_MSG_CHECKING([that generated files are newer than configure])
    if test -n "$am_sleep_pid"; then
@@ -1006,18 +1136,18 @@ AC_CONFIG_COMMANDS_PRE(
 rm -f conftest.file
 ])
 
-# Copyright (C) 2009-2021 Free Software Foundation, Inc.
+# Copyright (C) 2009-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
 # with or without modifications, as long as this notice is preserved.
 
-# AM_SILENT_RULES([DEFAULT])
-# --------------------------
-# Enable less verbose build rules; with the default set to DEFAULT
-# ("yes" being less verbose, "no" or empty being verbose).
-AC_DEFUN([AM_SILENT_RULES],
-[AC_ARG_ENABLE([silent-rules], [dnl
+# _AM_SILENT_RULES
+# ----------------
+# Enable less verbose build rules support.
+AC_DEFUN([_AM_SILENT_RULES],
+[AM_DEFAULT_VERBOSITY=1
+AC_ARG_ENABLE([silent-rules], [dnl
 AS_HELP_STRING(
   [--enable-silent-rules],
   [less verbose build output (undo: "make V=1")])
@@ -1025,11 +1155,6 @@ AS_HELP_STRING(
   [--disable-silent-rules],
   [verbose build output (undo: "make V=0")])dnl
 ])
-case $enable_silent_rules in @%:@ (((
-  yes) AM_DEFAULT_VERBOSITY=0;;
-   no) AM_DEFAULT_VERBOSITY=1;;
-    *) AM_DEFAULT_VERBOSITY=m4_if([$1], [yes], [0], [1]);;
-esac
 dnl
 dnl A few 'make' implementations (e.g., NonStop OS and NextStep)
 dnl do not support nested variable expansions.
@@ -1048,14 +1173,6 @@ am__doit:
 else
   am_cv_make_support_nested_variables=no
 fi])
-if test $am_cv_make_support_nested_variables = yes; then
-  dnl Using '$V' instead of '$(V)' breaks IRIX make.
-  AM_V='$(V)'
-  AM_DEFAULT_V='$(AM_DEFAULT_VERBOSITY)'
-else
-  AM_V=$AM_DEFAULT_VERBOSITY
-  AM_DEFAULT_V=$AM_DEFAULT_VERBOSITY
-fi
 AC_SUBST([AM_V])dnl
 AM_SUBST_NOTMAKE([AM_V])dnl
 AC_SUBST([AM_DEFAULT_V])dnl
@@ -1064,9 +1181,37 @@ AC_SUBST([AM_DEFAULT_VERBOSITY])dnl
 AM_BACKSLASH='\'
 AC_SUBST([AM_BACKSLASH])dnl
 _AM_SUBST_NOTMAKE([AM_BACKSLASH])dnl
+dnl Delay evaluation of AM_DEFAULT_VERBOSITY to the end to allow multiple calls
+dnl to AM_SILENT_RULES to change the default value.
+AC_CONFIG_COMMANDS_PRE([dnl
+case $enable_silent_rules in @%:@ (((
+  yes) AM_DEFAULT_VERBOSITY=0;;
+   no) AM_DEFAULT_VERBOSITY=1;;
+esac
+if test $am_cv_make_support_nested_variables = yes; then
+  dnl Using '$V' instead of '$(V)' breaks IRIX make.
+  AM_V='$(V)'
+  AM_DEFAULT_V='$(AM_DEFAULT_VERBOSITY)'
+else
+  AM_V=$AM_DEFAULT_VERBOSITY
+  AM_DEFAULT_V=$AM_DEFAULT_VERBOSITY
+fi
+])dnl
 ])
 
-# Copyright (C) 2001-2021 Free Software Foundation, Inc.
+# AM_SILENT_RULES([DEFAULT])
+# --------------------------
+# Set the default verbosity level to DEFAULT ("yes" being less verbose, "no" or
+# empty being verbose).
+AC_DEFUN([AM_SILENT_RULES],
+[AC_REQUIRE([_AM_SILENT_RULES])
+AM_DEFAULT_VERBOSITY=m4_if([$1], [yes], [0], [1])m4_newline
+dnl We intentionally force a newline after the assignment, since a) nothing
+dnl good can come of more text following, and b) that was the behavior
+dnl before 1.17. See https://bugs.gnu.org/72267.
+])
+
+# Copyright (C) 2001-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -1094,7 +1239,7 @@ fi
 INSTALL_STRIP_PROGRAM="\$(install_sh) -c -s"
 AC_SUBST([INSTALL_STRIP_PROGRAM])])
 
-# Copyright (C) 2006-2021 Free Software Foundation, Inc.
+# Copyright (C) 2006-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -1113,7 +1258,7 @@ AC_DEFUN([AM_SUBST_NOTMAKE], [_AM_SUBST_NOTMAKE($@)])
 
 # Check how to create a tarball.                            -*- Autoconf -*-
 
-# Copyright (C) 2004-2021 Free Software Foundation, Inc.
+# Copyright (C) 2004-2025 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -1159,15 +1304,19 @@ m4_if([$1], [v7],
       am_uid=`id -u || echo unknown`
       am_gid=`id -g || echo unknown`
       AC_MSG_CHECKING([whether UID '$am_uid' is supported by ustar format])
-      if test $am_uid -le $am_max_uid; then
-         AC_MSG_RESULT([yes])
+      if test x$am_uid = xunknown; then
+        AC_MSG_WARN([ancient id detected; assuming current UID is ok, but dist-ustar might not work])
+      elif test $am_uid -le $am_max_uid; then
+        AC_MSG_RESULT([yes])
       else
-         AC_MSG_RESULT([no])
-         _am_tools=none
+        AC_MSG_RESULT([no])
+        _am_tools=none
       fi
       AC_MSG_CHECKING([whether GID '$am_gid' is supported by ustar format])
-      if test $am_gid -le $am_max_gid; then
-         AC_MSG_RESULT([yes])
+      if test x$gm_gid = xunknown; then
+        AC_MSG_WARN([ancient id detected; assuming current GID is ok, but dist-ustar might not work])
+      elif test $am_gid -le $am_max_gid; then
+        AC_MSG_RESULT([yes])
       else
         AC_MSG_RESULT([no])
         _am_tools=none
@@ -1244,6 +1393,26 @@ AC_SUBST([am__tar])
 AC_SUBST([am__untar])
 ]) # _AM_PROG_TAR
 
+# Copyright (C) 2022-2025 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# _AM_PROG_XARGS_N
+# ----------------
+# Check whether 'xargs -n' works.  It should work everywhere, so the fallback
+# is not optimized at all as we never expect to use it.
+AC_DEFUN([_AM_PROG_XARGS_N],
+[AC_CACHE_CHECK([xargs -n works], am_cv_xargs_n_works, [dnl
+AS_IF([test "`echo 1 2 3 | xargs -n2 echo`" = "1 2
+3"], [am_cv_xargs_n_works=yes], [am_cv_xargs_n_works=no])])
+AS_IF([test "$am_cv_xargs_n_works" = yes], [am__xargs_n='xargs -n'], [dnl
+  am__xargs_n='am__xargs_n () { shift; sed "s/ /\\n/g" | while read am__xargs_n_arg; do "$@" "$am__xargs_n_arg"; done; }'
+])dnl
+AC_SUBST(am__xargs_n)
+])
+
 m4_include([m4/libtool.m4])
 m4_include([m4/ltoptions.m4])
 m4_include([m4/ltsugar.m4])

+ 0 - 0
libs/expat/cmake/autotools/expat.cmake → libs/expat/cmake/autotools/expat__linux.cmake.in


+ 107 - 0
libs/expat/cmake/autotools/expat__macos.cmake.in

@@ -0,0 +1,107 @@
+# Generated by CMake
+
+if("${CMAKE_MAJOR_VERSION}.${CMAKE_MINOR_VERSION}" LESS 2.8)
+   message(FATAL_ERROR "CMake >= 2.8.12 required")
+endif()
+if(CMAKE_VERSION VERSION_LESS "2.8.12")
+   message(FATAL_ERROR "CMake >= 2.8.12 required")
+endif()
+cmake_policy(PUSH)
+cmake_policy(VERSION 2.8.12...3.31)
+#----------------------------------------------------------------
+# Generated CMake target import file.
+#----------------------------------------------------------------
+
+# Commands may need to know the format version.
+set(CMAKE_IMPORT_FILE_VERSION 1)
+
+# Protect against multiple inclusion, which would fail when already imported targets are added once more.
+set(_cmake_targets_defined "")
+set(_cmake_targets_not_defined "")
+set(_cmake_expected_targets "")
+foreach(_cmake_expected_target IN ITEMS expat::expat)
+  list(APPEND _cmake_expected_targets "${_cmake_expected_target}")
+  if(TARGET "${_cmake_expected_target}")
+    list(APPEND _cmake_targets_defined "${_cmake_expected_target}")
+  else()
+    list(APPEND _cmake_targets_not_defined "${_cmake_expected_target}")
+  endif()
+endforeach()
+unset(_cmake_expected_target)
+if(_cmake_targets_defined STREQUAL _cmake_expected_targets)
+  unset(_cmake_targets_defined)
+  unset(_cmake_targets_not_defined)
+  unset(_cmake_expected_targets)
+  unset(CMAKE_IMPORT_FILE_VERSION)
+  cmake_policy(POP)
+  return()
+endif()
+if(NOT _cmake_targets_defined STREQUAL "")
+  string(REPLACE ";" ", " _cmake_targets_defined_text "${_cmake_targets_defined}")
+  string(REPLACE ";" ", " _cmake_targets_not_defined_text "${_cmake_targets_not_defined}")
+  message(FATAL_ERROR "Some (but not all) targets in this export set were already defined.\nTargets Defined: ${_cmake_targets_defined_text}\nTargets not yet defined: ${_cmake_targets_not_defined_text}\n")
+endif()
+unset(_cmake_targets_defined)
+unset(_cmake_targets_not_defined)
+unset(_cmake_expected_targets)
+
+
+# Compute the installation prefix relative to this file.
+get_filename_component(_IMPORT_PREFIX "${CMAKE_CURRENT_LIST_FILE}" PATH)
+get_filename_component(_IMPORT_PREFIX "${_IMPORT_PREFIX}" PATH)
+get_filename_component(_IMPORT_PREFIX "${_IMPORT_PREFIX}" PATH)
+get_filename_component(_IMPORT_PREFIX "${_IMPORT_PREFIX}" PATH)
+if(_IMPORT_PREFIX STREQUAL "/")
+  set(_IMPORT_PREFIX "")
+endif()
+
+# Create imported target expat::expat
+add_library(expat::expat SHARED IMPORTED)
+
+set_target_properties(expat::expat PROPERTIES
+  INTERFACE_INCLUDE_DIRECTORIES "${_IMPORT_PREFIX}/include"
+  INTERFACE_LINK_LIBRARIES "m"
+)
+
+# Load information for each installed configuration.
+file(GLOB _cmake_config_files "${CMAKE_CURRENT_LIST_DIR}/expat-*.cmake")
+foreach(_cmake_config_file IN LISTS _cmake_config_files)
+  include("${_cmake_config_file}")
+endforeach()
+unset(_cmake_config_file)
+unset(_cmake_config_files)
+
+# Cleanup temporary variables.
+set(_IMPORT_PREFIX)
+
+# Loop over all imported files and verify that they actually exist
+foreach(_cmake_target IN LISTS _cmake_import_check_targets)
+  if(CMAKE_VERSION VERSION_LESS "3.28"
+      OR NOT DEFINED _cmake_import_check_xcframework_for_${_cmake_target}
+      OR NOT IS_DIRECTORY "${_cmake_import_check_xcframework_for_${_cmake_target}}")
+    foreach(_cmake_file IN LISTS "_cmake_import_check_files_for_${_cmake_target}")
+      if(NOT EXISTS "${_cmake_file}")
+        message(FATAL_ERROR "The imported target \"${_cmake_target}\" references the file
+   \"${_cmake_file}\"
+but this file does not exist.  Possible reasons include:
+* The file was deleted, renamed, or moved to another location.
+* An install or uninstall procedure did not complete successfully.
+* The installation package was faulty and contained
+   \"${CMAKE_CURRENT_LIST_FILE}\"
+but not all the files it references.
+")
+      endif()
+    endforeach()
+  endif()
+  unset(_cmake_file)
+  unset("_cmake_import_check_files_for_${_cmake_target}")
+endforeach()
+unset(_cmake_target)
+unset(_cmake_import_check_targets)
+
+# This file does not depend on other imported targets which have
+# been exported from the same project but in a separate export set.
+
+# Commands beyond this point should not need to know the version.
+set(CMAKE_IMPORT_FILE_VERSION)
+cmake_policy(POP)

+ 107 - 0
libs/expat/cmake/autotools/expat__windows.cmake.in

@@ -0,0 +1,107 @@
+# Generated by CMake
+
+if("${CMAKE_MAJOR_VERSION}.${CMAKE_MINOR_VERSION}" LESS 2.8)
+   message(FATAL_ERROR "CMake >= 2.8.12 required")
+endif()
+if(CMAKE_VERSION VERSION_LESS "2.8.12")
+   message(FATAL_ERROR "CMake >= 2.8.12 required")
+endif()
+cmake_policy(PUSH)
+cmake_policy(VERSION 2.8.12...3.29)
+#----------------------------------------------------------------
+# Generated CMake target import file.
+#----------------------------------------------------------------
+
+# Commands may need to know the format version.
+set(CMAKE_IMPORT_FILE_VERSION 1)
+
+# Protect against multiple inclusion, which would fail when already imported targets are added once more.
+set(_cmake_targets_defined "")
+set(_cmake_targets_not_defined "")
+set(_cmake_expected_targets "")
+foreach(_cmake_expected_target IN ITEMS expat::expat)
+  list(APPEND _cmake_expected_targets "${_cmake_expected_target}")
+  if(TARGET "${_cmake_expected_target}")
+    list(APPEND _cmake_targets_defined "${_cmake_expected_target}")
+  else()
+    list(APPEND _cmake_targets_not_defined "${_cmake_expected_target}")
+  endif()
+endforeach()
+unset(_cmake_expected_target)
+if(_cmake_targets_defined STREQUAL _cmake_expected_targets)
+  unset(_cmake_targets_defined)
+  unset(_cmake_targets_not_defined)
+  unset(_cmake_expected_targets)
+  unset(CMAKE_IMPORT_FILE_VERSION)
+  cmake_policy(POP)
+  return()
+endif()
+if(NOT _cmake_targets_defined STREQUAL "")
+  string(REPLACE ";" ", " _cmake_targets_defined_text "${_cmake_targets_defined}")
+  string(REPLACE ";" ", " _cmake_targets_not_defined_text "${_cmake_targets_not_defined}")
+  message(FATAL_ERROR "Some (but not all) targets in this export set were already defined.\nTargets Defined: ${_cmake_targets_defined_text}\nTargets not yet defined: ${_cmake_targets_not_defined_text}\n")
+endif()
+unset(_cmake_targets_defined)
+unset(_cmake_targets_not_defined)
+unset(_cmake_expected_targets)
+
+
+# Compute the installation prefix relative to this file.
+get_filename_component(_IMPORT_PREFIX "${CMAKE_CURRENT_LIST_FILE}" PATH)
+get_filename_component(_IMPORT_PREFIX "${_IMPORT_PREFIX}" PATH)
+get_filename_component(_IMPORT_PREFIX "${_IMPORT_PREFIX}" PATH)
+get_filename_component(_IMPORT_PREFIX "${_IMPORT_PREFIX}" PATH)
+if(_IMPORT_PREFIX STREQUAL "/")
+  set(_IMPORT_PREFIX "")
+endif()
+
+# Create imported target expat::expat
+add_library(expat::expat SHARED IMPORTED)
+
+set_target_properties(expat::expat PROPERTIES
+  INTERFACE_INCLUDE_DIRECTORIES "${_IMPORT_PREFIX}/include"
+  INTERFACE_LINK_LIBRARIES "m"
+)
+
+# Load information for each installed configuration.
+file(GLOB _cmake_config_files "${CMAKE_CURRENT_LIST_DIR}/expat-*.cmake")
+foreach(_cmake_config_file IN LISTS _cmake_config_files)
+  include("${_cmake_config_file}")
+endforeach()
+unset(_cmake_config_file)
+unset(_cmake_config_files)
+
+# Cleanup temporary variables.
+set(_IMPORT_PREFIX)
+
+# Loop over all imported files and verify that they actually exist
+foreach(_cmake_target IN LISTS _cmake_import_check_targets)
+  if(CMAKE_VERSION VERSION_LESS "3.28"
+      OR NOT DEFINED _cmake_import_check_xcframework_for_${_cmake_target}
+      OR NOT IS_DIRECTORY "${_cmake_import_check_xcframework_for_${_cmake_target}}")
+    foreach(_cmake_file IN LISTS "_cmake_import_check_files_for_${_cmake_target}")
+      if(NOT EXISTS "${_cmake_file}")
+        message(FATAL_ERROR "The imported target \"${_cmake_target}\" references the file
+   \"${_cmake_file}\"
+but this file does not exist.  Possible reasons include:
+* The file was deleted, renamed, or moved to another location.
+* An install or uninstall procedure did not complete successfully.
+* The installation package was faulty and contained
+   \"${CMAKE_CURRENT_LIST_FILE}\"
+but not all the files it references.
+")
+      endif()
+    endforeach()
+  endif()
+  unset(_cmake_file)
+  unset("_cmake_import_check_files_for_${_cmake_target}")
+endforeach()
+unset(_cmake_target)
+unset(_cmake_import_check_targets)
+
+# This file does not depend on other imported targets which have
+# been exported from the same project but in a separate export set.
+
+# Commands beyond this point should not need to know the version.
+set(CMAKE_IMPORT_FILE_VERSION)
+cmake_policy(POP)

文件差异内容过多而无法显示
+ 352 - 158
libs/expat/configure


+ 17 - 7
libs/expat/configure.ac

@@ -24,6 +24,7 @@ dnl   Copyright (c) 2019      Kishore Kunche <[email protected]>
 dnl   Copyright (c) 2020      Jeffrey Walton <[email protected]>
 dnl   Copyright (c) 2024      Ferenc Géczi <[email protected]>
 dnl   Copyright (c) 2024      Dag-Erling Smørgrav <[email protected]>
+dnl   Copyright (c) 2025      Matthew Fernandez <[email protected]>
 dnl   Licensed under the MIT license:
 dnl
 dnl   Permission is  hereby granted,  free of charge,  to any  person obtaining
@@ -84,9 +85,9 @@ dnl
 dnl If the API changes incompatibly set LIBAGE back to 0
 dnl
 
-LIBCURRENT=11  # sync
-LIBREVISION=2  # with
-LIBAGE=10      # CMakeLists.txt!
+LIBCURRENT=12  # sync
+LIBREVISION=1  # with
+LIBAGE=11      # CMakeLists.txt!
 
 AC_CONFIG_HEADERS([expat_config.h])
 AH_TOP([#ifndef EXPAT_CONFIG_H
@@ -95,7 +96,6 @@ AH_BOTTOM([#endif // ndef EXPAT_CONFIG_H])
 
 AM_PROG_AR
 AC_PROG_INSTALL
-AC_PROG_LN_S
 AC_PROG_MAKE_SET
 
 LT_PREREQ([2.4])
@@ -440,12 +440,22 @@ AC_MSG_RESULT([${CMAKE_SHARED_LIBRARY_PREFIX}])
 AC_SUBST([CMAKE_SHARED_LIBRARY_PREFIX])
 
 AS_CASE("${host_os}",
-  [darwin*], [CMAKE_NOCONFIG_SOURCE=cmake/autotools/expat-noconfig__macos.cmake.in],
-  [mingw*|cygwin*], [CMAKE_NOCONFIG_SOURCE=cmake/autotools/expat-noconfig__windows.cmake.in],
-  [CMAKE_NOCONFIG_SOURCE=cmake/autotools/expat-noconfig__linux.cmake.in])
+  [darwin*], [
+    CMAKE_SOURCE=cmake/autotools/expat__macos.cmake.in
+    CMAKE_NOCONFIG_SOURCE=cmake/autotools/expat-noconfig__macos.cmake.in
+  ],
+  [mingw*|cygwin*], [
+    CMAKE_SOURCE=cmake/autotools/expat__windows.cmake.in
+    CMAKE_NOCONFIG_SOURCE=cmake/autotools/expat-noconfig__windows.cmake.in
+  ],
+  [
+    CMAKE_SOURCE=cmake/autotools/expat__linux.cmake.in
+    CMAKE_NOCONFIG_SOURCE=cmake/autotools/expat-noconfig__linux.cmake.in
+  ])
 AC_CONFIG_FILES([Makefile]
   [expat.pc]
   [cmake/expat-config.cmake]
+  [cmake/autotools/expat.cmake:${CMAKE_SOURCE}]
   [cmake/autotools/expat-config-version.cmake]
   [cmake/autotools/expat-noconfig.cmake:${CMAKE_NOCONFIG_SOURCE}]
   [doc/Makefile]

+ 20 - 9
libs/expat/doc/Makefile.in

@@ -1,7 +1,7 @@
-# Makefile.in generated by automake 1.16.5 from Makefile.am.
+# Makefile.in generated by automake 1.18.1 from Makefile.am.
 # @configure_input@
 
-# Copyright (C) 1994-2021 Free Software Foundation, Inc.
+# Copyright (C) 1994-2025 Free Software Foundation, Inc.
 
 # This Makefile.in is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -102,6 +102,8 @@ am__make_running_with_option = \
   test $$has_opt = yes
 am__make_dryrun = (target_option=n; $(am__make_running_with_option))
 am__make_keepgoing = (target_option=k; $(am__make_running_with_option))
+am__rm_f = rm -f $(am__rm_f_notfound)
+am__rm_rf = rm -rf $(am__rm_f_notfound)
 pkgdatadir = $(datadir)/@PACKAGE@
 pkgincludedir = $(includedir)/@PACKAGE@
 pkglibdir = $(libdir)/@PACKAGE@
@@ -184,10 +186,9 @@ am__base_list = \
   sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \
   sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g'
 am__uninstall_files_from_dir = { \
-  test -z "$$files" \
-    || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \
-    || { echo " ( cd '$$dir' && rm -f" $$files ")"; \
-         $(am__cd) "$$dir" && rm -f $$files; }; \
+  { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \
+  || { echo " ( cd '$$dir' && rm -f" $$files ")"; \
+       $(am__cd) "$$dir" && echo $$files | $(am__xargs_n) 40 $(am__rm_f); }; \
   }
 man1dir = $(mandir)/man1
 am__installdirs = "$(DESTDIR)$(man1dir)"
@@ -303,8 +304,10 @@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@
 am__include = @am__include@
 am__leading_dot = @am__leading_dot@
 am__quote = @am__quote@
+am__rm_f_notfound = @am__rm_f_notfound@
 am__tar = @am__tar@
 am__untar = @am__untar@
+am__xargs_n = @am__xargs_n@
 bindir = @bindir@
 build = @build@
 build_alias = @build_alias@
@@ -442,6 +445,7 @@ ctags CTAGS:
 cscope cscopelist:
 
 @WITH_DISTRIBUTABLE_MANPAGE_TRUE@dist-hook:
+
 distdir: $(BUILT_SOURCES)
 	$(MAKE) $(AM_MAKEFLAGS) distdir-am
 
@@ -507,11 +511,11 @@ install-strip:
 mostlyclean-generic:
 
 clean-generic:
-	-test -z "$(CLEANFILES)" || rm -f $(CLEANFILES)
+	-$(am__rm_f) $(CLEANFILES)
 
 distclean-generic:
-	-test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
-	-test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES)
+	-$(am__rm_f) $(CONFIG_CLEAN_FILES)
+	-test . = "$(srcdir)" || $(am__rm_f) $(CONFIG_CLEAN_VPATH_FILES)
 
 maintainer-clean-generic:
 	@echo "This command is intended for maintainers to use"
@@ -616,3 +620,10 @@ uninstall-man: uninstall-man1
 # Tell versions [3.59,3.63) of GNU make to not export all variables.
 # Otherwise a system limit (for SysV at least) may be exceeded.
 .NOEXPORT:
+
+# Tell GNU make to disable its built-in pattern rules.
+%:: %,v
+%:: RCS/%,v
+%:: RCS/%
+%:: s.%
+%:: SCCS/s.%

+ 134 - 12
libs/expat/doc/reference.html

@@ -52,7 +52,7 @@
   <div>
     <h1>
       The Expat XML Parser
-      <small>Release 2.7.1</small>
+      <small>Release 2.7.3</small>
     </h1>
   </div>
 <div class="content">
@@ -157,6 +157,8 @@ interface.</p>
       <ul>
         <li><a href="#XML_SetBillionLaughsAttackProtectionMaximumAmplification">XML_SetBillionLaughsAttackProtectionMaximumAmplification</a></li>
         <li><a href="#XML_SetBillionLaughsAttackProtectionActivationThreshold">XML_SetBillionLaughsAttackProtectionActivationThreshold</a></li>
+        <li><a href="#XML_SetAllocTrackerMaximumAmplification">XML_SetAllocTrackerMaximumAmplification</a></li>
+        <li><a href="#XML_SetAllocTrackerActivationThreshold">XML_SetAllocTrackerActivationThreshold</a></li>
         <li><a href="#XML_SetReparseDeferralEnabled">XML_SetReparseDeferralEnabled</a></li>
       </ul>
     </li>
@@ -319,7 +321,7 @@ directions in the next section. Otherwise if you have Microsoft's
 Developer Studio installed,
 you can use CMake to generate a <code>.sln</code> file, e.g.
 <code>
-cmake -G"Visual Studio 16 2019" -DCMAKE_BUILD_TYPE=RelWithDebInfo .
+cmake -G"Visual Studio 17 2022" -DCMAKE_BUILD_TYPE=RelWithDebInfo .
 </code>, and build Expat using <code>msbuild /m expat.sln</code> after.</p>
 
 <p>Alternatively, you may download the Win32 binary package that
@@ -1905,7 +1907,7 @@ struct XML_cp {
 <p>Sets a handler for element declarations in a DTD. The handler gets
 called with the name of the element in the declaration and a pointer
 to a structure that contains the element model. It's the user code's 
-responsibility to free model when finished with it. See <code>
+responsibility to free model when finished with via a call to <code>
 <a href="#XML_FreeContentModel">XML_FreeContentModel</a></code>.
 There is no need to free the model from the handler, it can be kept
 around and freed at a later stage.</p>
@@ -2135,8 +2137,8 @@ XML_Size XMLCALL
 XML_GetCurrentColumnNumber(XML_Parser p);
 </pre>
 <div class="fcndef">
-Return the offset, from the beginning of the current line, of
-the position.
+Return the <em>offset</em>, from the beginning of the current line, of
+the position.  The first column is reported as <code>0</code>.
 </div>
 
 <h4 id="XML_GetCurrentByteCount">XML_GetCurrentByteCount</h4>
@@ -2198,13 +2200,16 @@ XML_SetBillionLaughsAttackProtectionMaximumAmplification(XML_Parser p,
     returns <code>XML_TRUE</code> upon success and <code>XML_FALSE</code> upon error.
   </p>
 
-  The amplification factor is calculated as ..
-  <pre>
-    amplification := (direct + indirect) / direct
-  </pre>
-  .. while parsing, whereas
-  <code>direct</code> is the number of bytes read from the primary document in parsing and
-  <code>indirect</code> is the number of bytes added by expanding entities and reading of external DTD files, combined.
+  <p>
+    Once the <a href="#XML_SetBillionLaughsAttackProtectionActivationThreshold">threshold for activation</a> is reached,
+    the amplification factor is calculated as ..
+  </p>
+  <pre>amplification := (direct + indirect) / direct</pre>
+  <p>
+    .. while parsing, whereas
+    <code>direct</code> is the number of bytes read from the primary document in parsing and
+    <code>indirect</code> is the number of bytes added by expanding entities and reading of external DTD files, combined.
+  </p>
 
   <p>For a call to <code>XML_SetBillionLaughsAttackProtectionMaximumAmplification</code> to succeed:</p>
   <ul>
@@ -2267,6 +2272,123 @@ XML_SetBillionLaughsAttackProtectionActivationThreshold(XML_Parser p,
   </p>
 </div>
 
+<h4 id="XML_SetAllocTrackerMaximumAmplification">XML_SetAllocTrackerMaximumAmplification</h4>
+<pre class="fcndec">
+/* Added in Expat 2.7.2. */
+XML_Bool
+XML_SetAllocTrackerMaximumAmplification(XML_Parser p,
+                                        float maximumAmplificationFactor);
+</pre>
+<div class="fcndef">
+  <p>
+    Sets the maximum tolerated amplification factor
+    between direct input and bytes of dynamic memory allocated
+    (default: <code>100.0</code>)
+    of parser <code>p</code> to <code>maximumAmplificationFactor</code>, and
+    returns <code>XML_TRUE</code> upon success and <code>XML_FALSE</code> upon error.
+  </p>
+
+  <p>
+    <strong>Note:</strong>
+    There are three types of allocations that intentionally bypass tracking and limiting:
+  </p>
+  <ul>
+    <li>
+      application calls to functions
+      <code><a href="#XML_MemMalloc">XML_MemMalloc</a></code>
+      and
+      <code><a href="#XML_MemRealloc">XML_MemRealloc</a></code>
+      &mdash;
+      <em>healthy</em> use of these two functions continues to be a responsibility
+      of the application using Expat
+      &mdash;,
+    </li>
+    <li>
+      the main character buffer used by functions
+      <code><a href="#XML_GetBuffer">XML_GetBuffer</a></code>
+      and
+      <code><a href="#XML_ParseBuffer">XML_ParseBuffer</a></code>
+      (and thus also by plain
+      <code><a href="#XML_Parse">XML_Parse</a></code>), and
+    </li>
+    <li>
+      the <a href="#XML_SetElementDeclHandler">content model memory</a>
+      (that is passed to the
+      <a href="#XML_SetElementDeclHandler">element declaration handler</a>
+      and freed by a call to
+      <code><a href="#XML_FreeContentModel">XML_FreeContentModel</a></code>).
+    </li>
+  </ul>
+
+  <p>
+    Once the <a href="#XML_SetAllocTrackerActivationThreshold">threshold for activation</a> is reached,
+    the amplification factor is calculated as ..
+  </p>
+  <pre>amplification := allocated / direct</pre>
+  <p>
+    .. while parsing, whereas
+    <code>direct</code> is the number of bytes read from the primary document in parsing and
+    <code>allocated</code> is the number of bytes of dynamic memory allocated in the parser hierarchy.
+  </p>
+
+  <p>For a call to <code>XML_SetAllocTrackerMaximumAmplification</code> to succeed:</p>
+  <ul>
+    <li>parser <code>p</code> must be a non-<code>NULL</code> root parser (without any parent parsers) and</li>
+    <li><code>maximumAmplificationFactor</code> must be non-<code>NaN</code> and greater than or equal to <code>1.0</code>.</li>
+  </ul>
+
+  <p>
+    <strong>Note:</strong>
+    If you ever need to increase this value for non-attack payload,
+    please <a href="https://github.com/libexpat/libexpat/issues">file a bug report</a>.
+  </p>
+
+  <p>
+    <strong>Note:</strong>
+    Amplifications factors greater than <code>100.0</code> can been observed near the start of parsing
+    even with benign files in practice.
+
+    So if you do reduce the maximum allowed amplification,
+    please make sure that the activation threshold is still big enough
+    to not end up with undesired false positives (i.e. benign files being rejected).
+  </p>
+</div>
+
+<h4 id="XML_SetAllocTrackerActivationThreshold">XML_SetAllocTrackerActivationThreshold</h4>
+<pre class="fcndec">
+/* Added in Expat 2.7.2. */
+XML_Bool
+XML_SetAllocTrackerActivationThreshold(XML_Parser p,
+                                       unsigned long long activationThresholdBytes);
+</pre>
+<div class="fcndef">
+  <p>
+    Sets number of allocated bytes of dynamic memory
+    needed to activate protection against disproportionate use of RAM
+    (default: <code>64 MiB</code>)
+    of parser <code>p</code> to <code>activationThresholdBytes</code>, and
+    returns <code>XML_TRUE</code> upon success and <code>XML_FALSE</code> upon error.
+  </p>
+
+  <p>
+    <strong>Note:</strong>
+    For types of allocations that intentionally bypass tracking and limiting, please see
+    <code><a href="#XML_SetAllocTrackerMaximumAmplification">XML_SetAllocTrackerMaximumAmplification</a></code>
+    above.
+  </p>
+
+  <p>For a call to <code>XML_SetAllocTrackerActivationThreshold</code> to succeed:</p>
+  <ul>
+    <li>parser <code>p</code> must be a non-<code>NULL</code> root parser (without any parent parsers).</li>
+  </ul>
+
+  <p>
+    <strong>Note:</strong>
+    If you ever need to increase this value for non-attack payload,
+    please <a href="https://github.com/libexpat/libexpat/issues">file a bug report</a>.
+  </p>
+</div>
+
 <h4 id="XML_SetReparseDeferralEnabled">XML_SetReparseDeferralEnabled</h4>
 <pre class="fcndec">
 /* Added in Expat 2.6.0. */

+ 23 - 7
libs/expat/doc/xmlwf.1

@@ -5,7 +5,7 @@
 \\$2 \(la\\$1\(ra\\$3
 ..
 .if \n(.g .mso www.tmac
-.TH XMLWF 1 "March 27, 2025" "" ""
+.TH XMLWF 1 "September 24, 2025" "" ""
 .SH NAME
 xmlwf \- Determines if an XML document is well-formed
 .SH SYNOPSIS
@@ -88,7 +88,11 @@ supports both.
 .TP 
 \*(T<\fB\-a\fR\*(T> \fIfactor\fR
 Sets the maximum tolerated amplification factor
-for protection against billion laughs attacks (default: 100.0).
+for protection against amplification attacks
+like the billion laughs attack
+(default: 100.0
+for the sum of direct and indirect output and also
+for allocations of dynamic memory).
 The amplification factor is calculated as ..
 
 .nf
@@ -97,12 +101,22 @@ The amplification factor is calculated as ..
           
 .fi
 
-\&.. while parsing, whereas
+\&.. with regard to use of entities and ..
+
+.nf
+
+            amplification := allocated / direct
+          
+.fi
+
+\&.. with regard to dynamic memory while parsing.
 <direct> is the number of bytes read
-from the primary document in parsing and
+from the primary document in parsing,
 <indirect> is the number of bytes
 added by expanding entities and reading of external DTD files,
-combined.
+combined, and
+<allocated> is the total number of bytes of dynamic memory
+allocated (and not freed) per hierarchy of parsers.
 
 \fINOTE\fR:
 If you ever need to increase this value for non-attack payload,
@@ -110,8 +124,10 @@ please file a bug report.
 .TP 
 \*(T<\fB\-b\fR\*(T> \fIbytes\fR
 Sets the number of output bytes (including amplification)
-needed to activate protection against billion laughs attacks
-(default: 8 MiB).
+needed to activate protection against amplification attacks
+like billion laughs
+(default: 8 MiB for the sum of direct and indirect output,
+and 64 MiB for allocations of dynamic memory).
 This can be thought of as an "activation threshold".
 
 \fINOTE\fR:

+ 21 - 7
libs/expat/doc/xmlwf.xml

@@ -21,7 +21,7 @@
           "http://www.oasis-open.org/docbook/xml/4.2/docbookx.dtd" [
   <!ENTITY dhfirstname "<firstname>Scott</firstname>">
   <!ENTITY dhsurname   "<surname>Bronson</surname>">
-  <!ENTITY dhdate      "<date>March 27, 2025</date>">
+  <!ENTITY dhdate      "<date>September 24, 2025</date>">
   <!-- Please adjust this^^ date whenever cutting a new release. -->
   <!ENTITY dhsection   "<manvolnum>1</manvolnum>">
   <!ENTITY dhemail     "<email>[email protected]</email>">
@@ -158,19 +158,31 @@ supports both.
         <listitem>
           <para>
             Sets the maximum tolerated amplification factor
-            for protection against billion laughs attacks (default: 100.0).
+            for protection against amplification attacks
+            like the billion laughs attack
+            (default: 100.0
+            for the sum of direct and indirect output and also
+            for allocations of dynamic memory).
             The amplification factor is calculated as ..
           </para>
           <literallayout>
             amplification := (direct + indirect) / direct
           </literallayout>
           <para>
-            .. while parsing, whereas
+            .. with regard to use of entities and ..
+          </para>
+          <literallayout>
+            amplification := allocated / direct
+          </literallayout>
+          <para>
+            .. with regard to dynamic memory while parsing.
             &lt;direct&gt; is the number of bytes read
-              from the primary document in parsing and
+              from the primary document in parsing,
             &lt;indirect&gt; is the number of bytes
               added by expanding entities and reading of external DTD files,
-              combined.
+              combined, and
+            &lt;allocated&gt; is the total number of bytes of dynamic memory
+              allocated (and not freed) per hierarchy of parsers.
           </para>
           <para>
             <emphasis>NOTE</emphasis>:
@@ -185,8 +197,10 @@ supports both.
         <listitem>
           <para>
             Sets the number of output bytes (including amplification)
-            needed to activate protection against billion laughs attacks
-            (default: 8 MiB).
+            needed to activate protection against amplification attacks
+            like billion laughs
+            (default: 8 MiB for the sum of direct and indirect output,
+            and 64 MiB for allocations of dynamic memory).
             This can be thought of as an &quot;activation threshold&quot;.
           </para>
           <para>

+ 21 - 14
libs/expat/examples/Makefile.in

@@ -1,7 +1,7 @@
-# Makefile.in generated by automake 1.16.5 from Makefile.am.
+# Makefile.in generated by automake 1.18.1 from Makefile.am.
 # @configure_input@
 
-# Copyright (C) 1994-2021 Free Software Foundation, Inc.
+# Copyright (C) 1994-2025 Free Software Foundation, Inc.
 
 # This Makefile.in is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -101,6 +101,8 @@ am__make_running_with_option = \
   test $$has_opt = yes
 am__make_dryrun = (target_option=n; $(am__make_running_with_option))
 am__make_keepgoing = (target_option=k; $(am__make_running_with_option))
+am__rm_f = rm -f $(am__rm_f_notfound)
+am__rm_rf = rm -rf $(am__rm_f_notfound)
 pkgdatadir = $(datadir)/@PACKAGE@
 pkgincludedir = $(includedir)/@PACKAGE@
 pkglibdir = $(libdir)/@PACKAGE@
@@ -330,8 +332,10 @@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@
 am__include = @am__include@
 am__leading_dot = @am__leading_dot@
 am__quote = @am__quote@
+am__rm_f_notfound = @am__rm_f_notfound@
 am__tar = @am__tar@
 am__untar = @am__untar@
+am__xargs_n = @am__xargs_n@
 bindir = @bindir@
 build = @build@
 build_alias = @build_alias@
@@ -414,13 +418,8 @@ $(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps)
 $(am__aclocal_m4_deps):
 
 clean-noinstPROGRAMS:
-	@list='$(noinst_PROGRAMS)'; test -n "$$list" || exit 0; \
-	echo " rm -f" $$list; \
-	rm -f $$list || exit $$?; \
-	test -n "$(EXEEXT)" || exit 0; \
-	list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \
-	echo " rm -f" $$list; \
-	rm -f $$list
+	$(am__rm_f) $(noinst_PROGRAMS)
+	test -z "$(EXEEXT)" || $(am__rm_f) $(noinst_PROGRAMS:$(EXEEXT)=)
 
 element_declarations$(EXEEXT): $(element_declarations_OBJECTS) $(element_declarations_DEPENDENCIES) $(EXTRA_element_declarations_DEPENDENCIES) 
 	@rm -f element_declarations$(EXEEXT)
@@ -446,7 +445,7 @@ distclean-compile:
 
 $(am__depfiles_remade):
 	@$(MKDIR_P) $(@D)
-	@echo '# dummy' >$@-t && $(am__mv) $@-t $@
+	@: >>$@
 
 am--depfiles: $(am__depfiles_remade)
 
@@ -528,6 +527,7 @@ cscopelist-am: $(am__tagged_files)
 
 distclean-tags:
 	-rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags
+
 distdir: $(BUILT_SOURCES)
 	$(MAKE) $(AM_MAKEFLAGS) distdir-am
 
@@ -589,8 +589,8 @@ mostlyclean-generic:
 clean-generic:
 
 distclean-generic:
-	-test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
-	-test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES)
+	-$(am__rm_f) $(CONFIG_CLEAN_FILES)
+	-test . = "$(srcdir)" || $(am__rm_f) $(CONFIG_CLEAN_VPATH_FILES)
 
 maintainer-clean-generic:
 	@echo "This command is intended for maintainers to use"
@@ -601,7 +601,7 @@ clean-am: clean-generic clean-libtool clean-noinstPROGRAMS \
 	mostlyclean-am
 
 distclean: distclean-am
-		-rm -f ./$(DEPDIR)/element_declarations.Po
+	-rm -f ./$(DEPDIR)/element_declarations.Po
 	-rm -f ./$(DEPDIR)/elements.Po
 	-rm -f ./$(DEPDIR)/outline.Po
 	-rm -f Makefile
@@ -649,7 +649,7 @@ install-ps-am:
 installcheck-am:
 
 maintainer-clean: maintainer-clean-am
-		-rm -f ./$(DEPDIR)/element_declarations.Po
+	-rm -f ./$(DEPDIR)/element_declarations.Po
 	-rm -f ./$(DEPDIR)/elements.Po
 	-rm -f ./$(DEPDIR)/outline.Po
 	-rm -f Makefile
@@ -692,3 +692,10 @@ uninstall-am:
 # Tell versions [3.59,3.63) of GNU make to not export all variables.
 # Otherwise a system limit (for SysV at least) may be exceeded.
 .NOEXPORT:
+
+# Tell GNU make to disable its built-in pattern rules.
+%:: %,v
+%:: RCS/%,v
+%:: RCS/%
+%:: s.%
+%:: SCCS/s.%

+ 9 - 9
libs/expat/expat_config.h

@@ -26,7 +26,7 @@
 /* Define to 1 if you have the <fcntl.h> header file. */
 #define HAVE_FCNTL_H 1
 
-/* Define to 1 if you have the `getpagesize' function. */
+/* Define to 1 if you have the 'getpagesize' function. */
 #define HAVE_GETPAGESIZE 1
 
 /* Define to 1 if you have the `getrandom' function. */
@@ -35,10 +35,10 @@
 /* Define to 1 if you have the <inttypes.h> header file. */
 #define HAVE_INTTYPES_H 1
 
-/* Define to 1 if you have the `bsd' library (-lbsd). */
+/* Define to 1 if you have the 'bsd' library (-lbsd). */
 /* #undef HAVE_LIBBSD */
 
-/* Define to 1 if you have a working `mmap' system call. */
+/* Define to 1 if you have a working 'mmap' system call. */
 #define HAVE_MMAP 1
 
 /* Define to 1 if you have the <stdint.h> header file. */
@@ -84,7 +84,7 @@
 #define PACKAGE_NAME "expat"
 
 /* Define to the full name and version of this package. */
-#define PACKAGE_STRING "expat 2.7.1"
+#define PACKAGE_STRING "expat 2.7.3"
 
 /* Define to the one symbol short name of this package. */
 #define PACKAGE_TARNAME "expat"
@@ -93,15 +93,15 @@
 #define PACKAGE_URL ""
 
 /* Define to the version of this package. */
-#define PACKAGE_VERSION "2.7.1"
+#define PACKAGE_VERSION "2.7.3"
 
-/* Define to 1 if all of the C90 standard headers exist (not just the ones
+/* Define to 1 if all of the C89 standard headers exist (not just the ones
    required in a freestanding environment). This macro is provided for
    backward compatibility; new code need not use it. */
 #define STDC_HEADERS 1
 
 /* Version number of package */
-#define VERSION "2.7.1"
+#define VERSION "2.7.3"
 
 /* Define WORDS_BIGENDIAN to 1 if your processor stores words with the most
    significant byte first (like Motorola and SPARC, unlike Intel). */
@@ -135,10 +135,10 @@
 /* Define to make XML Namespaces functionality available. */
 #define XML_NS 1
 
-/* Define to empty if `const' does not conform to ANSI C. */
+/* Define to empty if 'const' does not conform to ANSI C. */
 /* #undef const */
 
-/* Define to `long int' if <sys/types.h> does not define. */
+/* Define to 'long int' if <sys/types.h> does not define. */
 /* #undef off_t */
 
 #endif // ndef EXPAT_CONFIG_H

+ 12 - 12
libs/expat/expat_config.h.cmake

@@ -1,7 +1,7 @@
 /* expat_config.h.cmake.  Based upon generated expat_config.h.in.  */
 
 #ifndef EXPAT_CONFIG_H
-#define EXPAT_CONFIG_H 1
+#  define EXPAT_CONFIG_H 1
 
 /* 1234 = LIL_ENDIAN, 4321 = BIGENDIAN */
 #cmakedefine BYTEORDER @BYTEORDER@
@@ -61,7 +61,7 @@
 #cmakedefine HAVE_UNISTD_H
 
 /* Name of package */
-#define PACKAGE "@PACKAGE_NAME@"
+#  define PACKAGE "@PACKAGE_NAME@"
 
 /* Define to the address where bug reports for this package should be sent. */
 #cmakedefine PACKAGE_BUGREPORT "@PACKAGE_BUGREPORT@"
@@ -76,15 +76,15 @@
 #cmakedefine PACKAGE_TARNAME "@PACKAGE_TARNAME@"
 
 /* Define to the home page for this package. */
-#define PACKAGE_URL ""
+#  define PACKAGE_URL ""
 
 /* Define to the version of this package. */
 #cmakedefine PACKAGE_VERSION "@PACKAGE_VERSION@"
 
 /* Define to 1 if you have the ANSI C header files. */
-#ifndef STDC_HEADERS
+#  ifndef STDC_HEADERS
 #cmakedefine STDC_HEADERS
-#endif
+#  endif
 
 /* whether byteorder is bigendian */
 #cmakedefine WORDS_BIGENDIAN
@@ -95,26 +95,26 @@
 
 /* Define to specify how much context to retain around the current parse
    point, 0 to disable. */
-#define XML_CONTEXT_BYTES @XML_CONTEXT_BYTES@
+#  define XML_CONTEXT_BYTES @XML_CONTEXT_BYTES@
 
-#if ! defined(_WIN32)
+#  if ! defined(_WIN32)
 /* Define to include code reading entropy from `/dev/urandom'. */
 #cmakedefine XML_DEV_URANDOM
-#endif
+#  endif
 
 /* Define to make parameter entity parsing functionality available. */
 #cmakedefine XML_DTD
 
 /* Define as 1/0 to enable/disable support for general entities. */
-#define XML_GE @XML_GE@
+#  define XML_GE @XML_GE@
 
 /* Define to make XML Namespaces functionality available. */
 #cmakedefine XML_NS
 
 /* Define to __FUNCTION__ or "" if `__func__' does not conform to ANSI C. */
-#ifdef _MSC_VER
-#  define __func__ __FUNCTION__
-#endif
+#  ifdef _MSC_VER
+#    define __func__ __FUNCTION__
+#  endif
 
 /* Define to `long' if <sys/types.h> does not define. */
 #cmakedefine off_t @off_t@

+ 6 - 6
libs/expat/expat_config.h.in

@@ -24,7 +24,7 @@
 /* Define to 1 if you have the <fcntl.h> header file. */
 #undef HAVE_FCNTL_H
 
-/* Define to 1 if you have the `getpagesize' function. */
+/* Define to 1 if you have the 'getpagesize' function. */
 #undef HAVE_GETPAGESIZE
 
 /* Define to 1 if you have the `getrandom' function. */
@@ -33,10 +33,10 @@
 /* Define to 1 if you have the <inttypes.h> header file. */
 #undef HAVE_INTTYPES_H
 
-/* Define to 1 if you have the `bsd' library (-lbsd). */
+/* Define to 1 if you have the 'bsd' library (-lbsd). */
 #undef HAVE_LIBBSD
 
-/* Define to 1 if you have a working `mmap' system call. */
+/* Define to 1 if you have a working 'mmap' system call. */
 #undef HAVE_MMAP
 
 /* Define to 1 if you have the <stdint.h> header file. */
@@ -93,7 +93,7 @@
 /* Define to the version of this package. */
 #undef PACKAGE_VERSION
 
-/* Define to 1 if all of the C90 standard headers exist (not just the ones
+/* Define to 1 if all of the C89 standard headers exist (not just the ones
    required in a freestanding environment). This macro is provided for
    backward compatibility; new code need not use it. */
 #undef STDC_HEADERS
@@ -133,10 +133,10 @@
 /* Define to make XML Namespaces functionality available. */
 #undef XML_NS
 
-/* Define to empty if `const' does not conform to ANSI C. */
+/* Define to empty if 'const' does not conform to ANSI C. */
 #undef const
 
-/* Define to `long int' if <sys/types.h> does not define. */
+/* Define to 'long int' if <sys/types.h> does not define. */
 #undef off_t
 
 #endif // ndef EXPAT_CONFIG_H

+ 4 - 2
libs/expat/fuzz/xml_lpm_fuzzer.cpp

@@ -354,8 +354,10 @@ ExternalEntityRefHandler(XML_Parser parser, const XML_Char *context,
   if (g_external_entity) {
     XML_Parser ext_parser
         = XML_ExternalEntityParserCreate(parser, context, g_encoding);
-    rc = Parse(ext_parser, g_external_entity, g_external_entity_size, 1);
-    XML_ParserFree(ext_parser);
+    if (ext_parser != NULL) {
+      rc = Parse(ext_parser, g_external_entity, g_external_entity_size, 1);
+      XML_ParserFree(ext_parser);
+    }
   }
 
   return rc;

+ 12 - 8
libs/expat/fuzz/xml_parse_fuzzer.c

@@ -15,6 +15,7 @@
  */
 
 #include <assert.h>
+#include <limits.h> // for INT_MAX
 #include <stdint.h>
 
 #include "expat.h"
@@ -65,8 +66,9 @@ ParseOneInput(XML_Parser p, const uint8_t *data, size_t size) {
   XML_SetUserData(p, p);
   XML_SetElementHandler(p, start, end);
   XML_SetCharacterDataHandler(p, may_stop_character_handler);
-  XML_Parse(p, (const XML_Char *)data, size, 0);
-  if (XML_Parse(p, (const XML_Char *)data, size, 1) == XML_STATUS_ERROR) {
+  assert(size <= INT_MAX);
+  XML_Parse(p, (const XML_Char *)data, (int)size, 0);
+  if (XML_Parse(p, (const XML_Char *)data, (int)size, 1) == XML_STATUS_ERROR) {
     XML_ErrorString(XML_GetErrorCode(p));
   }
   XML_GetCurrentLineNumber(p);
@@ -89,15 +91,17 @@ LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) {
 
   XML_Parser externalEntityParser
       = XML_ExternalEntityParserCreate(parentParser, "e1", NULL);
-  assert(externalEntityParser);
-  ParseOneInput(externalEntityParser, data, size);
-  XML_ParserFree(externalEntityParser);
+  if (externalEntityParser != NULL) {
+    ParseOneInput(externalEntityParser, data, size);
+    XML_ParserFree(externalEntityParser);
+  }
 
   XML_Parser externalDtdParser
       = XML_ExternalEntityParserCreate(parentParser, NULL, NULL);
-  assert(externalDtdParser);
-  ParseOneInput(externalDtdParser, data, size);
-  XML_ParserFree(externalDtdParser);
+  if (externalDtdParser != NULL) {
+    ParseOneInput(externalDtdParser, data, size);
+    XML_ParserFree(externalDtdParser);
+  }
 
   // finally frees this parser which served as parent
   XML_ParserFree(parentParser);

+ 14 - 10
libs/expat/fuzz/xml_parsebuffer_fuzzer.c

@@ -15,6 +15,7 @@
  */
 
 #include <assert.h>
+#include <limits.h> // for INT_MAX
 #include <stdint.h>
 #include <string.h>
 
@@ -66,16 +67,17 @@ ParseOneInput(XML_Parser p, const uint8_t *data, size_t size) {
   XML_SetUserData(p, p);
   XML_SetElementHandler(p, start, end);
   XML_SetCharacterDataHandler(p, may_stop_character_handler);
-  void *buf = XML_GetBuffer(p, size);
+  assert(size <= INT_MAX);
+  void *buf = XML_GetBuffer(p, (int)size);
   assert(buf);
   memcpy(buf, data, size);
-  XML_ParseBuffer(p, size, 0);
-  buf = XML_GetBuffer(p, size);
+  XML_ParseBuffer(p, (int)size, 0);
+  buf = XML_GetBuffer(p, (int)size);
   if (buf == NULL) {
     return;
   }
   memcpy(buf, data, size);
-  if (XML_ParseBuffer(p, size, 1) == XML_STATUS_ERROR) {
+  if (XML_ParseBuffer(p, (int)size, 1) == XML_STATUS_ERROR) {
     XML_ErrorString(XML_GetErrorCode(p));
   }
   XML_GetCurrentLineNumber(p);
@@ -101,15 +103,17 @@ LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) {
 
   XML_Parser externalEntityParser
       = XML_ExternalEntityParserCreate(parentParser, "e1", NULL);
-  assert(externalEntityParser);
-  ParseOneInput(externalEntityParser, data, size);
-  XML_ParserFree(externalEntityParser);
+  if (externalEntityParser != NULL) {
+    ParseOneInput(externalEntityParser, data, size);
+    XML_ParserFree(externalEntityParser);
+  }
 
   XML_Parser externalDtdParser
       = XML_ExternalEntityParserCreate(parentParser, NULL, NULL);
-  assert(externalDtdParser);
-  ParseOneInput(externalDtdParser, data, size);
-  XML_ParserFree(externalDtdParser);
+  if (externalDtdParser != NULL) {
+    ParseOneInput(externalDtdParser, data, size);
+    XML_ParserFree(externalDtdParser);
+  }
 
   // finally frees this parser which served as parent
   XML_ParserFree(parentParser);

+ 28 - 21
libs/expat/lib/Makefile.in

@@ -1,7 +1,7 @@
-# Makefile.in generated by automake 1.16.5 from Makefile.am.
+# Makefile.in generated by automake 1.18.1 from Makefile.am.
 # @configure_input@
 
-# Copyright (C) 1994-2021 Free Software Foundation, Inc.
+# Copyright (C) 1994-2025 Free Software Foundation, Inc.
 
 # This Makefile.in is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -104,6 +104,8 @@ am__make_running_with_option = \
   test $$has_opt = yes
 am__make_dryrun = (target_option=n; $(am__make_running_with_option))
 am__make_keepgoing = (target_option=k; $(am__make_running_with_option))
+am__rm_f = rm -f $(am__rm_f_notfound)
+am__rm_rf = rm -rf $(am__rm_f_notfound)
 pkgdatadir = $(datadir)/@PACKAGE@
 pkgincludedir = $(includedir)/@PACKAGE@
 pkglibdir = $(libdir)/@PACKAGE@
@@ -168,10 +170,9 @@ am__base_list = \
   sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \
   sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g'
 am__uninstall_files_from_dir = { \
-  test -z "$$files" \
-    || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \
-    || { echo " ( cd '$$dir' && rm -f" $$files ")"; \
-         $(am__cd) "$$dir" && rm -f $$files; }; \
+  { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \
+  || { echo " ( cd '$$dir' && rm -f" $$files ")"; \
+       $(am__cd) "$$dir" && echo $$files | $(am__xargs_n) 40 $(am__rm_f); }; \
   }
 am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(docdir)" \
 	"$(DESTDIR)$(includedir)"
@@ -368,8 +369,10 @@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@
 am__include = @am__include@
 am__leading_dot = @am__leading_dot@
 am__quote = @am__quote@
+am__rm_f_notfound = @am__rm_f_notfound@
 am__tar = @am__tar@
 am__untar = @am__untar@
+am__xargs_n = @am__xargs_n@
 bindir = @bindir@
 build = @build@
 build_alias = @build_alias@
@@ -513,26 +516,22 @@ uninstall-libLTLIBRARIES:
 	done
 
 clean-libLTLIBRARIES:
-	-test -z "$(lib_LTLIBRARIES)" || rm -f $(lib_LTLIBRARIES)
+	-$(am__rm_f) $(lib_LTLIBRARIES)
 	@list='$(lib_LTLIBRARIES)'; \
 	locs=`for p in $$list; do echo $$p; done | \
 	      sed 's|^[^/]*$$|.|; s|/[^/]*$$||; s|$$|/so_locations|' | \
 	      sort -u`; \
-	test -z "$$locs" || { \
-	  echo rm -f $${locs}; \
-	  rm -f $${locs}; \
-	}
+	echo rm -f $${locs}; \
+	$(am__rm_f) $${locs}
 
 clean-noinstLTLIBRARIES:
-	-test -z "$(noinst_LTLIBRARIES)" || rm -f $(noinst_LTLIBRARIES)
+	-$(am__rm_f) $(noinst_LTLIBRARIES)
 	@list='$(noinst_LTLIBRARIES)'; \
 	locs=`for p in $$list; do echo $$p; done | \
 	      sed 's|^[^/]*$$|.|; s|/[^/]*$$||; s|$$|/so_locations|' | \
 	      sort -u`; \
-	test -z "$$locs" || { \
-	  echo rm -f $${locs}; \
-	  rm -f $${locs}; \
-	}
+	echo rm -f $${locs}; \
+	$(am__rm_f) $${locs}
 
 libexpat.la: $(libexpat_la_OBJECTS) $(libexpat_la_DEPENDENCIES) $(EXTRA_libexpat_la_DEPENDENCIES) 
 	$(AM_V_CCLD)$(libexpat_la_LINK) -rpath $(libdir) $(libexpat_la_OBJECTS) $(libexpat_la_LIBADD) $(LIBS)
@@ -555,7 +554,7 @@ distclean-compile:
 
 $(am__depfiles_remade):
 	@$(MKDIR_P) $(@D)
-	@echo '# dummy' >$@-t && $(am__mv) $@-t $@
+	@: >>$@
 
 am--depfiles: $(am__depfiles_remade)
 
@@ -700,6 +699,7 @@ cscopelist-am: $(am__tagged_files)
 
 distclean-tags:
 	-rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags
+
 distdir: $(BUILT_SOURCES)
 	$(MAKE) $(AM_MAKEFLAGS) distdir-am
 
@@ -764,8 +764,8 @@ mostlyclean-generic:
 clean-generic:
 
 distclean-generic:
-	-test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
-	-test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES)
+	-$(am__rm_f) $(CONFIG_CLEAN_FILES)
+	-test . = "$(srcdir)" || $(am__rm_f) $(CONFIG_CLEAN_VPATH_FILES)
 
 maintainer-clean-generic:
 	@echo "This command is intended for maintainers to use"
@@ -776,7 +776,7 @@ clean-am: clean-generic clean-libLTLIBRARIES clean-libtool \
 	clean-noinstLTLIBRARIES mostlyclean-am
 
 distclean: distclean-am
-		-rm -f ./$(DEPDIR)/libtestpat_la-xmlparse.Plo
+	-rm -f ./$(DEPDIR)/libtestpat_la-xmlparse.Plo
 	-rm -f ./$(DEPDIR)/libtestpat_la-xmlrole.Plo
 	-rm -f ./$(DEPDIR)/libtestpat_la-xmltok.Plo
 	-rm -f ./$(DEPDIR)/xmlparse.Plo
@@ -828,7 +828,7 @@ install-ps-am:
 installcheck-am:
 
 maintainer-clean: maintainer-clean-am
-		-rm -f ./$(DEPDIR)/libtestpat_la-xmlparse.Plo
+	-rm -f ./$(DEPDIR)/libtestpat_la-xmlparse.Plo
 	-rm -f ./$(DEPDIR)/libtestpat_la-xmlrole.Plo
 	-rm -f ./$(DEPDIR)/libtestpat_la-xmltok.Plo
 	-rm -f ./$(DEPDIR)/xmlparse.Plo
@@ -885,3 +885,10 @@ uninstall-local:
 # Tell versions [3.59,3.63) of GNU make to not export all variables.
 # Otherwise a system limit (for SysV at least) may be exceeded.
 .NOEXPORT:
+
+# Tell GNU make to disable its built-in pattern rules.
+%:: %,v
+%:: RCS/%,v
+%:: RCS/%
+%:: s.%
+%:: SCCS/s.%

+ 39 - 25
libs/expat/lib/expat.h

@@ -19,6 +19,7 @@
    Copyright (c) 2023      Hanno Böck <[email protected]>
    Copyright (c) 2023      Sony Corporation / Snild Dolkow <[email protected]>
    Copyright (c) 2024      Taichi Haradaguchi <[email protected]>
+   Copyright (c) 2025      Matthew Fernandez <[email protected]>
    Licensed under the MIT license:
 
    Permission is  hereby granted,  free of charge,  to any  person obtaining
@@ -42,21 +43,21 @@
 */
 
 #ifndef Expat_INCLUDED
-#define Expat_INCLUDED 1
+#  define Expat_INCLUDED 1
 
-#include <stdlib.h>
-#include "expat_external.h"
+#  include <stdlib.h>
+#  include "expat_external.h"
 
-#ifdef __cplusplus
+#  ifdef __cplusplus
 extern "C" {
-#endif
+#  endif
 
 struct XML_ParserStruct;
 typedef struct XML_ParserStruct *XML_Parser;
 
 typedef unsigned char XML_Bool;
-#define XML_TRUE ((XML_Bool)1)
-#define XML_FALSE ((XML_Bool)0)
+#  define XML_TRUE ((XML_Bool)1)
+#  define XML_FALSE ((XML_Bool)0)
 
 /* The XML_Status enum gives the possible return values for several
    API functions.  The preprocessor #defines are included so this
@@ -73,11 +74,11 @@ typedef unsigned char XML_Bool;
 */
 enum XML_Status {
   XML_STATUS_ERROR = 0,
-#define XML_STATUS_ERROR XML_STATUS_ERROR
+#  define XML_STATUS_ERROR XML_STATUS_ERROR
   XML_STATUS_OK = 1,
-#define XML_STATUS_OK XML_STATUS_OK
+#  define XML_STATUS_OK XML_STATUS_OK
   XML_STATUS_SUSPENDED = 2
-#define XML_STATUS_SUSPENDED XML_STATUS_SUSPENDED
+#  define XML_STATUS_SUSPENDED XML_STATUS_SUSPENDED
 };
 
 enum XML_Error {
@@ -276,7 +277,7 @@ XML_ParserCreate_MM(const XML_Char *encoding,
 
 /* Prepare a parser object to be reused.  This is particularly
    valuable when memory allocation overhead is disproportionately high,
-   such as when a large number of small documnents need to be parsed.
+   such as when a large number of small documents need to be parsed.
    All handlers are cleared from the parser, except for the
    unknownEncodingHandler. The parser's external state is re-initialized
    except for the values of ns and ns_triplets.
@@ -680,7 +681,7 @@ XMLPARSEAPI(void)
 XML_SetUserData(XML_Parser parser, void *userData);
 
 /* Returns the last value set by XML_SetUserData or NULL. */
-#define XML_GetUserData(parser) (*(void **)(parser))
+#  define XML_GetUserData(parser) (*(void **)(parser))
 
 /* This is equivalent to supplying an encoding argument to
    XML_ParserCreate. On success XML_SetEncoding returns non-zero,
@@ -752,7 +753,7 @@ XML_GetSpecifiedAttributeCount(XML_Parser parser);
 XMLPARSEAPI(int)
 XML_GetIdAttributeIndex(XML_Parser parser);
 
-#ifdef XML_ATTR_INFO
+#  ifdef XML_ATTR_INFO
 /* Source file byte offsets for the start and end of attribute names and values.
    The value indices are exclusive of surrounding quotes; thus in a UTF-8 source
    file an attribute value of "blah" will yield:
@@ -773,7 +774,7 @@ typedef struct {
 */
 XMLPARSEAPI(const XML_AttrInfo *)
 XML_GetAttributeInfo(XML_Parser parser);
-#endif
+#  endif
 
 /* Parses some input. Returns XML_STATUS_ERROR if a fatal error is
    detected.  The last call to XML_Parse must have isFinal true; len
@@ -970,9 +971,9 @@ XMLPARSEAPI(const char *)
 XML_GetInputContext(XML_Parser parser, int *offset, int *size);
 
 /* For backwards compatibility with previous versions. */
-#define XML_GetErrorLineNumber XML_GetCurrentLineNumber
-#define XML_GetErrorColumnNumber XML_GetCurrentColumnNumber
-#define XML_GetErrorByteIndex XML_GetCurrentByteIndex
+#  define XML_GetErrorLineNumber XML_GetCurrentLineNumber
+#  define XML_GetErrorColumnNumber XML_GetCurrentColumnNumber
+#  define XML_GetErrorByteIndex XML_GetCurrentByteIndex
 
 /* Frees the content model passed to the element declaration handler */
 XMLPARSEAPI(void)
@@ -1032,7 +1033,10 @@ enum XML_FeatureEnum {
   XML_FEATURE_BILLION_LAUGHS_ATTACK_PROTECTION_MAXIMUM_AMPLIFICATION_DEFAULT,
   XML_FEATURE_BILLION_LAUGHS_ATTACK_PROTECTION_ACTIVATION_THRESHOLD_DEFAULT,
   /* Added in Expat 2.6.0. */
-  XML_FEATURE_GE
+  XML_FEATURE_GE,
+  /* Added in Expat 2.7.2. */
+  XML_FEATURE_ALLOC_TRACKER_MAXIMUM_AMPLIFICATION_DEFAULT,
+  XML_FEATURE_ALLOC_TRACKER_ACTIVATION_THRESHOLD_DEFAULT,
   /* Additional features must be added to the end of this enum. */
 };
 
@@ -1045,7 +1049,7 @@ typedef struct {
 XMLPARSEAPI(const XML_Feature *)
 XML_GetFeatureList(void);
 
-#if defined(XML_DTD) || (defined(XML_GE) && XML_GE == 1)
+#  if defined(XML_DTD) || (defined(XML_GE) && XML_GE == 1)
 /* Added in Expat 2.4.0 for XML_DTD defined and
  * added in Expat 2.6.0 for XML_GE == 1. */
 XMLPARSEAPI(XML_Bool)
@@ -1057,7 +1061,17 @@ XML_SetBillionLaughsAttackProtectionMaximumAmplification(
 XMLPARSEAPI(XML_Bool)
 XML_SetBillionLaughsAttackProtectionActivationThreshold(
     XML_Parser parser, unsigned long long activationThresholdBytes);
-#endif
+
+/* Added in Expat 2.7.2. */
+XMLPARSEAPI(XML_Bool)
+XML_SetAllocTrackerMaximumAmplification(XML_Parser parser,
+                                        float maximumAmplificationFactor);
+
+/* Added in Expat 2.7.2. */
+XMLPARSEAPI(XML_Bool)
+XML_SetAllocTrackerActivationThreshold(
+    XML_Parser parser, unsigned long long activationThresholdBytes);
+#  endif
 
 /* Added in Expat 2.6.0. */
 XMLPARSEAPI(XML_Bool)
@@ -1066,12 +1080,12 @@ XML_SetReparseDeferralEnabled(XML_Parser parser, XML_Bool enabled);
 /* Expat follows the semantic versioning convention.
    See https://semver.org
 */
-#define XML_MAJOR_VERSION 2
-#define XML_MINOR_VERSION 7
-#define XML_MICRO_VERSION 1
+#  define XML_MAJOR_VERSION 2
+#  define XML_MINOR_VERSION 7
+#  define XML_MICRO_VERSION 3
 
-#ifdef __cplusplus
+#  ifdef __cplusplus
 }
-#endif
+#  endif
 
 #endif /* not Expat_INCLUDED */

+ 62 - 61
libs/expat/lib/expat_external.h

@@ -38,7 +38,7 @@
 */
 
 #ifndef Expat_External_INCLUDED
-#define Expat_External_INCLUDED 1
+#  define Expat_External_INCLUDED 1
 
 /* External API definitions */
 
@@ -64,12 +64,12 @@
    compiled with the cdecl calling convention as the default since
    system headers may assume the cdecl convention.
 */
-#ifndef XMLCALL
-#  if defined(_MSC_VER)
-#    define XMLCALL __cdecl
-#  elif defined(__GNUC__) && defined(__i386) && ! defined(__INTEL_COMPILER)
-#    define XMLCALL __attribute__((cdecl))
-#  else
+#  ifndef XMLCALL
+#    if defined(_MSC_VER)
+#      define XMLCALL __cdecl
+#    elif defined(__GNUC__) && defined(__i386) && ! defined(__INTEL_COMPILER)
+#      define XMLCALL __attribute__((cdecl))
+#    else
 /* For any platform which uses this definition and supports more than
    one calling convention, we need to extend this definition to
    declare the convention used on that platform, if it's possible to
@@ -80,86 +80,87 @@
    pre-processor and how to specify the same calling convention as the
    platform's malloc() implementation.
 */
-#    define XMLCALL
-#  endif
-#endif /* not defined XMLCALL */
+#      define XMLCALL
+#    endif
+#  endif /* not defined XMLCALL */
 
-#if ! defined(XML_STATIC) && ! defined(XMLIMPORT)
-#  ifndef XML_BUILDING_EXPAT
+#  if ! defined(XML_STATIC) && ! defined(XMLIMPORT)
+#    ifndef XML_BUILDING_EXPAT
 /* using Expat from an application */
 
-#    if defined(_MSC_EXTENSIONS) && ! defined(__BEOS__) && ! defined(__CYGWIN__)
-#      define XMLIMPORT __declspec(dllimport)
+#      if defined(_MSC_EXTENSIONS) && ! defined(__BEOS__)                      \
+          && ! defined(__CYGWIN__)
+#        define XMLIMPORT __declspec(dllimport)
+#      endif
+
 #    endif
+#  endif /* not defined XML_STATIC */
 
+#  ifndef XML_ENABLE_VISIBILITY
+#    define XML_ENABLE_VISIBILITY 0
 #  endif
-#endif /* not defined XML_STATIC */
-
-#ifndef XML_ENABLE_VISIBILITY
-#  define XML_ENABLE_VISIBILITY 0
-#endif
 
-#if ! defined(XMLIMPORT) && XML_ENABLE_VISIBILITY
-#  define XMLIMPORT __attribute__((visibility("default")))
-#endif
+#  if ! defined(XMLIMPORT) && XML_ENABLE_VISIBILITY
+#    define XMLIMPORT __attribute__((visibility("default")))
+#  endif
 
 /* If we didn't define it above, define it away: */
-#ifndef XMLIMPORT
-#  define XMLIMPORT
-#endif
-
-#if defined(__GNUC__)                                                          \
-    && (__GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 96))
-#  define XML_ATTR_MALLOC __attribute__((__malloc__))
-#else
-#  define XML_ATTR_MALLOC
-#endif
-
-#if defined(__GNUC__)                                                          \
-    && ((__GNUC__ > 4) || (__GNUC__ == 4 && __GNUC_MINOR__ >= 3))
-#  define XML_ATTR_ALLOC_SIZE(x) __attribute__((__alloc_size__(x)))
-#else
-#  define XML_ATTR_ALLOC_SIZE(x)
-#endif
-
-#define XMLPARSEAPI(type) XMLIMPORT type XMLCALL
-
-#ifdef __cplusplus
-extern "C" {
-#endif
+#  ifndef XMLIMPORT
+#    define XMLIMPORT
+#  endif
+
+#  if defined(__GNUC__)                                                        \
+      && (__GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 96))
+#    define XML_ATTR_MALLOC __attribute__((__malloc__))
+#  else
+#    define XML_ATTR_MALLOC
+#  endif
 
-#ifdef XML_UNICODE_WCHAR_T
-#  ifndef XML_UNICODE
-#    define XML_UNICODE
+#  if defined(__GNUC__)                                                        \
+      && ((__GNUC__ > 4) || (__GNUC__ == 4 && __GNUC_MINOR__ >= 3))
+#    define XML_ATTR_ALLOC_SIZE(x) __attribute__((__alloc_size__(x)))
+#  else
+#    define XML_ATTR_ALLOC_SIZE(x)
 #  endif
-#  if defined(__SIZEOF_WCHAR_T__) && (__SIZEOF_WCHAR_T__ != 2)
-#    error "sizeof(wchar_t) != 2; Need -fshort-wchar for both Expat and libc"
+
+#  define XMLPARSEAPI(type) XMLIMPORT type XMLCALL
+
+#  ifdef __cplusplus
+extern "C" {
 #  endif
-#endif
 
-#ifdef XML_UNICODE /* Information is UTF-16 encoded. */
 #  ifdef XML_UNICODE_WCHAR_T
+#    ifndef XML_UNICODE
+#      define XML_UNICODE
+#    endif
+#    if defined(__SIZEOF_WCHAR_T__) && (__SIZEOF_WCHAR_T__ != 2)
+#      error "sizeof(wchar_t) != 2; Need -fshort-wchar for both Expat and libc"
+#    endif
+#  endif
+
+#  ifdef XML_UNICODE /* Information is UTF-16 encoded. */
+#    ifdef XML_UNICODE_WCHAR_T
 typedef wchar_t XML_Char;
 typedef wchar_t XML_LChar;
-#  else
+#    else
 typedef unsigned short XML_Char;
 typedef char XML_LChar;
-#  endif /* XML_UNICODE_WCHAR_T */
-#else    /* Information is UTF-8 encoded. */
+#    endif /* XML_UNICODE_WCHAR_T */
+#  else    /* Information is UTF-8 encoded. */
 typedef char XML_Char;
 typedef char XML_LChar;
-#endif   /* XML_UNICODE */
+#  endif   /* XML_UNICODE */
 
-#ifdef XML_LARGE_SIZE /* Use large integers for file/stream positions. */
+#  ifdef XML_LARGE_SIZE /* Use large integers for file/stream positions. */
 typedef long long XML_Index;
 typedef unsigned long long XML_Size;
-#else
+#  else
 typedef long XML_Index;
 typedef unsigned long XML_Size;
-#endif /* XML_LARGE_SIZE */
+#  endif /* XML_LARGE_SIZE */
 
-#ifdef __cplusplus
+#  ifdef __cplusplus
 }
-#endif
+#  endif
 
 #endif /* not Expat_External_INCLUDED */

+ 14 - 0
libs/expat/lib/internal.h

@@ -108,6 +108,7 @@
 #endif
 
 #include <limits.h> // ULONG_MAX
+#include <stddef.h> // size_t
 
 #if defined(_WIN32)                                                            \
     && (! defined(__USE_MINGW_ANSI_STDIO)                                      \
@@ -148,6 +149,16 @@
   100.0f
 #define EXPAT_BILLION_LAUGHS_ATTACK_PROTECTION_ACTIVATION_THRESHOLD_DEFAULT    \
   8388608 // 8 MiB, 2^23
+
+#define EXPAT_ALLOC_TRACKER_MAXIMUM_AMPLIFICATION_DEFAULT 100.0f
+#define EXPAT_ALLOC_TRACKER_ACTIVATION_THRESHOLD_DEFAULT                       \
+  67108864 // 64 MiB, 2^26
+
+// NOTE: If function expat_alloc was user facing, EXPAT_MALLOC_ALIGNMENT would
+//       have to take sizeof(long double) into account
+#define EXPAT_MALLOC_ALIGNMENT sizeof(long long) // largest parser (sub)member
+#define EXPAT_MALLOC_PADDING ((EXPAT_MALLOC_ALIGNMENT) - sizeof(size_t))
+
 /* NOTE END */
 
 #include "expat.h" // so we can use type XML_Parser below
@@ -171,6 +182,9 @@ extern
 #endif
     XML_Bool g_reparseDeferralEnabledDefault; // written ONLY in runtests.c
 #if defined(XML_TESTING)
+void *expat_malloc(XML_Parser parser, size_t size, int sourceLine);
+void expat_free(XML_Parser parser, void *ptr, int sourceLine);
+void *expat_realloc(XML_Parser parser, void *ptr, size_t size, int sourceLine);
 extern unsigned int g_bytesScanned; // used for testing only
 #endif
 

+ 3 - 0
libs/expat/lib/libexpat.def.cmake

@@ -79,3 +79,6 @@ EXPORTS
 @_EXPAT_COMMENT_DTD_OR_GE@ XML_SetBillionLaughsAttackProtectionMaximumAmplification @70
 ; added with version 2.6.0
   XML_SetReparseDeferralEnabled @71
+; added with version 2.7.2
+@_EXPAT_COMMENT_DTD_OR_GE@ XML_SetAllocTrackerMaximumAmplification @72
+@_EXPAT_COMMENT_DTD_OR_GE@ XML_SetAllocTrackerActivationThreshold @73

文件差异内容过多而无法显示
+ 478 - 94
libs/expat/lib/xmlparse.c


+ 15 - 21
libs/expat/lib/xmlrole.h

@@ -10,7 +10,7 @@
    Copyright (c) 2000      Clark Cooper <[email protected]>
    Copyright (c) 2002      Karl Waclawek <[email protected]>
    Copyright (c) 2002      Fred L. Drake, Jr. <[email protected]>
-   Copyright (c) 2017-2024 Sebastian Pipping <[email protected]>
+   Copyright (c) 2017-2025 Sebastian Pipping <[email protected]>
    Licensed under the MIT license:
 
    Permission is  hereby granted,  free of charge,  to any  person obtaining
@@ -34,19 +34,13 @@
 */
 
 #ifndef XmlRole_INCLUDED
-#define XmlRole_INCLUDED 1
+#  define XmlRole_INCLUDED 1
 
-#ifdef __VMS
-/*      0        1         2         3      0        1         2         3
-        1234567890123456789012345678901     1234567890123456789012345678901 */
-#  define XmlPrologStateInitExternalEntity XmlPrologStateInitExternalEnt
-#endif
+#  include "xmltok.h"
 
-#include "xmltok.h"
-
-#ifdef __cplusplus
+#  ifdef __cplusplus
 extern "C" {
-#endif
+#  endif
 
 enum {
   XML_ROLE_ERROR = -1,
@@ -107,11 +101,11 @@ enum {
   XML_ROLE_CONTENT_ELEMENT_PLUS,
   XML_ROLE_PI,
   XML_ROLE_COMMENT,
-#ifdef XML_DTD
+#  ifdef XML_DTD
   XML_ROLE_TEXT_DECL,
   XML_ROLE_IGNORE_SECT,
   XML_ROLE_INNER_PARAM_ENTITY_REF,
-#endif /* XML_DTD */
+#  endif /* XML_DTD */
   XML_ROLE_PARAM_ENTITY_REF
 };
 
@@ -120,23 +114,23 @@ typedef struct prolog_state {
                         const char *end, const ENCODING *enc);
   unsigned level;
   int role_none;
-#ifdef XML_DTD
+#  ifdef XML_DTD
   unsigned includeLevel;
   int documentEntity;
   int inEntityValue;
-#endif /* XML_DTD */
+#  endif /* XML_DTD */
 } PROLOG_STATE;
 
 void XmlPrologStateInit(PROLOG_STATE *state);
-#ifdef XML_DTD
+#  ifdef XML_DTD
 void XmlPrologStateInitExternalEntity(PROLOG_STATE *state);
-#endif /* XML_DTD */
+#  endif /* XML_DTD */
 
-#define XmlTokenRole(state, tok, ptr, end, enc)                                \
-  (((state)->handler)(state, tok, ptr, end, enc))
+#  define XmlTokenRole(state, tok, ptr, end, enc)                              \
+    (((state)->handler)(state, tok, ptr, end, enc))
 
-#ifdef __cplusplus
+#  ifdef __cplusplus
 }
-#endif
+#  endif
 
 #endif /* not XmlRole_INCLUDED */

+ 2 - 2
libs/expat/lib/xmltok.c

@@ -1398,7 +1398,7 @@ unknown_toUtf16(const ENCODING *enc, const char **fromP, const char *fromLim,
 }
 
 ENCODING *
-XmlInitUnknownEncoding(void *mem, int *table, CONVERTER convert,
+XmlInitUnknownEncoding(void *mem, const int *table, CONVERTER convert,
                        void *userData) {
   int i;
   struct unknown_encoding *e = (struct unknown_encoding *)mem;
@@ -1661,7 +1661,7 @@ initScan(const ENCODING *const *encodingTable, const INIT_ENCODING *enc,
 #  undef ns
 
 ENCODING *
-XmlInitUnknownEncodingNS(void *mem, int *table, CONVERTER convert,
+XmlInitUnknownEncodingNS(void *mem, const int *table, CONVERTER convert,
                          void *userData) {
   ENCODING *enc = XmlInitUnknownEncoding(mem, table, convert, userData);
   if (enc)

+ 113 - 113
libs/expat/lib/xmltok.h

@@ -35,113 +35,113 @@
 */
 
 #ifndef XmlTok_INCLUDED
-#define XmlTok_INCLUDED 1
+#  define XmlTok_INCLUDED 1
 
-#ifdef __cplusplus
+#  ifdef __cplusplus
 extern "C" {
-#endif
+#  endif
 
 /* The following token may be returned by XmlContentTok */
-#define XML_TOK_TRAILING_RSQB                                                  \
-  -5 /* ] or ]] at the end of the scan; might be                               \
-        start of illegal ]]> sequence */
+#  define XML_TOK_TRAILING_RSQB                                                \
+    -5 /* ] or ]] at the end of the scan; might be                             \
+          start of illegal ]]> sequence */
 /* The following tokens may be returned by both XmlPrologTok and
    XmlContentTok.
 */
-#define XML_TOK_NONE -4 /* The string to be scanned is empty */
-#define XML_TOK_TRAILING_CR                                                    \
-  -3                            /* A CR at the end of the scan;                \
-                                   might be part of CRLF sequence */
-#define XML_TOK_PARTIAL_CHAR -2 /* only part of a multibyte sequence */
-#define XML_TOK_PARTIAL -1      /* only part of a token */
-#define XML_TOK_INVALID 0
+#  define XML_TOK_NONE -4 /* The string to be scanned is empty */
+#  define XML_TOK_TRAILING_CR                                                  \
+    -3                            /* A CR at the end of the scan;              \
+                                     might be part of CRLF sequence */
+#  define XML_TOK_PARTIAL_CHAR -2 /* only part of a multibyte sequence */
+#  define XML_TOK_PARTIAL -1      /* only part of a token */
+#  define XML_TOK_INVALID 0
 
 /* The following tokens are returned by XmlContentTok; some are also
    returned by XmlAttributeValueTok, XmlEntityTok, XmlCdataSectionTok.
 */
-#define XML_TOK_START_TAG_WITH_ATTS 1
-#define XML_TOK_START_TAG_NO_ATTS 2
-#define XML_TOK_EMPTY_ELEMENT_WITH_ATTS 3 /* empty element tag <e/> */
-#define XML_TOK_EMPTY_ELEMENT_NO_ATTS 4
-#define XML_TOK_END_TAG 5
-#define XML_TOK_DATA_CHARS 6
-#define XML_TOK_DATA_NEWLINE 7
-#define XML_TOK_CDATA_SECT_OPEN 8
-#define XML_TOK_ENTITY_REF 9
-#define XML_TOK_CHAR_REF 10 /* numeric character reference */
+#  define XML_TOK_START_TAG_WITH_ATTS 1
+#  define XML_TOK_START_TAG_NO_ATTS 2
+#  define XML_TOK_EMPTY_ELEMENT_WITH_ATTS 3 /* empty element tag <e/> */
+#  define XML_TOK_EMPTY_ELEMENT_NO_ATTS 4
+#  define XML_TOK_END_TAG 5
+#  define XML_TOK_DATA_CHARS 6
+#  define XML_TOK_DATA_NEWLINE 7
+#  define XML_TOK_CDATA_SECT_OPEN 8
+#  define XML_TOK_ENTITY_REF 9
+#  define XML_TOK_CHAR_REF 10 /* numeric character reference */
 
 /* The following tokens may be returned by both XmlPrologTok and
    XmlContentTok.
 */
-#define XML_TOK_PI 11       /* processing instruction */
-#define XML_TOK_XML_DECL 12 /* XML decl or text decl */
-#define XML_TOK_COMMENT 13
-#define XML_TOK_BOM 14 /* Byte order mark */
+#  define XML_TOK_PI 11       /* processing instruction */
+#  define XML_TOK_XML_DECL 12 /* XML decl or text decl */
+#  define XML_TOK_COMMENT 13
+#  define XML_TOK_BOM 14 /* Byte order mark */
 
 /* The following tokens are returned only by XmlPrologTok */
-#define XML_TOK_PROLOG_S 15
-#define XML_TOK_DECL_OPEN 16  /* <!foo */
-#define XML_TOK_DECL_CLOSE 17 /* > */
-#define XML_TOK_NAME 18
-#define XML_TOK_NMTOKEN 19
-#define XML_TOK_POUND_NAME 20 /* #name */
-#define XML_TOK_OR 21         /* | */
-#define XML_TOK_PERCENT 22
-#define XML_TOK_OPEN_PAREN 23
-#define XML_TOK_CLOSE_PAREN 24
-#define XML_TOK_OPEN_BRACKET 25
-#define XML_TOK_CLOSE_BRACKET 26
-#define XML_TOK_LITERAL 27
-#define XML_TOK_PARAM_ENTITY_REF 28
-#define XML_TOK_INSTANCE_START 29
+#  define XML_TOK_PROLOG_S 15
+#  define XML_TOK_DECL_OPEN 16  /* <!foo */
+#  define XML_TOK_DECL_CLOSE 17 /* > */
+#  define XML_TOK_NAME 18
+#  define XML_TOK_NMTOKEN 19
+#  define XML_TOK_POUND_NAME 20 /* #name */
+#  define XML_TOK_OR 21         /* | */
+#  define XML_TOK_PERCENT 22
+#  define XML_TOK_OPEN_PAREN 23
+#  define XML_TOK_CLOSE_PAREN 24
+#  define XML_TOK_OPEN_BRACKET 25
+#  define XML_TOK_CLOSE_BRACKET 26
+#  define XML_TOK_LITERAL 27
+#  define XML_TOK_PARAM_ENTITY_REF 28
+#  define XML_TOK_INSTANCE_START 29
 
 /* The following occur only in element type declarations */
-#define XML_TOK_NAME_QUESTION 30        /* name? */
-#define XML_TOK_NAME_ASTERISK 31        /* name* */
-#define XML_TOK_NAME_PLUS 32            /* name+ */
-#define XML_TOK_COND_SECT_OPEN 33       /* <![ */
-#define XML_TOK_COND_SECT_CLOSE 34      /* ]]> */
-#define XML_TOK_CLOSE_PAREN_QUESTION 35 /* )? */
-#define XML_TOK_CLOSE_PAREN_ASTERISK 36 /* )* */
-#define XML_TOK_CLOSE_PAREN_PLUS 37     /* )+ */
-#define XML_TOK_COMMA 38
+#  define XML_TOK_NAME_QUESTION 30        /* name? */
+#  define XML_TOK_NAME_ASTERISK 31        /* name* */
+#  define XML_TOK_NAME_PLUS 32            /* name+ */
+#  define XML_TOK_COND_SECT_OPEN 33       /* <![ */
+#  define XML_TOK_COND_SECT_CLOSE 34      /* ]]> */
+#  define XML_TOK_CLOSE_PAREN_QUESTION 35 /* )? */
+#  define XML_TOK_CLOSE_PAREN_ASTERISK 36 /* )* */
+#  define XML_TOK_CLOSE_PAREN_PLUS 37     /* )+ */
+#  define XML_TOK_COMMA 38
 
 /* The following token is returned only by XmlAttributeValueTok */
-#define XML_TOK_ATTRIBUTE_VALUE_S 39
+#  define XML_TOK_ATTRIBUTE_VALUE_S 39
 
 /* The following token is returned only by XmlCdataSectionTok */
-#define XML_TOK_CDATA_SECT_CLOSE 40
+#  define XML_TOK_CDATA_SECT_CLOSE 40
 
 /* With namespace processing this is returned by XmlPrologTok for a
    name with a colon.
 */
-#define XML_TOK_PREFIXED_NAME 41
+#  define XML_TOK_PREFIXED_NAME 41
 
-#ifdef XML_DTD
-#  define XML_TOK_IGNORE_SECT 42
-#endif /* XML_DTD */
+#  ifdef XML_DTD
+#    define XML_TOK_IGNORE_SECT 42
+#  endif /* XML_DTD */
 
-#ifdef XML_DTD
-#  define XML_N_STATES 4
-#else /* not XML_DTD */
-#  define XML_N_STATES 3
-#endif /* not XML_DTD */
+#  ifdef XML_DTD
+#    define XML_N_STATES 4
+#  else /* not XML_DTD */
+#    define XML_N_STATES 3
+#  endif /* not XML_DTD */
 
-#define XML_PROLOG_STATE 0
-#define XML_CONTENT_STATE 1
-#define XML_CDATA_SECTION_STATE 2
-#ifdef XML_DTD
-#  define XML_IGNORE_SECTION_STATE 3
-#endif /* XML_DTD */
+#  define XML_PROLOG_STATE 0
+#  define XML_CONTENT_STATE 1
+#  define XML_CDATA_SECTION_STATE 2
+#  ifdef XML_DTD
+#    define XML_IGNORE_SECTION_STATE 3
+#  endif /* XML_DTD */
 
-#define XML_N_LITERAL_TYPES 2
-#define XML_ATTRIBUTE_VALUE_LITERAL 0
-#define XML_ENTITY_VALUE_LITERAL 1
+#  define XML_N_LITERAL_TYPES 2
+#  define XML_ATTRIBUTE_VALUE_LITERAL 0
+#  define XML_ENTITY_VALUE_LITERAL 1
 
 /* The size of the buffer passed to XmlUtf8Encode must be at least this. */
-#define XML_UTF8_ENCODE_MAX 4
+#  define XML_UTF8_ENCODE_MAX 4
 /* The size of the buffer passed to XmlUtf16Encode must be at least this. */
-#define XML_UTF16_ENCODE_MAX 2
+#  define XML_UTF16_ENCODE_MAX 2
 
 typedef struct position {
   /* first line and first column are 0 not 1 */
@@ -220,63 +220,63 @@ struct encoding {
    the prolog outside literals, comments and processing instructions.
 */
 
-#define XmlTok(enc, state, ptr, end, nextTokPtr)                               \
-  (((enc)->scanners[state])(enc, ptr, end, nextTokPtr))
+#  define XmlTok(enc, state, ptr, end, nextTokPtr)                             \
+    (((enc)->scanners[state])(enc, ptr, end, nextTokPtr))
 
-#define XmlPrologTok(enc, ptr, end, nextTokPtr)                                \
-  XmlTok(enc, XML_PROLOG_STATE, ptr, end, nextTokPtr)
+#  define XmlPrologTok(enc, ptr, end, nextTokPtr)                              \
+    XmlTok(enc, XML_PROLOG_STATE, ptr, end, nextTokPtr)
 
-#define XmlContentTok(enc, ptr, end, nextTokPtr)                               \
-  XmlTok(enc, XML_CONTENT_STATE, ptr, end, nextTokPtr)
+#  define XmlContentTok(enc, ptr, end, nextTokPtr)                             \
+    XmlTok(enc, XML_CONTENT_STATE, ptr, end, nextTokPtr)
 
-#define XmlCdataSectionTok(enc, ptr, end, nextTokPtr)                          \
-  XmlTok(enc, XML_CDATA_SECTION_STATE, ptr, end, nextTokPtr)
+#  define XmlCdataSectionTok(enc, ptr, end, nextTokPtr)                        \
+    XmlTok(enc, XML_CDATA_SECTION_STATE, ptr, end, nextTokPtr)
 
-#ifdef XML_DTD
+#  ifdef XML_DTD
 
-#  define XmlIgnoreSectionTok(enc, ptr, end, nextTokPtr)                       \
-    XmlTok(enc, XML_IGNORE_SECTION_STATE, ptr, end, nextTokPtr)
+#    define XmlIgnoreSectionTok(enc, ptr, end, nextTokPtr)                     \
+      XmlTok(enc, XML_IGNORE_SECTION_STATE, ptr, end, nextTokPtr)
 
-#endif /* XML_DTD */
+#  endif /* XML_DTD */
 
 /* This is used for performing a 2nd-level tokenization on the content
    of a literal that has already been returned by XmlTok.
 */
-#define XmlLiteralTok(enc, literalType, ptr, end, nextTokPtr)                  \
-  (((enc)->literalScanners[literalType])(enc, ptr, end, nextTokPtr))
+#  define XmlLiteralTok(enc, literalType, ptr, end, nextTokPtr)                \
+    (((enc)->literalScanners[literalType])(enc, ptr, end, nextTokPtr))
 
-#define XmlAttributeValueTok(enc, ptr, end, nextTokPtr)                        \
-  XmlLiteralTok(enc, XML_ATTRIBUTE_VALUE_LITERAL, ptr, end, nextTokPtr)
+#  define XmlAttributeValueTok(enc, ptr, end, nextTokPtr)                      \
+    XmlLiteralTok(enc, XML_ATTRIBUTE_VALUE_LITERAL, ptr, end, nextTokPtr)
 
-#define XmlEntityValueTok(enc, ptr, end, nextTokPtr)                           \
-  XmlLiteralTok(enc, XML_ENTITY_VALUE_LITERAL, ptr, end, nextTokPtr)
+#  define XmlEntityValueTok(enc, ptr, end, nextTokPtr)                         \
+    XmlLiteralTok(enc, XML_ENTITY_VALUE_LITERAL, ptr, end, nextTokPtr)
 
-#define XmlNameMatchesAscii(enc, ptr1, end1, ptr2)                             \
-  (((enc)->nameMatchesAscii)(enc, ptr1, end1, ptr2))
+#  define XmlNameMatchesAscii(enc, ptr1, end1, ptr2)                           \
+    (((enc)->nameMatchesAscii)(enc, ptr1, end1, ptr2))
 
-#define XmlNameLength(enc, ptr) (((enc)->nameLength)(enc, ptr))
+#  define XmlNameLength(enc, ptr) (((enc)->nameLength)(enc, ptr))
 
-#define XmlSkipS(enc, ptr) (((enc)->skipS)(enc, ptr))
+#  define XmlSkipS(enc, ptr) (((enc)->skipS)(enc, ptr))
 
-#define XmlGetAttributes(enc, ptr, attsMax, atts)                              \
-  (((enc)->getAtts)(enc, ptr, attsMax, atts))
+#  define XmlGetAttributes(enc, ptr, attsMax, atts)                            \
+    (((enc)->getAtts)(enc, ptr, attsMax, atts))
 
-#define XmlCharRefNumber(enc, ptr) (((enc)->charRefNumber)(enc, ptr))
+#  define XmlCharRefNumber(enc, ptr) (((enc)->charRefNumber)(enc, ptr))
 
-#define XmlPredefinedEntityName(enc, ptr, end)                                 \
-  (((enc)->predefinedEntityName)(enc, ptr, end))
+#  define XmlPredefinedEntityName(enc, ptr, end)                               \
+    (((enc)->predefinedEntityName)(enc, ptr, end))
 
-#define XmlUpdatePosition(enc, ptr, end, pos)                                  \
-  (((enc)->updatePosition)(enc, ptr, end, pos))
+#  define XmlUpdatePosition(enc, ptr, end, pos)                                \
+    (((enc)->updatePosition)(enc, ptr, end, pos))
 
-#define XmlIsPublicId(enc, ptr, end, badPtr)                                   \
-  (((enc)->isPublicId)(enc, ptr, end, badPtr))
+#  define XmlIsPublicId(enc, ptr, end, badPtr)                                 \
+    (((enc)->isPublicId)(enc, ptr, end, badPtr))
 
-#define XmlUtf8Convert(enc, fromP, fromLim, toP, toLim)                        \
-  (((enc)->utf8Convert)(enc, fromP, fromLim, toP, toLim))
+#  define XmlUtf8Convert(enc, fromP, fromLim, toP, toLim)                      \
+    (((enc)->utf8Convert)(enc, fromP, fromLim, toP, toLim))
 
-#define XmlUtf16Convert(enc, fromP, fromLim, toP, toLim)                       \
-  (((enc)->utf16Convert)(enc, fromP, fromLim, toP, toLim))
+#  define XmlUtf16Convert(enc, fromP, fromLim, toP, toLim)                     \
+    (((enc)->utf16Convert)(enc, fromP, fromLim, toP, toLim))
 
 typedef struct {
   ENCODING initEnc;
@@ -299,7 +299,7 @@ int XmlSizeOfUnknownEncoding(void);
 
 typedef int(XMLCALL *CONVERTER)(void *userData, const char *p);
 
-ENCODING *XmlInitUnknownEncoding(void *mem, int *table, CONVERTER convert,
+ENCODING *XmlInitUnknownEncoding(void *mem, const int *table, CONVERTER convert,
                                  void *userData);
 
 int XmlParseXmlDeclNS(int isGeneralTextEntity, const ENCODING *enc,
@@ -312,10 +312,10 @@ int XmlInitEncodingNS(INIT_ENCODING *p, const ENCODING **encPtr,
                       const char *name);
 const ENCODING *XmlGetUtf8InternalEncodingNS(void);
 const ENCODING *XmlGetUtf16InternalEncodingNS(void);
-ENCODING *XmlInitUnknownEncodingNS(void *mem, int *table, CONVERTER convert,
-                                   void *userData);
-#ifdef __cplusplus
+ENCODING *XmlInitUnknownEncodingNS(void *mem, const int *table,
+                                   CONVERTER convert, void *userData);
+#  ifdef __cplusplus
 }
-#endif
+#  endif
 
 #endif /* not XmlTok_INCLUDED */

+ 68 - 31
libs/expat/tests/Makefile.in

@@ -1,7 +1,7 @@
-# Makefile.in generated by automake 1.16.5 from Makefile.am.
+# Makefile.in generated by automake 1.18.1 from Makefile.am.
 # @configure_input@
 
-# Copyright (C) 1994-2021 Free Software Foundation, Inc.
+# Copyright (C) 1994-2025 Free Software Foundation, Inc.
 
 # This Makefile.in is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -102,6 +102,8 @@ am__make_running_with_option = \
   test $$has_opt = yes
 am__make_dryrun = (target_option=n; $(am__make_running_with_option))
 am__make_keepgoing = (target_option=k; $(am__make_running_with_option))
+am__rm_f = rm -f $(am__rm_f_notfound)
+am__rm_rf = rm -rf $(am__rm_f_notfound)
 pkgdatadir = $(datadir)/@PACKAGE@
 pkgincludedir = $(includedir)/@PACKAGE@
 pkglibdir = $(libdir)/@PACKAGE@
@@ -324,10 +326,9 @@ am__base_list = \
   sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \
   sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g'
 am__uninstall_files_from_dir = { \
-  test -z "$$files" \
-    || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \
-    || { echo " ( cd '$$dir' && rm -f" $$files ")"; \
-         $(am__cd) "$$dir" && rm -f $$files; }; \
+  { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \
+  || { echo " ( cd '$$dir' && rm -f" $$files ")"; \
+       $(am__cd) "$$dir" && echo $$files | $(am__xargs_n) 40 $(am__rm_f); }; \
   }
 am__recheck_rx = ^[ 	]*:recheck:[ 	]*
 am__global_test_result_rx = ^[ 	]*:global-test-result:[ 	]*
@@ -415,12 +416,13 @@ am__sh_e_setup = case $$- in *e*) set +e;; esac
 # Default flags passed to test drivers.
 am__common_driver_flags = \
   --color-tests "$$am__color_tests" \
+  $$am__collect_skipped_logs \
   --enable-hard-errors "$$am__enable_hard_errors" \
   --expect-failure "$$am__expect_failure"
 # To be inserted before the command running the test.  Creates the
 # directory for the log if needed.  Stores in $dir the directory
 # containing $f, in $tst the test, in $log the log.  Executes the
-# developer- defined test setup AM_TESTS_ENVIRONMENT (if any), and
+# developer-defined test setup AM_TESTS_ENVIRONMENT (if any), and
 # passes TESTS_ENVIRONMENT.  Set up options for the wrapper that
 # will run the test scripts (or their associated LOG_COMPILER, if
 # thy have one).
@@ -439,6 +441,11 @@ if test -f "./$$f"; then dir=./;			\
 elif test -f "$$f"; then dir=;				\
 else dir="$(srcdir)/"; fi;				\
 tst=$$dir$$f; log='$@'; 				\
+if test -n '$(IGNORE_SKIPPED_LOGS)'; then		\
+  am__collect_skipped_logs='--collect-skipped-logs no';	\
+else							\
+  am__collect_skipped_logs='';				\
+fi;							\
 if test -n '$(DISABLE_HARD_ERRORS)'; then		\
   am__enable_hard_errors=no; 				\
 else							\
@@ -620,8 +627,10 @@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@
 am__include = @am__include@
 am__leading_dot = @am__leading_dot@
 am__quote = @am__quote@
+am__rm_f_notfound = @am__rm_f_notfound@
 am__tar = @am__tar@
 am__untar = @am__untar@
+am__xargs_n = @am__xargs_n@
 bindir = @bindir@
 build = @build@
 build_alias = @build_alias@
@@ -757,13 +766,8 @@ $(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps)
 $(am__aclocal_m4_deps):
 
 clean-checkPROGRAMS:
-	@list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \
-	echo " rm -f" $$list; \
-	rm -f $$list || exit $$?; \
-	test -n "$(EXEEXT)" || exit 0; \
-	list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \
-	echo " rm -f" $$list; \
-	rm -f $$list
+	$(am__rm_f) $(check_PROGRAMS)
+	test -z "$(EXEEXT)" || $(am__rm_f) $(check_PROGRAMS:$(EXEEXT)=)
 
 runtests$(EXEEXT): $(runtests_OBJECTS) $(runtests_DEPENDENCIES) $(EXTRA_runtests_DEPENDENCIES) 
 	@rm -f runtests$(EXEEXT)
@@ -810,7 +814,7 @@ distclean-compile:
 
 $(am__depfiles_remade):
 	@$(MKDIR_P) $(@D)
-	@echo '# dummy' >$@-t && $(am__mv) $@-t $@
+	@: >>$@
 
 am--depfiles: $(am__depfiles_remade)
 
@@ -974,7 +978,6 @@ distclean-tags:
 am--fnord $(TEST_LOGS) $(TEST_LOGS:.log=.trs): $(am__force_recheck)
 am--force-recheck:
 	@:
-
 $(TEST_SUITE_LOG): $(TEST_LOGS)
 	@$(am__set_TESTS_bases); \
 	am__f_ok () { test -f "$$1" && test -r "$$1"; }; \
@@ -1050,10 +1053,37 @@ $(TEST_SUITE_LOG): $(TEST_LOGS)
 	  result_count $$1 "XPASS:" $$xpass "$$red"; \
 	  result_count $$1 "ERROR:" $$error "$$mgn"; \
 	}; \
+	output_system_information () \
+	{ \
+          echo;                                     \
+	  { uname -a | $(AWK) '{                    \
+  printf "System information (uname -a):";          \
+  for (i = 1; i < NF; ++i)                          \
+    {                                               \
+      if (i != 2)                                   \
+        printf " %s", $$i;                          \
+    }                                               \
+  printf "\n";                                      \
+}'; } 2>&1;                                         \
+	  if test -r /etc/os-release; then          \
+	    echo "Distribution information (/etc/os-release):"; \
+	    sed 8q /etc/os-release;                 \
+	  elif test -r /etc/issue; then             \
+	    echo "Distribution information (/etc/issue):";      \
+	    cat /etc/issue;                         \
+	  fi;                                       \
+	}; \
+	please_report () \
+	{ \
+echo "Some test(s) failed.  Please report this to $(PACKAGE_BUGREPORT),";    \
+echo "together with the test-suite.log file (gzipped) and your system";      \
+echo "information.  Thanks.";                                                \
+	}; \
 	{								\
 	  echo "$(PACKAGE_STRING): $(subdir)/$(TEST_SUITE_LOG)" |	\
 	    $(am__rst_title);						\
 	  create_testsuite_report --no-color;				\
+	  output_system_information;                                    \
 	  echo;								\
 	  echo ".. contents:: :depth: 2";				\
 	  echo;								\
@@ -1073,26 +1103,25 @@ $(TEST_SUITE_LOG): $(TEST_LOGS)
 	create_testsuite_report --maybe-color;				\
 	echo "$$col$$br$$std";						\
 	if $$success; then :; else					\
-	  echo "$${col}See $(subdir)/$(TEST_SUITE_LOG)$${std}";		\
+	  echo "$${col}See $(subdir)/$(TEST_SUITE_LOG) for debugging.$${std}";\
 	  if test -n "$(PACKAGE_BUGREPORT)"; then			\
-	    echo "$${col}Please report to $(PACKAGE_BUGREPORT)$${std}";	\
+	    please_report | sed -e "s/^/$${col}/" -e s/'$$'/"$${std}"/; \
 	  fi;								\
 	  echo "$$col$$br$$std";					\
 	fi;								\
 	$$success || exit 1
 
 check-TESTS: $(check_PROGRAMS)
-	@list='$(RECHECK_LOGS)';           test -z "$$list" || rm -f $$list
-	@list='$(RECHECK_LOGS:.log=.trs)'; test -z "$$list" || rm -f $$list
-	@test -z "$(TEST_SUITE_LOG)" || rm -f $(TEST_SUITE_LOG)
+	@$(am__rm_f) $(RECHECK_LOGS)
+	@$(am__rm_f) $(RECHECK_LOGS:.log=.trs)
+	@$(am__rm_f) $(TEST_SUITE_LOG)
 	@set +e; $(am__set_TESTS_bases); \
 	log_list=`for i in $$bases; do echo $$i.log; done`; \
-	trs_list=`for i in $$bases; do echo $$i.trs; done`; \
-	log_list=`echo $$log_list`; trs_list=`echo $$trs_list`; \
+	log_list=`echo $$log_list`; \
 	$(MAKE) $(AM_MAKEFLAGS) $(TEST_SUITE_LOG) TEST_LOGS="$$log_list"; \
 	exit $$?;
 recheck: all $(check_PROGRAMS)
-	@test -z "$(TEST_SUITE_LOG)" || rm -f $(TEST_SUITE_LOG)
+	@$(am__rm_f) $(TEST_SUITE_LOG)
 	@set +e; $(am__set_TESTS_bases); \
 	bases=`for i in $$bases; do echo $$i; done \
 	         | $(am__list_recheck_tests)` || exit 1; \
@@ -1130,6 +1159,7 @@ runtests_cxx.log: runtests_cxx$(EXEEXT)
 @am__EXEEXT_TRUE@	--log-file $$b.log --trs-file $$b.trs \
 @am__EXEEXT_TRUE@	$(am__common_driver_flags) $(AM_TEST_LOG_DRIVER_FLAGS) $(TEST_LOG_DRIVER_FLAGS) -- $(TEST_LOG_COMPILE) \
 @am__EXEEXT_TRUE@	"$$tst" $(AM_TESTS_FD_REDIRECT)
+
 distdir: $(BUILT_SOURCES)
 	$(MAKE) $(AM_MAKEFLAGS) distdir-am
 
@@ -1215,15 +1245,15 @@ install-strip:
 	    "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \
 	fi
 mostlyclean-generic:
-	-test -z "$(TEST_LOGS)" || rm -f $(TEST_LOGS)
-	-test -z "$(TEST_LOGS:.log=.trs)" || rm -f $(TEST_LOGS:.log=.trs)
-	-test -z "$(TEST_SUITE_LOG)" || rm -f $(TEST_SUITE_LOG)
+	-$(am__rm_f) $(TEST_LOGS)
+	-$(am__rm_f) $(TEST_LOGS:.log=.trs)
+	-$(am__rm_f) $(TEST_SUITE_LOG)
 
 clean-generic:
 
 distclean-generic:
-	-test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
-	-test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES)
+	-$(am__rm_f) $(CONFIG_CLEAN_FILES)
+	-test . = "$(srcdir)" || $(am__rm_f) $(CONFIG_CLEAN_VPATH_FILES)
 
 maintainer-clean-generic:
 	@echo "This command is intended for maintainers to use"
@@ -1234,7 +1264,7 @@ clean-am: clean-checkPROGRAMS clean-generic clean-libtool \
 	mostlyclean-am
 
 distclean: distclean-recursive
-		-rm -f ./$(DEPDIR)/acc_tests.Po
+	-rm -f ./$(DEPDIR)/acc_tests.Po
 	-rm -f ./$(DEPDIR)/acc_tests_cxx.Po
 	-rm -f ./$(DEPDIR)/alloc_tests.Po
 	-rm -f ./$(DEPDIR)/alloc_tests_cxx.Po
@@ -1307,7 +1337,7 @@ install-ps-am:
 installcheck-am:
 
 maintainer-clean: maintainer-clean-recursive
-		-rm -f ./$(DEPDIR)/acc_tests.Po
+	-rm -f ./$(DEPDIR)/acc_tests.Po
 	-rm -f ./$(DEPDIR)/acc_tests_cxx.Po
 	-rm -f ./$(DEPDIR)/alloc_tests.Po
 	-rm -f ./$(DEPDIR)/alloc_tests_cxx.Po
@@ -1376,3 +1406,10 @@ uninstall-am:
 # Tell versions [3.59,3.63) of GNU make to not export all variables.
 # Otherwise a system limit (for SysV at least) may be exceeded.
 .NOEXPORT:
+
+# Tell GNU make to disable its built-in pattern rules.
+%:: %,v
+%:: RCS/%,v
+%:: RCS/%
+%:: s.%
+%:: SCCS/s.%

+ 239 - 3
libs/expat/tests/alloc_tests.c

@@ -10,7 +10,7 @@
    Copyright (c) 2003      Greg Stein <[email protected]>
    Copyright (c) 2005-2007 Steven Solie <[email protected]>
    Copyright (c) 2005-2012 Karl Waclawek <[email protected]>
-   Copyright (c) 2016-2023 Sebastian Pipping <[email protected]>
+   Copyright (c) 2016-2025 Sebastian Pipping <[email protected]>
    Copyright (c) 2017-2022 Rhodri James <[email protected]>
    Copyright (c) 2017      Joe Orton <[email protected]>
    Copyright (c) 2017      José Gutiérrez de la Concha <[email protected]>
@@ -46,10 +46,16 @@
 #  undef NDEBUG /* because test suite relies on assert(...) at the moment */
 #endif
 
+#include <math.h> /* NAN, INFINITY */
+#include <stdbool.h>
+#include <stdint.h> /* for SIZE_MAX */
 #include <string.h>
 #include <assert.h>
 
+#include "expat_config.h"
+
 #include "expat.h"
+#include "internal.h"
 #include "common.h"
 #include "minicheck.h"
 #include "dummy.h"
@@ -323,7 +329,7 @@ START_TEST(test_alloc_run_external_parser) {
     XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
     XML_SetUserData(g_parser, foo_text);
     XML_SetExternalEntityRefHandler(g_parser, external_entity_null_loader);
-    g_allocation_count = i;
+    g_allocation_count = (int)i;
     if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
         != XML_STATUS_ERROR)
       break;
@@ -434,7 +440,7 @@ START_TEST(test_alloc_internal_entity) {
   const unsigned int max_alloc_count = 20;
 
   for (i = 0; i < max_alloc_count; i++) {
-    g_allocation_count = i;
+    g_allocation_count = (int)i;
     XML_SetUnknownEncodingHandler(g_parser, unknown_released_encoding_handler,
                                   NULL);
     if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
@@ -2085,6 +2091,226 @@ START_TEST(test_alloc_reset_after_external_entity_parser_create_fail) {
 }
 END_TEST
 
+#if XML_GE == 1
+static size_t
+sizeRecordedFor(void *ptr) {
+  return *(size_t *)((char *)ptr - EXPAT_MALLOC_PADDING - sizeof(size_t));
+}
+#endif // XML_GE == 1
+
+START_TEST(test_alloc_tracker_size_recorded) {
+  XML_Memory_Handling_Suite memsuite = {malloc, realloc, free};
+
+  bool values[] = {true, false};
+  for (size_t i = 0; i < sizeof(values) / sizeof(values[0]); i++) {
+    const bool useMemSuite = values[i];
+    set_subtest("useMemSuite=%d", (int)useMemSuite);
+    XML_Parser parser = useMemSuite
+                            ? XML_ParserCreate_MM(NULL, &memsuite, XCS("|"))
+                            : XML_ParserCreate(NULL);
+
+#if XML_GE == 1
+    void *ptr = expat_malloc(parser, 10, -1);
+
+    assert_true(ptr != NULL);
+    assert_true(sizeRecordedFor(ptr) == 10);
+
+    assert_true(expat_realloc(parser, ptr, SIZE_MAX / 2, -1) == NULL);
+
+    assert_true(sizeRecordedFor(ptr) == 10); // i.e. unchanged
+
+    ptr = expat_realloc(parser, ptr, 20, -1);
+
+    assert_true(ptr != NULL);
+    assert_true(sizeRecordedFor(ptr) == 20);
+
+    expat_free(parser, ptr, -1);
+#endif
+
+    XML_ParserFree(parser);
+  }
+}
+END_TEST
+
+START_TEST(test_alloc_tracker_pointer_alignment) {
+  XML_Parser parser = XML_ParserCreate(NULL);
+#if XML_GE == 1
+  assert_true(sizeof(long long) >= sizeof(size_t)); // self-test
+  long long *const ptr
+      = (long long *)expat_malloc(parser, 4 * sizeof(long long), -1);
+  ptr[0] = 0LL;
+  ptr[1] = 1LL;
+  ptr[2] = 2LL;
+  ptr[3] = 3LL;
+  expat_free(parser, ptr, -1);
+#endif
+  XML_ParserFree(parser);
+}
+END_TEST
+
+START_TEST(test_alloc_tracker_maximum_amplification) {
+  if (g_reparseDeferralEnabledDefault == XML_TRUE) {
+    return;
+  }
+
+  XML_Parser parser = XML_ParserCreate(NULL);
+
+  // Get .m_accounting.countBytesDirect from 0 to 3
+  const char *const chunk = "<e>";
+  assert_true(_XML_Parse_SINGLE_BYTES(parser, chunk, (int)strlen(chunk),
+                                      /*isFinal=*/XML_FALSE)
+              == XML_STATUS_OK);
+
+#if XML_GE == 1
+  // Stop activation threshold from interfering
+  assert_true(XML_SetAllocTrackerActivationThreshold(parser, 0) == XML_TRUE);
+
+  // Exceed maximum amplification: should be rejected.
+  assert_true(expat_malloc(parser, 1000, -1) == NULL);
+
+  // Increase maximum amplification, and try the same amount once more: should
+  // work.
+  assert_true(XML_SetAllocTrackerMaximumAmplification(parser, 3000.0f)
+              == XML_TRUE);
+
+  void *const ptr = expat_malloc(parser, 1000, -1);
+  assert_true(ptr != NULL);
+  expat_free(parser, ptr, -1);
+#endif
+
+  XML_ParserFree(parser);
+}
+END_TEST
+
+START_TEST(test_alloc_tracker_threshold) {
+  XML_Parser parser = XML_ParserCreate(NULL);
+
+#if XML_GE == 1
+  // Exceed maximum amplification *before* (default) threshold: should work.
+  void *const ptr = expat_malloc(parser, 1000, -1);
+  assert_true(ptr != NULL);
+  expat_free(parser, ptr, -1);
+
+  // Exceed maximum amplification *after* threshold: should be rejected.
+  assert_true(XML_SetAllocTrackerActivationThreshold(parser, 999) == XML_TRUE);
+  assert_true(expat_malloc(parser, 1000, -1) == NULL);
+#endif
+
+  XML_ParserFree(parser);
+}
+END_TEST
+
+START_TEST(test_alloc_tracker_getbuffer_unlimited) {
+  XML_Parser parser = XML_ParserCreate(NULL);
+
+#if XML_GE == 1
+  // Artificially lower threshold
+  assert_true(XML_SetAllocTrackerActivationThreshold(parser, 0) == XML_TRUE);
+
+  // Self-test: Prove that threshold is as rejecting as expected
+  assert_true(expat_malloc(parser, 1000, -1) == NULL);
+#endif
+  // XML_GetBuffer should be allowed to pass, though
+  assert_true(XML_GetBuffer(parser, 1000) != NULL);
+
+  XML_ParserFree(parser);
+}
+END_TEST
+
+START_TEST(test_alloc_tracker_api) {
+  XML_Parser parserWithoutParent = XML_ParserCreate(NULL);
+  XML_Parser parserWithParent = XML_ExternalEntityParserCreate(
+      parserWithoutParent, XCS("entity123"), NULL);
+  if (parserWithoutParent == NULL)
+    fail("parserWithoutParent is NULL");
+  if (parserWithParent == NULL)
+    fail("parserWithParent is NULL");
+
+#if XML_GE == 1
+  // XML_SetAllocTrackerMaximumAmplification, error cases
+  if (XML_SetAllocTrackerMaximumAmplification(NULL, 123.0f) == XML_TRUE)
+    fail("Call with NULL parser is NOT supposed to succeed");
+  if (XML_SetAllocTrackerMaximumAmplification(parserWithParent, 123.0f)
+      == XML_TRUE)
+    fail("Call with non-root parser is NOT supposed to succeed");
+  if (XML_SetAllocTrackerMaximumAmplification(parserWithoutParent, NAN)
+      == XML_TRUE)
+    fail("Call with NaN limit is NOT supposed to succeed");
+  if (XML_SetAllocTrackerMaximumAmplification(parserWithoutParent, -1.0f)
+      == XML_TRUE)
+    fail("Call with negative limit is NOT supposed to succeed");
+  if (XML_SetAllocTrackerMaximumAmplification(parserWithoutParent, 0.9f)
+      == XML_TRUE)
+    fail("Call with positive limit <1.0 is NOT supposed to succeed");
+
+  // XML_SetAllocTrackerMaximumAmplification, success cases
+  if (XML_SetAllocTrackerMaximumAmplification(parserWithoutParent, 1.0f)
+      == XML_FALSE)
+    fail("Call with positive limit >=1.0 is supposed to succeed");
+  if (XML_SetAllocTrackerMaximumAmplification(parserWithoutParent, 123456.789f)
+      == XML_FALSE)
+    fail("Call with positive limit >=1.0 is supposed to succeed");
+  if (XML_SetAllocTrackerMaximumAmplification(parserWithoutParent, INFINITY)
+      == XML_FALSE)
+    fail("Call with positive limit >=1.0 is supposed to succeed");
+
+  // XML_SetAllocTrackerActivationThreshold, error cases
+  if (XML_SetAllocTrackerActivationThreshold(NULL, 123) == XML_TRUE)
+    fail("Call with NULL parser is NOT supposed to succeed");
+  if (XML_SetAllocTrackerActivationThreshold(parserWithParent, 123) == XML_TRUE)
+    fail("Call with non-root parser is NOT supposed to succeed");
+
+  // XML_SetAllocTrackerActivationThreshold, success cases
+  if (XML_SetAllocTrackerActivationThreshold(parserWithoutParent, 123)
+      == XML_FALSE)
+    fail("Call with non-NULL parentless parser is supposed to succeed");
+#endif // XML_GE == 1
+
+  XML_ParserFree(parserWithParent);
+  XML_ParserFree(parserWithoutParent);
+}
+END_TEST
+
+START_TEST(test_mem_api_cycle) {
+  XML_Parser parser = XML_ParserCreate(NULL);
+
+  void *ptr = XML_MemMalloc(parser, 10);
+
+  assert_true(ptr != NULL);
+  memset(ptr, 'x', 10); // assert writability, with ASan in mind
+
+  ptr = XML_MemRealloc(parser, ptr, 20);
+
+  assert_true(ptr != NULL);
+  memset(ptr, 'y', 20); // assert writability, with ASan in mind
+
+  XML_MemFree(parser, ptr);
+
+  XML_ParserFree(parser);
+}
+END_TEST
+
+START_TEST(test_mem_api_unlimited) {
+  XML_Parser parser = XML_ParserCreate(NULL);
+
+#if XML_GE == 1
+  assert_true(XML_SetAllocTrackerActivationThreshold(parser, 0) == XML_TRUE);
+#endif
+
+  void *ptr = XML_MemMalloc(parser, 1000);
+
+  assert_true(ptr != NULL);
+
+  ptr = XML_MemRealloc(parser, ptr, 2000);
+
+  assert_true(ptr != NULL);
+
+  XML_MemFree(parser, ptr);
+
+  XML_ParserFree(parser);
+}
+END_TEST
+
 void
 make_alloc_test_case(Suite *s) {
   TCase *tc_alloc = tcase_create("allocation tests");
@@ -2151,4 +2377,14 @@ make_alloc_test_case(Suite *s) {
 
   tcase_add_test__ifdef_xml_dtd(
       tc_alloc, test_alloc_reset_after_external_entity_parser_create_fail);
+
+  tcase_add_test__if_xml_ge(tc_alloc, test_alloc_tracker_size_recorded);
+  tcase_add_test__if_xml_ge(tc_alloc, test_alloc_tracker_pointer_alignment);
+  tcase_add_test__if_xml_ge(tc_alloc, test_alloc_tracker_maximum_amplification);
+  tcase_add_test__if_xml_ge(tc_alloc, test_alloc_tracker_threshold);
+  tcase_add_test__if_xml_ge(tc_alloc, test_alloc_tracker_getbuffer_unlimited);
+  tcase_add_test__if_xml_ge(tc_alloc, test_alloc_tracker_api);
+
+  tcase_add_test(tc_alloc, test_mem_api_cycle);
+  tcase_add_test__if_xml_ge(tc_alloc, test_mem_api_unlimited);
 }

+ 6 - 2
libs/expat/tests/basic_tests.c

@@ -412,13 +412,13 @@ START_TEST(test_utf16_le_epilog_newline) {
 
   if (first_chunk_bytes >= sizeof(text) - 1)
     fail("bad value of first_chunk_bytes");
-  if (_XML_Parse_SINGLE_BYTES(g_parser, text, first_chunk_bytes, XML_FALSE)
+  if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)first_chunk_bytes, XML_FALSE)
       == XML_STATUS_ERROR)
     xml_failure(g_parser);
   else {
     enum XML_Status rc;
     rc = _XML_Parse_SINGLE_BYTES(g_parser, text + first_chunk_bytes,
-                                 sizeof(text) - first_chunk_bytes - 1,
+                                 (int)(sizeof(text) - first_chunk_bytes - 1),
                                  XML_TRUE);
     if (rc == XML_STATUS_ERROR)
       xml_failure(g_parser);
@@ -3123,6 +3123,10 @@ START_TEST(test_buffer_can_grow_to_max) {
   for (int i = 0; i < num_prefixes; ++i) {
     set_subtest("\"%s\"", prefixes[i]);
     XML_Parser parser = XML_ParserCreate(NULL);
+#if XML_GE == 1
+    assert_true(XML_SetAllocTrackerActivationThreshold(parser, (size_t)-1)
+                == XML_TRUE); // i.e. deactivate
+#endif
     const int prefix_len = (int)strlen(prefixes[i]);
     const enum XML_Status s
         = _XML_Parse_SINGLE_BYTES(parser, prefixes[i], prefix_len, XML_FALSE);

+ 21 - 14
libs/expat/tests/benchmark/Makefile.in

@@ -1,7 +1,7 @@
-# Makefile.in generated by automake 1.16.5 from Makefile.am.
+# Makefile.in generated by automake 1.18.1 from Makefile.am.
 # @configure_input@
 
-# Copyright (C) 1994-2021 Free Software Foundation, Inc.
+# Copyright (C) 1994-2025 Free Software Foundation, Inc.
 
 # This Makefile.in is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -101,6 +101,8 @@ am__make_running_with_option = \
   test $$has_opt = yes
 am__make_dryrun = (target_option=n; $(am__make_running_with_option))
 am__make_keepgoing = (target_option=k; $(am__make_running_with_option))
+am__rm_f = rm -f $(am__rm_f_notfound)
+am__rm_rf = rm -rf $(am__rm_f_notfound)
 pkgdatadir = $(datadir)/@PACKAGE@
 pkgincludedir = $(includedir)/@PACKAGE@
 pkglibdir = $(libdir)/@PACKAGE@
@@ -320,8 +322,10 @@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@
 am__include = @am__include@
 am__leading_dot = @am__leading_dot@
 am__quote = @am__quote@
+am__rm_f_notfound = @am__rm_f_notfound@
 am__tar = @am__tar@
 am__untar = @am__untar@
+am__xargs_n = @am__xargs_n@
 bindir = @bindir@
 build = @build@
 build_alias = @build_alias@
@@ -403,13 +407,8 @@ $(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps)
 $(am__aclocal_m4_deps):
 
 clean-noinstPROGRAMS:
-	@list='$(noinst_PROGRAMS)'; test -n "$$list" || exit 0; \
-	echo " rm -f" $$list; \
-	rm -f $$list || exit $$?; \
-	test -n "$(EXEEXT)" || exit 0; \
-	list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \
-	echo " rm -f" $$list; \
-	rm -f $$list
+	$(am__rm_f) $(noinst_PROGRAMS)
+	test -z "$(EXEEXT)" || $(am__rm_f) $(noinst_PROGRAMS:$(EXEEXT)=)
 
 benchmark$(EXEEXT): $(benchmark_OBJECTS) $(benchmark_DEPENDENCIES) $(EXTRA_benchmark_DEPENDENCIES) 
 	@rm -f benchmark$(EXEEXT)
@@ -425,7 +424,7 @@ distclean-compile:
 
 $(am__depfiles_remade):
 	@$(MKDIR_P) $(@D)
-	@echo '# dummy' >$@-t && $(am__mv) $@-t $@
+	@: >>$@
 
 am--depfiles: $(am__depfiles_remade)
 
@@ -507,6 +506,7 @@ cscopelist-am: $(am__tagged_files)
 
 distclean-tags:
 	-rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags
+
 distdir: $(BUILT_SOURCES)
 	$(MAKE) $(AM_MAKEFLAGS) distdir-am
 
@@ -568,8 +568,8 @@ mostlyclean-generic:
 clean-generic:
 
 distclean-generic:
-	-test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
-	-test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES)
+	-$(am__rm_f) $(CONFIG_CLEAN_FILES)
+	-test . = "$(srcdir)" || $(am__rm_f) $(CONFIG_CLEAN_VPATH_FILES)
 
 maintainer-clean-generic:
 	@echo "This command is intended for maintainers to use"
@@ -580,7 +580,7 @@ clean-am: clean-generic clean-libtool clean-noinstPROGRAMS \
 	mostlyclean-am
 
 distclean: distclean-am
-		-rm -f ./$(DEPDIR)/benchmark.Po
+	-rm -f ./$(DEPDIR)/benchmark.Po
 	-rm -f Makefile
 distclean-am: clean-am distclean-compile distclean-generic \
 	distclean-tags
@@ -626,7 +626,7 @@ install-ps-am:
 installcheck-am:
 
 maintainer-clean: maintainer-clean-am
-		-rm -f ./$(DEPDIR)/benchmark.Po
+	-rm -f ./$(DEPDIR)/benchmark.Po
 	-rm -f Makefile
 maintainer-clean-am: distclean-am maintainer-clean-generic
 
@@ -667,3 +667,10 @@ uninstall-am:
 # Tell versions [3.59,3.63) of GNU make to not export all variables.
 # Otherwise a system limit (for SysV at least) may be exceeded.
 .NOEXPORT:
+
+# Tell GNU make to disable its built-in pattern rules.
+%:: %,v
+%:: RCS/%,v
+%:: RCS/%
+%:: s.%
+%:: SCCS/s.%

+ 10 - 1
libs/expat/tests/common.c

@@ -303,7 +303,14 @@ duff_reallocator(void *ptr, size_t size) {
   return realloc(ptr, size);
 }
 
-// Portable remake of strndup(3) for C99; does not care about space efficiency
+// Portable remake of strnlen(3) for C99
+static size_t
+portable_strnlen(const char *s, size_t maxlen) {
+  const char *const end = (const char *)memchr(s, '\0', maxlen);
+  return (end == NULL) ? maxlen : (size_t)(end - s);
+}
+
+// Portable remake of strndup(3) for C99
 char *
 portable_strndup(const char *s, size_t n) {
   if ((s == NULL) || (n == SIZE_MAX)) {
@@ -311,6 +318,8 @@ portable_strndup(const char *s, size_t n) {
     return NULL;
   }
 
+  n = portable_strnlen(s, n);
+
   char *const buffer = (char *)malloc(n + 1);
   if (buffer == NULL) {
     errno = ENOMEM;

+ 15 - 14
libs/expat/tests/handlers.c

@@ -10,7 +10,7 @@
    Copyright (c) 2003      Greg Stein <[email protected]>
    Copyright (c) 2005-2007 Steven Solie <[email protected]>
    Copyright (c) 2005-2012 Karl Waclawek <[email protected]>
-   Copyright (c) 2016-2024 Sebastian Pipping <[email protected]>
+   Copyright (c) 2016-2025 Sebastian Pipping <[email protected]>
    Copyright (c) 2017-2022 Rhodri James <[email protected]>
    Copyright (c) 2017      Joe Orton <[email protected]>
    Copyright (c) 2017      José Gutiérrez de la Concha <[email protected]>
@@ -89,15 +89,15 @@ start_element_event_handler2(void *userData, const XML_Char *name,
                              const XML_Char **attr) {
   StructData *storage = (StructData *)userData;
   UNUSED_P(attr);
-  StructData_AddItem(storage, name, XML_GetCurrentColumnNumber(g_parser),
-                     XML_GetCurrentLineNumber(g_parser), STRUCT_START_TAG);
+  StructData_AddItem(storage, name, (int)XML_GetCurrentColumnNumber(g_parser),
+                     (int)XML_GetCurrentLineNumber(g_parser), STRUCT_START_TAG);
 }
 
 void XMLCALL
 end_element_event_handler2(void *userData, const XML_Char *name) {
   StructData *storage = (StructData *)userData;
-  StructData_AddItem(storage, name, XML_GetCurrentColumnNumber(g_parser),
-                     XML_GetCurrentLineNumber(g_parser), STRUCT_END_TAG);
+  StructData_AddItem(storage, name, (int)XML_GetCurrentColumnNumber(g_parser),
+                     (int)XML_GetCurrentLineNumber(g_parser), STRUCT_END_TAG);
 }
 
 void XMLCALL
@@ -132,7 +132,7 @@ counting_start_element_handler(void *userData, const XML_Char *name,
     fail("ID not present");
     return;
   }
-  if (id != -1 && xcstrcmp(atts[id], info->id_name)) {
+  if (id != -1 && xcstrcmp(atts[id], info->id_name) != 0) {
     fail("ID does not have the correct name");
     return;
   }
@@ -147,7 +147,7 @@ counting_start_element_handler(void *userData, const XML_Char *name,
       fail("Attribute not recognised");
       return;
     }
-    if (xcstrcmp(atts[1], attr->value)) {
+    if (xcstrcmp(atts[1], attr->value) != 0) {
       fail("Attribute has wrong value");
       return;
     }
@@ -1110,7 +1110,7 @@ external_entity_devaluer(XML_Parser parser, const XML_Char *context,
   UNUSED_P(publicId);
   if (systemId == NULL || ! xcstrcmp(systemId, XCS("bar")))
     return XML_STATUS_OK;
-  if (xcstrcmp(systemId, XCS("foo")))
+  if (xcstrcmp(systemId, XCS("foo")) != 0)
     fail("Unexpected system ID");
   ext_parser = XML_ExternalEntityParserCreate(parser, context, NULL);
   if (ext_parser == NULL)
@@ -1276,7 +1276,7 @@ external_entity_duff_loader(XML_Parser parser, const XML_Char *context,
   UNUSED_P(publicId);
   /* Try a few different allocation levels */
   for (i = 0; i < max_alloc_count; i++) {
-    g_allocation_count = i;
+    g_allocation_count = (int)i;
     new_parser = XML_ExternalEntityParserCreate(parser, context, NULL);
     if (new_parser != NULL) {
       XML_ParserFree(new_parser);
@@ -1552,15 +1552,16 @@ verify_attlist_decl_handler(void *userData, const XML_Char *element_name,
                             const XML_Char *default_value, int is_required) {
   AttTest *at = (AttTest *)userData;
 
-  if (xcstrcmp(element_name, at->element_name))
+  if (xcstrcmp(element_name, at->element_name) != 0)
     fail("Unexpected element name in attribute declaration");
-  if (xcstrcmp(attr_name, at->attr_name))
+  if (xcstrcmp(attr_name, at->attr_name) != 0)
     fail("Unexpected attribute name in attribute declaration");
-  if (xcstrcmp(attr_type, at->attr_type))
+  if (xcstrcmp(attr_type, at->attr_type) != 0)
     fail("Unexpected attribute type in attribute declaration");
   if ((default_value == NULL && at->default_value != NULL)
       || (default_value != NULL && at->default_value == NULL)
-      || (default_value != NULL && xcstrcmp(default_value, at->default_value)))
+      || (default_value != NULL
+          && xcstrcmp(default_value, at->default_value) != 0))
     fail("Unexpected default value in attribute declaration");
   if (is_required != at->is_required)
     fail("Requirement mismatch in attribute declaration");
@@ -1751,7 +1752,7 @@ param_entity_match_handler(void *userData, const XML_Char *entityName,
      * going to overflow an int.
      */
     if (value_length != (int)xcstrlen(entity_value_to_match)
-        || xcstrncmp(value, entity_value_to_match, value_length)) {
+        || xcstrncmp(value, entity_value_to_match, value_length) != 0) {
       entity_match_flag = ENTITY_MATCH_FAIL;
     } else {
       entity_match_flag = ENTITY_MATCH_SUCCESS;

+ 1 - 2
libs/expat/tests/minicheck.h

@@ -134,8 +134,7 @@ void _check_set_test_info(char const *function, char const *filename,
 __attribute__((noreturn))
 #    endif
 #  endif
-void
-_fail(const char *file, int line, const char *msg);
+void _fail(const char *file, int line, const char *msg);
 Suite *suite_create(const char *name);
 TCase *tcase_create(const char *name);
 void suite_add_tcase(Suite *suite, TCase *tc);

+ 98 - 3
libs/expat/tests/misc_tests.c

@@ -70,7 +70,7 @@ START_TEST(test_misc_alloc_create_parser) {
 
   /* Something this simple shouldn't need more than 10 allocations */
   for (i = 0; i < max_alloc_count; i++) {
-    g_allocation_count = i;
+    g_allocation_count = (int)i;
     g_parser = XML_ParserCreate_MM(NULL, &memsuite, NULL);
     if (g_parser != NULL)
       break;
@@ -90,7 +90,7 @@ START_TEST(test_misc_alloc_create_parser_with_encoding) {
 
   /* Try several levels of allocation */
   for (i = 0; i < max_alloc_count; i++) {
-    g_allocation_count = i;
+    g_allocation_count = (int)i;
     g_parser = XML_ParserCreate_MM(XCS("us-ascii"), &memsuite, NULL);
     if (g_parser != NULL)
       break;
@@ -211,7 +211,8 @@ START_TEST(test_misc_version) {
   if (! versions_equal(&read_version, &parsed_version))
     fail("Version mismatch");
 
-  if (xcstrcmp(version_text, XCS("expat_2.7.1"))) /* needs bump on releases */
+  if (xcstrcmp(version_text, XCS("expat_2.7.3"))
+      != 0) /* needs bump on releases */
     fail("XML_*_VERSION in expat.h out of sync?\n");
 }
 END_TEST
@@ -678,6 +679,98 @@ START_TEST(test_misc_expected_event_ptr_issue_980) {
 }
 END_TEST
 
+START_TEST(test_misc_sync_entity_tolerated) {
+  const char *const doc = "<!DOCTYPE t0 [\n"
+                          "   <!ENTITY a '<t1></t1>'>\n"
+                          "   <!ENTITY b '<t2>two</t2>'>\n"
+                          "   <!ENTITY c '<t3>three<t4>four</t4>three</t3>'>\n"
+                          "   <!ENTITY d '<t5>&b;</t5>'>\n"
+                          "]>\n"
+                          "<t0>&a;&b;&c;&d;</t0>\n";
+  XML_Parser parser = XML_ParserCreate(NULL);
+
+  assert_true(_XML_Parse_SINGLE_BYTES(parser, doc, (int)strlen(doc),
+                                      /*isFinal=*/XML_TRUE)
+              == XML_STATUS_OK);
+
+  XML_ParserFree(parser);
+}
+END_TEST
+
+START_TEST(test_misc_async_entity_rejected) {
+  struct test_case {
+    const char *doc;
+    enum XML_Status expectedStatusNoGE;
+    enum XML_Error expectedErrorNoGE;
+    XML_Size expectedErrorLine;
+    XML_Size expectedErrorColumn;
+  };
+  const struct test_case cases[] = {
+      // Opened by one entity, closed by another
+      {"<!DOCTYPE t0 [\n"
+       "   <!ENTITY open '<t1>'>\n"
+       "   <!ENTITY close '</t1>'>\n"
+       "]>\n"
+       "<t0>&open;&close;</t0>\n",
+       XML_STATUS_OK, XML_ERROR_NONE, 5, 4},
+      // Opened by tag, closed by entity (non-root case)
+      {"<!DOCTYPE t0 [\n"
+       "  <!ENTITY g0 ''>\n"
+       "  <!ENTITY g1 '&g0;</t1>'>\n"
+       "]>\n"
+       "<t0><t1>&g1;</t0>\n",
+       XML_STATUS_ERROR, XML_ERROR_TAG_MISMATCH, 5, 8},
+      // Opened by tag, closed by entity (root case)
+      {"<!DOCTYPE t0 [\n"
+       "  <!ENTITY g0 ''>\n"
+       "  <!ENTITY g1 '&g0;</t0>'>\n"
+       "]>\n"
+       "<t0>&g1;\n",
+       XML_STATUS_ERROR, XML_ERROR_NO_ELEMENTS, 5, 4},
+      // Opened by entity, closed by tag <-- regression from 2.7.0
+      {"<!DOCTYPE t0 [\n"
+       "  <!ENTITY g0 ''>\n"
+       "  <!ENTITY g1 '<t1>&g0;'>\n"
+       "]>\n"
+       "<t0>&g1;</t1></t0>\n",
+       XML_STATUS_ERROR, XML_ERROR_TAG_MISMATCH, 5, 4},
+      // Opened by tag, closed by entity; then the other way around
+      {"<!DOCTYPE t0 [\n"
+       "  <!ENTITY open '<t1>'>\n"
+       "  <!ENTITY close '</t1>'>\n"
+       "]>\n"
+       "<t0><t1>&close;&open;</t1></t0>\n",
+       XML_STATUS_OK, XML_ERROR_NONE, 5, 8},
+  };
+
+  for (size_t i = 0; i < sizeof(cases) / sizeof(cases[0]); i++) {
+    const struct test_case testCase = cases[i];
+    set_subtest("cases[%d]", (int)i);
+
+    const char *const doc = testCase.doc;
+#if XML_GE == 1
+    const enum XML_Status expectedStatus = XML_STATUS_ERROR;
+    const enum XML_Error expectedError = XML_ERROR_ASYNC_ENTITY;
+#else
+    const enum XML_Status expectedStatus = testCase.expectedStatusNoGE;
+    const enum XML_Error expectedError = testCase.expectedErrorNoGE;
+#endif
+
+    XML_Parser parser = XML_ParserCreate(NULL);
+    assert_true(_XML_Parse_SINGLE_BYTES(parser, doc, (int)strlen(doc),
+                                        /*isFinal=*/XML_TRUE)
+                == expectedStatus);
+    assert_true(XML_GetErrorCode(parser) == expectedError);
+#if XML_GE == 1
+    assert_true(XML_GetCurrentLineNumber(parser) == testCase.expectedErrorLine);
+    assert_true(XML_GetCurrentColumnNumber(parser)
+                == testCase.expectedErrorColumn);
+#endif
+    XML_ParserFree(parser);
+  }
+}
+END_TEST
+
 void
 make_miscellaneous_test_case(Suite *s) {
   TCase *tc_misc = tcase_create("miscellaneous tests");
@@ -706,4 +799,6 @@ make_miscellaneous_test_case(Suite *s) {
   tcase_add_test(tc_misc, test_misc_stopparser_rejects_unstarted_parser);
   tcase_add_test__if_xml_ge(tc_misc, test_renter_loop_finite_content);
   tcase_add_test(tc_misc, test_misc_expected_event_ptr_issue_980);
+  tcase_add_test(tc_misc, test_misc_sync_entity_tolerated);
+  tcase_add_test(tc_misc, test_misc_async_entity_rejected);
 }

+ 8 - 3
libs/expat/tests/nsalloc_tests.c

@@ -10,7 +10,7 @@
    Copyright (c) 2003      Greg Stein <[email protected]>
    Copyright (c) 2005-2007 Steven Solie <[email protected]>
    Copyright (c) 2005-2012 Karl Waclawek <[email protected]>
-   Copyright (c) 2016-2023 Sebastian Pipping <[email protected]>
+   Copyright (c) 2016-2025 Sebastian Pipping <[email protected]>
    Copyright (c) 2017-2022 Rhodri James <[email protected]>
    Copyright (c) 2017      Joe Orton <[email protected]>
    Copyright (c) 2017      José Gutiérrez de la Concha <[email protected]>
@@ -83,7 +83,7 @@ START_TEST(test_nsalloc_xmlns) {
   const unsigned int max_alloc_count = 30;
 
   for (i = 0; i < max_alloc_count; i++) {
-    g_allocation_count = i;
+    g_allocation_count = (int)i;
     /* Exercise more code paths with a default handler */
     XML_SetDefaultHandler(g_parser, dummy_default_handler);
     if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
@@ -454,10 +454,15 @@ START_TEST(test_nsalloc_realloc_attributes) {
     nsalloc_teardown();
     nsalloc_setup();
   }
+#if XML_GE == 1
+  assert_true(
+      i == 0); // because expat_realloc relies on expat_malloc to some extent
+#else
   if (i == 0)
     fail("Parsing worked despite failing reallocations");
   else if (i == max_realloc_count)
     fail("Parsing failed at max reallocation count");
+#endif
 }
 END_TEST
 
@@ -523,7 +528,7 @@ START_TEST(test_nsalloc_realloc_binding_uri) {
   /* Now repeat with a longer URI and a duff reallocator */
   for (i = 0; i < max_realloc_count; i++) {
     XML_ParserReset(g_parser, NULL);
-    g_reallocation_count = i;
+    g_reallocation_count = (int)i;
     if (_XML_Parse_SINGLE_BYTES(g_parser, second, (int)strlen(second), XML_TRUE)
         != XML_STATUS_ERROR)
       break;

+ 2 - 2
libs/expat/win32/README.txt

@@ -5,13 +5,13 @@ Expat can be built on Windows in two ways:
 * Cygwin:
   This follows the Unix build procedures.
 
-* MS Visual Studio 2019 and 2022:
+* MS Visual Studio 2022:
   Use CMake to generate a solution file for Visual Studio, then use msbuild
   to compile.  For example:
 
   md build
   cd build
-  cmake -G"Visual Studio 16 2019" -DCMAKE_BUILD_TYPE=RelWithDebInfo ..
+  cmake -G"Visual Studio 17 2022" -DCMAKE_BUILD_TYPE=RelWithDebInfo ..
   msbuild /m expat.sln
 
 * All MS C/C++ compilers:

+ 2 - 2
libs/expat/win32/build_expat_iss.bat

@@ -7,7 +7,7 @@ REM                     |  __//  \| |_) | (_| | |_
 REM                      \___/_/\_\ .__/ \__,_|\__|
 REM                               |_| XML parser
 REM
-REM Copyright (c) 2019-2024 Sebastian Pipping <[email protected]>
+REM Copyright (c) 2019-2025 Sebastian Pipping <[email protected]>
 REM Licensed under the MIT license:
 REM
 REM Permission is  hereby granted,  free of charge,  to any  person obtaining
@@ -29,7 +29,7 @@ REM DAMAGES OR  OTHER LIABILITY, WHETHER  IN AN  ACTION OF CONTRACT,  TORT OR
 REM OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
 REM USE OR OTHER DEALINGS IN THE SOFTWARE.
 
-SET GENERATOR=Visual Studio 16 2019
+SET GENERATOR=Visual Studio 17 2022
 
 REM Read by msbuild!
 SET CONFIGURATION=RelWithDebInfo

+ 1 - 1
libs/expat/win32/expat.iss

@@ -38,7 +38,7 @@
 ; OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
 ; USE OR OTHER DEALINGS IN THE SOFTWARE.
 
-#define expatVer "2.7.1"
+#define expatVer "2.7.3"
 
 [Setup]
 AppName=Expat

+ 22 - 15
libs/expat/xmlwf/Makefile.in

@@ -1,7 +1,7 @@
-# Makefile.in generated by automake 1.16.5 from Makefile.am.
+# Makefile.in generated by automake 1.18.1 from Makefile.am.
 # @configure_input@
 
-# Copyright (C) 1994-2021 Free Software Foundation, Inc.
+# Copyright (C) 1994-2025 Free Software Foundation, Inc.
 
 # This Makefile.in is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -100,6 +100,8 @@ am__make_running_with_option = \
   test $$has_opt = yes
 am__make_dryrun = (target_option=n; $(am__make_running_with_option))
 am__make_keepgoing = (target_option=k; $(am__make_running_with_option))
+am__rm_f = rm -f $(am__rm_f_notfound)
+am__rm_rf = rm -rf $(am__rm_f_notfound)
 pkgdatadir = $(datadir)/@PACKAGE@
 pkgincludedir = $(includedir)/@PACKAGE@
 pkglibdir = $(libdir)/@PACKAGE@
@@ -328,8 +330,10 @@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@
 am__include = @am__include@
 am__leading_dot = @am__leading_dot@
 am__quote = @am__quote@
+am__rm_f_notfound = @am__rm_f_notfound@
 am__tar = @am__tar@
 am__untar = @am__untar@
+am__xargs_n = @am__xargs_n@
 bindir = @bindir@
 build = @build@
 build_alias = @build_alias@
@@ -464,16 +468,11 @@ uninstall-binPROGRAMS:
 	`; \
 	test -n "$$list" || exit 0; \
 	echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \
-	cd "$(DESTDIR)$(bindir)" && rm -f $$files
+	cd "$(DESTDIR)$(bindir)" && $(am__rm_f) $$files
 
 clean-binPROGRAMS:
-	@list='$(bin_PROGRAMS)'; test -n "$$list" || exit 0; \
-	echo " rm -f" $$list; \
-	rm -f $$list || exit $$?; \
-	test -n "$(EXEEXT)" || exit 0; \
-	list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \
-	echo " rm -f" $$list; \
-	rm -f $$list
+	$(am__rm_f) $(bin_PROGRAMS)
+	test -z "$(EXEEXT)" || $(am__rm_f) $(bin_PROGRAMS:$(EXEEXT)=)
 
 xmlwf$(EXEEXT): $(xmlwf_OBJECTS) $(xmlwf_DEPENDENCIES) $(EXTRA_xmlwf_DEPENDENCIES) 
 	@rm -f xmlwf$(EXEEXT)
@@ -492,7 +491,7 @@ distclean-compile:
 
 $(am__depfiles_remade):
 	@$(MKDIR_P) $(@D)
-	@echo '# dummy' >$@-t && $(am__mv) $@-t $@
+	@: >>$@
 
 am--depfiles: $(am__depfiles_remade)
 
@@ -630,6 +629,7 @@ cscopelist-am: $(am__tagged_files)
 
 distclean-tags:
 	-rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags
+
 distdir: $(BUILT_SOURCES)
 	$(MAKE) $(AM_MAKEFLAGS) distdir-am
 
@@ -694,8 +694,8 @@ mostlyclean-generic:
 clean-generic:
 
 distclean-generic:
-	-test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
-	-test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES)
+	-$(am__rm_f) $(CONFIG_CLEAN_FILES)
+	-test . = "$(srcdir)" || $(am__rm_f) $(CONFIG_CLEAN_VPATH_FILES)
 
 maintainer-clean-generic:
 	@echo "This command is intended for maintainers to use"
@@ -705,7 +705,7 @@ clean: clean-am
 clean-am: clean-binPROGRAMS clean-generic clean-libtool mostlyclean-am
 
 distclean: distclean-am
-		-rm -f ./$(DEPDIR)/xmlwf-@[email protected]
+	-rm -f ./$(DEPDIR)/xmlwf-@[email protected]
 	-rm -f ./$(DEPDIR)/xmlwf-codepage.Po
 	-rm -f ./$(DEPDIR)/xmlwf-xmlfile.Po
 	-rm -f ./$(DEPDIR)/xmlwf-xmlwf.Po
@@ -754,7 +754,7 @@ install-ps-am:
 installcheck-am:
 
 maintainer-clean: maintainer-clean-am
-		-rm -f ./$(DEPDIR)/xmlwf-@[email protected]
+	-rm -f ./$(DEPDIR)/xmlwf-@[email protected]
 	-rm -f ./$(DEPDIR)/xmlwf-codepage.Po
 	-rm -f ./$(DEPDIR)/xmlwf-xmlfile.Po
 	-rm -f ./$(DEPDIR)/xmlwf-xmlwf.Po
@@ -798,3 +798,10 @@ uninstall-am: uninstall-binPROGRAMS
 # Tell versions [3.59,3.63) of GNU make to not export all variables.
 # Otherwise a system limit (for SysV at least) may be exceeded.
 .NOEXPORT:
+
+# Tell GNU make to disable its built-in pattern rules.
+%:: %,v
+%:: RCS/%,v
+%:: RCS/%
+%:: s.%
+%:: SCCS/s.%

+ 3 - 3
libs/expat/xmlwf/unixfilemap.c

@@ -10,7 +10,7 @@
    Copyright (c) 2000      Clark Cooper <[email protected]>
    Copyright (c) 2001-2002 Fred L. Drake, Jr. <[email protected]>
    Copyright (c) 2006      Karl Waclawek <[email protected]>
-   Copyright (c) 2016-2017 Sebastian Pipping <[email protected]>
+   Copyright (c) 2016-2025 Sebastian Pipping <[email protected]>
    Copyright (c) 2017      Rhodri James <[email protected]>
    Licensed under the MIT license:
 
@@ -41,6 +41,7 @@
 #include <errno.h>
 #include <string.h>
 #include <stdio.h>
+#include <stdlib.h> // NULL
 #include <unistd.h>
 
 #ifndef MAP_FILE
@@ -93,8 +94,7 @@ filemap(const tchar *name,
     close(fd);
     return 1;
   }
-  p = (void *)mmap((void *)0, (size_t)nbytes, PROT_READ, MAP_FILE | MAP_PRIVATE,
-                   fd, (off_t)0);
+  p = mmap(NULL, nbytes, PROT_READ, MAP_FILE | MAP_PRIVATE, fd, (off_t)0);
   if (p == (void *)-1) {
     tperror(name);
     close(fd);

+ 16 - 9
libs/expat/xmlwf/xmlfile.c

@@ -11,7 +11,7 @@
    Copyright (c) 2002-2003 Fred L. Drake, Jr. <[email protected]>
    Copyright (c) 2004-2006 Karl Waclawek <[email protected]>
    Copyright (c) 2005-2007 Steven Solie <[email protected]>
-   Copyright (c) 2016-2023 Sebastian Pipping <[email protected]>
+   Copyright (c) 2016-2025 Sebastian Pipping <[email protected]>
    Copyright (c) 2017      Rhodri James <[email protected]>
    Copyright (c) 2019      David Loffredo <[email protected]>
    Copyright (c) 2021      Donghee Na <[email protected]>
@@ -56,12 +56,19 @@
 #include "xmltchar.h"
 #include "filemap.h"
 
+/* Function "read": */
 #if defined(_MSC_VER)
 #  include <io.h>
-#endif
-
-#ifdef HAVE_UNISTD_H
+/* https://msdn.microsoft.com/en-us/library/wyssk1bs(v=vs.100).aspx */
+#  define EXPAT_read _read
+#  define EXPAT_read_count_t int
+#  define EXPAT_read_req_t unsigned int
+#else /* POSIX */
 #  include <unistd.h>
+/* https://pubs.opengroup.org/onlinepubs/009695399/functions/read.html */
+#  define EXPAT_read read
+#  define EXPAT_read_count_t ssize_t
+#  define EXPAT_read_req_t size_t
 #endif
 
 #ifndef O_BINARY
@@ -89,8 +96,8 @@ reportError(XML_Parser parser, const XML_Char *filename) {
     ftprintf(stdout,
              T("%s") T(":%") T(XML_FMT_INT_MOD) T("u") T(":%")
                  T(XML_FMT_INT_MOD) T("u") T(": %s\n"),
-             filename, XML_GetErrorLineNumber(parser),
-             XML_GetErrorColumnNumber(parser), message);
+             filename, XML_GetCurrentLineNumber(parser),
+             XML_GetCurrentColumnNumber(parser), message);
   else
     ftprintf(stderr, T("%s: (unknown message %u)\n"), filename,
              (unsigned int)code);
@@ -192,7 +199,7 @@ processStream(const XML_Char *filename, XML_Parser parser) {
     }
   }
   for (;;) {
-    int nread;
+    EXPAT_read_count_t nread;
     char *buf = (char *)XML_GetBuffer(parser, g_read_size_bytes);
     if (! buf) {
       if (filename != NULL)
@@ -201,14 +208,14 @@ processStream(const XML_Char *filename, XML_Parser parser) {
                filename != NULL ? filename : T("xmlwf"));
       return 0;
     }
-    nread = read(fd, buf, g_read_size_bytes);
+    nread = EXPAT_read(fd, buf, (EXPAT_read_req_t)g_read_size_bytes);
     if (nread < 0) {
       tperror(filename != NULL ? filename : T("STDIN"));
       if (filename != NULL)
         close(fd);
       return 0;
     }
-    if (XML_ParseBuffer(parser, nread, nread == 0) == XML_STATUS_ERROR) {
+    if (XML_ParseBuffer(parser, (int)nread, nread == 0) == XML_STATUS_ERROR) {
       reportError(parser, filename != NULL ? filename : T("STDIN"));
       if (filename != NULL)
         close(fd);

+ 17 - 4
libs/expat/xmlwf/xmlwf.c

@@ -11,7 +11,7 @@
    Copyright (c) 2001-2003 Fred L. Drake, Jr. <[email protected]>
    Copyright (c) 2004-2009 Karl Waclawek <[email protected]>
    Copyright (c) 2005-2007 Steven Solie <[email protected]>
-   Copyright (c) 2016-2023 Sebastian Pipping <[email protected]>
+   Copyright (c) 2016-2025 Sebastian Pipping <[email protected]>
    Copyright (c) 2017      Rhodri James <[email protected]>
    Copyright (c) 2019      David Loffredo <[email protected]>
    Copyright (c) 2020      Joe Orton <[email protected]>
@@ -305,7 +305,7 @@ static XML_Char *
 xcsdup(const XML_Char *s) {
   XML_Char *result;
   int count = 0;
-  int numBytes;
+  size_t numBytes;
 
   /* Get the length of the string, including terminator */
   while (s[count++] != 0) {
@@ -913,11 +913,11 @@ usage(const XML_Char *prog, int rc) {
       T("  -t             write no XML output for [t]iming of plain parsing\n")
       T("  -N             enable adding doctype and [n]otation declarations\n")
       T("\n")
-      T("billion laughs attack protection:\n")
+      T("amplification attack protection (e.g. billion laughs):\n")
       T("  NOTE: If you ever need to increase these values for non-attack payload, please file a bug report.\n")
       T("\n")
       T("  -a FACTOR      set maximum tolerated [a]mplification factor (default: 100.0)\n")
-      T("  -b BYTES       set number of output [b]ytes needed to activate (default: 8 MiB)\n")
+      T("  -b BYTES       set number of output [b]ytes needed to activate (default: 8 MiB/64 MiB)\n")
       T("\n")
       T("reparse deferral:\n")
       T("  -q             disable reparse deferral, and allow [q]uadratic parse runtime with large tokens\n")
@@ -926,6 +926,16 @@ usage(const XML_Char *prog, int rc) {
       T("  -h, --help     show this [h]elp message and exit\n")
       T("  -v, --version  show program's [v]ersion number and exit\n")
       T("\n")
+      T("environment variables:\n")
+      T("  EXPAT_ACCOUNTING_DEBUG=(0|1|2|3)\n")
+      T("                 Control verbosity of accounting debugging (default: 0)\n")
+      T("  EXPAT_ENTITY_DEBUG=(0|1)\n")
+      T("                 Control verbosity of entity debugging (default: 0)\n")
+      T("  EXPAT_ENTROPY_DEBUG=(0|1)\n")
+      T("                 Control verbosity of entropy debugging (default: 0)\n")
+      T("  EXPAT_MALLOC_DEBUG=(0|1|2)\n")
+      T("                 Control verbosity of allocation tracker (default: 0)\n")
+      T("\n")
       T("exit status:\n")
       T("  0              the input files are well-formed and the output (if requested) was written successfully\n")
       T("  1              could not allocate data structures, signals a serious problem with execution environment\n")
@@ -1171,12 +1181,15 @@ tmain(int argc, XML_Char **argv) {
 #if XML_GE == 1
       XML_SetBillionLaughsAttackProtectionMaximumAmplification(
           parser, attackMaximumAmplification);
+      XML_SetAllocTrackerMaximumAmplification(parser,
+                                              attackMaximumAmplification);
 #endif
     }
     if (attackThresholdGiven) {
 #if XML_GE == 1
       XML_SetBillionLaughsAttackProtectionActivationThreshold(
           parser, attackThresholdBytes);
+      XML_SetAllocTrackerActivationThreshold(parser, attackThresholdBytes);
 #else
       (void)attackThresholdBytes; // silence -Wunused-but-set-variable
 #endif

+ 14 - 4
libs/expat/xmlwf/xmlwf_helpgen.py

@@ -6,7 +6,7 @@
 #                      \___/_/\_\ .__/ \__,_|\__|
 #                               |_| XML parser
 #
-# Copyright (c) 2019-2023 Sebastian Pipping <[email protected]>
+# Copyright (c) 2019-2025 Sebastian Pipping <[email protected]>
 # Copyright (c) 2021      Tim Bray <[email protected]>
 # Licensed under the MIT license:
 #
@@ -32,6 +32,16 @@
 import argparse
 
 epilog = """
+environment variables:
+  EXPAT_ACCOUNTING_DEBUG=(0|1|2|3)
+                 Control verbosity of accounting debugging (default: 0)
+  EXPAT_ENTITY_DEBUG=(0|1)
+                 Control verbosity of entity debugging (default: 0)
+  EXPAT_ENTROPY_DEBUG=(0|1)
+                 Control verbosity of entropy debugging (default: 0)
+  EXPAT_MALLOC_DEBUG=(0|1|2)
+                 Control verbosity of allocation tracker (default: 0)
+
 exit status:
   0              the input files are well-formed and the output (if requested) was written successfully
   1              could not allocate data structures, signals a serious problem with execution environment
@@ -74,16 +84,16 @@ output_mode.add_argument('-m', action='store_true', help='write [m]eta XML, not
 output_mode.add_argument('-t', action='store_true', help='write no XML output for [t]iming of plain parsing')
 output_related.add_argument('-N', action='store_true', help='enable adding doctype and [n]otation declarations')
 
-billion_laughs = parser.add_argument_group('billion laughs attack protection',
+billion_laughs = parser.add_argument_group('amplification attack protection (e.g. billion laughs)',
                                            description='NOTE: '
                                                        'If you ever need to increase these values '
                                                        'for non-attack payload, please file a bug report.')
 billion_laughs.add_argument('-a', metavar='FACTOR',
                             help='set maximum tolerated [a]mplification factor (default: 100.0)')
-billion_laughs.add_argument('-b', metavar='BYTES', help='set number of output [b]ytes needed to activate (default: 8 MiB)')
+billion_laughs.add_argument('-b', metavar='BYTES', help='set number of output [b]ytes needed to activate (default: 8 MiB/64 MiB)')
 
 reparse_deferral = parser.add_argument_group('reparse deferral')
-reparse_deferral.add_argument('-q', metavar='FACTOR',
+reparse_deferral.add_argument('-q', action='store_true',
                             help='disable reparse deferral, and allow [q]uadratic parse runtime with large tokens')
 
 parser.add_argument('files', metavar='FILE', nargs='*', help='file to process (default: STDIN)')

部分文件因为文件数量过多而无法显示