mirror of
https://github.com/anchore/syft.git
synced 2026-10-30 14:02:26 +01:00
Add Linux Kernel cataloger (#1694)
* add kernel handler Signed-off-by: Avi Deitcher <avi@deitcher.net> * [wip] combine kernel and kernel module cataloging Signed-off-by: Alex Goodman <alex.goodman@anchore.com> * [wip] combine kernel and kernel module cataloging Signed-off-by: Alex Goodman <alex.goodman@anchore.com> Signed-off-by: Avi Deitcher <avi@deitcher.net> * rename Kernel package to LinuxKernel package Signed-off-by: Alex Goodman <alex.goodman@anchore.com> * split kernel and module packages within cataloger Signed-off-by: Alex Goodman <alex.goodman@anchore.com> * wire up application configuration with kernel cataloger options Signed-off-by: Alex Goodman <alex.goodman@anchore.com> * dont use references for packages on relationships Signed-off-by: Alex Goodman <alex.goodman@anchore.com> * fix linting and tests Signed-off-by: Alex Goodman <alex.goodman@anchore.com> * kernel cataloger should be resistent to partial failure Signed-off-by: Alex Goodman <alex.goodman@anchore.com> * log upon kernel module metadata missing Signed-off-by: Alex Goodman <alex.goodman@anchore.com> * add tests for linux kernel cataloger Signed-off-by: Alex Goodman <alex.goodman@anchore.com> * update integration tests Signed-off-by: Alex Goodman <alex.goodman@anchore.com> * update cli package test counts Signed-off-by: Alex Goodman <alex.goodman@anchore.com> * add evidence annotations for kernel packages Signed-off-by: Alex Goodman <alex.goodman@anchore.com> * reduce noise in cli test output Signed-off-by: Alex Goodman <alex.goodman@anchore.com> * missed cli test to reduce noise for Signed-off-by: Alex Goodman <alex.goodman@anchore.com> * fix package counts Signed-off-by: Alex Goodman <alex.goodman@anchore.com> * update docs with linux kernel cataloging refs Signed-off-by: Alex Goodman <alex.goodman@anchore.com> * bump json schema with new metadata fields Signed-off-by: Alex Goodman <alex.goodman@anchore.com> --------- Signed-off-by: Avi Deitcher <avi@deitcher.net> Signed-off-by: Alex Goodman <alex.goodman@anchore.com> Signed-off-by: <> Co-authored-by: Alex Goodman <alex.goodman@anchore.com>
This commit is contained in:
co-authored by
Alex Goodman
parent
5d156b8241
commit
cc731c7b19
@@ -55,11 +55,7 @@ func TestAllFormatsConvertable(t *testing.T) {
|
||||
for _, traitFn := range assertions {
|
||||
traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode())
|
||||
}
|
||||
if t.Failed() {
|
||||
t.Log("STDOUT:\n", stdout)
|
||||
t.Log("STDERR:\n", stderr)
|
||||
t.Log("COMMAND:", strings.Join(cmd.Args, " "))
|
||||
}
|
||||
logOutputOnFailure(t, cmd, stdout, stderr)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2,7 +2,6 @@ package cli
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"strings"
|
||||
"testing"
|
||||
|
||||
"github.com/stretchr/testify/require"
|
||||
@@ -34,11 +33,7 @@ func TestAllFormatsExpressible(t *testing.T) {
|
||||
for _, traitFn := range commonAssertions {
|
||||
traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode())
|
||||
}
|
||||
if t.Failed() {
|
||||
t.Log("STDOUT:\n", stdout)
|
||||
t.Log("STDERR:\n", stderr)
|
||||
t.Log("COMMAND:", strings.Join(cmd.Args, " "))
|
||||
}
|
||||
logOutputOnFailure(t, cmd, stdout, stderr)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
@@ -40,11 +40,7 @@ func TestConvertCmd(t *testing.T) {
|
||||
for _, traitFn := range assertions {
|
||||
traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode())
|
||||
}
|
||||
if t.Failed() {
|
||||
t.Log("STDOUT:\n", stdout)
|
||||
t.Log("STDERR:\n", stderr)
|
||||
t.Log("COMMAND:", strings.Join(cmd.Args, " "))
|
||||
}
|
||||
logOutputOnFailure(t, cmd, stdout, stderr)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
@@ -52,11 +52,7 @@ func TestValidCycloneDX(t *testing.T) {
|
||||
for _, traitFn := range test.assertions {
|
||||
traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode())
|
||||
}
|
||||
if t.Failed() {
|
||||
t.Log("STDOUT:\n", stdout)
|
||||
t.Log("STDERR:\n", stderr)
|
||||
t.Log("COMMAND:", strings.Join(cmd.Args, " "))
|
||||
}
|
||||
logOutputOnFailure(t, cmd, stdout, stderr)
|
||||
|
||||
validateCycloneDXJSON(t, stdout)
|
||||
})
|
||||
@@ -95,11 +91,7 @@ func assertValidCycloneDX(tb testing.TB, stdout, stderr string, rc int) {
|
||||
tb.Errorf("expected no validation failures for cyclonedx-cli but got rc=%d", rc)
|
||||
}
|
||||
|
||||
if tb.Failed() {
|
||||
tb.Log("STDOUT:\n", stdout)
|
||||
tb.Log("STDERR:\n", stderr)
|
||||
tb.Log("COMMAND:", strings.Join(cmd.Args, " "))
|
||||
}
|
||||
logOutputOnFailure(tb, cmd, stdout, stderr)
|
||||
}
|
||||
|
||||
// validate --input-format json --input-version v1_4 --input-file bom.json
|
||||
@@ -134,9 +126,5 @@ func validateCycloneDXJSON(t *testing.T, stdout string) {
|
||||
t.Errorf("expected no validation failures for cyclonedx-cli but found invalid BOM")
|
||||
}
|
||||
|
||||
if t.Failed() {
|
||||
t.Log("STDOUT:\n", stdout)
|
||||
t.Log("STDERR:\n", stderr)
|
||||
t.Log("COMMAND:", strings.Join(cmd.Args, " "))
|
||||
}
|
||||
logOutputOnFailure(t, cmd, stdout, stderr)
|
||||
}
|
||||
|
||||
@@ -2,7 +2,6 @@ package cli
|
||||
|
||||
import (
|
||||
"os/exec"
|
||||
"strings"
|
||||
"testing"
|
||||
"time"
|
||||
)
|
||||
@@ -37,10 +36,6 @@ func TestDirectoryScanCompletesWithinTimeout(t *testing.T) {
|
||||
traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode())
|
||||
}
|
||||
|
||||
if t.Failed() {
|
||||
t.Log("STDOUT:\n", stdout)
|
||||
t.Log("STDERR:\n", stderr)
|
||||
t.Log("COMMAND:", strings.Join(cmd.Args, " "))
|
||||
}
|
||||
logOutputOnFailure(t, cmd, stdout, stderr)
|
||||
|
||||
}
|
||||
|
||||
@@ -3,7 +3,6 @@ package cli
|
||||
import (
|
||||
"fmt"
|
||||
"path/filepath"
|
||||
"strings"
|
||||
"testing"
|
||||
)
|
||||
|
||||
@@ -97,7 +96,7 @@ func TestPackagesCmdFlags(t *testing.T) {
|
||||
name: "squashed-scope-flag",
|
||||
args: []string{"packages", "-o", "json", "-s", "squashed", coverageImage},
|
||||
assertions: []traitAssertion{
|
||||
assertPackageCount(35),
|
||||
assertPackageCount(37),
|
||||
assertSuccessfulReturnCode,
|
||||
},
|
||||
},
|
||||
@@ -214,7 +213,7 @@ func TestPackagesCmdFlags(t *testing.T) {
|
||||
// the application config in the log matches that of what we expect to have been configured.
|
||||
assertInOutput("parallelism: 2"),
|
||||
assertInOutput("parallelism=2"),
|
||||
assertPackageCount(35),
|
||||
assertPackageCount(37),
|
||||
assertSuccessfulReturnCode,
|
||||
},
|
||||
},
|
||||
@@ -225,7 +224,7 @@ func TestPackagesCmdFlags(t *testing.T) {
|
||||
// the application config in the log matches that of what we expect to have been configured.
|
||||
assertInOutput("parallelism: 1"),
|
||||
assertInOutput("parallelism=1"),
|
||||
assertPackageCount(35),
|
||||
assertPackageCount(37),
|
||||
assertSuccessfulReturnCode,
|
||||
},
|
||||
},
|
||||
@@ -239,7 +238,7 @@ func TestPackagesCmdFlags(t *testing.T) {
|
||||
assertions: []traitAssertion{
|
||||
assertNotInOutput("secret_password"),
|
||||
assertNotInOutput("secret_key_path"),
|
||||
assertPackageCount(35),
|
||||
assertPackageCount(37),
|
||||
assertSuccessfulReturnCode,
|
||||
},
|
||||
},
|
||||
@@ -251,11 +250,7 @@ func TestPackagesCmdFlags(t *testing.T) {
|
||||
for _, traitFn := range test.assertions {
|
||||
traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode())
|
||||
}
|
||||
if t.Failed() {
|
||||
t.Log("STDOUT:\n", stdout)
|
||||
t.Log("STDERR:\n", stderr)
|
||||
t.Log("COMMAND:", strings.Join(cmd.Args, " "))
|
||||
}
|
||||
logOutputOnFailure(t, cmd, stdout, stderr)
|
||||
})
|
||||
}
|
||||
}
|
||||
@@ -337,11 +332,7 @@ func TestRegistryAuth(t *testing.T) {
|
||||
for _, traitAssertionFn := range test.assertions {
|
||||
traitAssertionFn(t, stdout, stderr, cmd.ProcessState.ExitCode())
|
||||
}
|
||||
if t.Failed() {
|
||||
t.Log("STDOUT:\n", stdout)
|
||||
t.Log("STDERR:\n", stderr)
|
||||
t.Log("COMMAND:", strings.Join(cmd.Args, " "))
|
||||
}
|
||||
logOutputOnFailure(t, cmd, stdout, stderr)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
package cli
|
||||
|
||||
import (
|
||||
"strings"
|
||||
"testing"
|
||||
)
|
||||
|
||||
@@ -96,11 +95,7 @@ func TestPowerUserCmdFlags(t *testing.T) {
|
||||
for _, traitFn := range test.assertions {
|
||||
traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode())
|
||||
}
|
||||
if t.Failed() {
|
||||
t.Log("STDOUT:\n", stdout)
|
||||
t.Log("STDERR:\n", stderr)
|
||||
t.Log("COMMAND:", strings.Join(cmd.Args, " "))
|
||||
}
|
||||
logOutputOnFailure(t, cmd, stdout, stderr)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3,7 +3,6 @@ package cli
|
||||
import (
|
||||
"os"
|
||||
"path/filepath"
|
||||
"strings"
|
||||
"testing"
|
||||
|
||||
"github.com/sergi/go-diff/diffmatchpatch"
|
||||
@@ -109,11 +108,7 @@ func TestPersistentFlags(t *testing.T) {
|
||||
for _, traitFn := range test.assertions {
|
||||
traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode())
|
||||
}
|
||||
if t.Failed() {
|
||||
t.Log("STDOUT:\n", stdout)
|
||||
t.Log("STDERR:\n", stderr)
|
||||
t.Log("COMMAND:", strings.Join(cmd.Args, " "))
|
||||
}
|
||||
logOutputOnFailure(t, cmd, stdout, stderr)
|
||||
})
|
||||
}
|
||||
}
|
||||
@@ -151,11 +146,7 @@ func TestLogFile(t *testing.T) {
|
||||
for _, traitFn := range test.assertions {
|
||||
traitFn(t, stdout, stderr, cmd.ProcessState.ExitCode())
|
||||
}
|
||||
if t.Failed() {
|
||||
t.Log("STDOUT:\n", stdout)
|
||||
t.Log("STDERR:\n", stderr)
|
||||
t.Log("COMMAND:", strings.Join(cmd.Args, " "))
|
||||
}
|
||||
logOutputOnFailure(t, cmd, stdout, stderr)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3,6 +3,7 @@ package cli
|
||||
import (
|
||||
"bufio"
|
||||
"bytes"
|
||||
"flag"
|
||||
"fmt"
|
||||
"io"
|
||||
"math"
|
||||
@@ -21,6 +22,16 @@ import (
|
||||
"github.com/anchore/stereoscope/pkg/imagetest"
|
||||
)
|
||||
|
||||
var showOutput = flag.Bool("show-output", false, "show stdout and stderr for failing tests")
|
||||
|
||||
func logOutputOnFailure(t testing.TB, cmd *exec.Cmd, stdout, stderr string) {
|
||||
if t.Failed() && showOutput != nil && *showOutput {
|
||||
t.Log("STDOUT:\n", stdout)
|
||||
t.Log("STDERR:\n", stderr)
|
||||
t.Log("COMMAND:", strings.Join(cmd.Args, " "))
|
||||
}
|
||||
}
|
||||
|
||||
func runAndShow(t *testing.T, cmd *exec.Cmd) {
|
||||
t.Helper()
|
||||
|
||||
|
||||
@@ -11,6 +11,20 @@ type testCase struct {
|
||||
}
|
||||
|
||||
var imageOnlyTestCases = []testCase{
|
||||
{
|
||||
name: "find kernel packages",
|
||||
pkgType: pkg.LinuxKernelPkg,
|
||||
pkgInfo: map[string]string{
|
||||
"linux-kernel": "6.2.9-200.fc37.x86_64",
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "find kernel module packages",
|
||||
pkgType: pkg.LinuxKernelModulePkg,
|
||||
pkgInfo: map[string]string{
|
||||
"fsa4480": "",
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "find gemspec packages",
|
||||
pkgType: pkg.GemPkg,
|
||||
|
||||
@@ -221,6 +221,8 @@ func TestPkgCoverageDirectory(t *testing.T) {
|
||||
observedPkgs.Remove(string(pkg.UnknownPkg))
|
||||
definedPkgs.Remove(string(pkg.BinaryPkg))
|
||||
definedPkgs.Remove(string(pkg.UnknownPkg))
|
||||
definedPkgs.Remove(string(pkg.LinuxKernelPkg))
|
||||
definedPkgs.Remove(string(pkg.LinuxKernelModulePkg))
|
||||
|
||||
// for directory scans we should not expect to see any of the following package types
|
||||
definedPkgs.Remove(string(pkg.KbPkg))
|
||||
|
||||
@@ -1,5 +1,22 @@
|
||||
FROM fedora:37@sha256:3f987b7657e944cf87a129cc262982d4f80e38bd98f7db313ccaf90ca7069dd2
|
||||
|
||||
RUN dnf install 'dnf-command(download)' cpio xz -y
|
||||
RUN dnf download kernel-core kernel-modules-core -y
|
||||
|
||||
RUN rpm2cpio kernel-core-*.rpm | cpio -t && \
|
||||
rpm2cpio kernel-core-*.rpm | cpio -idmv ./lib/modules/6.2.9-200.fc37.x86_64/vmlinuz
|
||||
|
||||
RUN rpm2cpio kernel-modules-core-*.rpm | cpio -t && \
|
||||
rpm2cpio kernel-modules-core-*.rpm | cpio -idmv ./lib/modules/6.2.9-200.fc37.x86_64/kernel/drivers/usb/typec/mux/fsa4480.ko.xz
|
||||
|
||||
RUN unxz /lib/modules/6.2.9-200.fc37.x86_64/kernel/drivers/usb/typec/mux/fsa4480.ko.xz
|
||||
|
||||
FROM scratch
|
||||
|
||||
COPY --from=0 /lib/modules/6.2.9-200.fc37.x86_64/vmlinuz /lib/modules/6.2.9-200.fc37.x86_64/vmlinuz
|
||||
COPY --from=0 /lib/modules/6.2.9-200.fc37.x86_64/kernel/drivers/usb/typec/mux/fsa4480.ko /lib/modules/6.2.9-200.fc37.x86_64/kernel/drivers/usb/typec/mux/fsa4480.ko
|
||||
|
||||
COPY pkgs/ .
|
||||
# we duplicate to show a package count difference between all-layers and squashed scopes
|
||||
COPY lib lib
|
||||
COPY etc/ .
|
||||
COPY etc/ .
|
||||
|
||||
Reference in New Issue
Block a user