From f5dae04dd750ee9e3519eae26212541762c49931 Mon Sep 17 00:00:00 2001 From: Andrew Lilley Brinker Date: Thu, 13 Mar 2025 11:29:36 -0700 Subject: [PATCH 1/2] feat: Make "cpeApplicability" structure generic. This "renames" (not actually a rename, see below) the existing "cpeApplicability" structure and its children from CPE-specific names to generic names. For example, "cpeApplicability" becomes "applicability." This is intended to permit future record format updates to add support for additional kinds of software identifiers. This change itself does not add any new kinds of software identifiers. The prior "cpeApplicability" structure remains entirely supported, though CNAs and any future ADPs enriching with software ID information should be encouraged to use the more expressive new "applicability" structure instead, and use of both at the same time should be treated as an error to avoid ambiguity. Signed-off-by: Andrew Lilley Brinker --- schema/CVE_Record_Format.json | 94 ++++++++++++++++++++++++++++++++--- 1 file changed, 86 insertions(+), 8 deletions(-) diff --git a/schema/CVE_Record_Format.json b/schema/CVE_Record_Format.json index fde05ad596..9b0e964d05 100644 --- a/schema/CVE_Record_Format.json +++ b/schema/CVE_Record_Format.json @@ -212,7 +212,7 @@ }, "cpes": { "type": "array", - "description": "Affected products defined by CPE. This is an array of CPE values (vulnerable and not), we use an array so that we can make multiple statements about the same version and they are separate (if we used a JSON object we'd essentially be keying on the CPE name and they would have to overlap). Also, this allows things like cveDataVersion or cveDescription to be applied directly to the product entry. This also allows more complex statements such as \"Product X between versions 10.2 and 10.8\" to be put in a machine-readable format. As well since multiple statements can be used multiple branches of the same product can be defined here. NOTE: Consider using the newer cpeApplicability block for defining CPE data using the CPE Applicability Language which includes more options for defining CPE Names.", + "description": "Affected products defined by CPE. This is an array of CPE values (vulnerable and not), we use an array so that we can make multiple statements about the same version and they are separate (if we used a JSON object we'd essentially be keying on the CPE name and they would have to overlap). Also, this allows things like cveDataVersion or cveDescription to be applied directly to the product entry. This also allows more complex statements such as \"Product X between versions 10.2 and 10.8\" to be put in a machine-readable format. As well since multiple statements can be used multiple branches of the same product can be defined here. NOTE: Consider using the newer applicability block for defining CPE data using the CPE Applicability Language which includes more options for defining CPE Names.", "uniqueItems": true, "items": { "title": "CPE Name", @@ -500,6 +500,56 @@ "required": ["orgId"], "additionalProperties": false }, + "applicability": { + "type": "array", + "items": { + "$ref": "#/definitions/applicabilityElement" + } + }, + "applicabilityElement": { + "description": "Affected products defined using one or more software identifiers and applicability parameters. An operator property allows AND or OR logic between identifiers or combinations thereof. The negate and vulnerable Boolean properties allow applicability combinations to be inverted and/or defined as vulnerable or not. Multiple version fields are provided for capturing ranges of products when defining a Match String Range. NOTE: When defining an applicability block, it is recommended that it align with (as much as possible) the product data provided within the affected block.", + "properties": { + "operator": { + "type": "string", + "enum": ["AND", "OR"] + }, + "negate": { + "type": "boolean" + }, + "nodes": { + "type": "array", + "items": { + "$ref": "#/definitions/node" + } + } + } + }, + "node": { + "description": "Defines a configuration node in an applicability statement.", + "properties": { + "operator": { + "type": "string", + "enum": ["AND", "OR"] + }, + "negate": { + "type": "boolean" + }, + "cpeMatch": { + "type": "array", + "items": { + "$ref": "#/definitions/cpe_match" + } + } + }, + "allOf": [ + { "required": ["operator"] }, + { + "anyOf": [ + { "required": ["cpeMatch"] } + ] + } + ] + }, "cpeApplicabilityElement": { "description": "Affected products defined using an implementation of the CPE Applicability Language, mostly copied/forked from the NIST NVD CVE API v2.0 schema (optional). An operator property allows AND or OR logic between CPEs or combinations of CPEs. The negate and vulnerable Boolean properties allow CPEs to be inverted and/or defined as vulnerable or not. Multiple version fields are provided for capturing ranges of products when defining a CPE Match String Range. NOTE: When defining a cpeApplicability block, it is recommended that it align with (as much as possible) the product data provided within the affected block.", "properties": { @@ -608,6 +658,12 @@ "affected": { "$ref": "#/definitions/affected" }, + "applicability": { + "type": "array", + "items": { + "$ref": "#/definitions/applicabilityElement" + } + }, "cpeApplicability": { "type": "array", "items": { @@ -654,11 +710,20 @@ "$ref": "#/definitions/taxonomyMappings" } }, - "required": [ - "providerMetadata", - "descriptions", - "affected", - "references" + "allOf": [ + { + "required": [ + "providerMetadata", + "descriptions", + "affected", + "references" + ] + }, + { + "not": { + "required": ["applicability", "cpeApplicability"] + } + } ], "patternProperties": { "^x_[^.]*$": {} @@ -720,6 +785,12 @@ "affected": { "$ref": "#/definitions/affected" }, + "applicability": { + "type": "array", + "items": { + "$ref": "#/definitions/applicabilityElement" + } + }, "cpeApplicability": { "type": "array", "items": { @@ -766,8 +837,15 @@ "$ref": "#/definitions/taxonomyMappings" } }, - "required": [ - "providerMetadata" + "allOf": [ + { + "required": ["providerMetadata"] + }, + { + "not": { + "required": ["applicability", "cpeApplicability"] + } + } ], "minProperties": 2, "patternProperties": { From 8989c0cf2bb04bc2e6e488c5b11878411e3e62f6 Mon Sep 17 00:00:00 2001 From: Andrew Lilley Brinker Date: Tue, 1 Apr 2025 14:59:52 -0700 Subject: [PATCH 2/2] feat: Add support for Package URLs. Signed-off-by: Andrew Lilley Brinker --- schema/CVE_Record_Format.json | 39 ++++++++++++++++++++++++++++++++++- 1 file changed, 38 insertions(+), 1 deletion(-) diff --git a/schema/CVE_Record_Format.json b/schema/CVE_Record_Format.json index 9b0e964d05..4e682a1b6e 100644 --- a/schema/CVE_Record_Format.json +++ b/schema/CVE_Record_Format.json @@ -539,17 +539,54 @@ "items": { "$ref": "#/definitions/cpe_match" } + }, + "purlMatch": { + "type": "array", + "items": { + "$ref": "#/definitions/purl_match" + } } }, "allOf": [ { "required": ["operator"] }, { "anyOf": [ - { "required": ["cpeMatch"] } + { "required": ["cpeMatch"] }, + { "required": ["purlMatch"] } ] } ] }, + "purl_match": { + "description": "purl match string or range", + "type": "object", + "properties": { + "vulnerable": { + "type": "boolean" + }, + "criteria": { + "description": "Placeholder until we find a formal purl schema", + "$ref": "#/definitions/uriType" + }, + "matchCriteriaId": { + "$ref": "#/definitions/uuidType" + }, + "versionStartExcluding": { + "$ref": "#/definitions/version" + }, + "versionStartIncluding": { + "$ref": "#/definitions/version" + }, + "versionEndExcluding": { + "$ref": "#/definitions/version" + }, + "versionEndIncluding": { + "$ref": "#/definitions/version" + } + }, + "required": ["vulnerable", "criteria"], + "additionalProperties": false + }, "cpeApplicabilityElement": { "description": "Affected products defined using an implementation of the CPE Applicability Language, mostly copied/forked from the NIST NVD CVE API v2.0 schema (optional). An operator property allows AND or OR logic between CPEs or combinations of CPEs. The negate and vulnerable Boolean properties allow CPEs to be inverted and/or defined as vulnerable or not. Multiple version fields are provided for capturing ranges of products when defining a CPE Match String Range. NOTE: When defining a cpeApplicability block, it is recommended that it align with (as much as possible) the product data provided within the affected block.", "properties": {