sigma

package module
v0.0.0-...-dd8816d Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Mar 9, 2023 License: Apache-2.0 Imports: 19 Imported by: 0

README

warning: the work is extremely unstable, don't use in production code and if you're not prepared to resolve some issues that can occur

Fork of go-sigma-rule-engine

Added support for correlation

removed redundant (imho) structs

Golang library that implements a sigma log rule parser and match engine.

Sigma is a open and vendor-agnostic signature format for logs. Official sigma repository includes rule format definition, a public ruleset, and python tooling for converting rules into various SIEM alert formats. Essentially, it fills the same role in logging space as Suricata does in packet capture and YARA for file analysis. However, unlike those projects, the open Sigma project does not act as a match engine. Users are still expected to run a supported SIEM or log management solution, with necessary licencing to enable alerting features.

This project implements a rule parser and real-time match engine in Golang, to provide a lightweight alternative to those SIEM systems. Essentially, it's just a ~3000 line library that can be used by anyone to build their own IDS for logs. Initial version was experimental hack, cobbled together at the last minute with minimal testing, that was used by Crossed Swords 2020 exercise, organized by NATO CCDCOE. Yellow team log post-processor relied on the engine to detect Red team activities in gamenet targets, in real time. This code is archived into pkg/sigma/v1.

Since then, I rewrote the entire engine to provide a cleaner and more tested version as reference to anyone interested in building their own IDS for logs. This code can be found in pkg/sigma/v2. The project also includes a cli application in cmd/ folder, written with cobra. However, it is meant to be used as reference and testing, rather than a fully-fledged tool.

Basic usage

Simply pull the code using go get.

go get -u github.com/markuskont/go-sigma-rule-engine/

Then import the library into your project. PS - this path was refactored to project root in 0.3, as initial layout was not suitable to library project. Please update your imports accordingly when upgrading from 0.2.

import (
	"github.com/markuskont/go-sigma-rule-engine"
)
ruleset, err := sigma.NewRuleset(sigma.Config{
  Directory: viper.GetStringSlice("rules.dir"),
})
if err != nil {
  return err
}
logrus.Debugf("Found %d files, %d ok, %d failed, %d unsupported",
  ruleset.Total, ruleset.Ok, ruleset.Failed, ruleset.Unsupported)

Events can then be evaluated against full ruleset.

if result, match := ruleset.EvalAll(e); match {
  // handle match results here here
}

Individual rules could also be manually looped. For example, when early return is desired for avoiding full ruleset evaluation.

for _, rule := range ruleset.Rules {
  if rule.Match(e) {
    // handle rule match here
  }
}

Note that variable e should implement Event interface.

Matcher and Event

Our Sigma rule is built as a tree where each node must satisfy the Matcher interface that performs boolean evaluation for events.

type Matcher interface {
	Match(Event) bool
}

There are simply too many possible event formats for our simple Sigma library to handle. Therefore, users are expected to implement Event interface for any object that will be matched against the ruleset. This Event interface embeds field access methods for two Sigma rule types - keyword and selection.

// Keyworder implements keywords sigma rule type on arbitrary event
// Should return list of fields that are relevant for rule matching
type Keyworder interface {
	// Keywords implements Keyworder
	Keywords() ([]string, bool)
}

// Selector implements selection sigma rule type
type Selector interface {
	// Select implements Selector
	Select(string) (interface{}, bool)
}

// Event implements sigma rule types by embedding Keyworder and Selector
// Used by rules to extract relevant fields
type Event interface {
	Keyworder
	Selector
}

Helper function source file provides an example for handling dynamic hash maps.

Keywords

Keywords rule type is simply a list of patters that must exist in core message. Only one pattern must match.

  keywords:
    - 'wget * - http* | perl'
    - 'wget * - http* | sh'
    - 'wget * - http* | bash'
    - 'python -m SimpleHTTPServer'

Thus, the Keyworder interface simply returns a list of unstructured fields that could be considered core messages. It is built around slice because some event types, like Windows EventLog, could contain multiple fields that might contain this information. And returning a nil slice is cleaner than empty string when keyword rule type does not apply to event. However, in that case the second return value should always be false to ensure early return when rule does not apply to particular message.

