Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allow for individual lints to opt-out of the ZLint framework executing pre-flight applicability rules #842

Open
wants to merge 7 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 3 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
32 changes: 27 additions & 5 deletions v3/lint/base.go
Original file line number Diff line number Diff line change
Expand Up @@ -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.
Expand Down Expand Up @@ -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) && util.HasEmailSAN(cert)) || util.IsSMIMEBRCertificate(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) && util.HasEmailSAN(cert)) || util.IsSMIMEBRCertificate(cert)) {
return &LintResult{Status: NA}
}
}
lint := l.Lint()
err := config.MaybeConfigure(lint, l.Name)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -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,
})
Expand All @@ -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 {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -74,11 +74,11 @@ func TestOCSPIDPKIXOCSPNocheckExtNotIncludedServerAuth(t *testing.T) {
}, {
Name: "o1s0ep0a0nc0",
Filename: "o1s0ep0a0nc0.pem",
ExpectedResult: lint.NA,
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These are tests certs that do not have server auth, so they now apply.

ExpectedResult: lint.Error,
}, {
Name: "o1s0ep0a0nc1",
Filename: "o1s0ep0a0nc1.pem",
ExpectedResult: lint.NA,
ExpectedResult: lint.Pass,
}, {
Name: "o1s0ep0a1nc0",
Filename: "o1s0ep0a1nc0.pem",
Expand Down Expand Up @@ -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",
Expand Down
Loading