@@ -448,7 +448,11 @@ func Generate(ctx context.Context, path string, mrs *yarax.ScanResults, c malcon
448448
449449 b := buildBehavior (m , matchedStrings , key , ruleURL , risk )
450450
451- handleMetadata (m , b , fr , override , mrsMap , & pledges , & caps , & syscalls )
451+ // if the rule has an override tag but is not overriding a valid rule,
452+ // ignore this match rule so that we don't show errant false positive rules in reports
453+ if ! parseMetadata (m , b , fr , override , mrsMap , & pledges , & caps , & syscalls ) {
454+ continue
455+ }
452456
453457 // Fix YARA Forge rules that record their author URL as reference URLs
454458 if strings .HasPrefix (b .RuleURL , b .ReferenceURL ) {
@@ -476,8 +480,6 @@ func Generate(ctx context.Context, path string, mrs *yarax.ScanResults, c malcon
476480 }
477481
478482 updateBehavior (fr , b , key )
479-
480- // TODO: If we match multiple rules within a single namespace, merge matchstrings
481483 }
482484
483485 // Update the behaviors to account for overrides
@@ -589,10 +591,14 @@ func buildBehavior(m *yarax.Rule, matchedStrings []string, key string, ruleURL s
589591 }
590592}
591593
592- func handleMetadata (m * yarax.Rule , b * malcontent.Behavior , fr * malcontent.FileReport , override bool , mrsMap map [string ]* yarax.Rule , pledges * []string , caps * []string , syscalls * []string ) {
594+ func parseMetadata (m * yarax.Rule , b * malcontent.Behavior , fr * malcontent.FileReport , override bool , mrsMap map [string ]* yarax.Rule , pledges * []string , caps * []string , syscalls * []string ) bool {
593595 k := ""
594596 v := ""
595597
598+ // valid represents whether a rule's metadata contains a legitimate override
599+ // or is otherwise valid for the matching rule
600+ valid := true
601+
596602 for _ , meta := range m .Metadata () {
597603 k = meta .Identifier ()
598604 v = fmt .Sprintf ("%s" , meta .Value ())
@@ -601,25 +607,6 @@ func handleMetadata(m *yarax.Rule, b *malcontent.Behavior, fr *malcontent.FileRe
601607 continue
602608 }
603609
604- // If we find a match in the map for the metadata key, that's the rule to override
605- // Store this rule (the override) in the fr.Overrides behavior slice
606- // If an override rule is not overriding a valid rule, log an error
607- _ , exists := mrsMap [k ]
608- switch {
609- case exists && override :
610- var overrideSev int
611- if sev , ok := Levels [v ]; ok {
612- overrideSev = sev
613- }
614- b .RiskLevel = RiskLevels [overrideSev ]
615- b .RiskScore = overrideSev
616- b .Override = append (b .Override , k )
617- fr .Overrides = append (fr .Overrides , b )
618- case ! exists && override :
619- // TODO: return error if override references an unknown rule name
620- continue
621- }
622-
623610 switch k {
624611 case "author" :
625612 b .RuleAuthor = v
@@ -656,14 +643,47 @@ func handleMetadata(m *yarax.Rule, b *malcontent.Behavior, fr *malcontent.FileRe
656643 // YARAforge forgets to encode spaces
657644 b .RuleURL = fixURL (v )
658645 case "pledge" :
659- * pledges = append (* pledges , v )
646+ // pledges should not be nil when we get here, but guard against it
647+ if pledges != nil {
648+ * pledges = append (* pledges , v )
649+ }
660650 case "syscall" :
661- sy := strings .Split (v , "," )
662- * syscalls = append (* syscalls , sy ... )
651+ // syscalls should not be nil when we get here, but guard against it
652+ if syscalls != nil {
653+ calls := strings .Split (v , "," )
654+ * syscalls = append (* syscalls , calls ... )
655+ }
663656 case "cap" :
664- * caps = append (* caps , v )
657+ // caps should not be nil when we get here, but guard against it
658+ if caps != nil {
659+ * caps = append (* caps , v )
660+ }
661+ case "filetypes" :
662+ continue
663+ // If we find a match in the map for the metadata key after exhausting known keys, that's the rule to override
664+ // Store this rule (the override) in the fr.Overrides behavior slice
665+ // If an override rule is not overriding a valid rule, set `valid` to false so we can
666+ // skip the parent rule match in the report
667+ default :
668+ _ , exists := mrsMap [k ]
669+ switch {
670+ case exists && override :
671+ var overrideSev int
672+ if sev , ok := Levels [v ]; ok {
673+ overrideSev = sev
674+ }
675+ b .RiskLevel = RiskLevels [overrideSev ]
676+ b .RiskScore = overrideSev
677+ b .Override = append (b .Override , k )
678+ fr .Overrides = append (fr .Overrides , b )
679+ case ! exists && override :
680+ valid = false
681+ continue
682+ }
665683 }
666684 }
685+
686+ return valid
667687}
668688
669689func updateBehavior (fr * malcontent.FileReport , b * malcontent.Behavior , key string ) {
0 commit comments