fix: capture ${source:Version}, the number OSV ranges are actually stated in
OSV states Debian ranges in *source* package versions. A source package that ships several binaries gives each its own upstream version, and the two are unrelated numbers: `libldb2` is `2:2.11.0+samba4.22.11+dfsg-0+deb13u1` while its source, samba, is `2:4.22.11+dfsg-…`. A consumer that resolves the coordinate on `source_package` — which is what this driver's `source:Package` is for — and then compares `version` is comparing ldb's version against samba's range. dpkg reads `2.11.0` as older than the `2:4.17.4+dfsg-1` that fixed CVE-2022-44640, so a Debian 13 host running samba 4.22.11, five releases past the fix, was reported vulnerable on four packages at once. This driver cannot fix that comparison. It is the only place that can supply the number to make it with. Empty when dpkg considers it equal to `Version`, and empty on a dpkg that does not know the field, so it falls back to `Version` — which is the previous behaviour and correct everywhere except the shape above. `maxsplit` goes from 4 to 5 with the extra field. Summary stays last, so it keeps whatever it contains. **The fixture was carrying four fields against a format string asking for five.** `source_package` had been silently receiving the description, and no assertion looked at it. It now carries what dpkg-query actually returns, including a package whose source version is a different number from its own. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 5
parent
55635ab551
commit
e8eadb46c6
+20
-3
@@ -835,11 +835,13 @@ class LinuxDriver(OSDriver):
|
||||
def _get_packages_apt(self) -> list[PackageDict]:
|
||||
out = self._send(
|
||||
"dpkg-query -W -f='${Package}\\t${Version}\\t${Installed-Size}"
|
||||
"\\t${source:Package}\\t${binary:Summary}\\n' 2>/dev/null"
|
||||
"\\t${source:Package}\\t${source:Version}\\t${binary:Summary}\\n' 2>/dev/null"
|
||||
)
|
||||
packages: list[PackageDict] = []
|
||||
for line in out.splitlines():
|
||||
parts = line.split("\t", 4)
|
||||
# Summary stays last and keeps whatever it contains: maxsplit must
|
||||
# equal the number of tabs the format writes, not the field count.
|
||||
parts = line.split("\t", 5)
|
||||
if len(parts) < 2:
|
||||
continue
|
||||
name = parts[0].strip()
|
||||
@@ -847,7 +849,21 @@ class LinuxDriver(OSDriver):
|
||||
size = int(parts[2].strip()) * 1024 if len(parts) > 2 and parts[2].strip().isdigit() else 0
|
||||
# Debian source package (e.g. openssh-server → openssh) for OSV matching.
|
||||
source_package = parts[3].strip() if len(parts) > 3 and parts[3].strip() else name
|
||||
description = parts[4].strip() if len(parts) > 4 else ""
|
||||
# And its version, which is a different number from this package's.
|
||||
#
|
||||
# OSV states Debian ranges in *source* versions. A source package
|
||||
# that ships several binaries gives each its own upstream version:
|
||||
# libldb2 is 2:2.11.0+samba4.22.11+dfsg-… while its source, samba,
|
||||
# is 2:4.22.11+dfsg-…. A consumer matching on source_package and
|
||||
# comparing `version` compares two unrelated numbers — dpkg reads
|
||||
# ldb's 2.11.0 as older than the 2:4.17.4+dfsg-1 that fixed
|
||||
# CVE-2022-44640, and a host five releases past the fix was reported
|
||||
# vulnerable on four packages at once.
|
||||
#
|
||||
# dpkg leaves this empty when it equals `Version`; so does an older
|
||||
# dpkg that does not know the field at all.
|
||||
source_version = parts[4].strip() if len(parts) > 4 and parts[4].strip() else version
|
||||
description = parts[5].strip() if len(parts) > 5 else ""
|
||||
packages.append({
|
||||
"name": name,
|
||||
"version": version,
|
||||
@@ -856,6 +872,7 @@ class LinuxDriver(OSDriver):
|
||||
"size": size,
|
||||
"source": "apt",
|
||||
"source_package": source_package,
|
||||
"source_version": source_version,
|
||||
})
|
||||
return packages
|
||||
|
||||
|
||||
Reference in New Issue
Block a user