Sigma Rules¶
This documentation page describes the parsing of Sigma rules and working with Sigma objects resulting from parsed rules.
Parsing¶
Programatic Construction¶
Rule Collections¶
- class sigma.collection.SigmaCollection(rules: ~typing.List[~sigma.rule.base.SigmaRuleBase], errors: ~typing.List[~sigma.exceptions.SigmaError] = <factory>)¶
Collection of Sigma rules
- classmethod from_dicts(rules: List[dict], collect_errors: bool = False, source: SigmaRuleLocation | None = None) SigmaCollection ¶
Generate a rule collection from list of dicts containing parsed YAML content.
If the collect_errors parameters is set, exceptions are not raised while parsing but collected in the errors property individually for each Sigma rule and the whole SigmaCollection.
- classmethod from_yaml(yaml_str: bytes | str | IO, collect_errors: bool = False, source: SigmaRuleLocation | None = None) SigmaCollection ¶
Generate a rule collection from a string containing one or multiple YAML documents.
If the collect_errors parameters is set, exceptions are not raised while parsing but collected in the errors property individually for each Sigma rule and the whole SigmaCollection.
- get_output_rules() Iterable[SigmaRuleBase] ¶
Returns an iterator across all rules where the output property is set to true
- get_unreferenced_rules() Iterable[SigmaRuleBase] ¶
Returns an iterator across all rules that are not referenced by any other rule
- classmethod load_ruleset(inputs: List[str | Path], collect_errors: bool = False, on_beforeload: Callable[[Path], Path | None] | None = None, on_load: Callable[[Path, SigmaCollection], SigmaCollection | None] | None = None, recursion_pattern: str = '**/*.yml') SigmaCollection ¶
Load a ruleset from a list of files or directories and construct a
SigmaCollection
object.- Parameters:
inputs – List of strings and
pathlib.Path
objects that reference files or
directories that should be loaded. :param collect_errors: parse or verification errors are collected in
SigmaRuleBase
objects instead of raising them immediately. Defaults toFalse
. :param on_beforeload: Optional function that is called for each path to a Sigma rule before the parsing and construction of theSigmaCollection
object is done. The path returned by this function is used as input. A rule path is skipped ifNone
is returned. :param on_load: Optional function that is called after theSigmaCollection
was constructed from the path. The path and the SigmaCollection object are passed to this function and it is expected to return aSigmaCollection
object that is merged in the collection of the ruleset orNone
if the generated collection should be skipped. :param recursion_pattern: Pattern used to recurse into directories, defaults to**/*.yml
.- Returns:
SigmaCollection
of all sigma rules contained in given paths.
- classmethod merge(collections: Iterable[SigmaCollection]) SigmaCollection ¶
Merge multiple SigmaCollection objects into one and return it.
- classmethod resolve_paths(inputs: List[str | Path], recursion_pattern: str = '**/*.yml') Iterable[Path] ¶
Resolve list of paths inputs that can contain files as well as directories into a flat list of files matching resursion_pattern.
- resolve_rule_references()¶
Resolve rule references in correlation rules to the actual rule objects and sort the rules by reference order (rules that are referenced by other rules come first).
This must be called before referencing rules are converted into queries to make references available.
Rule Object Model¶
SigmaRule¶
- class sigma.rule.SigmaRule(title: str = '', id: ~uuid.UUID | None = None, name: str | None = None, taxonomy: str = 'sigma', related: sigma.rule.attributes.SigmaRelated | None = None, status: sigma.rule.attributes.SigmaStatus | None = None, description: str | None = None, license: str | None = None, references: ~typing.List[str] = <factory>, tags: ~typing.List[sigma.rule.attributes.SigmaRuleTag] = <factory>, author: str | None = None, date: datetime.date | None = None, modified: datetime.date | None = None, fields: ~typing.List[str] = <factory>, falsepositives: ~typing.List[str] = <factory>, level: sigma.rule.attributes.SigmaLevel | None = None, scope: ~typing.List[str] | None = None, errors: ~typing.List[~sigma.exceptions.SigmaError] = <factory>, source: ~sigma.exceptions.SigmaRuleLocation | None = None, custom_attributes: ~typing.Dict[str, ~typing.Any] = <factory>, logsource: ~sigma.rule.logsource.SigmaLogSource = <factory>, detection: ~sigma.rule.detection.SigmaDetections = <factory>)¶
A single Sigma rule.
- classmethod from_dict(rule: dict, collect_errors: bool = False, source: SigmaRuleLocation | None = None) SigmaRule ¶
Convert Sigma rule parsed in dict structure into SigmaRule object.
if collect_errors is set to False exceptions are collected in the errors property of the resulting SigmaRule object. Else the first recognized error is raised as exception.
- to_dict() dict ¶
Convert rule object into dict.
SigmaLogSource¶
- class sigma.rule.SigmaLogSource(category: str | None = None, product: str | None = None, service: str | None = None, definition: str | None = None, source: sigma.exceptions.SigmaRuleLocation | None = None, custom_attributes: Dict[str, Any] | None = None)¶
- classmethod from_dict(logsource: dict, source: SigmaRuleLocation | None = None) SigmaLogSource ¶
Returns SigmaLogSource object from dict with fields.
SigmaDetections¶
- class sigma.rule.SigmaDetections(detections: Dict[str, SigmaDetection], condition: List[str], source: SigmaRuleLocation | None = None)¶
Sigma detection section including named detections and condition.
SigmaDetection¶
- class sigma.rule.SigmaDetection(detection_items: List[SigmaDetectionItem | SigmaDetection], source: SigmaRuleLocation | None = None, item_linking: Type[ConditionAND] | Type[ConditionOR] | None = None)¶
A detection is a set of atomic event definitions represented by SigmaDetectionItem instances. SigmaDetectionItems of a SigmaDetection are OR-linked.
A detection can be defined by:
a mapping between field/value pairs that all should appear in matched events.
a plain value
a list of plain values or mappings defined and matched as in 1 where at least one of the items should appear in matched events.
- add_applied_processing_item(processing_item: ProcessingItem | None)¶
Propagate processing item to all contained detection items.
- classmethod from_definition(definition: Mapping | Sequence | str | int, source: SigmaRuleLocation | None = None) SigmaDetection ¶
Instantiate an appropriate SigmaDetection object from a parsed Sigma detection definition.
- postprocess(detections: SigmaDetections, parent: sigma.condition.ConditionItem | None = None) ConditionAND | ConditionOR ¶
Convert detection item into condition tree element
- to_plain() Dict[str, str | int | None] | List[str] ¶
Returns a dictionary or list representation of the detection.
SigmaDetectionItem¶
- class sigma.rule.SigmaDetectionItem(field: str | None, modifiers: ~typing.List[~typing.Type[~sigma.modifiers.SigmaModifier]], value: ~typing.List[~sigma.types.SigmaType], value_linking: ~typing.Type[~sigma.conditions.ConditionAND] | ~typing.Type[~sigma.conditions.ConditionOR] = <class 'sigma.conditions.ConditionOR'>, source: ~sigma.exceptions.SigmaRuleLocation | None = None, auto_modifiers: dataclasses.InitVar[bool] = True)¶
Single Sigma detection definition
A detection consists of: * an optional field name * a list of value modifiers that can also be empty * the mandatory value or a list of values (internally it’s always a list of values)
By default all values are OR-linked but the ‘all’ modifier can be used to override this behavior.
If the auto_modifiers parameter is set to False, modifiers are not automatically applied to the values. This shouldn’t normally be used, but only in test scenarios.
- apply_modifiers()¶
Applies modifiers to detection and values
- disable_conversion_to_plain()¶
Mark detection item as not convertible to plain data type. This is required in cases where the value and original value get out of sync, e.g. because transformation are applied and conversion with to_plain() would yield an outdated state.
- classmethod from_mapping(key: str | None, val: List[int | float | str] | int | float | str | None, source: SigmaRuleLocation | None = None) SigmaDetectionItem ¶
Constructs SigmaDetectionItem object from a mapping between field name containing modifiers and a value. This also supports keys containing only value modifiers which results in a keyword detection.
The value accepts plain values as well as lists of values and resolves them into the value list always contained in a SigmaDetectionItem instance.
- classmethod from_value(val: List[str | int] | int | str, source: SigmaRuleLocation | None = None) SigmaDetectionItem ¶
Convenience method for from_mapping(None, value).
- is_keyword() bool ¶
Returns True if detection item is a keyword detection without field reference.
- postprocess(detections: SigmaDetections, parent: sigma.condition.ConditionItem | None = None) ConditionAND | ConditionOR | ConditionFieldEqualsValueExpression | ConditionValueExpression ¶
Minimal default postprocessing implementation for classes which don’t bring their own postprocess method. Just sets the parent and source property.
- to_plain() Dict[str, str | int | None] | List[str] ¶
Convert detection item into plain Python type, that can be:
a plain value if it is a single plain keyword value.
a list of values if it is a list of keyword values
a dict in all other cases (detection item bound to field or keyword with modifiers)
- value_linking¶
alias of
ConditionOR
SigmaRuleTag¶
- class sigma.rule.SigmaRuleTag(namespace: str, name: str, source: sigma.exceptions.SigmaRuleLocation | None = None)¶
- classmethod from_str(tag: str, source: SigmaRuleLocation | None = None) SigmaRuleTag ¶
Build SigmaRuleTag class from plain text tag string.
SigmaLevel¶
- class sigma.rule.SigmaLevel(value)¶
An enumeration.
SigmaStatus¶
- class sigma.rule.SigmaStatus(value)¶
An enumeration.
Sigma Data Types¶
SigmaString¶
- class sigma.types.SigmaString(s: str | None = None)¶
Strings in Sigma detection values containing wildcards.
- contains_placeholder(include: List[str] | None = None, exclude: List[str] | None = None) bool ¶
Check if string contains placeholders and if any placeholder name is
contained on the include list (if there is one)
not contained on the include list (if there is one)
It is sufficient that one placeholder matches these conditions. The purpose of this method is to determine if there are placeholders for further processing.
- contains_special() bool ¶
Check if string contains special characters.
- convert(escape_char: str | None = '\\', wildcard_multi: str | None = '*', wildcard_single: str | None = '?', add_escaped: str = '', filter_chars: str = '') str ¶
Convert SigmaString into a query string or pattern. The following parameters allow to change the behavior:
escape_char: the character used to escape special characters. By default these are only the wildcard characters.
wildcard_multi and wildcard_single: strings that should be output as wildcards for multiple and single characters.
add_escaped: characters which are escaped in addition to the wildcards
filter_chars: characters that are filtered out.
Setting one of the wildcard or multiple parameters to None indicates that this feature is not supported. Appearance of these characters in a string will raise a SigmaValueError.
- endswith(val: str | SpecialChars) bool ¶
Check if string ends with a given string or special character.
- insert_placeholders() SigmaString ¶
Replace %something% placeholders with Placeholder stub objects that can be later handled by the processing pipeline. This implements the expand modifier.
- replace_placeholders(callback: Callable[[Placeholder], Iterator[str | SpecialChars | Placeholder]]) List[SigmaString] ¶
Iterate over all placeholders and call the callback for each one. The callback is called with the placeholder instance as argument and yields replacement values (plain strings or SpecialChars instances). Each yielded replacement value is concatenated to the SigmaString prefix before the placeholder and the method is called recursively with the suffix after the placeholder. All placeholder replacements are combined with all returned SigmaString suffixes. Therefore, the callback could be called multiple times with the same placeholder instance and should return the same results to ensure a consistent result.
The callback can return a plain string, a SpecialChars instance (for insertion of wildcards) or a Placeholder (e.g. to keep the placeholder for later processing pipeline items).
- replace_with_placeholder(regex: Pattern, placeholder_name: str) SigmaString ¶
Replace all occurrences of string part matching regular expression with placeholder.
- Parameters:
regex (Pattern) – regular expression that should be matched.
placeholder_name (str) – name of placeholder that should be inserted.
- Returns:
Returns a string with the replacement placeholders.
- Return type:
- startswith(val: str | SpecialChars) bool ¶
Check if string starts with a given string or special character.
- to_plain(regex: bool = False) str ¶
Generate string representation of SigmaString with or without regex escaping.
- to_plain_regex()¶
Return plain string representation of SigmaString with reduced escaping.
- to_regex(custom_escaped: str = '') SigmaRegularExpression ¶
Convert SigmaString into a regular expression.
SigmaNumber¶
- class sigma.types.SigmaNumber(number: int | float)¶
Numeric value type
SigmaBool¶
- class sigma.types.SigmaBool(boolean: bool)¶
Boolean value type
SigmaNull¶
- class sigma.types.SigmaNull(dummy: Any | None = None)¶
Empty/none/null value
SigmaRegularExpression¶
- class sigma.types.SigmaRegularExpression(regexp: str, flags: ~typing.Set[~sigma.types.SigmaRegularExpressionFlag] = <factory>)¶
Regular expression type
- compile()¶
Verify if regular expression is valid by compiling it
- escape(escaped: Tuple[str] = (), escape_char: str = '\\', escape_escape_char: bool = True, flag_prefix: bool = True) str ¶
Escape strings from escaped tuple as well as escape_char itself (can be disabled with escape_escape_char) with escape_char. Prepends a (?…) expression with set flags (i, m and s) if flag_prefix is set.
SigmaCIDRExpression¶
- class sigma.types.SigmaCIDRExpression(cidr: str, source: SigmaRuleLocation | None = None)¶
CIDR IP address range expression type
- expand(wildcard: str = '*') List[str] ¶
Convert CIDR range into a list of wildcard patterns or plain CIDR notation. The following parameters allow to change the behavior:
wildcard: string that should be output as wildcard. Usually not required because this is passed to SigmaString that generates a wildcard pecial character from ‘*’ that is converted into possible individual wildcard characters.
Setting wildcard to None indicates that this feature is not need and the query language handles CIDR notation properly.
SigmaCompareExpression¶
- class sigma.types.SigmaCompareExpression(number: SigmaNumber, op: CompareOperators, source: SigmaRuleLocation | None = None)¶
Type for numeric comparison.
SigmaQueryExpression¶
- class sigma.types.SigmaQueryExpression(expr: str, id: str)¶
Special purpose type for passing a query part (e.g. list lookups in placeholders) directly into the generated query. The query string may contain a {field} placeholder, which is replaced with the field name contained in the detection item containing the query expression. This is done by the finalize method.
Because this is very specific to the target language, it has to be used in late stages of the conversion process by backend-specific processing pipelines or the backend itself.