Alsa-Devel Archive on lore.kernel.org
 help / color / mirror / Atom feed
* alsa-lib: security hardening — UCM, conf parser, topology, PCM plugins (6 findings)
       [not found] <alsa-project/alsa-lib/pr/527@alsa-project.org>
@ 2026-09-19  5:11 ` GitHub pull_request - opened
  2026-09-30 18:59 ` GitHub pull_request - reopened
  1 sibling, 0 replies; 2+ messages in thread
From: GitHub pull_request - opened @ 2026-09-19  5:11 UTC (permalink / raw)
  To: alsa-devel

alsa-project/alsa-lib pull request #527 was opened from HarshRajSinghania:

This PR addresses **six independently-triggered security hardening issues** found during a source audit of commit `f84cd4c`, all verified with proof-of-concept programs.

A3 (`shell`/`system()`) and A6 (PCM file `popen`) are intentional features and are not patched here — hardening suggestions noted inline for maintainer consideration.

---

### A1 — UCM `sysw` path traversal (CWE-22) · `src/ucm/main.c`
`execute_sysw()` concatenates the sysfs root with a caller-supplied string via `snprintf()` with no `..` rejection or `realpath()` confinement. A UCM path like `../../etc/cron.d/x:value` writes to an arbitrary filesystem location. **Fix:** `realpath()` confinement — reject if resolved path does not remain within the sysfs root.

### A2 — UCM `cfg-save` unrestricted path (CWE-73) · `src/ucm/main.c`
`execute_cfgsave()` calls `snd_output_stdio_open(&out, file, "w+")` with a raw caller-supplied `file` and no restriction. Any writable path (e.g. `~/.ssh/authorized_keys`) is reachable. **Fix:** `realpath()` check — confine to `XDG_RUNTIME_DIR` (fallback `/tmp`).

### A4 — Config parser absolute include traversal (CWE-22) · `src/conf.c`
`input_stdio_open()` immediately opens any absolute path (`file[0]=='/'`) without checking for `..` components. A planted config with `</../../etc/shadow>` can read arbitrary files. **Fix:** reject paths containing `/../`.

### A5 — Topology control `uint32_t` integer overflow (CWE-190) · `src/topology/ctl.c`
`size2 = x->size + x->priv.size` is computed in 32-bit unsigned arithmetic before being widened to `size_t`. On a 64-bit host, `0xFFFFFFF0 + 0x20 = 0x10` (wraps), bypassing the subsequent `size2 > size` guard. Three sites: `tplg_decode_control_mixer`, `tplg_decode_control_enum`, `tplg_decode_control_bytes` (distinct from CVE-2026-25068 which was `tplg_decode_control_mixer1`). **Fix:** pre-check for overflow, then `(size_t)x->size + (size_t)x->priv.size`.

### A7 — PCM `route` plugin unbounded `ttable` allocation (CWE-770) · `src/pcm/pcm_route.c`
`csize`/`ssize` grow from config-supplied channel indices with no upper bound before `malloc(csize * ssize * sizeof(entry))`. Index `1073741823` → `malloc(8 GB)`. **Fix:** cap both at 1024 (consistent with `dmix`, `softvol`, other PCM plugins).

### A8 — PCM `multi` sparse bindings OOB assert (CWE-617) · `src/pcm/pcm_multi.c`
Sparse binding maps leave `sidxs[i] == -1` for gap indices. `assert(schannels[i] < schannels_count[sidxs[i]])` then dereferences `schannels_count[-1]` → SIGABRT (debug) / OOB read (NDEBUG). **Fix:** replace both `assert()`s with explicit `-EINVAL` returns with bounds and sign checks.

---

**Verified:** all six PoC programs confirmed on `libasound2 1.2.14` / `gcc 14.2`, commit `f84cd4c`.

**Signed-off-by:** Harsh Raj Singhania <raj.harshraut@gmail.com>

Request URL   : https://github.com/alsa-project/alsa-lib/pull/527
Patch URL     : https://github.com/alsa-project/alsa-lib/pull/527.patch
Repository URL: https://github.com/alsa-project/alsa-lib

^ permalink raw reply	[flat|nested] 2+ messages in thread

