diff --git a/v3/integration/config.json b/v3/integration/config.json index 52343e4ff..bf3e970af 100644 --- a/v3/integration/config.json +++ b/v3/integration/config.json @@ -576,7 +576,7 @@ "ErrCount": 370 }, "e_ocsp_id_pkix_ocsp_nocheck_ext_not_included_server_auth": { - "ErrCount": 95 + "ErrCount": 262 }, "e_old_root_ca_rsa_mod_less_than_2048_bits": { "ErrCount": 1 diff --git a/v3/lint/base.go b/v3/lint/base.go index c07d65a92..c219cc7cb 100644 --- a/v3/lint/base.go +++ b/v3/lint/base.go @@ -89,6 +89,26 @@ type LintMetadata struct { // true but with NotBefore >= IneffectiveDate. This check is bypassed if // IneffectiveDate is zero. Please see CheckEffective for more information. IneffectiveDate time.Time `json:"-"` + + // The ZLint linting framework performs a kind of pre-flight "CheckApplies" + // for every lint that gets ran. For example, if that lint in question + // is targeting a CABF baseline requirement, then the framework will + // assert that the certificate in question is a server auth certificate. + // Doing so allows for nearly universal "CheckApplies" logic to be hoisted + // out of each individual lint and into the framework itself. + // + // However, there are rare occasions wherein a lint disagrees with the + // framework's pre-flight "CheckApplies" logic. For example, CABF 4.9.9 + // places a constraint on OCSP signing certificates. However, since an + // OCSP signing certificate is not a server auth certificate, this lint + // never gets ran due to the framework filtering CABF lints to only + // apply to server auth certificates. + // + // If a lint declares OverrideFrameworkFilter to be true, then the framework + // will perform no pre-flight check. This means that the lint in question + // is entirely responsible for accurately encoding all applicability rules + // in its own CheckApplies method. + OverrideFrameworkFilter bool `json:"overrideFrameworkFilter,omitempty"` } // A Lint struct represents a single lint, e.g. @@ -218,11 +238,13 @@ func (l *CertificateLint) CheckEffective(c *x509.Certificate) bool { // CheckEffective() // Execute() func (l *CertificateLint) Execute(cert *x509.Certificate, config Configuration) *LintResult { - if l.Source == CABFBaselineRequirements && !util.IsServerAuthCert(cert) { - return &LintResult{Status: NA} - } - if l.Source == CABFSMIMEBaselineRequirements && !util.IsEmailProtectionCert(cert) { - return &LintResult{Status: NA} + if !l.OverrideFrameworkFilter { + if l.Source == CABFBaselineRequirements && !util.IsServerAuthCert(cert) { + return &LintResult{Status: NA} + } + if l.Source == CABFSMIMEBaselineRequirements && !util.IsEmailProtectionCert(cert) { + return &LintResult{Status: NA} + } } lint := l.Lint() err := config.MaybeConfigure(lint, l.Name) diff --git a/v3/lints/cabf_br/lint_ocsp_id_pkix_ocsp_nocheck_ext_not_included_server_auth.go b/v3/lints/cabf_br/lint_ocsp_id_pkix_ocsp_nocheck_ext_not_included_server_auth.go index ecc0d8cba..4a8091de3 100644 --- a/v3/lints/cabf_br/lint_ocsp_id_pkix_ocsp_nocheck_ext_not_included_server_auth.go +++ b/v3/lints/cabf_br/lint_ocsp_id_pkix_ocsp_nocheck_ext_not_included_server_auth.go @@ -28,9 +28,10 @@ func init() { Name: "e_ocsp_id_pkix_ocsp_nocheck_ext_not_included_server_auth", Description: "OCSP signing Certificate MUST contain an extension of type id-pkixocsp-nocheck, as" + " defined by RFC6960", - Citation: "BRs: 4.9.9", - Source: lint.CABFBaselineRequirements, - EffectiveDate: util.CABEffectiveDate, + Citation: "BRs: 4.9.9", + Source: lint.CABFBaselineRequirements, + EffectiveDate: util.CABEffectiveDate, + OverrideFrameworkFilter: true, }, Lint: NewOCSPIDPKIXOCSPNocheckExtNotIncludedServerAuth, }) @@ -41,7 +42,7 @@ func NewOCSPIDPKIXOCSPNocheckExtNotIncludedServerAuth() lint.LintInterface { } func (l *OCSPIDPKIXOCSPNocheckExtNotIncludedServerAuth) CheckApplies(c *x509.Certificate) bool { - return util.IsDelegatedOCSPResponderCert(c) && util.IsServerAuthCert(c) + return util.IsDelegatedOCSPResponderCert(c) } func (l *OCSPIDPKIXOCSPNocheckExtNotIncludedServerAuth) Execute(c *x509.Certificate) *lint.LintResult { diff --git a/v3/lints/cabf_br/lint_ocsp_id_pkix_ocsp_nocheck_ext_not_included_server_auth_test.go b/v3/lints/cabf_br/lint_ocsp_id_pkix_ocsp_nocheck_ext_not_included_server_auth_test.go index b1a324080..b27c6b16f 100644 --- a/v3/lints/cabf_br/lint_ocsp_id_pkix_ocsp_nocheck_ext_not_included_server_auth_test.go +++ b/v3/lints/cabf_br/lint_ocsp_id_pkix_ocsp_nocheck_ext_not_included_server_auth_test.go @@ -74,11 +74,11 @@ func TestOCSPIDPKIXOCSPNocheckExtNotIncludedServerAuth(t *testing.T) { }, { Name: "o1s0ep0a0nc0", Filename: "o1s0ep0a0nc0.pem", - ExpectedResult: lint.NA, + ExpectedResult: lint.Error, }, { Name: "o1s0ep0a0nc1", Filename: "o1s0ep0a0nc1.pem", - ExpectedResult: lint.NA, + ExpectedResult: lint.Pass, }, { Name: "o1s0ep0a1nc0", Filename: "o1s0ep0a1nc0.pem", @@ -142,11 +142,11 @@ func TestOCSPIDPKIXOCSPNocheckExtNotIncludedServerAuth(t *testing.T) { }, { Name: "o1s0ep1a0nc0", Filename: "o1s0ep1a0nc0.pem", - ExpectedResult: lint.NA, + ExpectedResult: lint.Error, }, { Name: "o1s0ep1a0nc1", Filename: "o1s0ep1a0nc1.pem", - ExpectedResult: lint.NA, + ExpectedResult: lint.Pass, }, { Name: "o1s0ep1a1nc0", Filename: "o1s0ep1a1nc0.pem",