type Keyworder interface {
	Keywords() ([]string, bool)
}

Dynamic JSON objects can be implemented as stub because this rule type does not support key-value lookups.

// Keywords implements Keyworder
func (s DynamicMap) Keywords() ([]string, bool) {
	return nil, false
}

Alternatively, structs for well-known and standardized messages, such as BSD syslog, might simply return the Message field.

func (m Syslog) Keywords() ([]string, bool) {
	return m.Message.Keywords()
}

That message could be a unstructured string that also implements our Event interface.

type Message string

func (m Message) Keywords() ([]string, bool) {
	return []string{string(m)}, true
}

Dynamic structured events, like Suricata EVE, could have well known fields that might qualify as message.

func (s DynamicMap) Keywords() ([]string, bool) {
	if val, ok := s.Select("alert.signature"); ok {
		if str, ok := val.(string); ok {
			return []string{str}, true
		}
	}
	return nil, false
}

Multiple fields could be extracted and passed to the rule with this method. For example, payload_printable, alert.category, etc.

Selection

This rule type is for key-value lookups.

  selection:
    winlog.event_data.ScriptBlockText:
    - ' -FromBase64String'

Like with keyword, this rule type might simply may not apply to some events.

func (s UnstructuredEvent) Select(key string) (interface{}, bool) {
	return nil, false
}

Otherwise, dynamic maps might simply implement it as wrapper for key-value lookup.

func (s DynamicMap) Select(key string) (interface{}, bool) {
	if val, ok := d[key]; ok {
		return val, true
	}
	return nil, false
}

Static structs for well-standardized event formats may simply handle these lookups manually.

type Syslog struct {
	Timestamp time.Time `json:"@timestamp"`
	Host      string    `json:"host"`
	Program   string    `json:"program"`
	Pid       int       `json:"pid"`
	Severity  int       `json:"severity"`
	Facility  int       `json:"facility"`
	Sender    net.IP    `json:"ip"`

	Message `json:"message"`
}

func (m Syslog) Select(key string) (interface{}, bool) {
	switch key {
	case "timestamp", "@timestamp":
		return m.Timestamp, true
	case "host":
		return m.Host, true
	case "program":
		return m.Program, true
	case "pid":
		return m.Pid, true
	case "severity":
		return m.Severity, true
	case "facility":
		return m.Facility, true
	case "sender":
		if m.Sender == nil {
			return nil, false
		}
		return m.Sender.String(), true
	case "message", "msg":
		return m.Keywords(), true
	default:
		return nil, false
	}
}

Performance

BenchmarkTreePositive0-12         867567              1363 ns/op
BenchmarkTreePositive1-12         862962              1494 ns/op
BenchmarkTreePositive2-12         795531              1380 ns/op
BenchmarkTreePositive3-12         854679              1393 ns/op
BenchmarkTreePositive4-12         884188              1364 ns/op
BenchmarkTreePositive5-12         809140              1390 ns/op
BenchmarkTreePositive6-12         773706              1410 ns/op
BenchmarkTreeNegative0-12         776173              1385 ns/op
BenchmarkTreeNegative1-12         812887              1481 ns/op
BenchmarkTreeNegative2-12         850477              1401 ns/op
BenchmarkTreeNegative3-12         840723              1390 ns/op
BenchmarkTreeNegative4-12         819126              1417 ns/op
BenchmarkTreeNegative5-12         748514              1416 ns/op
BenchmarkTreeNegative6-12         856683              1382 ns/op

Limitations

Ruleset is not thread safe. Nor can it be easily deep-copied due to possible pointers behind interfaces and pattern containers. Each worker thread should instantiate independent ruleset. However, public sigma ruleset only produces about ~500 rules, so overhead is currently trivial.

