Fedora Account System
Red Hat Associate
Red Hat Customer
MANUALLY_VERIFIED_REPORT package: libsolv-0.7.36-2.hum1 ------ [Security] Stack-based Buffer Overflow in Debian Metadata Parser via SHA512 Checksum Summary: Stack-based buffer overflow in libsolv's Debian metadata/control parser when handling `SHA384`/`SHA512` checksum tags. Requirements to exploit: Ability to supply crafted Debian repository metadata (e.g., a malicious `Packages` file) that a victim processes with libsolv (directly or via a consumer that uses libsolv for Debian metadata ingestion). Component affected: libsolv Version affected: <= 0.7.36 Patch available: no Version fixed (if any already): >= TBD CVSS (optional): 6.5 (Medium) — CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:U/C:N/I:N/A:H (Base metrics only; calculator: https://nvd.nist.gov/vuln-metrics/cvss/v3-calculator) Impact (optional): Moderate (proposed). Per https://access.redhat.com/security/updates/classification this is memory corruption reachable via untrusted repository metadata ingestion and can at least cause a denial of service; it is not clearly "High" because an attacker typically needs the victim to consume attacker-controlled repository metadata (configuration/user action) and reliable system compromise is not demonstrated here. This may be "Low" instead in product contexts where the vulnerable path is not used by default, is only reachable via uncommon workflows, or is effectively mitigated (e.g., only trusted/signed metadata is processed). Embargo: no Acknowledgement: Aisle Research Steps to reproduce if available: See "Reproduction Steps" below. Mitigation if available: Prefer only consuming trusted/signed repository metadata; avoid processing untrusted `Packages` inputs until patched. Original report: report.36/vuln_4_47_1_stage5_email_v2.md Hello libsolv maintainers, We believe that we have discovered a potential security vulnerability in `ext/repo_deb.c` while parsing Debian metadata/control content. ### Vulnerability Details `control2solvable()` uses a fixed stack buffer sized for 32-byte digests (65 hex chars incl. NUL), but accepts `sha384`/`sha512` tags and validates their full lengths before copying with `strcpy`. ```c /* ext/repo_deb.c */ char checksum[32 * 2 + 1]; // 65 bytes ... case 'S' << 8 | 'H': newtype = solv_chksum_str2type(tag); if (!newtype || solv_chksum_len(newtype) * 2 != strlen(q)) break; if (!checksumtype || (newtype == REPOKEY_TYPE_SHA1 && checksumtype != REPOKEY_TYPE_SHA256) || newtype == REPOKEY_TYPE_SHA256) { strcpy(checksum, q); // overflow for SHA384/SHA512 checksumtype = newtype; } break; ``` And supported checksum types include SHA384/SHA512: ```c /* src/chksum.c */ if (!strcasecmp(str, "sha384")) return REPOKEY_TYPE_SHA384; if (!strcasecmp(str, "sha512")) return REPOKEY_TYPE_SHA512; ``` For SHA512, `strlen(q) == 128` passes validation, then `strcpy` writes 129 bytes into a 65-byte stack buffer (64-byte overflow + NUL), causing stack corruption. Relevant CWEs: - `CWE-121` (Stack-based Buffer Overflow): direct stack overwrite. - `CWE-787` (Out-of-bounds Write): write past fixed local buffer. - `CWE-120` (Classic Buffer Copy without Checking Size): unbounded `strcpy` into fixed array. ### Reproduction Steps 1. Build libsolv with ASan (`-fsanitize=address -fno-omit-frame-pointer`). 2. Create a Debian metadata file `Packages`: ``` python3 - <<'PY' > Packages print("Package: p") print("Version: 1") print("Architecture: all") print("SHA512: " + "00"*64) # 128 hex chars print() PY ``` 3. Run ASAN_OPTIONS=abort_on_error=1 ./build-asan/tools/deb2solv -r Packages >/dev/null Crash: [root@c28a4ffb0823 workspace]# ASAN_OPTIONS=abort_on_error=1 ./build-asan/tools/deb2solv -r Packages >/dev/null ================================================================= ==534==ERROR: AddressSanitizer: stack-buffer-overflow on address 0x7ffffd600061 at pc 0x000000488c0e bp 0x7ffffffc60d0 sp 0x7ffffffc5888 WRITE of size 129 at 0x7ffffd600061 thread T0 #0 0x000000488c0d (/workspace/build-asan/tools/deb2solv+0x488c0d) (BuildId: ced6cc77c46768e740df09b8c5a390709bbaaa4c) #1 0x7fffff7a3758 (/workspace/build-asan/ext/libsolvext.so.1+0x1b758) (BuildId: 4d8400e7ec4d874117c3a5bdb29c0faa3a6b1fa8) #2 0x7fffff7a2515 (/workspace/build-asan/ext/libsolvext.so.1+0x1a515) (BuildId: 4d8400e7ec4d874117c3a5bdb29c0faa3a6b1fa8) #3 0x0000004e319b (/workspace/build-asan/tools/deb2solv+0x4e319b) (BuildId: ced6cc77c46768e740df09b8c5a390709bbaaa4c) #4 0x7fffff2b4447 (/lib64/libc.so.6+0x3447) (BuildId: dae6ae6929d69dca842288f5300af5a33d1bdcd7) #5 0x7fffff2b450a (/lib64/libc.so.6+0x350a) (BuildId: dae6ae6929d69dca842288f5300af5a33d1bdcd7) #6 0x000000401524 (/workspace/build-asan/tools/deb2solv+0x401524) (BuildId: ced6cc77c46768e740df09b8c5a390709bbaaa4c) Address 0x7ffffd600061 is located in stack of thread T0 at offset 97 in frame #0 0x7fffff7a28bf (/workspace/build-asan/ext/libsolvext.so.1+0x1a8bf) (BuildId: 4d8400e7ec4d874117c3a5bdb29c0faa3a6b1fa8) This frame has 1 object(s): [32, 97) 'checksum' (line 371) <== Memory access at offset 97 overflows this variable HINT: this may be a false positive if your program uses some custom stack unwind mechanism, swapcontext or vfork (longjmp and C++ exceptions *are* supported) SUMMARY: AddressSanitizer: stack-buffer-overflow (/workspace/build-asan/tools/deb2solv+0x488c0d) (BuildId: ced6cc77c46768e740df09b8c5a390709bbaaa4c) Shadow bytes around the buggy address: 0x7ffffd5ffd80: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x7ffffd5ffe00: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x7ffffd5ffe80: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x7ffffd5fff00: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x7ffffd5fff80: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 =>0x7ffffd600000: f1 f1 f1 f1 00 00 00 00 00 00 00 00[01]f3 f3 f3 0x7ffffd600080: f3 f3 f3 f3 00 00 00 00 00 00 00 00 00 00 00 00 0x7ffffd600100: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x7ffffd600180: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x7ffffd600200: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x7ffffd600280: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 This is reachable from untrusted repository/package metadata ingestion paths. ### Proposed Fix ```diff diff --git a/ext/repo_deb.c b/ext/repo_deb.c @@ - char checksum[32 * 2 + 1]; + char checksum[64 * 2 + 1]; @@ - strcpy(checksum, q); + memcpy(checksum, q, strlen(q) + 1); checksumtype = REPOKEY_TYPE_MD5; @@ - strcpy(checksum, q); + memcpy(checksum, q, strlen(q) + 1); checksumtype = newtype; ``` Aisle Research ------ This report was generated using AI technology. Always review AI-generated content prior to use
This issue has been addressed in the following products: Red Hat Enterprise Linux 10 Via RHSA-2026:28236 https://access.redhat.com/errata/RHSA-2026:28236