github.com/lineaje-labs/syft@v0.98.1-0.20231227153149-9e393f60ff1b/syft/pkg/cataloger/kernel/parse_linux_kernel_file.go (about) 1 package kernel 2 3 import ( 4 "fmt" 5 "strconv" 6 "strings" 7 8 "github.com/deitch/magic/pkg/magic" 9 10 "github.com/anchore/syft/syft/artifact" 11 "github.com/anchore/syft/syft/file" 12 "github.com/anchore/syft/syft/pkg" 13 "github.com/anchore/syft/syft/pkg/cataloger/generic" 14 "github.com/lineaje-labs/syft/internal/log" 15 "github.com/lineaje-labs/syft/syft/pkg/cataloger/internal/unionreader" 16 ) 17 18 const linuxKernelMagicName = "Linux kernel" 19 20 func parseLinuxKernelFile( 21 _ file.Resolver, _ *generic.Environment, reader file.LocationReadCloser, 22 ) ([]pkg.Package, []artifact.Relationship, error) { 23 unionReader, err := unionreader.GetUnionReader(reader) 24 if err != nil { 25 return nil, nil, fmt.Errorf("unable to get union reader for file: %w", err) 26 } 27 magicType, err := magic.GetType(unionReader) 28 if err != nil { 29 return nil, nil, fmt.Errorf("unable to get magic type for file: %w", err) 30 } 31 if len(magicType) < 1 || magicType[0] != linuxKernelMagicName { 32 return nil, nil, nil 33 } 34 metadata := parseLinuxKernelMetadata(magicType) 35 if metadata.Version == "" { 36 return nil, nil, nil 37 } 38 39 return []pkg.Package{ 40 newLinuxKernelPackage( 41 metadata, 42 reader.Location, 43 ), 44 }, nil, nil 45 } 46 47 func parseLinuxKernelMetadata(magicType []string) (p pkg.LinuxKernel) { 48 // Linux kernel x86 boot executable bzImage, 49 // version 5.10.121-linuxkit (root@buildkitsandbox) #1 SMP Fri Dec 2 10:35:42 UTC 2022, 50 // RO-rootFS, 51 // swap_dev 0XA, 52 // Normal VGA 53 for _, t := range magicType { 54 switch { 55 case strings.HasPrefix(t, "x86 "): 56 p.Architecture = "x86" 57 case strings.Contains(t, "ARM64 "): 58 p.Architecture = "arm64" 59 case strings.Contains(t, "ARM "): 60 p.Architecture = "arm" 61 case t == "bzImage": 62 p.Format = "bzImage" 63 case t == "zImage": 64 p.Format = "zImage" 65 case strings.HasPrefix(t, "version "): 66 p.ExtendedVersion = strings.TrimPrefix(t, "version ") 67 fields := strings.Fields(p.ExtendedVersion) 68 if len(fields) > 0 { 69 p.Version = fields[0] 70 } 71 case strings.Contains(t, "rootFS") && strings.HasPrefix(t, "RW-"): 72 p.RWRootFS = true 73 case strings.HasPrefix(t, "swap_dev "): 74 swapDevStr := strings.TrimPrefix(t, "swap_dev ") 75 swapDev, err := strconv.ParseInt(swapDevStr, 16, 32) 76 if err != nil { 77 log.Warnf("unable to parse swap device: %s", err) 78 continue 79 } 80 p.SwapDevice = int(swapDev) 81 case strings.HasPrefix(t, "root_dev "): 82 rootDevStr := strings.TrimPrefix(t, "root_dev ") 83 rootDev, err := strconv.ParseInt(rootDevStr, 16, 32) 84 if err != nil { 85 log.Warnf("unable to parse root device: %s", err) 86 continue 87 } 88 p.SwapDevice = int(rootDev) 89 case strings.Contains(t, "VGA") || strings.Contains(t, "Video"): 90 p.VideoMode = t 91 } 92 } 93 return p 94 }