From 6a561c64700d05ff2141860c768374d6ca1ea07d Mon Sep 17 00:00:00 2001 From: Ice3man Date: Tue, 24 Sep 2024 18:43:35 +0530 Subject: [PATCH] feat: clone event in clustering to generate correct failure events (#5653) --- pkg/output/output.go | 10 ++++++++++ pkg/templates/cluster.go | 34 +++++++++++++++++++--------------- 2 files changed, 29 insertions(+), 15 deletions(-) diff --git a/pkg/output/output.go b/pkg/output/output.go index 07c6f4c71f..fbc9f71306 100644 --- a/pkg/output/output.go +++ b/pkg/output/output.go @@ -5,6 +5,7 @@ import ( "fmt" "io" "log/slog" + "maps" "os" "path/filepath" "regexp" @@ -99,6 +100,15 @@ type InternalWrappedEvent struct { InteractshMatched atomic.Bool } +func (iwe *InternalWrappedEvent) CloneShallow() *InternalWrappedEvent { + return &InternalWrappedEvent{ + InternalEvent: maps.Clone(iwe.InternalEvent), + Results: nil, + OperatorsResult: nil, + UsesInteractsh: iwe.UsesInteractsh, + } +} + func (iwe *InternalWrappedEvent) HasOperatorResult() bool { iwe.RLock() defer iwe.RUnlock() diff --git a/pkg/templates/cluster.go b/pkg/templates/cluster.go index a4a4ac4bad..8f1af96b74 100644 --- a/pkg/templates/cluster.go +++ b/pkg/templates/cluster.go @@ -251,23 +251,25 @@ func (e *ClusterExecuter) Execute(ctx *scan.ScanContext) (bool, error) { event.InternalEvent = make(map[string]interface{}) } for _, operator := range e.operators { - result, matched := operator.operator.Execute(event.InternalEvent, e.requests.Match, e.requests.Extract, e.options.Options.Debug || e.options.Options.DebugResponse) - event.InternalEvent["template-id"] = operator.templateID - event.InternalEvent["template-path"] = operator.templatePath - event.InternalEvent["template-info"] = operator.templateInfo + clonedEvent := event.CloneShallow() + + result, matched := operator.operator.Execute(clonedEvent.InternalEvent, e.requests.Match, e.requests.Extract, e.options.Options.Debug || e.options.Options.DebugResponse) + clonedEvent.InternalEvent["template-id"] = operator.templateID + clonedEvent.InternalEvent["template-path"] = operator.templatePath + clonedEvent.InternalEvent["template-info"] = operator.templateInfo if result == nil && !matched && e.options.Options.MatcherStatus { - if err := e.options.Output.WriteFailure(event); err != nil { + if err := e.options.Output.WriteFailure(clonedEvent); err != nil { gologger.Warning().Msgf("Could not write failure event to output: %s\n", err) } continue } if matched && result != nil { - event.OperatorsResult = result - event.Results = e.requests.MakeResultEvent(event) + clonedEvent.OperatorsResult = result + clonedEvent.Results = e.requests.MakeResultEvent(clonedEvent) results = true - _ = writer.WriteResult(event, e.options.Output, e.options.Progress, e.options.IssuesClient) + _ = writer.WriteResult(clonedEvent, e.options.Output, e.options.Progress, e.options.IssuesClient) } } }) @@ -290,14 +292,16 @@ func (e *ClusterExecuter) ExecuteWithResults(ctx *scan.ScanContext) ([]*output.R } err := e.requests.ExecuteWithResults(inputItem, dynamicValues, nil, func(event *output.InternalWrappedEvent) { for _, operator := range e.operators { - result, matched := operator.operator.Execute(event.InternalEvent, e.requests.Match, e.requests.Extract, e.options.Options.Debug || e.options.Options.DebugResponse) + clonedEvent := event.CloneShallow() + + result, matched := operator.operator.Execute(clonedEvent.InternalEvent, e.requests.Match, e.requests.Extract, e.options.Options.Debug || e.options.Options.DebugResponse) if matched && result != nil { - event.OperatorsResult = result - event.InternalEvent["template-id"] = operator.templateID - event.InternalEvent["template-path"] = operator.templatePath - event.InternalEvent["template-info"] = operator.templateInfo - event.Results = e.requests.MakeResultEvent(event) - scanCtx.LogEvent(event) + clonedEvent.OperatorsResult = result + clonedEvent.InternalEvent["template-id"] = operator.templateID + clonedEvent.InternalEvent["template-path"] = operator.templatePath + clonedEvent.InternalEvent["template-info"] = operator.templateInfo + clonedEvent.Results = e.requests.MakeResultEvent(clonedEvent) + scanCtx.LogEvent(clonedEvent) } } })