* alsa-lib: security hardening — UCM, conf parser, topology, PCM plugins (6 findings)
       [not found] <alsa-project/alsa-lib/pr/527@alsa-project.org>
  2026-09-19  5:11 ` alsa-lib: security hardening — UCM, conf parser, topology, PCM plugins (6 findings) GitHub pull_request - opened
@ 2026-09-30 18:59 ` GitHub pull_request - reopened
  1 sibling, 0 replies; 2+ messages in thread
From: GitHub pull_request - reopened @ 2026-09-30 18:59 UTC (permalink / raw)
  To: alsa-devel

alsa-project/alsa-lib pull request #527 was reopened from HarshRajSinghania:

This PR addresses **six independently-triggered security hardening issues** found during a source audit of commit `f84cd4c`, all verified with proof-of-concept programs.

A3 (`shell`/`system()`) and A6 (PCM file `popen`) are intentional features and are not patched here — hardening suggestions noted inline for maintainer consideration.

---

### A1 — UCM `sysw` path traversal (CWE-22) · `src/ucm/main.c`
`execute_sysw()` concatenates the sysfs root with a caller-supplied string via `snprintf()` with no `..` rejection or `realpath()` confinement. A UCM path like `../../etc/cron.d/x:value` writes to an arbitrary filesystem location. **Fix:** `realpath()` confinement — reject if resolved path does not remain within the sysfs root.

### A2 — UCM `cfg-save` unrestricted path (CWE-73) · `src/ucm/main.c`
`execute_cfgsave()` calls `snd_output_stdio_open(&out, file, "w+")` with a raw caller-supplied `file` and no restriction. Any writable path (e.g. `~/.ssh/authorized_keys`) is reachable. **Fix:** `realpath()` check — confine to `XDG_RUNTIME_DIR` (fallback `/tmp`).

### A4 — Config parser absolute include traversal (CWE-22) · `src/conf.c`
`input_stdio_open()` immediately opens any absolute path (`file[0]=='/'`) without checking for `..` components. A planted config with `</../../etc/shadow>` can read arbitrary files. **Fix:** reject paths containing `/../`.

### A5 — Topology control `uint32_t` integer overflow (CWE-190) · `src/topology/ctl.c`
`size2 = x->size + x->priv.size` is computed in 32-bit unsigned arithmetic before being widened to `size_t`. On a 64-bit host, `0xFFFFFFF0 + 0x20 = 0x10` (wraps), bypassing the subsequent `size2 > size` guard. Three sites: `tplg_decode_control_mixer`, `tplg_decode_control_enum`, `tplg_decode_control_bytes` (distinct from CVE-2026-25068 which was `tplg_decode_control_mixer1`). **Fix:** pre-check for overflow, then `(size_t)x->size + (size_t)x->priv.size`.

### A7 — PCM `route` plugin unbounded `ttable` allocation (CWE-770) · `src/pcm/pcm_route.c`
`csize`/`ssize` grow from config-supplied channel indices with no upper bound before `malloc(csize * ssize * sizeof(entry))`. Index `1073741823` → `malloc(8 GB)`. **Fix:** cap both at 1024 (consistent with `dmix`, `softvol`, other PCM plugins).

### A8 — PCM `multi` sparse bindings OOB assert (CWE-617) · `src/pcm/pcm_multi.c`
Sparse binding maps leave `sidxs[i] == -1` for gap indices. `assert(schannels[i] < schannels_count[sidxs[i]])` then dereferences `schannels_count[-1]` → SIGABRT (debug) / OOB read (NDEBUG). **Fix:** replace both `assert()`s with explicit `-EINVAL` returns with bounds and sign checks.

---

**Verified:** all six PoC programs confirmed on `libasound2 1.2.14` / `gcc 14.2`, commit `f84cd4c`.

**Signed-off-by:** Harsh Raj Singhania <raj.harshraut@gmail.com>

Request URL   : https://github.com/alsa-project/alsa-lib/pull/527
Patch URL     : https://github.com/alsa-project/alsa-lib/pull/527.patch
Repository URL: https://github.com/alsa-project/alsa-lib

^ permalink raw reply	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2026-09-30 19:00 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
     [not found] <alsa-project/alsa-lib/pr/527@alsa-project.org>
2026-09-19  5:11 ` alsa-lib: security hardening — UCM, conf parser, topology, PCM plugins (6 findings) GitHub pull_request - opened
2026-09-30 18:59 ` GitHub pull_request - reopened

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox