Update third-party dependencies for security fixes and validate on Linux and Windows

Replace the libzip 0.10 fork with upstream 1.12.1. Only zip.h's zipconf.h
include is patched; hand-written config.h/zipconf.h replace CMake's
feature checks, and the platform file backends live in posix/ and win32/.
Port Zip to the current libzip API: read-only opens use ZIP_RDONLY, which
handles UTF-8 paths on Windows, so the fdopen workaround is gone. Remove
the ZIP bounded-open mode and the ZipProvider entry and metadata limits;
archives are limited only by the format and libzip. 65,536-entry InfoZIP
archives now open.

Update Mbed TLS to 3.6.7, libvorbis to 1.3.7, Monocypher to 4.0.3 and
simdutf to 9.2.1, retaining eepp's Mbed TLS configuration (PSA and
TLS 1.3 stay disabled) and the reduced simdutf feature set. Add TLS
certificate/hostname, Vorbis encoder and ZIP range regression tests.

Fix SFTP watch channels on Linux: efsw-agent now exits immediately on
EOF (efsw 0712eec), and a refused agent channel is retried briefly
instead of disabling native watching on the host for five minutes.
Start the SFTP test sshd without PerSourcePenalties on OpenSSH < 9.8,
so the integration tests run on Ubuntu 24.04. CI installs OpenSSH and
requires them.

