Skip to content

Commit

Permalink
Merge pull request #148 from influxdata/jdstrand/pkg-modifier
Browse files Browse the repository at this point in the history
fix: allow '_' in package modifier as was intended
  • Loading branch information
jdstrand committed Nov 21, 2023
2 parents 77e38c4 + 004e4c4 commit b296862
Show file tree
Hide file tree
Showing 5 changed files with 65 additions and 14 deletions.
16 changes: 13 additions & 3 deletions cvelib/common.py
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,16 @@
r"^[a-z0-9+.-]{1,%(software_len)d}$"
% ({"software_len": _patLengths["pkg-software"]})
),
# foo, foo1, foo-bar, foo.bar, for-bar-1.0, foo_bar
"pkg-modifier": re.compile(
r"^[a-z0-9+._-]{1,%(modifier_len)d}$"
% ({"modifier_len": _patLengths["pkg-modifier"]})
),
# foo, foo1, foo-bar, foo.bar, for-bar-1.0
"pkg-modifier-ubuntu": re.compile(
r"^[a-z0-9+.-]{1,%(modifier_len)d}$"
% ({"modifier_len": _patLengths["pkg-modifier"]})
),
# add others distros and build artifacts (oci, etc) as desired
"pkg-product": re.compile(
r"^(upstream|%s)$"
Expand All @@ -116,7 +126,7 @@
),
# the string form
"pkg-full": re.compile(
r"^(upstream|%(products)s)(/[a-z0-9+.-]{1,%(where_len)d})?_[a-zA-Z0-9+._-]{1,%(software_len)d}(/[a-z0-9+.-]{1,%(modifier_len)d})?: (needs-triage|needed|pending|released|deferred|ignored|DNE|not-affected)( \([a-zA-Z0-9 +.,/'\":~\[\]_()<>#=|`-]{1,%(when_len)d}\))?$"
r"^(upstream|%(products)s)(/[a-z0-9+.-]{1,%(where_len)d})?_[a-zA-Z0-9+._-]{1,%(software_len)d}(/[a-z0-9+._-]{1,%(modifier_len)d})?: (needs-triage|needed|pending|released|deferred|ignored|DNE|not-affected)( \([a-zA-Z0-9 +.,/'\":~\[\]_()<>#=|`-]{1,%(when_len)d}\))?$"
% (
{
"products": "|".join(
Expand Down Expand Up @@ -241,7 +251,7 @@
),
# TODO: reuse product/where
"pkg-tags-key": re.compile(
r"^Tags_[a-zA-Z0-9+.-][a-zA-Z0-9+._-]{0,%(software_len1)d}[a-zA-Z0-9+.-](/[a-z0-9+.-]{1,%(software_len2)d})?$"
r"^Tags_[a-zA-Z0-9+.-][a-zA-Z0-9+._-]{0,%(software_len1)d}[a-zA-Z0-9+.-](/[a-z0-9+._-]{1,%(software_len2)d})?$"
% (
{
"software_len1": _patLengths["pkg-software"] - 2,
Expand All @@ -254,7 +264,7 @@
% ({"software_len": _patLengths["pkg-software"]})
),
"pkg-priority-key": re.compile(
r"^Priority_[a-zA-Z0-9+.-][a-zA-Z0-9+._-]{0,%(software_len1)d}[a-zA-Z0-9+.-](/[a-z0-9+.-]{1,%(software_len2)d})?$"
r"^Priority_[a-zA-Z0-9+.-][a-zA-Z0-9+._-]{0,%(software_len1)d}[a-zA-Z0-9+.-](/[a-z0-9+._-]{1,%(software_len2)d})?$"
% (
{
"software_len1": _patLengths["pkg-software"] - 2,
Expand Down
5 changes: 2 additions & 3 deletions cvelib/pkg.py
Original file line number Diff line number Diff line change
Expand Up @@ -124,9 +124,9 @@ def setModifier(self, modifier: str) -> None:
if len(modifier) > _patLengths["pkg-modifier"]:
raise CveException("invalid modifier '%s'" % modifier)
if self.compatUbuntu:
if not rePatterns["pkg-software-ubuntu"].search(modifier):
if not rePatterns["pkg-modifier-ubuntu"].search(modifier):
raise CveException("invalid compat modifier '%s'" % modifier)
elif not rePatterns["pkg-software"].search(modifier):
elif not rePatterns["pkg-modifier"].search(modifier):
raise CveException("invalid modifier '%s'" % modifier)
self.modifier = modifier

Expand Down Expand Up @@ -226,7 +226,6 @@ def parse(s: str, compatUbuntu: bool = False) -> CvePkg:
else:
product = product_where

# compatUbuntu allows foo_bar/baz, otherwise allow foo/bar/baz
if "/" in software_mod:
software, modifier = software_mod.split("/")
else:
Expand Down
8 changes: 4 additions & 4 deletions extras/vim/syntax/cve.vim
Original file line number Diff line number Diff line change
Expand Up @@ -57,19 +57,19 @@ syn match cveScanReportsValue contained /^ \(- type: oci\| \(component\|detecte
syn match cveKey "^\%(Candidate\|OpenDate\|PublicDate\|CRD\|References\|Description\|GitHub-Advanced-Security\|Scan-Reports\|Notes\|Mitigation\|CVSS\|Bugs\|Discovered-by\|Assigned-to\): *"

" CloseDate[_<software>[/<modifier>]]: <date>
syn match cveCloseDateKey "^CloseDate\(_[a-zA-Z0-9][a-zA-Z0-9+._-]\+\(/[a-z0-9+.-]\+\)\?\)\?: *"
syn match cveCloseDateKey "^CloseDate\(_[a-zA-Z0-9][a-zA-Z0-9+._-]\+\(/[a-z0-9+._-]\+\)\?\)\?: *"

" Priority[_<software>[/<modifier>]]: <priority>
syn match cvePriorityKey "^Priority\(_[a-zA-Z0-9][a-zA-Z0-9+._-]\+\(/[a-z0-9+.-]\+\)\?\)\?: *"
syn match cvePriorityKey "^Priority\(_[a-zA-Z0-9][a-zA-Z0-9+._-]\+\(/[a-z0-9+._-]\+\)\?\)\?: *"

" Patches_<software>:
syn match cvePatchesKey "^Patches_[a-zA-Z0-9][a-zA-Z0-9+._-]\+: *"

" Tags_<software>[/<modifier>]: <tag>
syn match cveTagKey "^Tags_[a-zA-Z0-9][a-zA-Z0-9+._-]\+\(/[a-z0-9+.-]\+\)\?: *"
syn match cveTagKey "^Tags_[a-zA-Z0-9][a-zA-Z0-9+._-]\+\(/[a-z0-9+._-]\+\)\?: *"

" <product>[/<where>]_<software>[/<modifier>]:
syn match cveProductKey "^\%(upstream\|bzr\|cvs\|git\|hg\|svn\|appimage\|archive\|deb\|dmg\|exe\|flatpak\|oci\|rpm\|shell\|snap\|alpine\|android\|centos\|debian\|distroless\|flatcar\|ios\|opensuse\|osx\|rhel\|suse\|ubuntu\|windows\)\(/[a-z0-9+.-]\+\)\?_[a-zA-Z0-9][a-zA-Z0-9+._-]\+\(/[a-z0-9+.-]\+\)\?: *"
syn match cveProductKey "^\%(upstream\|bzr\|cvs\|git\|hg\|svn\|appimage\|archive\|deb\|dmg\|exe\|flatpak\|oci\|rpm\|shell\|snap\|alpine\|android\|centos\|debian\|distroless\|flatcar\|ios\|opensuse\|osx\|rhel\|suse\|ubuntu\|windows\)\(/[a-z0-9+.-]\+\)\?_[a-zA-Z0-9][a-zA-Z0-9+._-]\+\(/[a-z0-9+._-]\+\)\?: *"


"
Expand Down
39 changes: 35 additions & 4 deletions tests/test_cve.py
Original file line number Diff line number Diff line change
Expand Up @@ -837,18 +837,30 @@ def test_setData(self):
hdrs = self._mockHeaders(t)
cvelib.cve.CVE().setData(hdrs)

# valid Tags_foo_bar ('_' in name)
# valid Tags_foo/bar ('_' in modifier)
t = self._cve_template()
t["Tags_foo/bar"] = "apparmor"
hdrs = self._mockHeaders(t)
cvelib.cve.CVE().setData(hdrs)

# valid Tags_foo_bar ('_' in software)
t = self._cve_template()
t["Tags_foo_bar"] = "apparmor pie"
hdrs = self._mockHeaders(t)
cvelib.cve.CVE().setData(hdrs)

# valid Tags_foo_bar/baz ('_' in name)
# valid Tags_foo_bar/baz ('_' in software)
t = self._cve_template()
t["Tags_foo_bar/baz"] = "apparmor pie"
hdrs = self._mockHeaders(t)
cvelib.cve.CVE().setData(hdrs)

# valid Tags_foo_bar/baz ('_' in software and modifier)
t = self._cve_template()
t["Tags_foo_bar/baz_norf"] = "apparmor pie"
hdrs = self._mockHeaders(t)
cvelib.cve.CVE().setData(hdrs)

# valid Priority_foo
t = self._cve_template()
t["Priority_foo"] = "medium"
Expand All @@ -867,18 +879,30 @@ def test_setData(self):
hdrs = self._mockHeaders(t)
cvelib.cve.CVE().setData(hdrs)

# valid Priority_foo_bar ('_' in name)
# valid Priority_foo/bar_baz ('_' in modifier)
t = self._cve_template()
t["Priority_foo/bar_baz"] = "medium"
hdrs = self._mockHeaders(t)
cvelib.cve.CVE().setData(hdrs)

# valid Priority_foo_bar ('_' in software)
t = self._cve_template()
t["Priority_foo_bar"] = "medium"
hdrs = self._mockHeaders(t)
cvelib.cve.CVE().setData(hdrs)

# valid Priority_foo_bar/baz ('_' in name)
# valid Priority_foo_bar/baz ('_' in software)
t = self._cve_template()
t["Priority_foo_bar/baz"] = "medium"
hdrs = self._mockHeaders(t)
cvelib.cve.CVE().setData(hdrs)

# valid Priority_foo_bar/baz ('_' in software and modifier)
t = self._cve_template()
t["Priority_foo_bar/baz_norf"] = "medium"
hdrs = self._mockHeaders(t)
cvelib.cve.CVE().setData(hdrs)

# invalid
hdrs = self._mockHeaders(self._cve_template())
del hdrs["Candidate"]
Expand Down Expand Up @@ -997,7 +1021,13 @@ def test_setDataPriorityKeys(self):
("Priority_foo", False, True),
("Priority_%s" % ("a" * 50), False, True),
("Priority_foo_bar", False, True), # non-compat allows '_' in software
("Priority_foo/bar_baz", False, True), # non-compat allows '_' in modifier
("Priority_foo_bar/baz", False, True),
(
"Priority_foo_bar/baz_norf",
False,
True,
), # non-compat allows '_' in modifier
("Priority_%s/foo" % ("a" * 50), False, True),
("Priority_foo/%s" % ("a" * 50), False, True),
("Priority_FOO", False, True),
Expand All @@ -1023,6 +1053,7 @@ def test_setDataPriorityKeys(self):
("Priority_foo_%s" % ("a" * 51), True, False),
("Priority_foo/bar", True, False),
("Priority_foo_bar_baz", True, False),
("Priority_foo_precise/esm_bad", True, False),
("Priority_FOO", True, False),
]
for key, compat, valid in tsts:
Expand Down
11 changes: 11 additions & 0 deletions tests/test_pkg.py
Original file line number Diff line number Diff line change
Expand Up @@ -256,13 +256,22 @@ def test_setModifier(self):
tsts = [
# valid
("foo", True, False),
("foo1", True, False),
("foo-bar", True, False),
("foo.bar", True, False),
("for-bar-1.0", True, False),
("foo_bar", True, False),
("a" * 40, True, False),
# valid compat
("foo", True, True),
("foo1", True, True),
("foo-bar", True, True),
("foo.bar", True, True),
("for-bar-1.0", True, True),
("a" * 40, True, True),
# invalid
("b@d", False, False),
("FOO", False, False),
("foo ", False, False),
(" foo ", False, False),
("a" * 41, False, False),
Expand Down Expand Up @@ -621,6 +630,7 @@ def test_parse(self):
("alpine/3.16_foo: needed (123-4)", False, True),
("debian/buster_foo: needed (123-4)", False, True),
("debian/buster_foo/bar: needed (123-4)", False, True),
("debian/buster_foo/bar_baz: needed (123-4)", False, True),
("ubuntu/focal_foo: needed", False, True),
(
"ubuntu/trusty_gcc-snapshot: DNE (trusty was not-affected 20140405-0ubuntu1)",
Expand Down Expand Up @@ -738,6 +748,7 @@ def test_parse(self):
("focal_foo/%s: needed" % ("a" * 40), False, False),
("focal_foo: needed (%s)" % ("a" * 101), True, False),
("upstream_foo_bar: needed (123-4)", True, False),
("upstream_foo/bar_baz: needed (123-4)", True, False),
("upstream_FOO: needed", True, False),
("upstream_foo-BAR: needed", True, False),
("upstream/foo: needed", True, False),
Expand Down

0 comments on commit b296862

Please sign in to comment.