github.com/google/osv-scalibr@v0.4.1/binary/proto/vex.go (about) 1 // Copyright 2025 Google LLC 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package proto 16 17 import ( 18 "errors" 19 20 "github.com/google/osv-scalibr/inventory/vex" 21 22 spb "github.com/google/osv-scalibr/binary/proto/scan_result_go_proto" 23 ) 24 25 var ( 26 // --- Errors 27 28 // ErrVulnIdentifiersAndMatchsAllSet will be returned if both VulnIdentifiers and MatchesAllVulns are set. 29 ErrVulnIdentifiersAndMatchsAllSet = errors.New("cannot set both VulnIdentifiers and MatchesAllVulns") 30 31 // structToProtoVEX is a map of struct VEX justifications to their corresponding proto values. 32 structToProtoVEX = map[vex.Justification]spb.VexJustification{ 33 vex.Unspecified: spb.VexJustification_VEX_JUSTIFICATION_UNSPECIFIED, 34 vex.ComponentNotPresent: spb.VexJustification_COMPONENT_NOT_PRESENT, 35 vex.VulnerableCodeNotPresent: spb.VexJustification_VULNERABLE_CODE_NOT_PRESENT, 36 vex.VulnerableCodeNotInExecutePath: spb.VexJustification_VULNERABLE_CODE_NOT_IN_EXECUTE_PATH, 37 vex.VulnerableCodeCannotBeControlledByAdversary: spb.VexJustification_VULNERABLE_CODE_CANNOT_BE_CONTROLLED_BY_ADVERSARY, 38 vex.InlineMitigationAlreadyExists: spb.VexJustification_INLINE_MITIGATION_ALREADY_EXISTS, 39 } 40 // protoToStructVEX is a map of proto VEX justifications to their corresponding struct values. 41 // It is initialized from structToProtoVEX during runtime to ensure both maps are in sync. 42 protoToStructVEX = func() map[spb.VexJustification]vex.Justification { 43 m := make(map[spb.VexJustification]vex.Justification) 44 for k, v := range structToProtoVEX { 45 m[v] = k 46 } 47 if len(m) != len(structToProtoVEX) { 48 panic("protoToStructAnnotations does not contain all values from structToProtoAnnotations") 49 } 50 return m 51 }() 52 ) 53 54 // --- Struct to Proto 55 56 // PackageVEXToProto converts a struct PackageExploitabilitySignal to its proto representation. 57 func PackageVEXToProto(v *vex.PackageExploitabilitySignal) (*spb.PackageExploitabilitySignal, error) { 58 if v == nil { 59 return nil, nil 60 } 61 if len(v.VulnIdentifiers) != 0 && v.MatchesAllVulns { 62 return nil, ErrVulnIdentifiersAndMatchsAllSet 63 } 64 65 p := &spb.PackageExploitabilitySignal{ 66 Plugin: v.Plugin, 67 Justification: structToProtoVEX[v.Justification], 68 } 69 if v.MatchesAllVulns { 70 p.VulnFilter = &spb.PackageExploitabilitySignal_MatchesAllVulns{MatchesAllVulns: true} 71 } else { 72 p.VulnFilter = &spb.PackageExploitabilitySignal_VulnIdentifiers{ 73 VulnIdentifiers: &spb.VulnIdentifiers{Identifiers: v.VulnIdentifiers}, 74 } 75 } 76 return p, nil 77 } 78 79 // FindingVEXToProto converts a struct FindingExploitabilitySignal to its proto representation. 80 func FindingVEXToProto(v *vex.FindingExploitabilitySignal) *spb.FindingExploitabilitySignal { 81 if v == nil { 82 return nil 83 } 84 85 return &spb.FindingExploitabilitySignal{ 86 Plugin: v.Plugin, 87 Justification: structToProtoVEX[v.Justification], 88 } 89 } 90 91 // --- Proto to Struct 92 93 // PackageVEXToStruct converts a proto PackageExploitabilitySignal to its struct representation. 94 func PackageVEXToStruct(p *spb.PackageExploitabilitySignal) (*vex.PackageExploitabilitySignal, error) { 95 if p == nil { 96 return nil, nil 97 } 98 99 v := &vex.PackageExploitabilitySignal{ 100 Plugin: p.Plugin, 101 Justification: protoToStructVEX[p.Justification], 102 } 103 if ids := p.GetVulnIdentifiers(); ids != nil { 104 v.VulnIdentifiers = ids.Identifiers 105 } else { 106 v.MatchesAllVulns = p.GetMatchesAllVulns() 107 } 108 return v, nil 109 } 110 111 // FindingVEXToStruct converts a proto FindingExploitabilitySignal to its struct representation. 112 func FindingVEXToStruct(p *spb.FindingExploitabilitySignal) *vex.FindingExploitabilitySignal { 113 if p == nil { 114 return nil 115 } 116 117 return &vex.FindingExploitabilitySignal{ 118 Plugin: p.Plugin, 119 Justification: protoToStructVEX[p.Justification], 120 } 121 }