Fix GCC builds on Linux AArch64 (mojoAL NEON target attributes, the
physics example's signed bitmap) anation.

Keep a NanoSVG libFuzzer target and CI.
Record the updates, checksums and retained patches in the security
audit and inventory.
This commit is contained in:
Martín Lucas Golini
2026-10-25 18:27:34 -03:00
parent 33dd9d6212
commit 7069bb03e6
424 changed files with 49380 additions and 14499 deletions
+17 -1
View File
@@ -24,7 +24,8 @@ jobs:
sudo apt update
sudo apt install -y gcc-13 g++-13 wget mesa-utils xvfb xauth gdb zstd \
weston xdotool imagemagick \
python3-gi gir1.2-atspi-2.0 at-spi2-core dbus-x11
python3-gi gir1.2-atspi-2.0 at-spi2-core dbus-x11 \
openssh-server openssh-client netcat-openbsd clang
bash projects/linux/scripts/install_sdl3.sh --keep-build
wget https://cdn.ensoft.dev/eepp-assets/premake-5.0.0-beta6-linux.tar.gz
tar xvzf premake-5.0.0-beta6-linux.tar.gz
@@ -95,9 +96,24 @@ jobs:
SDL_AUDIODRIVER: dummy
SDL_AUDIO_DRIVER: dummy
ALSOFT_DRIVERS: "null"
# The SFTP integration tests start a loopback sshd; fail instead of silently skipping.
EEPP_REQUIRE_SFTP_TESTS: "1"
run: |
cd projects/scripts
bash ./run_gdb_tests.sh
- name: NanoSVG Fuzzing
# The vendored NanoSVG fork carries local security patches and has no upstream fuzzing.
if: ${{ !cancelled() && steps.build.outcome == 'success' }}
timeout-minutes: 10
run: |
./premake5 --disable-static-build --with-debug-symbols --with-backend=SDL3 --with-security-fuzz gmake
make -C make/linux -e config=release_x86_64 CC=clang CXX=clang++ eepp-fuzz-nanosvg -j$(nproc)
# New inputs go to the output folder so the committed seeds stay unchanged; crash
# reproducers are uploaded with the other test output.
mkdir -p bin/unit_tests/output/fuzz-nanosvg/corpus
bin/security/eepp-fuzz-nanosvg -max_total_time=60 -max_len=8192 \
-artifact_prefix=bin/unit_tests/output/fuzz-nanosvg/ \
bin/unit_tests/output/fuzz-nanosvg/corpus src/tests/security/corpus/nanosvg
- name: Native X11 Drag and Drop Tests
timeout-minutes: 5
shell: bash
+1
View File
@@ -73,6 +73,7 @@ ecode.dmg
/.cache/
/compile_commands.json
/bin/benchmarks*
/bin/security*
/bin/unit_tests/eepp*
/bin/unit_tests/lib*
/bin/unit_tests/output/*
+5 -7
View File
@@ -517,15 +517,13 @@ I/O scheduler's mount isolation and timeouts.
Only `file://` backing archives are supported initially. Password-protected entries and unsupported
compression methods report `Unsupported`. ZIP symlink attributes are not followed: their stored
data is exposed as a regular file. Unsafe names (absolute paths, traversal components, backslashes
or drive/stream colons) are excluded. Indexes are limited to 262,144 entries including implicit
directories and a conservative 64 MiB metadata budget covering libzip's decoded directory,
nodes, stored paths and container growth. Oversized central directories are rejected before
decoding; budget violations return `InvalidOperation`. At most eight indexes are cached;
or drive/stream colons) are excluded. Indexes have no fixed entry limit beyond what the ZIP
format and libzip support; their memory grows with the size of the central directory.
Inconsistent central directories return `InvalidOperation`. At most eight indexes are cached;
existing handles can retain older indexes.
Legacy InfoZIP archives whose 16-bit entry count wraps to zero with a nonempty central directory
(for example, exactly 65,536 entries) are intentionally rejected as inconsistent. A zero count is
accepted only for an empty central directory.
Legacy InfoZIP archives without ZIP64 records, whose 16-bit entry count wraps past 65,535, are
read using the central directory size; the recovered count must match the entries present.
In eefm, Enter or double-click on a local `.zip`, `.jar`, `.apk` or `.epub` file enters it
(extensions are case-insensitive). These ZIP-based formats share `ZipProvider` and `zip://` locations.
+126 -92
View File
@@ -20,29 +20,34 @@ release has not been established.
| libssh2 | 1.11.1 plus local crypto integration | **1.11.2_DEV**, pinned to upstream `6e7b2076a6ced2230968b27ee7c1abb77fe5a88d` | Refreshed the complete imported library source, preserving eepp's build configuration, classic Mbed TLS APIs and Monocypher integration. This is an unreleased snapshot, not a 1.11.2 release. |
| libpng | 1.6.37 | **1.6.59** | Imported upstream library sources, architecture implementations and the release's prebuilt configuration without source patches. |
| NanoSVG | Modified FLTK-derived snapshot | Same snapshot plus manual security fixes | Patched the reported arc conversion, fixed-point conversion/advancement and stroke tessellation issues while retaining local style/currentColor behavior. |
| libzip | 0.10 plus local hardening | **1.12.1** | Replaced the fork with the upstream release; only an include-path patch remains. `Zip` uses the current API. ZIP browsing limits were removed. |
| Mbed TLS | 3.6.0 | **3.6.7** (LTS) | Library and headers match the release; eepp's `mbedtls_config.h` block is retained (PSA crypto, TLS 1.3 and weak algorithms remain disabled). |
| libvorbis | 1.3.6 | **1.3.7** | Includes the CVE-2018-10393 encoder bounds fix and the channel validation changes; all imported files match the release. |
| Monocypher | 4.0.2 | **4.0.3** | Fixes the compiler-dependent Ed25519 signing timing leak; imported sources match the release. |
| simdutf | 9.2.0 | **9.2.1** | Regenerated amalgamation with the same UTF-8/UTF-32-only feature set; Base64 stays disabled. |
The release unit-test target builds with the required macOS script. The final full
native release suite passed **2,124 tests**, including all **34 SFTP integration tests**
against isolated loopback SSH servers and all **6 focused security tests**. The
security cases cover five NanoSVG numeric/style regressions and RGB/RGBA palette
decoding with 17-pixel rows. Both palette Neon functions are linked into the test
executable on this ARM64 host.
Validation of the complete working tree:
The full suite includes PNG color-font loading/rendering, image loading and SVG UI
coverage. No cross-platform build, optional OpenSSL-backend build or sanitizer/fuzz
campaign was performed. Passing functional tests does not establish absence of all
malformed-input vulnerabilities.
- macOS ARM64: the full native release suite passed all 2,128 tests, including the SFTP
integration tests against loopback SSH servers and the PNG, NanoSVG, ZIP, TLS and Vorbis
security tests.
- Linux ARM64 (Ubuntu 24.04, GCC 13, SDL 3.4.10, Docker): the release build succeeded and the
headless suite passed 2,139 of 2,140 tests with all SFTP tests required; one font test
skipped for lack of a font with a non-normal stretch.
- Windows x86_64 (MinGW-w64 GCC 13 cross-build, Wine 7.7): the unit tests build and all ZIP
tests pass; the full suite under Wine was not conclusive (file-watch, long-path and headless
UI failures not reproduced on real Windows).
- ASan/UBSan libFuzzer runs: ZIP (300 s, 3.39 M inputs) and NanoSVG, without findings. The
Linux CI job now fuzzes NanoSVG for 60 s and requires the SFTP tests to run.
Not run: Linux x86_64, Android, Emscripten and the optional OpenSSL backend. Passing
functional tests does not establish absence of all malformed-input vulnerabilities.
## Remaining cleanup order
| Order | Component | Current source | Action | Reason and qualification |
| --- | --- | --- | --- | --- |
| 1 | libzip | 0.10 plus local hardening | Resolve residual arithmetic checks; plan a modern libzip migration | Local changes address one old CVE, but other unchecked arithmetic remains. Bounded VFS opens and the public unrestricted ZIP API have different exposure. |
| 2 | Mbed TLS | 3.6.0 | Upgrade within LTS to 3.6.7 | Substantial security backlog. Many high-scoring findings require unused APIs, a TLS server role, unusual compiler behavior, or deployment conditions. Do not characterize the ordinary eepp HTTPS client as a confirmed RCE. |
| 3 | libvorbis | 1.3.6 | Upgrade to 1.3.7 | The CVE-2018-10393 encoder bounds fix is absent; eepp includes an encoder. |
| 4 | Bundled SDL2 source | 2.0.12 | Reconcile Android source with the newer SDL2 pin | Old source has high-severity surface/blit issues; an application exploit path was not established. |
| 5 | simdutf | 9.2.0 | Update to at least 9.2.1 | High upstream advisory affects Base64 APIs that eepp does not currently call. |
| 6 | Monocypher | 4.0.2 | Update to 4.0.3 | Compiler-dependent EdDSA/Ed25519 timing fix. Signing is used by our SSH backend; no high CVE for that issue was established. |
| 1 | Bundled SDL2 source | 2.0.12 | Reconcile Android source with the newer SDL2 pin | Old source has high-severity surface/blit issues; an application exploit path was not established. |
Orders indicate engineering priority for this repository, not a new CVSS score.
Targets are releases verified during the initial audit; check upstream again before
@@ -144,46 +149,84 @@ These findings concern numeric undefined behavior and availability. The original
reports include sanitizer-triggered termination; neither the initial audit nor this
remediation establishes an eepp RCE or a deterministic release-build crash.
## Remaining findings
### libzip
### libzip: old release with meaningful local changes
Replaced the 0.10 fork with [libzip 1.12.1](https://github.com/nih-at/libzip/releases/tag/v1.12.1)
(`libzip-1.12.1.tar.xz`, SHA-256
`c40062022a1963c80573d48f6070792297cecd7c6bffe3aefcac0d8b9bee8913`, matching the GitHub
release digest). [`README.eepp.md`](../../src/thirdparty/libzip/README.eepp.md) records the
imported sources, the hand-written `config.h`/`zipconf.h` that replace CMake, the generated
error table and the retained patches.
[`zipconf.h`](../../src/thirdparty/libzip/zipconf.h) says 0.10, but the source is not
an unmodified 0.10 release. In particular:
The initial audit's open questions about the old code no longer apply:
- CVE-2012-1162's zero-entry allocation/write condition is guarded in
[`zip_open.c`](../../src/thirdparty/libzip/zip_open.c), and the empty-directory
case returns before the original `do` loop. Do not list this as unpatched.
- CVE-2017-12858's upstream fix removes a second free of a `zip_buffer` in
`_zip_dirent_process_winzip_aes()` failure handling. That machinery is absent
here. A scanner's version-only match is insufficient. ZIP64 advisory
CVE-2017-14107 likewise targets code not present in this old implementation.
- The allocation bounds check associated with CVE-2015-2331 is absent from
`_zip_cdir_new()`, and `_zip_cdir_grow()` also multiplies without an allocation
overflow check. Exact reachability depends on entry-count handling and platform
size; the initial count here is only 16-bit, so this is not a reproduced CVE.
- The expression `cd->offset + cd->size` still adds two `unsigned int` fields
before checking the end of the directory. This is the family of offset/size
arithmetic covered by CVE-2012-1163 (legacy CVSS 2.0 6.8). It warrants a focused
review even though it falls below this audit's nominal high threshold.
- The `cd->offset + cd->size` addition (CVE-2012-1163 family) and the unchecked
`_zip_cdir_new()`/`_zip_cdir_grow()` multiplications (CVE-2015-2331 family) are gone. 1.12.1
reads 64-bit EOCD fields through bounds-checked buffers, rejects wrapping offsets and sizes,
rejects ZIP64 entry counts larger than the directory can hold, and grows arrays through
overflow-checked `ZIP_REALLOC`.
- The signed-shift undefined behavior that a sanitizer run found in the old `_zip_read4()`, and the
entry-capacity update made before `realloc()` succeeded, existed only in the old fork. No
uncommitted fixes to 0.10 were kept.
- CVE-2017-12858 and CVE-2017-14107 are fixed upstream. 1.12.1 also includes the later
hardening listed in the [security history](https://libzip.org/security/).
The VFS path uses `OpenMode::ReadOnlyBounded` / `ZIP_LIMIT_METADATA`, which constrains
large directories. The ordinary public `Zip::open()` uses `zip_open(..., 0, ...)`.
Do not apply the VFS mitigation to every caller.
The only source patch is `zip.h` including `"zipconf.h"` instead of `<zipconf.h>`.
Sources: [libzip security history](https://libzip.org/security/),
[CVE-2015-2331 allocation fix](https://github.com/php/php-src/commit/ef8fc4b53d92fbfcd8ef1abbd6f2f5fe2c4a11e5),
[CVE-2017-12858 actual fix](https://github.com/nih-at/libzip/commit/2217022b7d1142738656d891e00b3d2d9179b796).
The verified current upstream release is 1.12.1. Migration needs work on our
custom APIs, file-descriptor ownership, metadata limits and build integration;
it is not a drop-in replacement for the current fork.
The old fork's `ZIP_LIMIT_METADATA` bounded open, and the VFS `ZipProvider` limits of 262,144
entries and a 64 MiB metadata budget, were removed at the maintainer's direction. ZIP browsing
now accepts whatever the format and libzip support. libzip bounds the entry count by the
central directory size, so index memory grows with the archive: about 300 bytes per typical
entry, and roughly 10× the directory size for a crafted directory of empty extra fields.
`ArchiveProvider` (libarchive) still has its own 262,144-entry / 64 MiB limits.
### Mbed TLS: upgrade, with precise exposure accounting
`Zip` now opens read-only mode with `zip_open(ZIP_RDONLY)`. libzip converts UTF-8 paths to
wide paths on Windows, so the `fopenUtf8`/`dup`/`zip_fdopen` ownership workaround was removed,
and `ReadWrite` opens gain Unicode support on Windows. Deprecated calls were replaced by
`zip_file_add`, `zip_get_error`, `zip_error_strerror` and `zip_discard`. The old 0.10
Windows `rename()` workaround is superseded by upstream's Win32 backend. bzip2, xz, zstd and
WinZip AES remain disabled, as they were in 0.10. On Windows, `advapi32` is now linked for
upstream's random-number and ACL code.
Default TLS backend is selected in `premake5.lua`; OpenSSL is optional.
[`build_info.h`](../../src/thirdparty/mbedtls/include/mbedtls/build_info.h)
identifies 3.6.0. The [3.6.7 LTS release](https://github.com/Mbed-TLS/mbedtls/releases/tag/mbedtls-3.6.7)
is the verified update target, avoiding a simultaneous 4.x migration.
InfoZIP archives whose 16-bit count wraps (for example, exactly 65,536 entries) now open,
and libzip recovers the count from the directory size; the old fork rejected them because it
could not decode them safely.
Validation:
[`zip_security_tests.cpp`](../../src/tests/unit_tests/zip_security_tests.cpp) covers wrapped and
high-bit 32-bit ranges, 64-bit offset/size wrapping, and ZIP64 counts at 2^32 and 2^32−1 (which
wrap a 32-bit allocation). A 300 s ASan/UBSan libFuzzer run of a temporary ZIP target, through
the public `zip_open_from_source()` API, executed 3.39 M inputs without a finding. That target was
then removed: libzip is now unmodified apart from one include line, and upstream maintains
OSS-Fuzz harnesses. The NanoSVG target remains, because the local fork has no upstream fuzzing;
the Linux CI job fuzzes it for 60 s on every run.
- macOS ARM64: the full native release suite passed all 2,128 tests.
- Linux ARM64 (Ubuntu 24.04, GCC 13, SDL 3.4.10, in Docker): the release build and the full
headless suite passed 2,139 of 2,140 tests, with all SFTP integration tests required and
run; one font test skipped for lack of a font with a non-normal stretch.
- Windows x86_64 (MinGW-w64 GCC 13 cross-build, run under Wine 7.7): libzip builds without
warnings and all 21 ZIP tests pass. The full suite under Wine is not conclusive: file-watch,
long-path and headless UI tests failed or crashed in ways not yet reproduced on real Windows.
- Linux x86_64, Android and Emscripten builds of the new configuration were not run.
### Mbed TLS
Updated from 3.6.0 to the [3.6.7 LTS release](https://github.com/Mbed-TLS/mbedtls/releases/tag/mbedtls-3.6.7)
(`mbedtls-3.6.7.tar.bz2`, SHA-256
`a7e8bcbec0e6f761b4af24f25677626b35f762f68eef79c08677a363212d11f6`), avoiding a simultaneous
4.x migration. Every imported library source and header matches the release except
`include/mbedtls/mbedtls_config.h`, whose trailing eepp block is retained: weak key exchanges,
DES and DHM disabled, deprecated APIs removed, AESCE limited to AArch64 Linux, and
`MBEDTLS_PSA_CRYPTO_C`, `MBEDTLS_SSL_PROTO_TLS1_3` and LMS disabled. The release's PSA
sources are present again (3.6.0's import had deleted them as unused); with PSA disabled they
compile to empty objects. They are kept deliberately: TLS 1.3 in Mbed TLS 3.6 requires PSA, and
enabling it is planned as a separate migration. The libssh2 classic-API adapter is unchanged.
The default TLS backend is selected in `premake5.lua`; OpenSSL is optional and was not
built in this validation. [`tls_security_tests.cpp`](../../src/tests/unit_tests/tls_security_tests.cpp)
connects to a loopback OpenSSL `s_server` (TLS 1.2), and checks that a trusted certificate is
accepted while a wrong host name and an untrusted certificate are rejected.
The ordinary [`MbedTLSSocket`](../../src/eepp/network/ssl/backend/mbedtls/mbedtlssocket.cpp)
is a stream TLS client. It sets the hostname, uses certificate verification when
@@ -207,7 +250,7 @@ matches, not a claim they all affect that client:
| CVE-2026-49300 | Malformed certificate interpreted as a CA. Upstream's exploit scenario requires accepting untrusted certificates through a different validator/trust-registration process; such a workflow was not found here. |
| CVE-2026-50580 | TLS 1.2 ECDHE-PSK client with oversized configured PSK identity. No PSK configuration calls found. |
| CVE-2026-50579 | Reused PKCS7 context; no PKCS7 caller found. |
| CVE-2026-50713 | Introduced in 3.6.3; 3.6.0 is outside the affected interval. DTLS also differs from the eepp stream TLS path. |
| CVE-2026-50713 | Introduced in 3.6.3, after the old 3.6.0, and fixed in 3.6.7 (DTLS renegotiation with `badmac_limit`). DTLS also differs from the eepp stream TLS path. |
Advisory definitions and fixes: [official security index](https://mbed-tls.readthedocs.io/en/latest/security-advisories/).
The individual documents were read from the official `Mbed-TLS/mbedtls-docs`
@@ -215,25 +258,24 @@ source archive, including issues whose NVD descriptions omit configuration detai
The [AESNI advisory](https://mbed-tls.readthedocs.io/en/latest/security-advisories/mbedtls-security-advisory-2025-06-1/)
is particularly useful when assessing x86 distribution builds.
Several additional low/medium fixes apply to this old TLS baseline. Keeping 3.6.0
because an individual high-CVE precondition is absent would leave that backlog.
An upgrade is recommended, but the distinctions above should remain in the record.
Advisory definitions and fixes: [official security index](https://mbed-tls.readthedocs.io/en/latest/security-advisories/).
The individual documents were read from the official `Mbed-TLS/mbedtls-docs`
source archive, including issues whose NVD descriptions omit configuration details.
The [AESNI advisory](https://mbed-tls.readthedocs.io/en/latest/security-advisories/mbedtls-security-advisory-2025-06-1/)
is particularly useful when assessing x86 distribution builds. 3.6.7 also clears the low and
medium fixes accumulated since 3.6.0.
### libvorbis: encoder update
### libvorbis
[`lib/info.c`](../../src/thirdparty/libvorbis/lib/info.c) identifies 1.3.6.
[`lib/psy.c`](../../src/thirdparty/libvorbis/lib/psy.c) still lacks the loop/index
bounds added for CVE-2018-10393 (CVSS 3.1 7.5). This was verified by comparing the
local file with the official 1.3.7 archive.
[`SoundFileWriterOgg`](../../src/eepp/audio/soundfilewriterogg.cpp) configures the
Vorbis encoder with the supplied sample rate/channel count and invokes its analysis
pipeline. The relevant issue is encoding unusual low sample rates, not ordinary
playback of every Ogg file. Upgrade to 1.3.7 and test those input conditions.
CVE-2018-10392 is another version match involving channel validation; its precise
caller conditions were not reproduced. Include the upstream channel-validation
changes in the refresh.
Source: [upstream 1.3.7 changelog](https://github.com/xiph/vorbis/blob/v1.3.7/CHANGES).
Updated from 1.3.6 to [1.3.7](https://github.com/xiph/vorbis/blob/v1.3.7/CHANGES)
(`libvorbis-1.3.7.tar.xz`, SHA-256
`b33cc4934322bcbf6efcbacf49e3ca01aadbea4114ec9589d1b1e9d20f72954b`). All imported files match
the release, including the CVE-2018-10393 loop/index bounds in `lib/psy.c` and the
CVE-2018-10392 channel validation. The standalone tool sources that eepp removed earlier
(`tone.c`, `barkmel.c`) remain excluded. [`SoundFileWriterOgg`](../../src/eepp/audio/soundfilewriterogg.cpp)
drives the encoder; [`vorbis_security_tests.cpp`](../../src/tests/unit_tests/vorbis_security_tests.cpp)
encodes and decodes mono and stereo at 1 Hz to 44.1 kHz and checks that invalid rates and
channel counts are rejected.
## High findings whose current eepp API conditions were not found
@@ -269,18 +311,16 @@ Sources: [Cairo advisory](https://github.com/harfbuzz/harfbuzz/security/advisori
### simdutf and Monocypher
simdutf 9.2.0 is within the high
simdutf was updated from 9.2.0 to 9.2.1, which fixes the high
[GHSA-pw55-7mm7-cvhh](https://github.com/simdutf/simdutf/security/advisories/GHSA-pw55-7mm7-cvhh)
range. It affects Base64 decoding into exactly sized output buffers, and is fixed
in 9.2.1. eepp uses Unicode conversion/counting functions; no affected Base64
consumer was found. The related LASX Latin-1 issue is also fixed in 9.2.1, but those
conversion functions were not found among current callers. Neither advisory had a
CVE assigned when checked.
Base64 issue and the related LASX Latin-1 issue. eepp vendors a regenerated amalgamation
limited to UTF-8 and UTF-32, as before; Base64 and Latin-1 support are not compiled, so
neither advisory was reachable.
Monocypher 4.0.3 fixes an EdDSA/Ed25519 timing leak in 4.0.2 and earlier with certain
compiler/options combinations. Our SSH integration does sign using Ed25519, so
update it during the SSH refresh. No high-scored CVE was found for that particular
issue. Sources: [known bugs](https://monocypher.org/bugs),
Monocypher was updated from 4.0.2 to 4.0.3, which fixes the compiler-dependent EdDSA/Ed25519
timing leak. Our SSH integration signs with Ed25519, so this was relevant. The imported
`monocypher.{c,h}` and `monocypher-ed25519.{c,h}` match the release. Sources:
[known bugs](https://monocypher.org/bugs),
[4.0.3 release](https://github.com/LoupVaillant/Monocypher/releases/tag/4.0.3).
### SDL version selection
@@ -350,15 +390,15 @@ and establish a verified tag/commit before calling a future update routine.
| libogg | 1.3.3 | Screened | [framing.c](../../src/thirdparty/libogg/src/framing.c) |
| libpng | 1.6.59 | Fixed | [png.h](../../src/thirdparty/libpng/png.h) |
| libssh2 | 1.11.2_DEV @ 6e7b2076 + local integration | Fixed | [libssh2.h](../../src/thirdparty/libssh2/include/libssh2.h) |
| libvorbis | 1.3.6 | Upgrade | [info.c](../../src/thirdparty/libvorbis/lib/info.c) |
| libvorbis | 1.3.7 | Fixed | [info.c](../../src/thirdparty/libvorbis/lib/info.c) |
| libwebp | 1.5.0 | Screened | [vp8i_dec.h](../../src/thirdparty/libwebp/src/dec/vp8i_dec.h) |
| libyaml | 0.2.5 | Screened | [config.h](../../src/thirdparty/libyaml/src/config.h) |
| libzip | 0.10 + local hardening | Review | [zipconf.h](../../src/thirdparty/libzip/zipconf.h) |
| mbedtls | 3.6.0 | Upgrade | [build_info.h](../../src/thirdparty/mbedtls/include/mbedtls/build_info.h) |
| libzip | 1.12.1 | Fixed | [zipconf.h](../../src/thirdparty/libzip/zipconf.h) |
| mbedtls | 3.6.7 | Fixed | [build_info.h](../../src/thirdparty/mbedtls/include/mbedtls/build_info.h) |
| md4c | Unversioned/patched snapshot | Snapshot | [md4c.c](../../src/thirdparty/md4c/md4c.c) |
| mojoAL | 2.0.1 | Screened | [mojoal.c](../../src/thirdparty/mojoAL/mojoal.c) |
| mojoAL-SDL3 | 2.9.9 | Screened | [mojoal.c](../../src/thirdparty/mojoAL-SDL3/mojoal.c) |
| monocypher | 4.0.2 | Maintenance | [monocypher.h](../../src/thirdparty/monocypher/monocypher.h) |
| monocypher | 4.0.3 | Fixed | [monocypher.h](../../src/thirdparty/monocypher/monocypher.h) |
| nanosvg | Snapshot + 2026-10-25 security patches | Fixed | [nanosvg.h](../../src/thirdparty/nanosvg/nanosvg.h) |
| nlohmann | 3.12.0 | Screened | [json.hpp](../../src/thirdparty/nlohmann/json.hpp) |
| oniguruma | 6.9.10 | Screened | [oniguruma.h](../../src/thirdparty/oniguruma/oniguruma.h) |
@@ -367,7 +407,7 @@ and establish a verified tag/commit before calling a future update routine.
| pugixml | 1.12 | Screened | [pugixml.hpp](../../src/thirdparty/pugixml/pugixml.hpp) |
| SDL2 | 2.0.12 | Conditional | [SDL_version.h](../../src/thirdparty/SDL2/include/SDL_version.h) |
| SheenBidi | 2.9.0 | Screened | [SBVersion.h](../../src/thirdparty/SheenBidi/Headers/SheenBidi/SBVersion.h) |
| simdutf | 9.2.0 | Maintenance | [simdutf.h](../../src/thirdparty/simdutf/simdutf.h) |
| simdutf | 9.2.1 (UTF-8/UTF-32 build) | Fixed | [simdutf.h](../../src/thirdparty/simdutf/simdutf.h) |
| SOIL2 | 1.3.0 snapshot | Screened | [SOIL2.h](../../src/thirdparty/SOIL2/src/SOIL2/SOIL2.h) |
| subprocess | Unversioned/patched snapshot | Snapshot | [subprocess.h](../../src/thirdparty/subprocess/subprocess.h) |
| tabulate | 1.5.0 | Screened | [tabulate.hpp](../../src/thirdparty/tabulate/tabulate.hpp) |
@@ -457,16 +497,10 @@ Coverage gaps that remain explicit:
## Remaining implementation batches
1. **ZIP follow-up:** resolve arithmetic questions in the current fork, then decide
between focused security backports and migration to modern libzip. Preserve
bounded-open behavior and ownership semantics during migration.
2. **Cryptography maintenance:** Mbed TLS 3.6.7 and Monocypher 4.0.3, validating HTTP,
certificate checks, SSH keys, session lifetime and backend compatibility. Retain
the libssh2 classic API adapter unless PSA/threading migration is deliberate.
3. **Audio/platform maintenance:** Vorbis 1.3.7 and Android SDL source reconciliation.
4. **Small exposure-reducing updates:** simdutf >=9.2.1 and PCRE2 10.49. Establish
verified provenance for the remaining snapshot-only imports.
5. Replace the libssh2 development snapshot with a security-fixed stable release
1. **Platform maintenance:** reconcile the Android SDL2 source with the newer SDL2 pin.
2. **Small exposure-reducing updates:** PCRE2 10.49. Establish verified provenance for the
remaining snapshot-only imports.
3. Replace the libssh2 development snapshot with a security-fixed stable release
when one is available, retaining the recorded integration patches.
For subsequent updates, record the upstream release/commit and retained patches
@@ -305,14 +305,26 @@
{
"name": "libvorbis",
"path": "src/thirdparty/libvorbis",
"version": "1.3.6",
"version": "1.3.7",
"version_evidence": "src/thirdparty/libvorbis/lib/info.c",
"upstream": "https://github.com/xiph/vorbis",
"assessment": "upgrade",
"notes": "Encoder CVE-2018-10393 fix is absent in psy.c. Upgrade to 1.3.7; assess encoder input conditions.",
"assessment": "fixed",
"notes": "All imported include/ and lib/ files match the 1.3.7 release; standalone tool sources stay excluded. Encoder low-sample-rate and invalid-setup regression test added.",
"source_revision": "1116575774d174fc1e79fbb0e1458319be0af548",
"source_revision_kind": "last eepp commit touching directory",
"source_fingerprint_sha256": "a070982556e996e0cb19ed9d3e1723700779db6e278e29cb9ae4ed1ef5bd7e35"
"source_fingerprint_sha256": "c12284fba99ae046b5113ca8e1b3ae385e1cd10061008b60be7d2d911530619d",
"baseline_source_fingerprint_sha256": "a070982556e996e0cb19ed9d3e1723700779db6e278e29cb9ae4ed1ef5bd7e35",
"upstream_tag": "v1.3.7",
"retained_patches": [
".clang-format"
],
"resolved_advisories": [
"CVE-2018-10393",
"CVE-2018-10392"
],
"working_tree_modified": true,
"updated_at": "2026-10-25",
"upstream_archive_sha256": "b33cc4934322bcbf6efcbacf49e3ca01aadbea4114ec9589d1b1e9d20f72954b"
},
{
"name": "libwebp",
@@ -341,26 +353,72 @@
{
"name": "libzip",
"path": "src/thirdparty/libzip",
"version": "0.10 + local hardening",
"version": "1.12.1",
"version_evidence": "src/thirdparty/libzip/zipconf.h",
"upstream": "https://libzip.org/",
"assessment": "review",
"notes": "CVE-2012-1162 guarded locally. Old offset/size arithmetic and allocation checks still need work; modern libzip migration needs API/build review.",
"assessment": "fixed",
"notes": "Replaced the 0.10 fork with upstream lib/ sources; hand-written config.h/zipconf.h, generated zip_err_str.c. Old offset/size and allocation arithmetic is gone. Only zip.h's zipconf.h include is patched. The fork's ZIP_LIMIT_METADATA bounded open and the VFS ZIP limits were removed at the maintainer's direction. bzip2/xz/zstd/WinZip AES not built.",
"source_revision": "a94a6f5f7ed694cabe344c6227357db6e94cfecd",
"source_revision_kind": "last eepp commit touching directory",
"source_fingerprint_sha256": "fe27084b4570a8471912c9244187f0c508e37565b3662a93cb1ca9d16a3612e8"
"source_fingerprint_sha256": "29220266a16ee1fd0c4663f10bc321876ea1bca5f1d3a1cb50457c81e2df4559",
"baseline_source_fingerprint_sha256": "fe27084b4570a8471912c9244187f0c508e37565b3662a93cb1ca9d16a3612e8",
"upstream_tag": "v1.12.1",
"retained_patches": [
"zip.h",
"zip_err_str.c",
"config.h",
"zipconf.h",
"README.eepp.md",
".clang-format"
],
"resolved_advisories": [
"CVE-2012-1163",
"CVE-2015-2331",
"CVE-2017-12858",
"CVE-2017-14107"
],
"working_tree_modified": true,
"updated_at": "2026-10-25",
"upstream_archive_sha256": "c40062022a1963c80573d48f6070792297cecd7c6bffe3aefcac0d8b9bee8913"
},
{
"name": "mbedtls",
"path": "src/thirdparty/mbedtls",
"version": "3.6.0",
"version": "3.6.7",
"version_evidence": "src/thirdparty/mbedtls/include/mbedtls/build_info.h",
"upstream": "https://github.com/Mbed-TLS/mbedtls",
"assessment": "upgrade",
"notes": "Upgrade within LTS to 3.6.7. Multiple advisories have API, compiler, protocol-role or deployment preconditions; no blanket remote-RCE claim for eepp TLS client.",
"assessment": "fixed",
"notes": "Library sources and headers match the 3.6.7 LTS release except include/mbedtls/mbedtls_config.h, whose eepp block is retained (PSA crypto, TLS 1.3, LMS and weak key exchanges disabled). Restored PSA sources compile to empty objects. TLS client trust/hostname test added.",
"source_revision": "1576fa7eb1c1664135326850c0fcf9f4d694d0b9",
"source_revision_kind": "last eepp commit touching directory",
"source_fingerprint_sha256": "d4ef114cebeaf7a0ebada30fc7cfb6469cb3b32fdee3bff1f064d20141aab764"
"source_fingerprint_sha256": "54c9b453ec73b73dfd413a07a457e0383c1ced78d20919f2e0f0d5ff51d4ca14",
"baseline_source_fingerprint_sha256": "d4ef114cebeaf7a0ebada30fc7cfb6469cb3b32fdee3bff1f064d20141aab764",
"upstream_tag": "mbedtls-3.6.7",
"retained_patches": [
"include/mbedtls/mbedtls_config.h",
".clang-format"
],
"resolved_advisories": [
"CVE-2024-45158",
"CVE-2024-45159",
"CVE-2024-49195",
"CVE-2025-47917",
"CVE-2025-48965",
"CVE-2025-52496",
"CVE-2026-25833",
"CVE-2026-25835",
"CVE-2026-34872",
"CVE-2026-34873",
"CVE-2026-34874",
"CVE-2026-34875",
"CVE-2026-34876",
"CVE-2026-49300",
"CVE-2026-50579",
"CVE-2026-50580"
],
"working_tree_modified": true,
"updated_at": "2026-10-25",
"upstream_archive_sha256": "a7e8bcbec0e6f761b4af24f25677626b35f762f68eef79c08677a363212d11f6"
},
{
"name": "md4c",
@@ -401,14 +459,23 @@
{
"name": "monocypher",
"path": "src/thirdparty/monocypher",
"version": "4.0.2",
"version": "4.0.3",
"version_evidence": "src/thirdparty/monocypher/monocypher.h",
"upstream": "https://monocypher.org/",
"assessment": "maintenance",
"notes": "4.0.3 fixes compiler-dependent Ed25519/EdDSA timing leakage. Used for libssh2 Ed25519 signing and X25519; no high CVE assigned to this issue found.",
"assessment": "fixed",
"notes": "monocypher.{c,h} and monocypher-ed25519.{c,h} match the 4.0.3 release, fixing the compiler-dependent Ed25519 signing timing leak used by the SSH backend.",
"source_revision": "88675a7c84b0785295d55a96477a8c046cc9f34c",
"source_revision_kind": "last eepp commit touching directory",
"source_fingerprint_sha256": "0061c4d2f475444b87289c62c9821de09c13b683f6b3cf01a594f9cd8fc80d6e"
"source_fingerprint_sha256": "6b1c995a9faa61f3f3222b1c2636a26b40e2ae6ced9208db54ba2d215568eb7c",
"baseline_source_fingerprint_sha256": "0061c4d2f475444b87289c62c9821de09c13b683f6b3cf01a594f9cd8fc80d6e",
"upstream_tag": "4.0.3",
"retained_patches": [
"README.eepp.md",
".clang-format"
],
"working_tree_modified": true,
"updated_at": "2026-10-25",
"upstream_archive_sha256": "8cc9bc341a66249016db9bd70e9142d8d0aef9945973744b1ac05dbc55d8ee66"
},
{
"name": "nanosvg",
@@ -522,14 +589,26 @@
{
"name": "simdutf",
"path": "src/thirdparty/simdutf",
"version": "9.2.0",
"version": "9.2.1",
"version_evidence": "src/thirdparty/simdutf/simdutf.h",
"upstream": "https://github.com/simdutf/simdutf",
"assessment": "maintenance",
"notes": "High GHSA-pw55-7mm7-cvhh is fixed in 9.2.1, but eepp does not call the affected Base64 APIs. Recommend >=9.2.1.",
"assessment": "fixed",
"notes": "Regenerated 9.2.1 amalgamation limited to UTF-8 and UTF-32, the same feature set as before; Base64 and Latin-1 are not compiled, so GHSA-pw55-7mm7-cvhh was not reachable.",
"source_revision": "e2174aa04482cace8d416ac2bc960e9e9b724f54",
"source_revision_kind": "last eepp commit touching directory",
"source_fingerprint_sha256": "485a6b6e2b917237612bc99005cc0fba40504b8e5931a8aa91db6d2a3a126b49"
"source_fingerprint_sha256": "3bb0cd4013f8067968c4b40d43d0d915b3858f1c7c992db036679eefca8c7b95",
"baseline_source_fingerprint_sha256": "485a6b6e2b917237612bc99005cc0fba40504b8e5931a8aa91db6d2a3a126b49",
"upstream_tag": "v9.2.1",
"retained_patches": [
"simdutf.h",
"simdutf.cpp",
".clang-format"
],
"resolved_advisories": [
"GHSA-pw55-7mm7-cvhh"
],
"working_tree_modified": true,
"updated_at": "2026-10-25"
},
{
"name": "SOIL2",
+4 -17
View File
@@ -8,9 +8,8 @@ struct zip;
namespace EE { namespace System {
/** ZIP archive reader/writer and optional resource pack. Use Zip(false) and
* OpenMode::ReadOnlyBounded for untrusted standalone browsing. Entry streams borrow the archive
* and must be destroyed before it.
/** ZIP archive reader/writer and optional resource pack. Use Zip(false) and OpenMode::ReadOnly
* for standalone browsing. Entry streams borrow the archive and must be destroyed before it.
* Serialize access to an archive and its streams when sharing them between threads. */
class EE_API Zip : public Pack {
public:
@@ -23,13 +22,7 @@ class EE_API Zip : public Pack {
Uint32 crc{ 0 };
};
enum class OpenMode : Uint8 {
ReadOnly,
ReadWrite,
/** Read-only with a 64 MiB metadata allocation bound, checked before decoding the
* central directory. Suitable for untrusted archive browsing. */
ReadOnlyBounded
};
enum class OpenMode : Uint8 { ReadOnly, ReadWrite };
enum class Error : Uint8 {
None,
@@ -54,15 +47,11 @@ class EE_API Zip : public Pack {
* use create() explicitly. */
bool open( const std::string& path );
/** ReadOnly supports Unicode native paths and cannot modify or create an archive. */
/** Paths are UTF-8 on every platform. Read-only modes cannot modify or create an archive. */
bool open( const std::string& path, OpenMode mode );
Uint64 entryCount() const;
/** Conservative decoded central-directory memory estimate, including allocation slack.
* This excludes decompressed file data and indexes built by the caller. */
Uint64 metadataSize() const;
bool entry( Uint64 index, Entry& result );
/** Opens an entry without extracting it into memory. Backward seeks replay the prefix;
@@ -138,8 +127,6 @@ class EE_API Zip : public Pack {
struct zip* getZip();
private:
bool openReadOnly( const std::string& path );
void setError( int code, int systemCode = 0 );
bool writable();
+26 -9
View File
@@ -163,6 +163,7 @@ if _OPTIONS.platform then
premake.gcc.platforms['Native'] = premake.gcc.platforms[_OPTIONS.platform]
end
newoption { trigger = "with-security-fuzz", description = "Build the standalone NanoSVG libFuzzer target with ASan and UBSan (Clang required)." }
newoption { trigger = "with-openssl", description = "Enables OpenSSL support ( and disables mbedtls backend )." }
newoption { trigger = "with-dynamic-freetype", description = "Dynamic link against freetype." }
newoption { trigger = "with-static-eepp", description = "Force to build the demos and tests with eepp compiled statically" }
@@ -393,7 +394,6 @@ function build_base_configuration( package_name )
end
if is_vs() then
includedirs { "src/thirdparty/libzip/vs" }
buildoptions { "/utf-8" }
end
@@ -729,11 +729,11 @@ function generate_os_links()
table.insert( os_links, "dl" )
end
elseif os.is_real("windows") then
multiple_insert( os_links, { "opengl32", "glu32", "gdi32", "ws2_32", "winmm", "ole32", "oleaut32", "uuid", "shell32", "shlwapi", "dwrite", "uiautomationcore", "comctl32" } )
multiple_insert( os_links, { "opengl32", "glu32", "gdi32", "ws2_32", "winmm", "ole32", "oleaut32", "uuid", "shell32", "shlwapi", "dwrite", "uiautomationcore", "comctl32", "advapi32" } )
elseif os.is_real("mingw32") then
multiple_insert( os_links, { "opengl32", "glu32", "gdi32", "ws2_32", "winmm", "ole32", "oleaut32", "uuid", "shell32", "shlwapi", "dwrite", "uiautomationcore", "comctl32" } )
multiple_insert( os_links, { "opengl32", "glu32", "gdi32", "ws2_32", "winmm", "ole32", "oleaut32", "uuid", "shell32", "shlwapi", "dwrite", "uiautomationcore", "comctl32", "advapi32" } )
elseif os.is_real("mingw64") then
multiple_insert( os_links, { "opengl32", "glu32", "gdi32", "ws2_32", "winmm", "ole32", "oleaut32", "uuid", "shell32", "shlwapi", "dwrite", "uiautomationcore", "comctl32" } )
multiple_insert( os_links, { "opengl32", "glu32", "gdi32", "ws2_32", "winmm", "ole32", "oleaut32", "uuid", "shell32", "shlwapi", "dwrite", "uiautomationcore", "comctl32", "advapi32" } )
elseif os.is_real("macosx") then
multiple_insert( os_links, { "eepp-macos-helper-static", "Cocoa.framework", "OpenGL.framework", "CoreFoundation.framework", "CoreServices.framework", "CoreText.framework" } )
elseif os.is_real("bsd") then
@@ -1221,10 +1221,6 @@ function build_eepp( build_name )
add_static_links()
if is_vs() then
includedirs { "src/thirdparty/libzip/vs" }
end
if not is_vs() then
buildoptions{ "-std=c++20" }
else
@@ -1388,7 +1384,12 @@ solution "eepp"
language "C"
set_targetdir("libs/" .. os.get_real() .. "/thirdparty/")
files { "src/thirdparty/libzip/*.c" }
includedirs { "src/thirdparty/zlib" }
if os.is_real("windows") or os.is_real("mingw32") or os.is_real("mingw64") then
files { "src/thirdparty/libzip/win32/*.c" }
else
files { "src/thirdparty/libzip/posix/*.c" }
end
includedirs { "src/thirdparty/libzip", "src/thirdparty/zlib" }
build_base_configuration( "libzip" )
project "libpng-static"
@@ -2389,6 +2390,22 @@ solution "eepp"
configuration {}
end
-- Self-contained target instruments the vendored NanoSVG fork without reusing production archives.
if _OPTIONS["with-security-fuzz"] then
project "eepp-fuzz-nanosvg"
kind "ConsoleApp"
language "C++"
configuration {}
targetdir "bin/security"
targetname "eepp-fuzz-nanosvg"
objdir "obj/security-fuzz/nanosvg"
includedirs { "src/thirdparty" }
files { "src/tests/security/fuzz_nanosvg.cpp" }
buildoptions { "-g", "-O1", "-fno-omit-frame-pointer",
"-fsanitize=fuzzer,address,undefined", "-fno-sanitize-recover=all" }
linkoptions { "-fsanitize=fuzzer,address,undefined" }
end
if os.isfile("external_projects.lua") then
dofile("external_projects.lua")
end
+25 -5
View File
@@ -19,6 +19,7 @@ if true or premake_is_previous_to_beta8() then
require "premake.premake-ninja.ninja"
end
newoption { trigger = "with-security-fuzz", description = "Build the standalone NanoSVG libFuzzer target with ASan and UBSan (Clang required)." }
newoption { trigger = "with-openssl", description = "Enables OpenSSL support ( and disables mbedtls backend )." }
newoption { trigger = "with-dynamic-freetype", description = "Dynamic link against freetype." }
newoption { trigger = "with-static-eepp", description = "Force to build the demos and tests with eepp compiled statically" }
@@ -402,7 +403,6 @@ function build_base_configuration( package_name )
buildoptions { "-Wall" }
filter "action:vs*"
incdirs { "src/thirdparty/libzip/vs" }
buildoptions { "/utf-8" }
filter "system:emscripten"
@@ -685,9 +685,9 @@ function generate_os_links()
table.insert( os_links, "dl" )
end
elseif os.istarget("windows") then
multiple_insert( os_links, { "opengl32", "glu32", "gdi32", "ws2_32", "winmm", "ole32", "oleaut32", "uuid", "shell32", "shlwapi", "dwrite", "uiautomationcore", "comctl32" } )
multiple_insert( os_links, { "opengl32", "glu32", "gdi32", "ws2_32", "winmm", "ole32", "oleaut32", "uuid", "shell32", "shlwapi", "dwrite", "uiautomationcore", "comctl32", "advapi32" } )
elseif os.istarget("mingw32") then
multiple_insert( os_links, { "opengl32", "glu32", "gdi32", "ws2_32", "winmm", "ole32", "oleaut32", "uuid", "shell32", "shlwapi", "dwrite", "uiautomationcore", "comctl32" } )
multiple_insert( os_links, { "opengl32", "glu32", "gdi32", "ws2_32", "winmm", "ole32", "oleaut32", "uuid", "shell32", "shlwapi", "dwrite", "uiautomationcore", "comctl32", "advapi32" } )
elseif os.istarget("macosx") then
multiple_insert( os_links, { "eepp-macos-helper-static", "Cocoa.framework", "OpenGL.framework", "CoreFoundation.framework", "CoreServices.framework", "CoreText.framework" } )
elseif os.istarget("bsd") then
@@ -1220,7 +1220,6 @@ function build_eepp( build_name )
incdirs { get_sdl_arm64_cross_tools_path() .. "/include/" }
filter "action:vs*"
incdirs { "src/thirdparty/libzip/vs" }
buildoptions{ "/std:c++20", "/utf-8", "/bigobj", "/Zc:preprocessor" }
filter { "action:export-compile-commands", "system:macosx" }
@@ -1419,9 +1418,14 @@ workspace "eepp"
kind "StaticLib"
language "C"
files { "src/thirdparty/libzip/*.c" }
incdirs { "src/thirdparty/zlib" }
incdirs { "src/thirdparty/libzip", "src/thirdparty/zlib" }
build_base_configuration( "libzip" )
target_dir_thirdparty()
filter "system:windows"
files { "src/thirdparty/libzip/win32/*.c" }
filter "system:not windows"
files { "src/thirdparty/libzip/posix/*.c" }
filter {}
project "libpng-static"
kind "StaticLib"
@@ -2397,6 +2401,22 @@ workspace "eepp"
filter {}
end
-- Self-contained target instruments the vendored NanoSVG fork without reusing production archives.
if _OPTIONS["with-security-fuzz"] then
project "eepp-fuzz-nanosvg"
kind "ConsoleApp"
language "C++"
filter {}
targetdir "bin/security"
targetname "eepp-fuzz-nanosvg"
objdir "obj/security-fuzz/nanosvg"
incdirs { "src/thirdparty" }
files { "src/tests/security/fuzz_nanosvg.cpp" }
buildoptions { "-g", "-O1", "-fno-omit-frame-pointer",
"-fsanitize=fuzzer,address,undefined", "-fno-sanitize-recover=all" }
linkoptions { "-fsanitize=fuzzer,address,undefined" }
end
if os.isfile("external_projects.lua") then
dofile("external_projects.lua")
end
+21 -2
View File
@@ -76,7 +76,6 @@ LOCAL_CFLAGS := $(EEPP_C_FLAGS)
CODE_SRCS := \
../thirdparty/SOIL2/src/SOIL2/*.c \
../thirdparty/zlib/*.c \
../thirdparty/libzip/*.c \
../thirdparty/jpeg-compressor/*.cpp \
../thirdparty/imageresampler/*.cpp \
../thirdparty/pugixml/*.cpp \
@@ -116,7 +115,7 @@ LOCAL_C_INCLUDES := $(EEPP_C_INCLUDES)
LOCAL_SRC_FILES := $(foreach F, $(CODE_SRCS), $(addprefix $(dir $(F)),$(notdir $(wildcard $(LOCAL_PATH)/$(F)))))
LOCAL_STATIC_LIBRARIES := simdutf freetype libpng libwebp md4c pcre2 oniguruma harfbuzz sheenbidi gumbo-parser brotli
LOCAL_STATIC_LIBRARIES := simdutf freetype libpng libzip libwebp md4c pcre2 oniguruma harfbuzz sheenbidi gumbo-parser brotli
LOCAL_SHARED_LIBRARIES := SDL2
@@ -203,6 +202,26 @@ LOCAL_SRC_FILES := $(foreach F, $(LIBPNG_SRCS), $(addprefix $(dir $(F)),$(notd
include $(BUILD_STATIC_LIBRARY)
#*************** LIBPNG ***************
#*************** LIBZIP ***************
include $(CLEAR_VARS)
LOCAL_PATH := $(EEPP_THIRD_PARTY_PATH)
LOCAL_MODULE := libzip
LIBZIP_SRCS := \
libzip/*.c \
libzip/posix/*.c
# Kept out of the eepp module: libzip's config.h and compat.h must not shadow other headers.
LOCAL_C_INCLUDES := $(LOCAL_PATH)/libzip/ $(LOCAL_PATH)/zlib/
LOCAL_CFLAGS := -Os
LOCAL_SRC_FILES := $(foreach F, $(LIBZIP_SRCS), $(addprefix $(dir $(F)),$(notdir $(wildcard $(LOCAL_PATH)/$(F)))))
include $(BUILD_STATIC_LIBRARY)
#*************** LIBZIP ***************
#*************** LIBWEBP ***************
include $(CLEAR_VARS)
+16 -2
View File
@@ -1,13 +1,24 @@
#!/bin/sh
cd $(dirname "$0")
CRYPTO_OPTION=
FUZZ_OPTION=
for arg do
shift
case "$arg" in
--with-openssl) CRYPTO_OPTION=--with-openssl ;;
--with-security-fuzz) FUZZ_OPTION=--with-security-fuzz ;;
*) set -- "$@" "$arg" ;;
esac
done
USE_ARCH=
if command -v premake4 &> /dev/null
then
premake4 --file=../../premake4.lua --use-frameworks --disable-static-build gmake
premake4 --file=../../premake4.lua --use-frameworks --disable-static-build ${CRYPTO_OPTION:+$CRYPTO_OPTION} ${FUZZ_OPTION:+$FUZZ_OPTION} gmake || exit 1
elif command -v premake5 &> /dev/null
then
premake5 --file=../../premake5.lua --use-frameworks --disable-static-build gmake
premake5 --file=../../premake5.lua --use-frameworks --disable-static-build ${CRYPTO_OPTION:+$CRYPTO_OPTION} ${FUZZ_OPTION:+$FUZZ_OPTION} gmake || exit 1
USE_ARCH=arm64/
else
echo "Neither premake5 nor premake4 is available. Please install one."
@@ -25,4 +36,7 @@ if ! [ "$JOBS" -gt 0 ] 2>/dev/null; then
exit 1
fi
if [ -n "$FUZZ_OPTION" ]; then
set -- "$@" "CC=${CC:-clang}" "CXX=${CXX:-clang++}"
fi
make -j"$JOBS" "$@"
+10 -2
View File
@@ -3,6 +3,8 @@ cd $(dirname "$0")
BACKEND=SDL2
DEBUG_SYMBOLS=
FUZZ_OPTION=
CRYPTO_OPTION=
for arg do
shift
case "$arg" in
@@ -10,6 +12,8 @@ for arg do
--backend=SDL3|--backend=sdl3) BACKEND=SDL3 ;;
--backend=*) echo "Unsupported backend: ${arg#*=}" >&2; exit 1 ;;
--with-debug-symbols) DEBUG_SYMBOLS=--with-debug-symbols ;;
--with-openssl) CRYPTO_OPTION=--with-openssl ;;
--with-security-fuzz) FUZZ_OPTION=--with-security-fuzz ;;
*) set -- "$@" "$arg" ;;
esac
done
@@ -17,10 +21,10 @@ done
USE_ARCH=
if command -v premake4 &> /dev/null
then
premake4 --file=../../premake4.lua --disable-static-build --with-backend="$BACKEND" ${DEBUG_SYMBOLS:+$DEBUG_SYMBOLS} gmake || exit 1
premake4 --file=../../premake4.lua --disable-static-build --with-backend="$BACKEND" ${DEBUG_SYMBOLS:+$DEBUG_SYMBOLS} ${CRYPTO_OPTION:+$CRYPTO_OPTION} ${FUZZ_OPTION:+$FUZZ_OPTION} gmake || exit 1
elif command -v premake5 &> /dev/null
then
premake5 --file=../../premake5.lua --disable-static-build --with-backend="$BACKEND" ${DEBUG_SYMBOLS:+$DEBUG_SYMBOLS} gmake || exit 1
premake5 --file=../../premake5.lua --disable-static-build --with-backend="$BACKEND" ${DEBUG_SYMBOLS:+$DEBUG_SYMBOLS} ${CRYPTO_OPTION:+$CRYPTO_OPTION} ${FUZZ_OPTION:+$FUZZ_OPTION} gmake || exit 1
USE_ARCH=arm64
else
echo "Neither premake5 nor premake4 is available. Please install one."
@@ -38,4 +42,8 @@ if ! [ "$JOBS" -gt 0 ] 2>/dev/null; then
exit 1
fi
if [ -n "$FUZZ_OPTION" ]; then
# Apple Clang does not ship libFuzzer; callers may select an LLVM installation.
set -- "$@" "CC=${CC:-clang}" "CXX=${CXX:-clang++}"
fi
make -j"$JOBS" "$@"
+25 -79
View File
@@ -8,12 +8,6 @@
#include <libzip/zip.h>
#include <limits>
#if EE_PLATFORM == EE_PLATFORM_WIN
#include <io.h>
#else
#include <unistd.h>
#endif
namespace EE { namespace System {
Zip* Zip::New() {
@@ -56,16 +50,13 @@ bool Zip::open( const std::string& path, OpenMode mode ) {
mError = Error::None;
mErrorMessage.clear();
mOpenMode = mode;
if ( mode != OpenMode::ReadWrite ) {
if ( !openReadOnly( path ) )
return false;
} else {
int error = ZIP_ER_OK;
mZip = zip_open( path.c_str(), 0, &error );
if ( !mZip ) {
setError( error, errno );
return false;
}
// libzip opens UTF-8 paths as wide paths on Windows.
int error = ZIP_ER_OK;
mZip = zip_open( path.c_str(), mode == OpenMode::ReadOnly ? ZIP_RDONLY : 0, &error );
if ( !mZip ) {
// zip_open() reports the system error or inconsistency detail through errno.
setError( error, errno );
return false;
}
mZipPath = path;
mIsOpen = true;
@@ -76,14 +67,11 @@ bool Zip::open( const std::string& path, OpenMode mode ) {
bool Zip::close() {
if ( mZip ) {
// zip_close() writes the pending changes. When that fails the archive is left allocated
// (and unchanged on disk): release it and report the failure.
// (and unchanged on disk): release it without writing and report the failure.
bool written = zip_close( mZip ) == 0;
if ( !written ) {
// Without pending changes zip_close() only frees the archive.
zip_unchange_all( mZip );
zip_close( mZip );
}
if ( !written )
zip_discard( mZip );
mIsOpen = false;
@@ -115,8 +103,7 @@ bool Zip::addFile( const Uint8* data, const Uint32& dataSize, const std::string&
struct zip_source* zs = zip_source_buffer( mZip, (const void*)data, dataSize, 0 );
if ( NULL != zs ) {
Int32 Result = (Int32)zip_add( mZip, inpack.c_str(), zs );
if ( Result < 0 ) {
if ( zip_file_add( mZip, inpack.c_str(), zs, ZIP_FL_ENC_GUESS ) < 0 ) {
zip_source_free( zs );
return false;
}
@@ -228,7 +215,7 @@ bool Zip::extractStream( IOStream& stream, Uint8* data, size_t size ) {
Int32 Zip::exists( const std::string& path ) {
if ( isOpen() )
return zip_name_locate( mZip, path.c_str(), 0 );
return static_cast<Int32>( zip_name_locate( mZip, path.c_str(), 0 ) );
return -1;
}
@@ -262,54 +249,11 @@ zip* Zip::getZip() {
return mZip;
}
bool Zip::openReadOnly( const std::string& path ) {
// fopenUtf8 preserves Windows Unicode paths. zip_fdopen consumes a duplicated descriptor,
// so the FILE owned here can always be closed normally.
FILE* file = FileSystem::fopenUtf8( path, "rb" );
if ( !file ) {
setError( errno == ENOENT ? ZIP_ER_NOENT : ZIP_ER_OPEN, errno );
return false;
}
#if EE_PLATFORM == EE_PLATFORM_WIN
int descriptor = _dup( _fileno( file ) );
#else
int descriptor = dup( fileno( file ) );
#endif
const int duplicateError = errno;
std::fclose( file );
if ( descriptor < 0 ) {
setError( ZIP_ER_OPEN, duplicateError );
return false;
}
int error = ZIP_ER_OK;
mZip = zip_fdopen( descriptor, mOpenMode == OpenMode::ReadOnlyBounded ? ZIP_LIMIT_METADATA : 0,
&error );
if ( !mZip ) {
// This vendored libzip consumes descriptor after fdopen succeeds. Only its two early
// ZIP_ER_OPEN failures (dup/fdopen) leave it for the caller to close.
const int systemError = errno;
if ( error == ZIP_ER_OPEN ) {
#if EE_PLATFORM == EE_PLATFORM_WIN
_close( descriptor );
#else
::close( descriptor );
#endif
}
setError( error, systemError );
return false;
}
return true;
}
Uint64 Zip::entryCount() const {
if ( !mZip )
return 0;
const auto count = zip_get_num_entries( mZip, 0 );
return count == std::numeric_limits<Uint64>::max() ? 0 : count;
}
Uint64 Zip::metadataSize() const {
return mZip ? zip_get_metadata_size( mZip ) : 0;
return count < 0 ? 0 : static_cast<Uint64>( count );
}
bool Zip::entry( Uint64 index, Entry& result ) {
@@ -339,32 +283,34 @@ std::unique_ptr<IOStream> Zip::openStream( Uint64 index ) {
}
auto stream = std::make_unique<IOStreamZip>( this, index );
if ( !stream->isOpen() ) {
int code = 0;
int systemCode = 0;
zip_error_get( mZip, &code, &systemCode );
setError( code, systemCode );
const zip_error_t* error = zip_get_error( mZip );
setError( zip_error_code_zip( error ), zip_error_code_system( error ) );
return {};
}
return stream;
}
void Zip::setError( int code, int systemCode ) {
zip_error_t error;
zip_error_init( &error );
zip_error_set( &error, code, systemCode );
if ( code == ZIP_ER_NOENT )
mError = Error::NotFound;
else if ( zip_error_get_sys_type( code ) == ZIP_ET_SYS &&
else if ( zip_error_system_type( &error ) == ZIP_ET_SYS &&
( systemCode == EACCES || systemCode == EPERM ) )
mError = Error::PermissionDenied;
else if ( code == ZIP_ER_NOZIP || code == ZIP_ER_INCONS || code == ZIP_ER_EOF ||
code == ZIP_ER_METADATA )
code == ZIP_ER_TRUNCATED_ZIP || code == ZIP_ER_COMPRESSED_DATA ||
code == ZIP_ER_DATA_LENGTH )
mError = Error::InvalidArchive;
else if ( code == ZIP_ER_COMPNOTSUPP || code == ZIP_ER_MULTIDISK ||
code == ZIP_ER_ENCRNOTSUPP || code == ZIP_ER_NOPASSWD || code == ZIP_ER_WRONGPASSWD )
code == ZIP_ER_ENCRNOTSUPP || code == ZIP_ER_NOPASSWD || code == ZIP_ER_WRONGPASSWD ||
code == ZIP_ER_OPNOTSUPP )
mError = Error::Unsupported;
else
mError = Error::IO;
char message[256];
zip_error_to_str( message, sizeof( message ), code, systemCode );
mErrorMessage = message;
mErrorMessage = zip_error_strerror( &error );
zip_error_fini( &error );
}
bool Zip::writable() {
+2 -1
View File
@@ -54,7 +54,8 @@ static const int image_width = 188;
static const int image_height = 35;
static const int image_row_length = 24;
static const char image_bitmap[] = {
// Signed explicitly: the bitmap uses negative literals, and char is unsigned on AArch64 Linux.
static const signed char image_bitmap[] = {
15, -16, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 7, -64, 15, 63, -32, -2, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 31, -64, 15, 127, -125, -1,
@@ -23,8 +23,6 @@ constexpr ProviderCapabilities
static_cast<Uint32>( VFSCapability::Seek ) |
static_cast<Uint32>( VFSCapability::CaseSensitive ) );
constexpr Uint64 NoEntry = std::numeric_limits<Uint64>::max();
constexpr size_t MaxEntries = 262144;
constexpr size_t MaxMetadata = 64 * 1024 * 1024;
VFSError readOnly( const URI& uri ) {
return VFSError( VFSErrorCode::ReadOnly, uri, "ZIP archives are read-only" );
@@ -87,15 +85,10 @@ struct ZipArchive {
VFSResult<void> index( Zip& reader, const URI& uri, const CancellationToken& token ) {
const auto count = reader.entryCount();
if ( count > MaxEntries )
return Err(
VFSError( VFSErrorCode::InvalidOperation, uri, "ZIP has too many entries" ) );
const Uint64 libraryMetadata = reader.metadataSize();
if ( libraryMetadata > MaxMetadata ) {
return Err(
VFSError( VFSErrorCode::InvalidOperation, uri, "ZIP metadata budget exceeded" ) );
}
size_t budget = MaxMetadata - static_cast<size_t>( libraryMetadata );
// libzip bounds the count by the central directory size. Implicit directories can add
// nodes beyond it; reserving the explicit ones avoids repeated growth of large indexes.
nodes.reserve( static_cast<size_t>( count ) + 1 );
paths.reserve( static_cast<size_t>( count ) + 1 );
nodes.push_back( { info( "/", true ), {}, NoEntry } );
paths.emplace( "", 0 );
Zip::Entry metadata;
@@ -122,14 +115,6 @@ struct ZipArchive {
auto found = paths.find( path );
size_t node;
if ( found == paths.end() ) {
// Include the node/name, full path-map key, child index, hash buckets and
// allocator/vector growth slack before retaining any of those allocations.
const size_t cost = 2 * ( sizeof( ZipNode ) + path.size() + end - start + 128 );
if ( nodes.size() >= MaxEntries || cost > budget ) {
return Err( VFSError( VFSErrorCode::InvalidOperation, uri,
"ZIP metadata budget exceeded" ) );
}
budget -= cost;
node = nodes.size();
paths.emplace( std::move( path ), node );
nodes[parent].children.push_back( node );
@@ -376,7 +361,7 @@ class ZipProviderImpl : public std::enable_shared_from_this<ZipProviderImpl> {
std::string_view( reinterpret_cast<const char*>( revision.data() ), revision.size() ) );
archive->route = scheduler->resolvedRouteFor( path, true );
Zip reader( false );
if ( !reader.open( path, Zip::OpenMode::ReadOnlyBounded ) )
if ( !reader.open( path, Zip::OpenMode::ReadOnly ) )
return Err( readerError( reader, uri ) );
auto indexed = archive->index( reader, uri, token );
if ( !indexed )
@@ -498,7 +483,7 @@ VFSTask<FileHandle> ZipProvider::open( const URI& uri, const OpenOptions& option
if ( info.info.type == FileType::Directory )
return Err( VFSError( VFSErrorCode::IsDirectory, uri ) );
auto reader = std::make_unique<Zip>( false );
if ( !reader->open( archive->path, Zip::OpenMode::ReadOnlyBounded ) )
if ( !reader->open( archive->path, Zip::OpenMode::ReadOnly ) )
return Err( readerError( *reader, uri ) );
auto current =
LocalProvider::statSync( URI::fromFSPath( archive->path ), archive->path, true );
@@ -31,6 +31,8 @@ struct RemoteWatch {
Uint32 retries{ 0 };
Mode mode{ Mode::Establishing };
bool established{ false };
/** Agent channel refusals retried since the last confirmed watch. */
Uint8 channelRetries{ 0 };
};
class RemoteWatchBackendImpl;
@@ -51,6 +53,9 @@ class AgentClient : public SSHChannelPump, public std::enable_shared_from_this<A
State state() const { return mState.load(); }
/** The server refused the exec channel itself, so the agent was never started. */
bool channelRefused() const { return mChannelRefused.load(); }
const std::shared_ptr<SSHConnection>& connection() const { return mConnection; }
/** Opens the exec channel (serialized on the connection queue) and starts the handshake. */
@@ -94,6 +99,7 @@ class AgentClient : public SSHChannelPump, public std::enable_shared_from_this<A
std::vector<uint8_t> mOut;
std::string mStderr;
std::atomic<State> mState{ State::Starting };
std::atomic<bool> mChannelRefused{ false };
bool mHello{ false };
bool mPumping{ false };
};
@@ -156,6 +162,12 @@ class RemoteWatchBackendImpl : public std::enable_shared_from_this<RemoteWatchBa
static constexpr Uint32 MaxReconnectDelaySeconds = 30;
/** A refused agent channel is retried this many times, doubling the delay, before that watch
* polls. Abandoned watches free their channels once their agents exit, within milliseconds. */
static constexpr Uint8 MaxChannelRetries = 3;
static constexpr std::chrono::milliseconds ChannelRetryDelay{ 25 };
RemoteWatchBackendImpl( std::shared_ptr<SFTPProviderImpl> provider, VirtualFileSystem& vfs,
Time establishmentTimeout ) :
mProvider( provider ),
@@ -252,13 +264,17 @@ class RemoteWatchBackendImpl : public std::enable_shared_from_this<RemoteWatchBa
void agentDead( const std::shared_ptr<AgentClient>& client, bool wasReady,
const std::string& reason ) {
std::vector<std::shared_ptr<RemoteWatch>> affected;
const bool usable = client->connection()->isUsable();
// A refused channel on a usable session (its session limit is full) says nothing about
// whether the agent is installed.
const bool refused = usable && client->channelRefused();
{
std::lock_guard<std::mutex> lock( mMutex );
auto it = mAgents.find( client->key() );
if ( it != mAgents.end() && it->second.agent == client ) {
it->second.agent.reset();
it->second.lastError = reason;
if ( !wasReady && client->connection()->isUsable() ) {
if ( !wasReady && usable && !refused ) {
// The SSH session is fine but the agent never answered: not installed or
// not runnable on that host.
it->second.unavailableUntil = std::chrono::steady_clock::now() + UnavailableFor;
@@ -271,9 +287,11 @@ class RemoteWatchBackendImpl : public std::enable_shared_from_this<RemoteWatchBa
}
}
}
bool agentMissing = !wasReady && client->connection()->isUsable();
bool agentMissing = !wasReady && usable && !refused;
for ( auto& watch : affected ) {
if ( agentMissing ) {
if ( refused ) {
retryRefusedChannel( watch );
} else if ( agentMissing ) {
usePolling( watch );
} else {
{
@@ -302,6 +320,7 @@ class RemoteWatchBackendImpl : public std::enable_shared_from_this<RemoteWatchBa
watch->mode = RemoteWatch::Mode::Agent;
watch->established = true;
watch->retries = 0;
watch->channelRetries = 0;
}
if ( auto sink = watch->sink.lock() ) {
sink->setStatus( generic ? WatchStatus::Polling : WatchStatus::Active );
@@ -472,6 +491,36 @@ class RemoteWatchBackendImpl : public std::enable_shared_from_this<RemoteWatchBa
} );
}
/** Retries briefly within the establishment window, then polls only this watch. The host is
* not marked unavailable, so later watches use the agent again. */
void retryRefusedChannel( const std::shared_ptr<RemoteWatch>& watch ) {
Uint8 attempt;
{
std::lock_guard<std::mutex> lock( mMutex );
if ( watch->mode == RemoteWatch::Mode::Closed )
return;
attempt = watch->channelRetries++;
}
if ( attempt >= MaxChannelRetries ) {
usePolling( watch );
return;
}
std::weak_ptr<RemoteWatchBackendImpl> weak = weak_from_this();
std::weak_ptr<RemoteWatch> weakWatch = watch;
mRunner.runAfter( ChannelRetryDelay * ( 1 << attempt ), [weak, weakWatch] {
auto self = weak.lock();
auto watch = weakWatch.lock();
if ( !self || !watch )
return;
{
std::lock_guard<std::mutex> lock( self->mMutex );
if ( watch->mode == RemoteWatch::Mode::Closed )
return;
}
self->establish( watch );
} );
}
void scheduleRetry( const std::shared_ptr<RemoteWatch>& watch ) {
Uint32 retries;
{
@@ -631,6 +680,7 @@ void AgentClient::start( const std::string& command ) {
if ( !self->mChannel ) {
if ( libssh2_session_last_errno( c.session() ) == LIBSSH2_ERROR_EAGAIN )
return std::nullopt;
self->mChannelRefused = true;
return VFSResult<void>(
Err( c.lastError( URI(), "efsw-agent: could not open a channel" ) ) );
}
@@ -0,0 +1 @@
<svg width="16" height="16"><path d="M1 1 A57.1E2857 3 0 0 1 12 12 L1 12 Z"/></svg>

After

Width:  |  Height:  |  Size: 83 B

@@ -0,0 +1 @@
<svg width="16" height="16"><path d="M-3e7 0 L-3e7 16 L-4e7 8 Z"/></svg>

After

Width:  |  Height:  |  Size: 72 B

@@ -0,0 +1 @@
<svg width="16" height="16"><path stroke="red" stroke-width="10662107277" stroke-linecap="round" d="M1 1 L12 12"/></svg>

After

Width:  |  Height:  |  Size: 120 B

@@ -0,0 +1 @@
<svg width="16" height="16"><rect x="2" y="2" width="12" height="12" fill="red"/></svg>

After

Width:  |  Height:  |  Size: 87 B

+26
View File
@@ -0,0 +1,26 @@
#include <cstdint>
#include <cstring>
#define NANOSVG_IMPLEMENTATION
#define NANOSVGRAST_IMPLEMENTATION
#include <nanosvg/nanosvg.h>
#include <nanosvg/nanosvgrast.h>
extern "C" int LLVMFuzzerTestOneInput( const uint8_t* data, size_t size ) {
if ( size > 8192 )
return 0;
char input[8193];
std::memcpy( input, data, size );
input[size] = '\0';
NSVGimage* image = nsvgParse( input, "px", 96, 0xFFFFFFFF );
if ( !image )
return 0;
NSVGrasterizer* rasterizer = nsvgCreateRasterizer();
if ( rasterizer ) {
unsigned char pixels[32 * 32 * 4];
nsvgRasterize( rasterizer, image, 0, 0, 1, pixels, 32, 32, 32 * 4 );
nsvgDeleteRasterizer( rasterizer );
}
nsvgDelete( image );
return 0;
}
+20 -6
View File
@@ -10,6 +10,7 @@
#include <array>
#include <condition_variable>
#include <cstdlib>
#include <cstring>
#include <eepp/system/base64.hpp>
#include <eepp/system/process.hpp>
#include <eepp/vfs/path.hpp>
@@ -50,6 +51,11 @@ class TestSSHServer {
bool available() const { return mAvailable; }
static bool required() {
const char* value = std::getenv( "EEPP_REQUIRE_SFTP_TESTS" );
return value && std::strcmp( value, "1" ) == 0;
}
const std::string& skipReason() const { return mSkipReason; }
const std::string& dir() const { return mDir; }
@@ -158,6 +164,13 @@ class TestSSHServer {
FileSystem::fileRemove( mDir + "id_ed25519_nopub.pub" );
FileSystem::fileWrite( mDir + "authorized_keys", std::string_view( authorized ) );
// Tests fail authentication on purpose; OpenSSH >= 9.8 would otherwise penalize (refuse)
// the loopback source afterwards. Older servers reject the option and refuse to start.
const std::string probe = mDir + "sshd_penalties_probe";
FileSystem::fileWrite( probe, std::string_view( "HostKey " + mDir +
"host_ed25519\nPerSourcePenalties no\n" ) );
const bool penalties = run( sshd, { "-t", "-f", probe } );
std::string user = SSHConfigContext::system( "x" ).localUser;
for ( int attempt = 0; attempt < 5 && !mServer; ++attempt ) {
mPort =
@@ -188,10 +201,8 @@ class TestSSHServer {
"AllowTcpForwarding yes\n"
"Subsystem sftp internal-sftp" +
( mDisablePosixRename ? " -P posix-rename\n" : "\n" ) +
"LogLevel ERROR\n"
// Tests fail authentication on purpose; OpenSSH >= 9.8 would
// otherwise penalize (refuse) the loopback source afterwards.
"PerSourcePenalties no\n";
"LogLevel ERROR\n" +
( penalties ? "PerSourcePenalties no\n" : "" );
FileSystem::fileWrite( mDir + "sshd_config", std::string_view( config ) );
auto server = std::make_unique<Process>();
if ( !server->create( sshd, { "-D", "-e", "-f", mDir + "sshd_config" } ) )
@@ -410,7 +421,8 @@ class BlackholeProxy {
auto& server = TestSSHServer::instance(); \
if ( !server.available() ) { \
printf( " SFTP integration test skipped: %s\n", server.skipReason().c_str() ); \
return; \
ASSERT_FALSE( TestSSHServer::required() ); \
UTEST_SKIP( "Local SSH server is unavailable" ); \
}
class FixedVerifier : public SSHHostKeyVerifier {
@@ -657,6 +669,7 @@ UTEST( SFTP, differentVerifiedPeersSupportCrossServerTransfers ) {
auto& other = TestSSHServer::independent();
if ( !other.available() ) {
printf( " Independent SSH server unavailable: %s\n", other.skipReason().c_str() );
ASSERT_FALSE( TestSSHServer::required() );
UTEST_SKIP( "Independent SSH server is unavailable" );
}
TempDir configDir;
@@ -707,7 +720,8 @@ UTEST( SFTP, replacementWithoutPosixRenamePreservesBothFiles ) {
auto& server = TestSSHServer::withoutPosixRename();
if ( !server.available() ) {
printf( " SFTP integration test skipped: %s\n", server.skipReason().c_str() );
return;
ASSERT_FALSE( TestSSHServer::required() );
UTEST_SKIP( "Local SSH server is unavailable" );
}
VirtualFileSystem vfs;
auto sftp = server.provider();
+4 -2
View File
@@ -94,8 +94,10 @@ UTEST( TextFormat, autodetectProject ) {
auto files = FileSystem::filesInfoGetInPath( folder, false, true, true, true );
for ( const auto& file : files ) {
if ( file.isDirectory() ) {
// Downloaded SDL SDKs contain platform binaries outside this source scan.
if ( !LuaPattern::hasMatches( file.getFileName(), "^SDL[23]%-%d+%.%d+%.%d+$" ) )
// Downloaded SDL SDKs contain platform binaries outside this source scan. Fuzz
// corpora hold deliberately malformed inputs of any encoding.
if ( !LuaPattern::hasMatches( file.getFileName(), "^SDL[23]%-%d+%.%d+%.%d+$" ) &&
file.getFileName() != "corpus" )
checkFolder( file.getFilepath() );
continue;
}
+136
View File
@@ -0,0 +1,136 @@
#include "utest.hpp"
#include "vfs_test_utils.hpp"
#include <cstdlib>
#include <cstring>
#include <eepp/network/ssl/sslsocket.hpp>
#include <eepp/network/tcplistener.hpp>
#include <eepp/system/process.hpp>
#include <eepp/system/sys.hpp>
#include <thread>
using namespace EE;
using namespace EE::Network;
using namespace EE::System;
namespace {
class LocalTLSServer {
public:
LocalTLSServer() {
const std::string openssl = Sys::which( "openssl" );
if ( openssl.empty() )
return;
mCertificate = mDirectory.path + "server.pem";
mOtherCertificate = mDirectory.path + "other.pem";
const std::string key = mDirectory.path + "server.key";
if ( !generate( openssl, mCertificate, key ) ||
!generate( openssl, mOtherCertificate, mDirectory.path + "other.key" ) )
return;
TcpListener reservation;
if ( reservation.listen( Socket::AnyPort, IpAddress::LocalHost ) != Socket::Done )
return;
mPort = reservation.getLocalPort();
reservation.close();
if ( !mProcess.create(
openssl, { "s_server", "-accept", "127.0.0.1:" + String::toString( mPort ),
"-cert", mCertificate, "-key", key, "-www", "-quiet", "-tls1_2" } ) )
return;
for ( int attempt = 0; attempt < 100; ++attempt ) {
TcpSocket probe;
if ( probe.connect( IpAddress::LocalHost, mPort, Milliseconds( 50 ) ) ==
Socket::Done ) {
mAvailable = true;
break;
}
std::this_thread::sleep_for( std::chrono::milliseconds( 20 ) );
}
}
~LocalTLSServer() { mProcess.kill(); }
bool available() const { return mAvailable; }
unsigned short port() const { return mPort; }
const std::string& certificate() const { return mCertificate; }
const std::string& otherCertificate() const { return mOtherCertificate; }
private:
static bool generate( const std::string& openssl, const std::string& certificate,
const std::string& key ) {
Process process;
if ( !process.create( openssl, { "req", "-x509", "-newkey", "rsa:2048", "-nodes", "-sha256",
"-days", "1", "-subj", "/CN=localhost", "-addext",
"subjectAltName=DNS:localhost", "-keyout", key, "-out",
certificate } ) )
return false;
int code = -1;
process.join( &code );
return code == 0;
}
vfstest::TempDir mDirectory;
Process mProcess;
std::string mCertificate;
std::string mOtherCertificate;
unsigned short mPort{ 0 };
bool mAvailable{ false };
};
class TLSCertificateScope {
public:
TLSCertificateScope() : mOriginal( SSL::SSLSocket::CertificatesPath ) { SSL::SSLSocket::end(); }
~TLSCertificateScope() {
SSL::SSLSocket::end();
SSL::SSLSocket::CertificatesPath = std::move( mOriginal );
}
static std::unique_ptr<SSL::SSLSocket> socket( const std::string& certificate,
const std::string& hostname ) {
SSL::SSLSocket::end();
SSL::SSLSocket::CertificatesPath = certificate;
return std::unique_ptr<SSL::SSLSocket>( SSL::SSLSocket::New( hostname, true, true ) );
}
private:
std::string mOriginal;
};
} // namespace
UTEST( TLSSecurity, HTTPSAcceptsTrustedPeerAndRejectsWrongHostAndUntrustedCertificate ) {
if ( !SSL::SSLSocket::isSupported() )
UTEST_SKIP( "TLS backend disabled" );
LocalTLSServer server;
if ( !server.available() ) {
const char* required = std::getenv( "EEPP_REQUIRE_TLS_TESTS" );
ASSERT_FALSE_MSG( required && std::strcmp( required, "1" ) == 0,
"Could not start the required loopback OpenSSL TLS server" );
UTEST_SKIP( "OpenSSL CLI with req -addext and s_server is required" );
}
TLSCertificateScope trust;
{
auto socket = TLSCertificateScope::socket( server.certificate(), "localhost" );
ASSERT_EQ( socket->connect( IpAddress::LocalHost, server.port(), Seconds( 5 ) ),
Socket::Done );
const char request[] = "GET / HTTP/1.0\r\nHost: localhost\r\n\r\n";
ASSERT_EQ( socket->send( request, sizeof( request ) - 1 ), Socket::Done );
char response[1024];
size_t received = 0;
ASSERT_EQ( socket->receive( response, sizeof( response ), received ), Socket::Done );
ASSERT_GE( received, 5u );
EXPECT_EQ( std::memcmp( response, "HTTP/", 5 ), 0 );
}
{
auto socket = TLSCertificateScope::socket( server.certificate(), "wrong.invalid" );
EXPECT_NE( socket->connect( IpAddress::LocalHost, server.port(), Seconds( 5 ) ),
Socket::Done );
}
{
auto socket = TLSCertificateScope::socket( server.otherCertificate(), "localhost" );
EXPECT_NE( socket->connect( IpAddress::LocalHost, server.port(), Seconds( 5 ) ),
Socket::Done );
}
}
@@ -0,0 +1,37 @@
#include "utest.hpp"
#include "vfs_test_utils.hpp"
#include <array>
#include <eepp/audio/inputsoundfile.hpp>
#include <eepp/audio/outputsoundfile.hpp>
using namespace EE;
using namespace EE::Audio;
UTEST( VorbisSecurity, EncoderHandlesLowSampleRatesAndRejectsInvalidSetup ) {
vfstest::TempDir temp;
std::array<Int16, 512> samples{};
for ( unsigned channels : { 1u, 2u } ) {
for ( unsigned rate : { 1u, 1000u, 4000u, 8000u, 22050u, 44100u } ) {
const std::string path = temp.path + "encoded.ogg";
bool opened;
{
OutputSoundFile output;
opened = output.openFromFile( path, rate, channels );
if ( opened )
output.write( samples.data(), samples.size() );
}
if ( rate >= 8000 )
EXPECT_TRUE( opened );
if ( opened ) {
InputSoundFile input;
ASSERT_TRUE( input.openFromFile( path ) );
EXPECT_EQ( input.getSampleRate(), rate );
EXPECT_EQ( input.getChannelCount(), channels );
EXPECT_EQ( input.read( samples.data(), samples.size() ), samples.size() );
}
}
}
OutputSoundFile output;
EXPECT_FALSE( output.openFromFile( temp.path + "invalid.ogg", 0, 1 ) );
EXPECT_FALSE( output.openFromFile( temp.path + "invalid.ogg", 44100, 0 ) );
}
@@ -0,0 +1,87 @@
#include "utest.hpp"
#include "vfs_test_utils.hpp"
#include <eepp/system/zip.hpp>
#include <initializer_list>
using namespace EE;
using namespace EE::System;
namespace {
void put( std::string& bytes, size_t offset, Uint64 value, size_t width ) {
for ( size_t i = 0; i < width; ++i )
bytes[offset + i] = static_cast<char>( value >> ( i * 8 ) );
}
// A ZIP64 end record at offset 0 followed by its locator and a classic end record whose
// fields defer to it. Only the declared directory range and entry count vary.
std::string zip64EndRecords( Uint64 offset, Uint64 size, Uint64 count ) {
std::string bytes( 56 + 20 + 22, '\0' );
put( bytes, 0, 0x06064b50, 4 );
put( bytes, 4, 44, 8 );
put( bytes, 12, 45, 2 );
put( bytes, 14, 45, 2 );
put( bytes, 24, count, 8 );
put( bytes, 32, count, 8 );
put( bytes, 40, size, 8 );
put( bytes, 48, offset, 8 );
put( bytes, 56, 0x07064b50, 4 );
put( bytes, 64, 0, 8 );
put( bytes, 72, 1, 4 );
put( bytes, 76, 0x06054b50, 4 );
put( bytes, 84, 0xffff, 2 );
put( bytes, 86, 0xffff, 2 );
put( bytes, 88, 0xffffffff, 4 );
put( bytes, 92, 0xffffffff, 4 );
return bytes;
}
} // namespace
UTEST( ZipSecurity, WrappedDirectoryRangesAreRejectedInEveryOpenMode ) {
vfstest::TempDir temp;
const std::string path = temp.path + "wrapped.zip";
// High-bit offsets and sizes also cover sign handling of 32-bit fields.
for ( auto range : { std::pair<Uint32, Uint32>{ 0xfffffff0u, 0x30u },
{ 0x80000000u, 0x80000030u },
{ 23u, 46u },
{ 0u, 45u } } ) {
std::string bytes( 22, '\0' );
put( bytes, 0, 0x06054b50, 4 );
put( bytes, 8, 1, 2 );
put( bytes, 10, 1, 2 );
put( bytes, 12, range.second, 4 );
put( bytes, 16, range.first, 4 );
ASSERT_TRUE( FileSystem::fileWrite( path, std::string_view( bytes ) ) );
Zip archive( false );
for ( auto mode : { Zip::OpenMode::ReadOnly, Zip::OpenMode::ReadWrite } ) {
EXPECT_FALSE( archive.open( path, mode ) );
EXPECT_EQ( archive.error(), Zip::Error::InvalidArchive );
}
}
}
UTEST( ZipSecurity, Zip64RangesAndCountsCannotWrapOrOverAllocate ) {
vfstest::TempDir temp;
const std::string path = temp.path + "zip64.zip";
struct Case {
Uint64 offset;
Uint64 size;
Uint64 count;
};
// 64-bit offset + size wraps, offsets past the signed seek range, entry counts that wrap
// a 32-bit allocation size, and a directory that cannot fit before the end record.
for ( const Case& value :
{ Case{ 0xffffffffffffff00ull, 0x200, 1 }, Case{ 0x8000000000000000ull, 0x10, 0 },
Case{ 0, 46, 0x100000000ull }, Case{ 0, 46, 0xffffffffull },
Case{ 0, 0xffffffffffffffffull, 1 } } ) {
const std::string bytes = zip64EndRecords( value.offset, value.size, value.count );
ASSERT_TRUE( FileSystem::fileWrite( path, std::string_view( bytes ) ) );
Zip archive( false );
for ( auto mode : { Zip::OpenMode::ReadOnly, Zip::OpenMode::ReadWrite } ) {
EXPECT_FALSE( archive.open( path, mode ) );
EXPECT_NE( archive.error(), Zip::Error::None );
EXPECT_EQ( archive.entryCount(), 0u );
}
}
}
+35 -26
View File
@@ -143,21 +143,24 @@ UTEST( ZipProvider, listsImplicitAndEmptyDirectoriesWithMetadata ) {
EXPECT_TRUE( waitFor( handle.close() ).hasValue() );
}
UTEST( ZipProvider, aggregateMetadataBudgetBoundsDeepIndexes ) {
UTEST( ZipProvider, deepAndManyEntryIndexesAreListed ) {
TempDir temp;
const std::string path = temp.path + "deep.zip";
std::string nested;
for ( int i = 0; i < 64; ++i )
nested += std::string( 60, 'd' ) + '/';
ASSERT_TRUE( makeEmptyZip( path, 512, [&nested]( Uint16 i ) {
return std::to_string( i ) + '/' + nested + "file";
} ) );
ASSERT_TRUE( makeEmptyZip(
path, 4, [&nested]( Uint16 i ) { return std::to_string( i ) + '/' + nested + "file"; } ) );
VirtualFileSystem vfs;
// Every implicit directory of the 64-level paths is indexed.
auto listed = waitFor( vfs.listAll( ZipProvider::makeURI( URI::fromFSPath( path ) ) ) );
ASSERT_FALSE( listed );
EXPECT_EQ( VFSErrorCode::InvalidOperation, listed.error().code );
EXPECT_TRUE( listed.error().message.find( "metadata budget" ) != std::string::npos );
// A normal many-entry archive stays well below the budget and remains usable after failure.
ASSERT_TRUE( listed );
EXPECT_EQ( 4u, listed.value().size() );
auto leaf = waitFor( vfs.listAll( ZipProvider::makeURI(
URI::fromFSPath( path ), "/3/" + nested.substr( 0, nested.size() - 1 ) ) ) );
ASSERT_TRUE( leaf );
ASSERT_EQ( 1u, leaf.value().size() );
EXPECT_STDSTREQ( "file", leaf.value()[0].name );
const std::string normal = temp.path + "many.zip";
ASSERT_TRUE(
makeEmptyZip( normal, 1024, []( Uint16 i ) { return "dir/file" + std::to_string( i ); } ) );
@@ -169,49 +172,55 @@ UTEST( ZipProvider, aggregateMetadataBudgetBoundsDeepIndexes ) {
UTEST( ZipProvider, malformedCentralDirectoriesAreRejectedBeforeAllocation ) {
TempDir temp;
// A tiny EOCD claims a huge directory. The bounded reader rejects its declared metadata
// before allocating its entry array or attempting to decode any names/comments/extra fields.
std::array<Uint8, 22> eocd{};
// A tiny EOCD claims a huge directory starting at a central-directory signature. It is
// rejected because the directory cannot fit before the end record, before allocating its
// entry array or decoding any names/comments/extra fields.
std::array<Uint8, 26> eocd{};
eocd[0] = 'P';
eocd[1] = 'K';
eocd[2] = 5;
eocd[3] = 6;
eocd[8] = eocd[9] = eocd[10] = eocd[11] = 255;
eocd[15] = 4; // 64 MiB of encoded metadata, before decoded objects/allocation slack.
eocd[2] = 1;
eocd[3] = 2;
eocd[4] = 'P';
eocd[5] = 'K';
eocd[6] = 5;
eocd[7] = 6;
eocd[12] = eocd[13] = eocd[14] = eocd[15] = 255;
eocd[19] = 4; // 64 MiB of encoded metadata.
const std::string path = temp.path + "oversized.zip";
ASSERT_TRUE( FileSystem::fileWrite( path, eocd.data(), eocd.size() ) );
Zip reader( false );
EXPECT_FALSE( reader.open( path, Zip::OpenMode::ReadOnlyBounded ) );
EXPECT_FALSE( reader.open( path, Zip::OpenMode::ReadOnly ) );
EXPECT_EQ( Zip::Error::InvalidArchive, reader.error() );
EXPECT_TRUE( reader.errorMessage().find( "metadata budget" ) != std::string::npos );
VirtualFileSystem vfs;
auto listed = waitFor( vfs.listAll( ZipProvider::makeURI( URI::fromFSPath( path ) ) ) );
EXPECT_EQ( VFSErrorCode::InvalidOperation, codeOf( listed ) );
// An empty-directory count must not allow a nonempty directory to be decoded into
// storage allocated for zero entries.
// A zero count with a nonempty directory is read as a wrapped InfoZIP count, which must
// then match the entries actually present.
const std::string inconsistent = temp.path + "inconsistent.zip";
ASSERT_TRUE( makeEmptyZip( inconsistent, 1, []( Uint16 ) { return std::string( "file" ); } ) );
std::string bytes;
ASSERT_TRUE( FileSystem::fileGet( inconsistent, bytes ) );
std::fill_n( bytes.end() - 14, 4, '\0' );
ASSERT_TRUE( FileSystem::fileWrite( inconsistent, std::string_view( bytes ) ) );
EXPECT_FALSE( reader.open( inconsistent, Zip::OpenMode::ReadOnlyBounded ) );
EXPECT_FALSE( reader.open( inconsistent, Zip::OpenMode::ReadOnly ) );
EXPECT_EQ( Zip::Error::InvalidArchive, reader.error() );
}
UTEST( ZipProvider, wrappedZeroInfoZipCountIsIntentionallyRejected ) {
UTEST( ZipProvider, wrappedZeroInfoZipCountIsRecovered ) {
TempDir temp;
const std::string path = temp.path + "wrapped-zero.zip";
// The fixture writes all 65,536 headers, but its two 16-bit EOCD counts wrap to zero.
// libzip recovers the InfoZIP count from the directory size.
ASSERT_TRUE(
makeEmptyZip( path, 65536, []( Uint32 i ) { return "file" + std::to_string( i ); } ) );
Zip reader( false );
for ( auto mode : { Zip::OpenMode::ReadOnly, Zip::OpenMode::ReadOnlyBounded } ) {
EXPECT_FALSE( reader.open( path, mode ) );
EXPECT_EQ( Zip::Error::InvalidArchive, reader.error() );
}
ASSERT_TRUE( reader.open( path, Zip::OpenMode::ReadOnly ) );
EXPECT_EQ( 65536u, reader.entryCount() );
ASSERT_TRUE( reader.close() );
VirtualFileSystem vfs;
EXPECT_FALSE( waitFor( vfs.listAll( ZipProvider::makeURI( URI::fromFSPath( path ) ) ) ) );
auto listed = waitFor( vfs.listAll( ZipProvider::makeURI( URI::fromFSPath( path ) ) ) );
ASSERT_TRUE( listed );
EXPECT_EQ( 65536u, listed.value().size() );
}
UTEST( ZipProvider, streamingReadsSeekBackwardsAndCopyAcrossProviders ) {
+3
View File
@@ -0,0 +1,3 @@
# Preserve upstream formatting and preprocessor continuations.
DisableFormat: true
SortIncludes: Never
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2001 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2001 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+11 -11
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2007 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
@@ -115,14 +115,14 @@ typedef struct OggVorbis_File {
ogg_sync_state oy;
/* If the FILE handle isn't seekable (eg, a pipe), only the current
stream appears */
stream appears */
int links;
ogg_int64_t *offsets;
ogg_int64_t *dataoffsets;
long *serialnos;
ogg_int64_t *pcmlengths; /* overloaded to maintain binary
compatibility; x2 size, stores both
beginning and end values */
compatibility; x2 size, stores both
beginning and end values */
vorbis_info *vi;
vorbis_comment *vc;
@@ -136,7 +136,7 @@ typedef struct OggVorbis_File {
double samptrack;
ogg_stream_state os; /* take physical pages, weld into a logical
stream of packets */
stream of packets */
vorbis_dsp_state vd; /* central working state for the packet->PCM decoder */
vorbis_block vb; /* local working space for packet->PCM decode */
@@ -149,11 +149,11 @@ extern int ov_clear(OggVorbis_File *vf);
extern int ov_fopen(const char *path,OggVorbis_File *vf);
extern int ov_open(FILE *f,OggVorbis_File *vf,const char *initial,long ibytes);
extern int ov_open_callbacks(void *datasource, OggVorbis_File *vf,
const char *initial, long ibytes, ov_callbacks callbacks);
const char *initial, long ibytes, ov_callbacks callbacks);
extern int ov_test(FILE *f,OggVorbis_File *vf,const char *initial,long ibytes);
extern int ov_test_callbacks(void *datasource, OggVorbis_File *vf,
const char *initial, long ibytes, ov_callbacks callbacks);
const char *initial, long ibytes, ov_callbacks callbacks);
extern int ov_test_open(OggVorbis_File *vf);
extern long ov_bitrate(OggVorbis_File *vf,int i);
@@ -186,12 +186,12 @@ extern vorbis_info *ov_info(OggVorbis_File *vf,int link);
extern vorbis_comment *ov_comment(OggVorbis_File *vf,int link);
extern long ov_read_float(OggVorbis_File *vf,float ***pcm_channels,int samples,
int *bitstream);
int *bitstream);
extern long ov_read_filter(OggVorbis_File *vf,char *buffer,int length,
int bigendianp,int word,int sgned,int *bitstream,
void (*filter)(float **pcm,long channels,long samples,void *filter_param),void *filter_param);
int bigendianp,int word,int sgned,int *bitstream,
void (*filter)(float **pcm,long channels,long samples,void *filter_param),void *filter_param);
extern long ov_read(OggVorbis_File *vf,char *buffer,int length,
int bigendianp,int word,int sgned,int *bitstream);
int bigendianp,int word,int sgned,int *bitstream);
extern int ov_crosslap(OggVorbis_File *vf1,OggVorbis_File *vf2);
extern int ov_halfrate(OggVorbis_File *vf,int flag);
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2007 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2007 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2015 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2010 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
*
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2007 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2007 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2007 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2015 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2015 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2015 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2015 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+15 -7
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2015 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
@@ -19,7 +19,6 @@
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#include <ogg/ogg.h>
#include "vorbis/codec.h"
#include "codec_internal.h"
@@ -30,8 +29,8 @@
#include "misc.h"
#include "os.h"
#define GENERAL_VENDOR_STRING "Xiph.Org libVorbis 1.3.6"
#define ENCODE_VENDOR_STRING "Xiph.Org libVorbis I 20180316 (Now 100% fewer shells)"
#define GENERAL_VENDOR_STRING "Xiph.Org libVorbis 1.3.7"
#define ENCODE_VENDOR_STRING "Xiph.Org libVorbis I 20200704 (Reducing Environment)"
/* helpers */
static void _v_writestring(oggpack_buffer *o,const char *s, int bytes){
@@ -47,6 +46,10 @@ static void _v_readstring(oggpack_buffer *o,char *buf,int bytes){
}
}
static int _v_toupper(int c) {
return (c >= 'a' && c <= 'z') ? (c & ~('a' - 'A')) : c;
}
void vorbis_comment_init(vorbis_comment *vc){
memset(vc,0,sizeof(*vc));
}
@@ -78,7 +81,7 @@ void vorbis_comment_add_tag(vorbis_comment *vc, const char *tag, const char *con
static int tagcompare(const char *s1, const char *s2, int n){
int c=0;
while(c < n){
if(toupper(s1[c]) != toupper(s2[c]))
if(_v_toupper(s1[c]) != _v_toupper(s2[c]))
return !0;
c++;
}
@@ -203,6 +206,7 @@ void vorbis_info_clear(vorbis_info *vi){
static int _vorbis_unpack_info(vorbis_info *vi,oggpack_buffer *opb){
codec_setup_info *ci=vi->codec_setup;
int bs;
if(!ci)return(OV_EFAULT);
vi->version=oggpack_read(opb,32);
@@ -215,8 +219,12 @@ static int _vorbis_unpack_info(vorbis_info *vi,oggpack_buffer *opb){
vi->bitrate_nominal=(ogg_int32_t)oggpack_read(opb,32);
vi->bitrate_lower=(ogg_int32_t)oggpack_read(opb,32);
ci->blocksizes[0]=1<<oggpack_read(opb,4);
ci->blocksizes[1]=1<<oggpack_read(opb,4);
bs = oggpack_read(opb,4);
if(bs<0)goto err_out;
ci->blocksizes[0]=1<<bs;
bs = oggpack_read(opb,4);
if(bs<0)goto err_out;
ci->blocksizes[1]=1<<bs;
if(vi->rate<1)goto err_out;
if(vi->channels<1)goto err_out;
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2007 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2007 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+3 -2
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
@@ -15,9 +15,10 @@
The LSP generation code is taken (with minimal modification and a
few bugfixes) from "On the Computation of the LSP Frequencies" by
Joseph Rothweiler (see http://www.rothweiler.us for contact info).
The paper is available at:
http://www.myown1.com/joe/lsf
https://web.archive.org/web/20110810174000/http://home.myfairpoint.net/vzenxj75/myown1/joe/lsf/index.html
********************************************************************/
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2010 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2015 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2010 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2007 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2007 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2010 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+6 -7
View File
@@ -8,7 +8,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2015 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
@@ -60,7 +60,7 @@ void *_alloca(size_t size);
# define FAST_HYPOT hypot
#endif
#endif
#endif /* _V_IFDEFJAIL_H_ */
#ifdef HAVE_ALLOCA_H
# include <alloca.h>
@@ -80,7 +80,7 @@ void *_alloca(size_t size);
/* Special i386 GCC implementation */
#if defined(__i386__) && defined(__GNUC__) && !defined(__BEOS__)
#if defined(__i386__) && defined(__GNUC__) && !defined(__BEOS__) && !defined(__SSE2_MATH__)
# define VORBIS_FPU_CONTROL
/* both GCC and MSVC are kinda stupid about rounding/casting to int.
Because of encapsulation constraints (GCC can't see inside the asm
@@ -119,8 +119,7 @@ static inline int vorbis_ftoi(double f){ /* yes, double! Otherwise,
/* MSVC inline assembly. 32 bit only; inline ASM isn't implemented in the
* 64 bit compiler and doesn't work on arm. */
#if defined(_MSC_VER) && !defined(_WIN64) && \
!defined(_WIN32_WCE) && !defined(_M_ARM)
#if defined(_MSC_VER) && defined(_M_IX86) && !defined(_WIN32_WCE)
# define VORBIS_FPU_CONTROL
typedef ogg_int16_t vorbis_fpu_control;
@@ -147,7 +146,7 @@ static __inline void vorbis_fpu_restore(vorbis_fpu_control fpu){
/* Optimized code path for x86_64 builds. Uses SSE2 intrinsics. This can be
done safely because all x86_64 CPUs supports SSE2. */
#if (defined(_MSC_VER) && defined(_WIN64) && defined (_M_X64)) || (defined(__GNUC__) && defined (__x86_64__))
#if (defined(_MSC_VER) && defined(_M_X64)) || (defined(__GNUC__) && defined (__SSE2_MATH__))
# define VORBIS_FPU_CONTROL
typedef ogg_int16_t vorbis_fpu_control;
@@ -174,7 +173,7 @@ static __inline void vorbis_fpu_restore(vorbis_fpu_control fpu){
typedef int vorbis_fpu_control;
static int vorbis_ftoi(double f){
STIN int vorbis_ftoi(double f){
/* Note: MSVC and GCC (at least on some systems) round towards zero, thus,
the floor() call is required to ensure correct roudning of
negative numbers */
+15 -11
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2010 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
@@ -599,11 +599,12 @@ static void bark_noise_hybridmp(int n,const long *b,
XY[i] = tXY;
}
for (i = 0, x = 0.f;; i++, x += 1.f) {
for (i = 0, x = 0.f; i < n; i++, x += 1.f) {
lo = b[i] >> 16;
if( lo>=0 ) break;
hi = b[i] & 0xffff;
if( lo>=0 || -lo>=n ) break;
if( hi>=n ) break;
tN = N[hi] + N[-lo];
tX = X[hi] - X[-lo];
@@ -615,17 +616,17 @@ static void bark_noise_hybridmp(int n,const long *b,
B = tN * tXY - tX * tY;
D = tN * tXX - tX * tX;
R = (A + x * B) / D;
if (R < 0.f)
R = 0.f;
if (R < 0.f) R = 0.f;
noise[i] = R - offset;
}
for ( ;; i++, x += 1.f) {
for ( ; i < n; i++, x += 1.f) {
lo = b[i] >> 16;
hi = b[i] & 0xffff;
if(hi>=n)break;
if( lo<0 || lo>=n ) break;
if( hi>=n ) break;
tN = N[hi] - N[lo];
tX = X[hi] - X[lo];
@@ -641,6 +642,7 @@ static void bark_noise_hybridmp(int n,const long *b,
noise[i] = R - offset;
}
for ( ; i < n; i++, x += 1.f) {
R = (A + x * B) / D;
@@ -651,10 +653,11 @@ static void bark_noise_hybridmp(int n,const long *b,
if (fixed <= 0) return;
for (i = 0, x = 0.f;; i++, x += 1.f) {
for (i = 0, x = 0.f; i < n; i++, x += 1.f) {
hi = i + fixed / 2;
lo = hi - fixed;
if(lo>=0)break;
if ( hi>=n ) break;
if ( lo>=0 ) break;
tN = N[hi] + N[-lo];
tX = X[hi] - X[-lo];
@@ -670,11 +673,12 @@ static void bark_noise_hybridmp(int n,const long *b,
if (R - offset < noise[i]) noise[i] = R - offset;
}
for ( ;; i++, x += 1.f) {
for ( ; i < n; i++, x += 1.f) {
hi = i + fixed / 2;
lo = hi - fixed;
if(hi>=n)break;
if ( hi>=n ) break;
if ( lo<0 ) break;
tN = N[hi] - N[lo];
tX = X[hi] - X[lo];
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2007 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -4
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2010 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
@@ -30,9 +30,6 @@
#include "misc.h"
#include "os.h"
//#define TRAIN_RES 1
//#define TRAIN_RESAUX 1
#if defined(TRAIN_RES) || defined (TRAIN_RESAUX)
#include <stdio.h>
#endif
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+13 -4
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2015 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
@@ -50,7 +50,7 @@ long _float32_pack(float val){
sign=0x80000000;
val= -val;
}
exp= floor(log(val)/log(2.f)+.001); //+epsilon
exp= floor(log(val)/log(2.f)+.001); /* +epsilon */
mant=rint(ldexp(val,(VQ_FMAN-1)-exp));
exp=(exp+VQ_FEXP_BIAS)<<VQ_FMAN;
@@ -62,7 +62,15 @@ float _float32_unpack(long val){
int sign=val&0x80000000;
long exp =(val&0x7fe00000L)>>VQ_FMAN;
if(sign)mant= -mant;
return(ldexp(mant,exp-(VQ_FMAN-1)-VQ_FEXP_BIAS));
exp=exp-(VQ_FMAN-1)-VQ_FEXP_BIAS;
/* clamp excessive exponent values */
if (exp>63){
exp=63;
}
if (exp<-63){
exp=-63;
}
return(ldexp(mant,exp));
}
/* given a list of word lengths, generate a list of codewords. Works
@@ -294,7 +302,7 @@ int vorbis_book_init_encode(codebook *c,const static_codebook *s){
c->used_entries=s->entries;
c->dim=s->dim;
c->codelist=_make_words(s->lengthlist,s->entries,0);
//c->valuelist=_book_unquantize(s,s->entries,NULL);
/* c->valuelist=_book_unquantize(s,s->entries,NULL); */
c->quantvals=_book_maptype1_quantvals(s);
c->minval=(int)rint(_float32_unpack(s->q_min));
c->delta=(int)rint(_float32_unpack(s->q_delta));
@@ -573,6 +581,7 @@ void run_test(static_codebook *b,float *comp){
exit(1);
}
}
free(out);
}
int main(){
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2007 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2015 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+3 -2
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2015 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
@@ -684,6 +684,7 @@ int vorbis_encode_setup_init(vorbis_info *vi){
highlevel_encode_setup *hi=&ci->hi;
if(ci==NULL)return(OV_EINVAL);
if(vi->channels<1||vi->channels>255)return(OV_EINVAL);
if(!hi->impulse_block_p)i0=1;
/* too low/high an ATH floater is nonsensical, but doesn't break anything */
@@ -1210,7 +1211,7 @@ int vorbis_encode_ctl(vorbis_info *vi,int number,void *arg){
hi->req,
hi->managed,
&new_base);
if(!hi->setup)return OV_EIMPL;
if(!new_template)return OV_EIMPL;
hi->setup=new_template;
hi->base_setting=new_base;
vorbis_encode_setup_setting(vi,vi->channels,vi->rate);
+14 -11
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2015 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
@@ -264,6 +264,10 @@ static ogg_int64_t _get_prev_page_serial(OggVorbis_File *vf, ogg_int64_t begin,
}
}
}
/*We started from the beginning of the stream and found nothing.
This should be impossible unless the contents of the stream changed out
from under us after we read from it.*/
if(!begin&&vf->offset<0)return OV_EBADLINK;
}
/* we're not interested in the page... just the serialno and granpos. */
@@ -1230,7 +1234,6 @@ double ov_time_total(OggVorbis_File *vf,int i){
int ov_raw_seek(OggVorbis_File *vf,ogg_int64_t pos){
ogg_stream_state work_os;
int ret;
if(vf->ready_state<OPENED)return(OV_EINVAL);
if(!vf->seekable)
@@ -1253,8 +1256,12 @@ int ov_raw_seek(OggVorbis_File *vf,ogg_int64_t pos){
vf->current_serialno); /* must set serialno */
vorbis_synthesis_restart(&vf->vd);
ret=_seek_helper(vf,pos);
if(ret)goto seek_error;
if(_seek_helper(vf,pos)) {
/* dump the machine so we're in a known state */
vf->pcm_offset=-1;
_decode_clear(vf);
return OV_EBADLINK;
}
/* we need to make sure the pcm_offset is set, but we don't want to
advance the raw cursor past good packets just to get to the first
@@ -1388,13 +1395,6 @@ int ov_raw_seek(OggVorbis_File *vf,ogg_int64_t pos){
vf->bittrack=0.f;
vf->samptrack=0.f;
return(0);
seek_error:
/* dump the machine so we're in a known state */
vf->pcm_offset=-1;
ogg_stream_clear(&work_os);
_decode_clear(vf);
return OV_EBADLINK;
}
/* Page granularity seek (faster than sample granularity because we
@@ -1964,6 +1964,7 @@ long ov_read_filter(OggVorbis_File *vf,char *buffer,int length,
long samples;
if(vf->ready_state<OPENED)return(OV_EINVAL);
if(word<=0)return(OV_EINVAL);
while(1){
if(vf->ready_state==INITSET){
@@ -1989,6 +1990,8 @@ long ov_read_filter(OggVorbis_File *vf,char *buffer,int length,
long channels=ov_info(vf,-1)->channels;
long bytespersample=word * channels;
vorbis_fpu_control fpu;
if(channels<1||channels>255)return(OV_EINVAL);
if(samples>length/bytespersample)samples=length/bytespersample;
if(samples <= 0)
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+1 -1
View File
@@ -6,7 +6,7 @@
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2007 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* by the Xiph.Org Foundation https://xiph.org/ *
* *
********************************************************************
+31
View File
@@ -0,0 +1,31 @@
Copyright (C) 1999-2026 Dieter Baron and Thomas Klausner
The authors can be contacted at <info@libzip.org>
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions
are met:
1. Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
2. Redistributions in binary form must reproduce the above copyright
notice, this list of conditions and the following disclaimer in
the documentation and/or other materials provided with the
distribution.
3. The names of the authors may not be used to endorse or promote
products derived from this software without specific prior
written permission.
THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS
OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY
DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+28
View File
@@ -0,0 +1,28 @@
# libzip 1.12.1
Source: `lib/` of the libzip 1.12.1 release (https://libzip.org,
`libzip-1.12.1.tar.xz`, SHA-256
`c40062022a1963c80573d48f6070792297cecd7c6bffe3aefcac0d8b9bee8913`), BSD-3-Clause, see `LICENSE`.
Only the sources upstream's `lib/CMakeLists.txt` builds for deflate/store archives are imported.
bzip2, xz, zstd and WinZip AES (`HAVE_CRYPTO`) support are not built; traditional PKWARE
encryption is. The platform file and random backends are split into `posix/` and `win32/` so
build scripts can select them by directory; they require `src/thirdparty/libzip` on the
include path.
## Generated and eepp files
- `config.h` and `zipconf.h` replace the files CMake generates; they hold the feature checks for
every eepp platform. `ZIP_STATIC` is always defined.
- `zip_err_str.c` is generated from `zip.h` and `zipint.h` with upstream's
`cmake/GenerateZipErrorStrings.cmake`. Regenerate it when updating:
`cmake -DPROJECT_SOURCE_DIR=<dir with lib/zip.h and lib/zipint.h> -DCMAKE_CURRENT_BINARY_DIR=<out> -P GenerateZipErrorStrings.cmake`.
## Local patches
Every other imported file is unmodified.
- `zip.h` includes `"zipconf.h"` instead of `<zipconf.h>` (marked `eepp:`), so eepp includes
`<libzip/zip.h>` without adding `src/thirdparty/libzip` to every project's include path.
When updating, re-apply this patch and regenerate `zip_err_str.c`.
+271
View File
@@ -0,0 +1,271 @@
#ifndef _HAD_LIBZIP_COMPAT_H
#define _HAD_LIBZIP_COMPAT_H
/*
compat.h -- compatibility defines.
Copyright (C) 1999-2025 Dieter Baron and Thomas Klausner
This file is part of libzip, a library to manipulate ZIP archives.
The authors can be contacted at <info@libzip.org>
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions
are met:
1. Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
2. Redistributions in binary form must reproduce the above copyright
notice, this list of conditions and the following disclaimer in
the documentation and/or other materials provided with the
distribution.
3. The names of the authors may not be used to endorse or promote
products derived from this software without specific prior
written permission.
THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS
OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY
DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
/* to have *_MAX definitions for all types when compiling with g++ */
#define __STDC_LIMIT_MACROS
/* to have ISO C secure library functions */
#define __STDC_WANT_LIB_EXT1__ 1
#include "config.h"
#include <sys/stat.h>
#ifdef _WIN32
#ifndef ZIP_EXTERN
#ifndef ZIP_STATIC
#define ZIP_EXTERN __declspec(dllexport)
#endif
#endif
/* for dup(), close(), etc. */
#include <io.h>
#endif
#ifdef HAVE_STDBOOL_H
#include <stdbool.h>
#else
typedef char bool;
#define true 1
#define false 0
#endif
#include <errno.h>
/* at least MinGW does not provide EOPNOTSUPP, see
* http://sourceforge.net/p/mingw/bugs/263/
*/
#ifndef EOPNOTSUPP
#define EOPNOTSUPP EINVAL
#endif
/* at least MinGW does not provide EOVERFLOW, see
* http://sourceforge.net/p/mingw/bugs/242/
*/
#ifndef EOVERFLOW
#define EOVERFLOW EFBIG
#endif
#include <fcntl.h>
/* not supported on at least Windows */
#ifndef O_CLOEXEC
#define O_CLOEXEC 0
#endif
#ifdef _WIN32
#if defined(HAVE__CLOSE)
#define close _close
#endif
#if defined(HAVE__DUP)
#define dup _dup
#endif
/* crashes reported when using fdopen instead of _fdopen on Windows/Visual Studio 10/Win64 */
#if defined(HAVE__FDOPEN)
#define fdopen _fdopen
#endif
#if !defined(HAVE_FILENO) && defined(HAVE__FILENO)
#define fileno _fileno
#endif
#if !defined(HAVE_SNPRINTF) && defined(HAVE__SNPRINTF)
#define snprintf _snprintf
#endif
#if !defined(HAVE__SNWPRINTF_S)
#define _snwprintf_s(buf, bufsz, len, fmt, ...) (_snwprintf((buf), (len), (fmt), __VA_ARGS__))
#endif
#if defined(HAVE__STRDUP)
#if !defined(HAVE_STRDUP) || defined(_WIN32)
#undef strdup
#define strdup _strdup
#endif
#endif
#if !defined(HAVE__SETMODE) && defined(HAVE_SETMODE)
#define _setmode setmode
#endif
#if !defined(HAVE_STRTOLL) && defined(HAVE__STRTOI64)
#define strtoll _strtoi64
#endif
#if !defined(HAVE_STRTOULL) && defined(HAVE__STRTOUI64)
#define strtoull _strtoui64
#endif
#if defined(HAVE__UNLINK)
#define unlink _unlink
#endif
#endif
#if defined(HAVE__FSEEKI64) && defined(HAVE__FSTAT64) && defined(HAVE__FTELLI64)
/* Windows API using int64 */
typedef zip_int64_t zip_off_t;
typedef struct _stat64 zip_os_stat_t;
#define zip_os_stat _stat64
#define zip_os_fstat _fstat64
#define zip_os_fseek _fseeki64
#define zip_os_ftell _ftelli64
#define ZIP_FSEEK_MAX ZIP_INT64_MAX
#define ZIP_FSEEK_MIN ZIP_INT64_MIN
#else
/* Normal API */
typedef struct stat zip_os_stat_t;
#define zip_os_fstat fstat
#define zip_os_stat stat
#if defined(HAVE_FTELLO) && defined(HAVE_FSEEKO)
/* Using off_t */
typedef off_t zip_off_t;
#if SIZEOF_OFF_T == 8
#define ZIP_OFF_MAX ZIP_INT64_MAX
#define ZIP_OFF_MIN ZIP_INT64_MIN
#elif SIZEOF_OFF_T == 4
#define ZIP_OFF_MAX ZIP_INT32_MAX
#define ZIP_OFF_MIN ZIP_INT32_MIN
#elif SIZEOF_OFF_T == 2
#define ZIP_OFF_MAX ZIP_INT16_MAX
#define ZIP_OFF_MIN ZIP_INT16_MIN
#else
#error unsupported size of off_t
#endif
#define ZIP_FSEEK_MAX ZIP_OFF_MAX
#define ZIP_FSEEK_MIN ZIP_OFF_MIN
#define zip_os_fseek fseeko
#define zip_os_ftell ftello
#else
/* Using long */
typedef long zip_off_t;
#include <limits.h>
#define ZIP_FSEEK_MAX LONG_MAX
#define ZIP_FSEEK_MIN LONG_MIN
#define zip_os_fseek fseek
#define zip_os_ftell ftell
#endif
#endif
#ifndef HAVE_FTELLO
#define ftello(s) ((long)ftell((s)))
#endif
#ifdef HAVE_LOCALTIME_S
#ifdef _WIN32
/* Windows is incompatible to the C11 standard, hurray! */
#define zip_localtime(t, tm) (localtime_s((tm), (t)) == 0 ? tm : NULL)
#else
#define zip_localtime localtime_s
#endif
#else
#ifdef HAVE_LOCALTIME_R
#define zip_localtime localtime_r
#else
#define zip_localtime(t, tm) (localtime(t))
#endif
#endif
#ifndef HAVE_MEMCPY_S
#define memcpy_s(dest, destsz, src, count) (memcpy((dest), (src), (count)) == NULL)
#endif
#ifndef HAVE_SNPRINTF_S
#ifdef HAVE__SNPRINTF_S
#define snprintf_s(buf, bufsz, fmt, ...) (_snprintf_s((buf), (bufsz), (bufsz), (fmt), __VA_ARGS__))
#else
#define snprintf_s snprintf
#endif
#endif
#if !defined(HAVE_STRCASECMP)
#if defined(HAVE__STRICMP)
#define strcasecmp _stricmp
#elif defined(HAVE_STRICMP)
#define strcasecmp stricmp
#endif
#endif
#ifndef HAVE_STRNCPY_S
#define strncpy_s(dest, destsz, src, count) (strncpy((dest), (src), (count)), 0)
#endif
#ifndef HAVE_STRERROR_S
#define strerrorlen_s(errnum) (strlen(strerror(errnum)))
#define strerror_s(buf, bufsz, errnum) ((void)strncpy_s((buf), (bufsz), strerror(errnum), (bufsz)), (buf)[(bufsz) - 1] = '\0', strerrorlen_s(errnum) >= (bufsz))
#else
#ifndef HAVE_STRERRORLEN_S
#define strerrorlen_s(errnum) 8192
#endif
#endif
#ifndef SIZE_MAX
#if SIZEOF_SIZE_T == 8
#define SIZE_MAX ZIP_INT64_MAX
#elif SIZEOF_SIZE_T == 4
#define SIZE_MAX ZIP_INT32_MAX
#elif SIZEOF_SIZE_T == 2
#define SIZE_MAX ZIP_INT16_MAX
#else
#error unsupported size of size_t
#endif
#endif
#ifndef PRId64
#ifdef _MSC_VER
#define PRId64 "I64d"
#else
#define PRId64 "lld"
#endif
#endif
#ifndef PRIu64
#ifdef _MSC_VER
#define PRIu64 "I64u"
#else
#define PRIu64 "llu"
#endif
#endif
#ifndef S_ISDIR
#define S_ISDIR(mode) (((mode) & S_IFMT) == S_IFDIR)
#endif
#ifndef S_ISREG
#define S_ISREG(mode) (((mode) & S_IFMT) == S_IFREG)
#endif
#endif /* compat.h */
+101 -21
View File
@@ -1,27 +1,107 @@
#ifndef ZIP_HAD_CONFIG_H
#define ZIP_HAD_CONFIG_H
#if !defined( __WIN32__ ) && !defined( _WIN32 )
#define HAVE_MKSTEMP
#define HAVE_FSEEKO
#define HAVE_FTELLO
#else
/* eepp: rename() cannot replace an existing file on Windows, which made every zip_close()
of an existing archive fail. zipint.h then uses MoveFileExA(MOVEFILE_REPLACE_EXISTING). */
#define HAVE_MOVEFILEEXA
#ifndef HAD_CONFIG_H
#define HAD_CONFIG_H
#ifndef _HAD_ZIPCONF_H
#include "zipconf.h"
#endif
#if (!defined (_MSCVER) && !defined (_MSC_VER))
#ifndef ZIP_HAVE_UNISTD_H
#define ZIP_HAVE_UNISTD_H
#endif
/* eepp: hand-written replacement for the CMake feature checks in config.h.in.
Only deflate/store and traditional PKWARE encryption are built: bzip2, xz,
zstd and WinZip AES (HAVE_CRYPTO) are disabled. Platform file backends live
in posix/ and win32/. */
#define ENABLE_FDOPEN
#ifdef _WIN32
#ifndef WIN32_LEAN_AND_MEAN
#define WIN32_LEAN_AND_MEAN
#endif
#define HAVE__CLOSE
#define HAVE__DUP
#define HAVE__FDOPEN
#define HAVE__FILENO
#define HAVE__FSEEKI64
#define HAVE__FSTAT64
#define HAVE__FTELLI64
#define HAVE__SETMODE
#define HAVE__SNPRINTF
#define HAVE__STRDUP
#define HAVE__STRICMP
#define HAVE__STRTOI64
#define HAVE__STRTOUI64
#define HAVE__UNLINK
#define HAVE_GETSECURITYINFO
#define HAVE_SNPRINTF
#define HAVE_STRTOLL
#define HAVE_STRTOULL
/* MSVC and MinGW-w64 (MINGW_HAS_SECURE_API, on by default) both declare these. compat.h would
otherwise define replacement macros that break MinGW's own declarations. */
#define HAVE__SNPRINTF_S
#define HAVE__SNWPRINTF_S
#define HAVE_LOCALTIME_S
#define HAVE_MEMCPY_S
#define HAVE_STRERROR_S
#define HAVE_STRNCPY_S
#ifndef _MSC_VER
/* MinGW declares ftello; libzip still uses _fseeki64/_ftelli64 on Windows. */
#define HAVE_FTELLO
/* MSVC defines DWORD_MAX in intsafe.h; MinGW-w64 headers do not (win32/ named source). */
#ifndef DWORD_MAX
#define DWORD_MAX 0xffffffffUL
#endif
#endif
#else /* POSIX */
#if defined(__APPLE__) || defined(__FreeBSD__) || defined(__NetBSD__) || defined(__OpenBSD__) \
|| defined(__DragonFly__) || defined(__ANDROID__)
#define HAVE_ARC4RANDOM
#endif
#define HAVE_FILENO
#define HAVE_FSEEKO
#define HAVE_FTELLO
#define HAVE_LOCALTIME_R
#define HAVE_RANDOM
#define HAVE_SNPRINTF
#define HAVE_STRCASECMP
#define HAVE_STRDUP
#define HAVE_STRINGS_H
#define HAVE_STRTOLL
#define HAVE_STRTOULL
#ifndef HAVE_UNISTD_H
#define HAVE_UNISTD_H
#endif
/* off_t is 64-bit on these platforms regardless of _FILE_OFFSET_BITS. */
#if defined(__APPLE__) || defined(__FreeBSD__) || defined(__NetBSD__) || defined(__OpenBSD__) \
|| defined(__DragonFly__) || defined(__HAIKU__) || defined(__EMSCRIPTEN__) || defined(__LP64__) \
|| defined(_LP64) || (defined(_FILE_OFFSET_BITS) && _FILE_OFFSET_BITS == 64)
#define SIZEOF_OFF_T 8
#else
#define SIZEOF_OFF_T 4
#endif
#include <sys/types.h>
/* Fails to compile if the off_t guess above is wrong for a new target. */
typedef char zip_eepp_off_t_size_check[sizeof(off_t) == SIZEOF_OFF_T ? 1 : -1];
#endif /* _WIN32 */
#define HAVE_STDBOOL_H
#if defined(__SIZEOF_SIZE_T__)
#define SIZEOF_SIZE_T __SIZEOF_SIZE_T__
#elif defined(_WIN64)
#define SIZEOF_SIZE_T 8
#else
#define SIZEOF_SIZE_T 4
#endif
#define PACKAGE "libzip"
#define VERSION "0.10"
#define VERSION "1.12.1"
#endif
#endif /* HAD_CONFIG_H */
-166
View File
@@ -1,166 +0,0 @@
/* Adapted from NetBSB libc by Dieter Baron */
/* NetBSD: gettemp.c,v 1.13 2003/12/05 00:57:36 uebayasi Exp */
/*
* Copyright (c) 1987, 1993
* The Regents of the University of California. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#include <sys/types.h>
#include <sys/stat.h>
#include <assert.h>
#include <ctype.h>
#include <errno.h>
#include <fcntl.h>
#ifdef _WIN32
#include <io.h>
#endif
#include <stdio.h>
#include <stdlib.h>
#ifndef O_BINARY
#define O_BINARY 0
#endif
#if ( defined (_MSCVER) || defined (_MSC_VER) )
typedef int pid_t;
# define _IFMT 0170000 // type of file
# define _IFDIR 0040000 // directory
# define S_ISDIR(m) (((m)&_IFMT) == _IFDIR)
#endif
#if !defined( __WIN32__ ) && !defined( _WIN32 )
#include <unistd.h>
#endif
#if defined( _WIN32 )
#include <process.h>
#include <io.h>
#endif
int
_zip_mkstemp(char *path)
{
#ifdef _WIN32
int ret;
ret = _creat(_mktemp(path), _S_IREAD|_S_IWRITE);
if (ret == -1) {
return 0;
} else {
return ret;
}
#else
int fd;
char *start, *trv;
struct stat sbuf;
pid_t pid;
/* To guarantee multiple calls generate unique names even if
the file is not created. 676 different possibilities with 7
or more X's, 26 with 6 or less. */
static char xtra[2] = "aa";
int xcnt = 0;
pid = getpid();
/* Move to end of path and count trailing X's. */
for (trv = path; *trv; ++trv)
if (*trv == 'X')
xcnt++;
else
xcnt = 0;
/* Use at least one from xtra. Use 2 if more than 6 X's. */
if (*(trv - 1) == 'X')
*--trv = xtra[0];
if (xcnt > 6 && *(trv - 1) == 'X')
*--trv = xtra[1];
/* Set remaining X's to pid digits with 0's to the left. */
while (*--trv == 'X') {
*trv = (pid % 10) + '0';
pid /= 10;
}
/* update xtra for next call. */
if (xtra[0] != 'z')
xtra[0]++;
else {
xtra[0] = 'a';
if (xtra[1] != 'z')
xtra[1]++;
else
xtra[1] = 'a';
}
/*
* check the target directory; if you have six X's and it
* doesn't exist this runs for a *very* long time.
*/
for (start = trv + 1;; --trv) {
if (trv <= path)
break;
if (*trv == '/') {
*trv = '\0';
if (stat(path, &sbuf))
return (0);
if (!S_ISDIR(sbuf.st_mode)) {
errno = ENOTDIR;
return (0);
}
*trv = '/';
break;
}
}
for (;;) {
if ((fd=open(path, O_CREAT|O_EXCL|O_RDWR|O_BINARY, 0600)) >= 0)
return (fd);
if (errno != EEXIST)
return (0);
/* tricky little algorithm for backward compatibility */
for (trv = start;;) {
if (!*trv)
return (0);
if (*trv == 'z')
*trv++ = 'a';
else {
if (isdigit((unsigned char)*trv))
*trv = 'a';
else
++*trv;
break;
}
}
}
/*NOTREACHED*/
#endif
}

Some files were not shown because too many files have changed in this diff Show More