Library is built around distinct rules, rather than entire ruleset. That means that each rule could run separate map lookups and no data is shared between them. While individual rules are quite efficient, even in current unoptimized form, passing each event thought entire ruleset means traversing hundreds of rules. Thus having significant performance overhead. For example, we measured that passing an ECS formatted Windows EventLog message through all Windows rules in public Sigma ruleset took 4.5 times the amount of time that was otherwise spent on simply decoding the message.

Ruleset splitting and pre-filtering must be handled by the user. Sigma has logsource field to indicate which events should be evaluated against a rule. We simply handled this externally, parsing rules into a map of smaller rulesets. So, we had separate rulesets for Syslog, Snoopy, Suricata and EventLog. Logsource field was used to determine which ruleset was executed for event.

No support for aggregations or event correlation. Relatively small amount of Sigma rules use aggregations with count() > N or Near() keywords. Implementing them in streaming scenario is quite complex, as they require sharing state between messages over sliding window. Thus requiring full event correlation to be implemented. However, this did not fit our present concurrency model where N workers load balance over common message channel and no information is shared between them. Future work.

Documentation

Index

Constants

This section is empty.

Variables

View Source
var ErrUnableToReflect = errors.New("unable to reflect on pattern kind")

ErrUnableToReflect indicates that kind reflection could not be done, as typeOf returned a nil value likely a missing pattern

Functions

func NewRuleFileList

func NewRuleFileList(dirs []string) ([]string, error)

NewRuleFileList finds all yaml files from defined root directories Subtree is scanned recursively No file validation, other than suffix matching

Types

type Branch

type Branch interface {
	Matcher
}

Branch implements Matcher with additional methods for walking and debugging the tree

func NewSelectionBranch

func NewSelectionBranch(expr interface{}, noCollapseWS bool) (Branch, error)

type Config

type Config struct {
	// root directory for recursive rule search
	// rules must be readable files with "yml" suffix
	Directory []string
}

Config is used as argument to creating a new ruleset

type ContentPattern

type ContentPattern struct {
	Token        string
	Lowercase    bool
	NoCollapseWS bool
}

ContentPattern is a token for literal content matching

func (ContentPattern) StringMatch

func (c ContentPattern) StringMatch(msg string) bool

StringMatch implements StringMatcher

type Correlation

type Correlation struct {
	Name string `yaml:"name" json:"name"`
	// Action will be correlation for correlations, and empty for rules.
	Action actions.Action `yaml:"action" json:"action"`
	// event_count, value_count, temporal
	Type      ruleTypes.RuleType                           `yaml:"type" json:"type"`
	Condition map[conditionTypes.ConditionType]interface{} `yaml:"condition" json:"condition"`

	// RulesString exists for a first step of getting rules of a correlation
	RulesString []string `yaml:"rules" json:"-"`

	Matchers []Matcher `yaml:"-" json:"rules"`

	GroupBy []string `yaml:"group-by" json:"group_by"`

	// Timespan defines a time period in which the correlation should be applied.
	// The following format must be used: number + letter (in lowercase)
	//     Xs seconds
	//     Xm minutes
	//     Xh hours
	//     Xd days
	Timespan *time.Duration `yaml:"timespan" json:"timespan"`
}

func (Correlation) Match

func (c Correlation) Match(e Event) (bool, bool)

func (*Correlation) Matcher

func (c *Correlation) Matcher(e Event) (bool, bool)

func (Correlation) NewTree

func (c Correlation) NewTree() (*Tree, error)

NewTree parses rule handle into an abstract syntax tree

type Detection

type Detection map[string]interface{}

Detection represents the detection field in sigma rule contains condition expression and identifier fields for building AST

func (Detection) ExtractCondition

func (d Detection) ExtractCondition() map[string]interface{}

type ErrBulkParseYaml

type ErrBulkParseYaml struct {
	Errs []ErrParseYaml
}

ErrGotBrokenYamlFiles is a bulk error handler for dealing with broken sigma rules Some rules are bound to fail, no reason to exit entire application Individual errors can be collected and returned at the end Called decides if they should be only reported or it warrants full exit

func (ErrBulkParseYaml) Error

func (e ErrBulkParseYaml) Error() string

