feat(scan): support dnf modules (#1114)

* feat(scan): support dnf modules

* change dnf module list --installed to --enabled

* chore: refactor

* feat(report): detect logic for dnf modularity label

* fix func name

* chore: update go mods
This commit is contained in:
Kota Kanbe
2021-01-06 11:36:41 +09:00
committed by GitHub
parent 8405e0fad6
commit b13f93a2d3
10 changed files with 219 additions and 34 deletions

View File

@@ -78,6 +78,7 @@ type request struct {
arch string
binaryPackNames []string
isSrcPack bool
modularityLabel string // RHEL 8 or later only
}
type response struct {
@@ -147,7 +148,7 @@ func getDefsByPackNameViaHTTP(r *models.ScanResult) (
select {
case res := <-resChan:
for _, def := range res.defs {
affected, notFixedYet, fixedIn := isOvalDefAffected(def, res.request, r.Family, r.RunningKernel)
affected, notFixedYet, fixedIn := isOvalDefAffected(def, res.request, r.Family, r.RunningKernel, r.EnabledDnfModules)
if !affected {
continue
}
@@ -250,7 +251,7 @@ func getDefsByPackNameFromOvalDB(driver db.DB, r *models.ScanResult) (relatedDef
return relatedDefs, xerrors.Errorf("Failed to get %s OVAL info by package: %#v, err: %w", r.Family, req, err)
}
for _, def := range definitions {
affected, notFixedYet, fixedIn := isOvalDefAffected(def, req, r.Family, r.RunningKernel)
affected, notFixedYet, fixedIn := isOvalDefAffected(def, req, r.Family, r.RunningKernel, r.EnabledDnfModules)
if !affected {
continue
}
@@ -291,12 +292,27 @@ func major(version string) string {
return ver[0:strings.Index(ver, ".")]
}
func isOvalDefAffected(def ovalmodels.Definition, req request, family string, running models.Kernel) (affected, notFixedYet bool, fixedIn string) {
func isOvalDefAffected(def ovalmodels.Definition, req request, family string, running models.Kernel, enabledMods []string) (affected, notFixedYet bool, fixedIn string) {
for _, ovalPack := range def.AffectedPacks {
if req.packName != ovalPack.Name {
continue
}
isModularityLabelEmptyOrSame := false
if ovalPack.ModularityLabel != "" {
for _, mod := range enabledMods {
if mod == ovalPack.ModularityLabel {
isModularityLabelEmptyOrSame = true
break
}
}
} else {
isModularityLabelEmptyOrSame = true
}
if !isModularityLabelEmptyOrSame {
continue
}
if running.Release != "" {
switch family {
case config.RedHat, config.CentOS:

View File

@@ -202,6 +202,7 @@ func TestIsOvalDefAffected(t *testing.T) {
req request
family string
kernel models.Kernel
mods []string
}
var tests = []struct {
in in
@@ -1076,9 +1077,85 @@ func TestIsOvalDefAffected(t *testing.T) {
notFixedYet: false,
fixedIn: "3.1.0",
},
// dnf module
{
in: in{
family: config.RedHat,
def: ovalmodels.Definition{
AffectedPacks: []ovalmodels.Package{
{
Name: "nginx",
Version: "1.16.1-1.module+el8.3.0+8844+e5e7039f.1",
NotFixedYet: false,
ModularityLabel: "nginx:1.16",
},
},
},
req: request{
packName: "nginx",
versionRelease: "1.16.0-1.module+el8.3.0+8844+e5e7039f.1",
},
mods: []string{
"nginx:1.16",
},
},
affected: true,
notFixedYet: false,
fixedIn: "1.16.1-1.module+el8.3.0+8844+e5e7039f.1",
},
// dnf module 2
{
in: in{
family: config.RedHat,
def: ovalmodels.Definition{
AffectedPacks: []ovalmodels.Package{
{
Name: "nginx",
Version: "1.16.1-1.module+el8.3.0+8844+e5e7039f.1",
NotFixedYet: false,
ModularityLabel: "nginx:1.16",
},
},
},
req: request{
packName: "nginx",
versionRelease: "1.16.2-1.module+el8.3.0+8844+e5e7039f.1",
},
mods: []string{
"nginx:1.16",
},
},
affected: false,
notFixedYet: false,
},
// dnf module 3
{
in: in{
family: config.RedHat,
def: ovalmodels.Definition{
AffectedPacks: []ovalmodels.Package{
{
Name: "nginx",
Version: "1.16.1-1.module+el8.3.0+8844+e5e7039f.1",
NotFixedYet: false,
ModularityLabel: "nginx:1.16",
},
},
},
req: request{
packName: "nginx",
versionRelease: "1.16.0-1.module+el8.3.0+8844+e5e7039f.1",
},
mods: []string{
"nginx:1.14",
},
},
affected: false,
notFixedYet: false,
},
}
for i, tt := range tests {
affected, notFixedYet, fixedIn := isOvalDefAffected(tt.in.def, tt.in.req, tt.in.family, tt.in.kernel)
affected, notFixedYet, fixedIn := isOvalDefAffected(tt.in.def, tt.in.req, tt.in.family, tt.in.kernel, tt.in.mods)
if tt.affected != affected {
t.Errorf("[%d] affected\nexpected: %v\n actual: %v\n", i, tt.affected, affected)
}