A hands-on challenge to understand Sigma rule structure and detection logic.
The case is a single Sigma rule, not a compromised host, so the work is reading detection logic rather than hunting an intruder. The rule watches Windows endpoint telemetry for the Background Intelligent Transfer Service command-line client being used to pull a file down. It matches on the binary’s path or its original PE name, then on either a one-shot transfer switch or a create-plus-HTTP combination, and it records the command line and parent command line for the analyst. Its tags place the behaviour under two ATT&CK tactics and point at the BITS Jobs technique, which is how this service is abused in real intrusions.
proc_creation_win_bitsadmin_download.yml → open in any text editor or read with cat. Plain YAML, no tooling neededFormat note: Every task shows a masked answer pattern (asterisks for letters, literal punctuation). Match the pattern’s length and punctuation, since the rule’s strings are copied exactly as they appear in the YAML.
Start with the logsource block. It has a category and a product, and the category is the generic Sigma event class the backend maps to a concrete log source such as Sysmon Event ID 1 or Security 4688. It names an event class, not a specific channel.
grep -A2 '^logsource' proc_creation_win_bitsadmin_download.yml
In detection, the selection_img block is a list with two entries, an Image|endswith match and an OriginalFileName match. Both resolve to the same binary, so the second entry catches a renamed copy that the path match would miss.
grep -A3 'selection_img' proc_creation_win_bitsadmin_download.yml
selection_cmd is a single CommandLine|contains test with the value wrapped in spaces. That makes it the standalone path to a match: image plus this one switch is enough, no other selection required.
grep -A1 'selection_cmd' proc_creation_win_bitsadmin_download.yml
selection_cli_1 holds two alternative substrings, one for starting a job and one for attaching a file to it. The question asks for the one that creates the transfer. This selection only matters in combination with selection_cli_2, never alone.
grep -A3 'selection_cli_1' proc_creation_win_bitsadmin_download.yml
Gotcha: The list has two entries, so don’t answer with the file-attachment switch. The question asks about creating the job.
selection_cli_2 is the second half of the multi-step pattern. It tests CommandLine|contains for a bare scheme prefix with no colon or slashes, so one short string covers both the plain and the TLS form.
grep -A1 'selection_cli_2' proc_creation_win_bitsadmin_download.yml
Read the condition line as a tree. The image selection is mandatory. Beyond that, either the one-shot switch hits, or every selection whose name starts with selection_cli_ hits, which means both the job-creation test and the HTTP test. The all of wildcard is what ties the two cli selections together.
grep condition proc_creation_win_bitsadmin_download.yml
Tip: Copy the line as written, including the parentheses and the trailing wildcard. The format mask in the task mirrors it character for character.
The fields block lists what the alert should surface for the analyst. Two entries appear, one for the process itself and one for its parent. The first is the one that shows the command being executed.
grep -A3 '^fields' proc_creation_win_bitsadmin_download.yml
The tags list mixes tactic tags, technique IDs and a software ID. Tactics use the bare tactic name after attack., so only the first entry fits, and the hyphenated form is how Sigma writes multi-word tactics. A persistence tag follows it, and the technique tag points at BITS Jobs.
grep -A6 '^tags' proc_creation_win_bitsadmin_download.yml
| Phase | Action |
|---|---|
| Execution of BITS client | A BITS job is created or a transfer is started through the built-in command-line client to pull a file over HTTP |
| Persistence | BITS jobs can outlive the initial command, which is why the rule also carries a persistence tag |
No host or network indicators exist in this case. The rule’s match strings are the observables it hunts for.
| Type | Value |
|---|---|
| Process image | \bitsadmin.exe (also matched by original PE name) |
| Command-line substrings | /transfer, /create, /addfile, http |
| Technique | ID | Description |
|---|---|---|
| BITS Jobs | T1197 | Downloading a file through the BITS command-line client |
| Masquerading: Rename System Utilities | T1036.003 | Covered by the OriginalFileName match, which catches a renamed copy of the client |
Match on original file name as well as path. The image selection pairs an Image|endswith test with an OriginalFileName test. Renaming the binary defeats the first and not the second, so any rule for a living-off-the-land binary should carry both, and your telemetry must populate the original-name field (Sysmon Event ID 1 does).
Understand which branch of the condition fires. A command with the one-shot transfer switch matches on its own. The job-creation route only matches when the command line also contains the HTTP substring, so a job created against a non-HTTP source and populated in a later command would not satisfy that branch. Test the rule against the real command shapes in your environment.
Substring matches on padded strings are brittle. The switch tests include a leading and trailing space, so a switch at the very end of a command line or separated by other whitespace could slip past. Pair this rule with one that watches BITS activity from a second angle.
Tune for the stated false positives. The rule is rated medium and warns that some legitimate applications use the tool. Baseline which parents normally launch it, which is exactly why the rule outputs the parent command line.
One short YAML file carries a complete detection: a log source, a path-or-original-name image filter, two routes to a match, and the output fields an analyst needs. Reading the
conditionline first and then each named selection is the fastest way to understand any Sigma rule.