type ErrEmptyDetection

type ErrEmptyDetection struct{}

ErrEmptyDetection indicates detection field present but empty

func (ErrEmptyDetection) Error

func (e ErrEmptyDetection) Error() string

type ErrIncompleteDetection

type ErrIncompleteDetection struct {
	Condition string
	Keys      []string
	Msg       string
}

ErrIncompleteDetection indicates a rule has defined identifiers that are missing in detection map

func (ErrIncompleteDetection) Error

func (e ErrIncompleteDetection) Error() string

type ErrIncompleteTokenSeq

type ErrIncompleteTokenSeq struct {
	Expression string
	Items      []Item
	Last       Item
}

ErrIncompleteTokenSeq is invoked when lex channel drain does not end with EOF thus indicating incomplete lexing sequence

func (ErrIncompleteTokenSeq) Error

func (e ErrIncompleteTokenSeq) Error() string

type ErrInvalidKeywordConstruct

type ErrInvalidKeywordConstruct struct {
	Msg  string
	Expr interface{}
}

ErrInvalidKeywordConstruct indicates that parser found a keyword expression that did not match any known keyword rule structure could be unmarshal issue

func (ErrInvalidKeywordConstruct) Error

type ErrInvalidKind

type ErrInvalidKind struct {
	reflect.Kind
	Msg      string
	T        identType
	Critical bool
}

ErrInvalidKind indicates that type switching function received an unsupported or unhandled data type Contains the type in question, arbitrary error text and keyword/selection indicator Critical is used to indicate if this error should cause an exit or can simply be handled as a warning for future improvements

func (ErrInvalidKind) Error

func (e ErrInvalidKind) Error() string

type ErrInvalidRegex

type ErrInvalidRegex struct {
	Pattern string
	Err     error
}

ErrInvalidRegex contextualizes broken regular expressions presented by the user

func (ErrInvalidRegex) Error

func (e ErrInvalidRegex) Error() string

Error implements error

type ErrInvalidSelectionConstruct

type ErrInvalidSelectionConstruct struct {
	Msg  string
	Expr interface{}
}

ErrInvalidSelectionConstruct indicates that parser found a selection expression that did not match any known selection rule structure could be unmarshal issue

func (ErrInvalidSelectionConstruct) Error

type ErrInvalidTokenSeq

type ErrInvalidTokenSeq struct {
	Prev, Next Item
	Collected  []Item
}

ErrInvalidTokenSeq indicates expression syntax error from rule writer For example, two indents should be separated by a logical AND / OR operator

func (ErrInvalidTokenSeq) Error

func (e ErrInvalidTokenSeq) Error() string

type ErrMissingCondition

type ErrMissingCondition struct{}

ErrMissingCondition indicates missing condition field

func (ErrMissingCondition) Error

func (e ErrMissingCondition) Error() string

type ErrMissingConditionItem

type ErrMissingConditionItem struct {
	Key string
}

ErrMissingConditionItem indicates that identifier in condition is missing in detection map

func (ErrMissingConditionItem) Error

func (e ErrMissingConditionItem) Error() string

type ErrMissingDetection

type ErrMissingDetection struct{}

ErrMissingDetection indicates missing detection field

func (ErrMissingDetection) Error

func (e ErrMissingDetection) Error() string

type ErrParseYaml

type ErrParseYaml struct {
	Path  string
	Err   error
	Count int
}

ErrParseYaml indicates YAML parsing error

func (ErrParseYaml) Error

func (e ErrParseYaml) Error() string

type ErrUnsupportedExpression

type ErrUnsupportedExpression struct {
	Msg      string
	T        identType
	Expr     interface{}
	Critical bool
}

ErrUnsupportedExpression indicates that rule expression is not yet supported by parser mostly a type issue

func (ErrUnsupportedExpression) Error

func (e ErrUnsupportedExpression) Error() string

type ErrUnsupportedToken

type ErrUnsupportedToken struct{ Msg string }

ErrUnsupportedToken is a parser error indicating lexical token that is not yet supported Meant to be used as informational warning, rather than application breaking error

func (ErrUnsupportedToken) Error

func (e ErrUnsupportedToken) Error() string

type ErrWip

type ErrWip struct{}

ErrWip indicates a rule expression that is currently Work In Progress Functions like ErrUnsupportedToken but indicates that feature is under active development Non-critical escape hatch while debugging

func (ErrWip) Error

func (e ErrWip) Error() string

type Event

type Event interface {
	Keyworder
	Selector
}

Event implements sigma rule types by embedding Keyworder and Selector Used by rules to extract relevant fields

type GlobPattern

type GlobPattern struct {
	Glob         *glob.Glob
	NoCollapseWS bool
}

GlobPattern is similar to ContentPattern but allows for asterisk wildcards

func (GlobPattern) StringMatch

func (g GlobPattern) StringMatch(msg string) bool

StringMatch implements StringMatcher

type Item

type Item struct {
	T   Token
	Val string
	// contains filtered or unexported fields
}

Item is lexical token along with respective plaintext value Item is communicated between lexer and parser

func (*Item) Glob

func (i *Item) Glob() *glob.Glob

Item.Glob() - Wraps getting the compiled glob of Item.Val to ensure it is compiled properly. Do NOT access globVal directly as it won't be compiled until the first call to Item.Glob()

func (Item) String

func (i Item) String() string

type Keyword

type Keyword struct {
	S StringMatcher
	// contains filtered or unexported fields
}

Keyword is a container for patterns joined by logical disjunction

func NewKeyword

func NewKeyword(expr interface{}, noCollapseWS bool) (*Keyword, error)

func (Keyword) Match

func (k Keyword) Match(msg Event) (bool, bool)

Match implements Matcher

type Keyworder

type Keyworder interface {
	// Keywords implements Keyworder
	Keywords() ([]string, bool)
}

Keyworder implements keywords sigma rule type on arbitrary event Should return list of fields that are relevant for rule matching

type Logsource

type Logsource struct {
	Product    string `yaml:"product" json:"product"`
	Category   string `yaml:"category" json:"category"`
	Service    string `yaml:"service" json:"service"`
	Definition string `yaml:"definition" json:"definition"`
}

Logsource represents the logsource field in sigma rule It defines relevant event streams and is used for pre-filtering

type Matcher

type Matcher interface {
	// Match implements Matcher
	Match(Event) (bool, bool)
}

Matcher is used for implementing Abstract Syntax Tree for Sigma engine

type NodeAnd

type NodeAnd struct {
	L, R Branch
}

NodeAnd is a two element node of a binary tree with Left and Right branches connected via logical conjunction

func (NodeAnd) Match

func (n NodeAnd) Match(e Event) (bool, bool)

Match implements Matcher

type NodeNot

type NodeNot struct {
	B Branch
}

NodeNot negates a branch

func (NodeNot) Match

func (n NodeNot) Match(e Event) (bool, bool)

Match implements Matcher

type NodeOr

type NodeOr struct {
	L, R Branch
}

NodeOr is a two element node of a binary tree with Left and Right branches connected via logical disjunction

func (NodeOr) Match

func (n NodeOr) Match(e Event) (bool, bool)

Match implements Matcher

type NodeSimpleAnd

type NodeSimpleAnd []Branch

NodeSimpleAnd is a list of matchers connected with logical conjunction

func (NodeSimpleAnd) Match

func (n NodeSimpleAnd) Match(e Event) (bool, bool)

Match implements Matcher

func (NodeSimpleAnd) Reduce

func (n NodeSimpleAnd) Reduce() Branch

Reduce cleans up unneeded slices Static structures can be used if node only holds one or two elements Avoids pointless runtime loops

type NodeSimpleOr

type NodeSimpleOr []Branch

NodeSimpleOr is a list of matchers connected with logical disjunction

func (NodeSimpleOr) Match

func (n NodeSimpleOr) Match(e Event) (bool, bool)

Match implements Matcher

func (NodeSimpleOr) Reduce

func (n NodeSimpleOr) Reduce() Branch

Reduce cleans up unneeded slices Static structures can be used if node only holds one or two elements Avoids pointless runtime loops

type NumMatcher

type NumMatcher interface {
	// NumMatch implements NumMatcher
	NumMatch(int) bool
}

NumMatcher is an atomic pattern for numeric item or list of items

func NewNumMatcher

func NewNumMatcher(patterns ...int) (NumMatcher, error)

type NumMatchers

type NumMatchers []NumMatcher

NumMatchers holds multiple numeric matchers

func (NumMatchers) NumMatch

func (n NumMatchers) NumMatch(val int) bool

NumMatch implements NumMatcher

type NumPattern

type NumPattern struct {
	Val int
}

NumPattern matches on numeric value

func (NumPattern) NumMatch

func (n NumPattern) NumMatch(val int) bool

NumMatch implements NumMatcher

type PrefixPattern

type PrefixPattern struct {
	Token        string
	Lowercase    bool
	NoCollapseWS bool
}

PrefixPattern is a token for literal content matching

func (PrefixPattern) StringMatch

func (c PrefixPattern) StringMatch(msg string) bool

StringMatch implements StringMatcher

type RegexPattern

type RegexPattern struct {
	Re *regexp.Regexp
}

RegexPattern is for matching messages with regular expresions

func (RegexPattern) StringMatch

func (r RegexPattern) StringMatch(msg string) bool

StringMatch implements StringMatcher

type Result

type Result struct {
	Tags `json:"tags"`

	ID          string `json:"id"`
	Title       string `json:"title"`
	Description string `json:"description"`
}

Result is an object returned on positive sigma match

type Results

type Results []Result

Results should be returned when single event matches multiple rules

type Rule

type Rule interface {
	NewTree() (*Tree, error)
}

func RulesFromFiles

func RulesFromFiles(files []string) ([]Rule, error)

RulesFromFiles reads a list of sigma rule paths and parses them to rule objects

type Ruleset

type Ruleset struct {
	Rules []*Tree
	// contains filtered or unexported fields
}

Ruleset is a collection of rules

func NewRuleset

func NewRuleset(c Config) (*Ruleset, error)

NewRuleset instanciates a Ruleset object

type Selection

type Selection struct {
	N []SelectionNumItem
	S []SelectionStringItem
	// contains filtered or unexported fields
}

func (Selection) Match

func (s Selection) Match(msg Event) (bool, bool)

Match implements Matcher TODO - numeric and boolean pattern match

type SelectionNumItem

type SelectionNumItem struct {
	Key     string
	Pattern NumMatcher
}

type SelectionStringItem

type SelectionStringItem struct {
	Key     string
	Pattern StringMatcher
}

type Selector

type Selector interface {
	// Select implements Selector
	Select(string) (interface{}, bool)
}

Selector implements selection sigma rule type

type SimplePattern

type SimplePattern struct {
	Token        string
	NoCollapseWS bool
}

SimplePattern is a reference type to illustrate StringMatcher

func (SimplePattern) StringMatch

func (s SimplePattern) StringMatch(msg string) bool

StringMatch implements StringMatcher

type SimpleRule

type SimpleRule struct {
	Name   string `yaml:"name" json:"name"`
	Author string `yaml:"author" json:"author"`
	// Date           *time.Time `yaml:"date" json:"date"`
	// Modified       *time.Time `yaml:"modified" json:"modified"`
	Description    string   `yaml:"description" json:"description"`
	Falsepositives []string `yaml:"falsepositives" json:"falsepositives"`
	Fields         []string `yaml:"fields" json:"fields"`
	ID             string   `yaml:"id" json:"id"`
	Level          string   `yaml:"level" json:"level"`
	Title          string   `yaml:"title" json:"title"`
	Status         string   `yaml:"status" json:"status"`
	References     []string `yaml:"references" json:"references"`

	Logsource Logsource `yaml:"logsource" json:"logsource"`
	Detection Detection `yaml:"detection" json:"detection"`
	Tags      Tags      `yaml:"tags" json:"tags"`
}

Rule defines raw rule conforming to sigma rule specification https://github.com/Neo23x0/sigma/wiki/Specification only meant to be used for parsing yaml that matches Sigma rule definition

func (SimpleRule) NewTree

func (r SimpleRule) NewTree() (*Tree, error)

NewTree parses rule handle into an abstract syntax tree

type StringMatcher

type StringMatcher interface {
	// StringMatch implements StringMatcher
	StringMatch(string) bool
}

StringMatcher is an atomic pattern that could implement glob, literal or regex matchers

func NewStringMatcher

func NewStringMatcher(
	mod TextPatternModifier,
	lower, all, noCollapseWS bool,
	patterns ...string,
) (StringMatcher, error)

type StringMatchers

type StringMatchers []StringMatcher

StringMatchers holds multiple atomic matchers Patterns are meant to be list of possibilities thus, objects are joined with logical disjunctions

func (StringMatchers) Optimize

func (s StringMatchers) Optimize() StringMatchers

Optimize creates a new StringMatchers slice ordered by matcher type First match wins, thus we can optimize by making sure fast string patterns are executed first, then globs, and finally slow regular expressions

func (StringMatchers) StringMatch

func (s StringMatchers) StringMatch(msg string) bool

StringMatch implements StringMatcher

type StringMatchersConj

type StringMatchersConj []StringMatcher

StringMatchersConj is similar to StringMatcher but elements are joined with conjunction, i.e. all patterns must match used to implement "all" specifier for selection types

func (StringMatchersConj) Optimize

Optimize creates a new StringMatchers slice ordered by matcher type First match wins, thus we can optimize by making sure fast string patterns are executed first, then globs, and finally slow regular expressions

func (StringMatchersConj) StringMatch

func (s StringMatchersConj) StringMatch(msg string) bool

StringMatch implements StringMatcher

type SuffixPattern

type SuffixPattern struct {
	Token        string
	Lowercase    bool
	NoCollapseWS bool
}

SuffixPattern is a token for literal content matching

func (SuffixPattern) StringMatch

func (c SuffixPattern) StringMatch(msg string) bool

StringMatch implements StringMatcher

type Tags

type Tags []string

Tags contains a metadata list for tying positive matches together with other threat intel sources For example, for attaching MITRE ATT&CK tactics or techniques to the event

type TextPatternModifier

type TextPatternModifier int
const (
	TextPatternNone TextPatternModifier = iota
	TextPatternContains
	TextPatternPrefix
	TextPatternSuffix
	TextPatternAll
	TextPatternRegex
	TextPatternKeyword
)

type Token

type Token int

Token is a lexical token extracted from condition field

const (
	TokBegin Token = iota

	// Helpers for internal stuff
	TokErr
	TokUnsupp
	TokNil

	// user-defined word
	TokIdentifier
	TokIdentifierWithWildcard
	TokIdentifierAll

	// Literals
	TokLitEof

	// Separators
	TokSepLpar
	TokSepRpar
	TokSepPipe

	// Operators
	TokOpEq
	TokOpGt
	TokOpGte
	TokOpLt
	TokOpLte

	// Keywords
	TokKeywordAnd
	TokKeywordOr
	TokKeywordNot
	TokKeywordAgg

	// TODO
	TokKeywordNear
	TokKeywordBy

	// Statements
	TokStOne
	TokStAll
)

func (Token) Literal

func (t Token) Literal() string

Literal documents plaintext values of a token Uses special symbols and expressions, as used in a rule

func (Token) Rune

func (t Token) Rune() rune

Rune returns UTF-8 numeric value of symbol

func (Token) String

func (t Token) String() string

String documents human readable textual value of token For visual debugging, so symbols will be written out and everything is uppercased

type Tree

type Tree struct {
	Root Branch
	Rule Rule
}

Tree represents the full AST for a sigma rule

func (Tree) Eval

func (t Tree) Eval(e Event) bool

func (Tree) Match

func (t Tree) Match(e Event) (bool, bool)

Match implements Matcher

Directories

Path Synopsis
examples
models

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL