Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: remove default usage of parse-arguments #4331

Merged
merged 6 commits into from
Oct 9, 2024

Conversation

geyslan
Copy link
Member

@geyslan geyslan commented Sep 26, 2024

Close: #2177

1. Explain what the PR does

47451f5 feat(cmd): disable arg parsing by default
cb48e1f fix: possible overwrite of Args on Derive stage
3cfe5c5 chore(ebpf): copy event before parsing it
0fce183 feat(rego): parse event arguments in sig
ec478cc feat(sigs): refactor to use nonparsed arguments
ddc219a chore(go.mod): bump sig helpers to 0b23713

3cfe5c5 chore(ebpf): copy event before parsing it

Refactor 'event feeding to engine' logic to copy the event before
parsing it, cloning its arguments.

0fce183 feat(rego): parse event arguments in sig

Removing default argument parsing will break rego signatures, whose
implementation depends on parsed arguments. In order to keep the option
of readability in REGO signatures, events will be parsed by default in
the context of evaluating these kind of signatures.
This will also ensure that they will not be broken depending on the
selection of parse-arguments.

Co-authored-by: Geyslan Gregório <geyslan@gmail.com>

ec478cc feat(sigs): refactor to use nonparsed arguments

Co-authored-by: Geyslan Gregório <geyslan@gmail.com>

2. Explain how to test it

-e ptrace -o json

{"timestamp":1727372470993574813,"threadStartTime":1727372470988592715,"processorId":30,"processId":250996,"cgroupId":15795,"threadId":250996,"parentProcessId":250785,"hostProcessId":250996,"hostThreadId":250996,"hostParentProcessId":250785,"userId":1000,"mountNamespace":4026531841,"pidNamespace":4026531836,"processName":"strace","executable":{"path":""},"hostName":"hb0","containerId":"","container":{},"kubernetes":{},"eventId":"101","eventName":"ptrace","matchedPolicies":[""],"argsNum":4,"returnValue":0,"syscall":"ptrace","stackAddresses":null,"contextFlags":{"containerStarted":false,"isCompat":false},"threadEntityId":1253568537,"processEntityId":1253568537,"parentEntityId":1331977861,"args":[{"name":"request","type":"long","value":24},{"name":"pid","type":"pid_t","value":250999},{"name":"addr","type":"void*","value":0},{"name":"data","type":"void*","value":0}]}

-e ptrace -o json -o option:parse-arguments

{"timestamp":1727372519574101498,"threadStartTime":1727372519569629604,"processorId":2,"processId":252379,"cgroupId":15795,"threadId":252379,"parentProcessId":250785,"hostProcessId":252379,"hostThreadId":252379,"hostParentProcessId":250785,"userId":1000,"mountNamespace":4026531841,"pidNamespace":4026531836,"processName":"strace","executable":{"path":""},"hostName":"hb0","containerId":"","container":{},"kubernetes":{},"eventId":"101","eventName":"ptrace","matchedPolicies":[""],"argsNum":4,"returnValue":0,"syscall":"ptrace","stackAddresses":null,"contextFlags":{"containerStarted":false,"isCompat":false},"threadEntityId":611073971,"processEntityId":611073971,"parentEntityId":1331977861,"args":[{"name":"request","type":"string","value":"PTRACE_SYSCALL"},{"name":"pid","type":"pid_t","value":252382},{"name":"addr","type":"void*","value":"0x0"},{"name":"data","type":"void*","value":"0x0"}]}

-e ptrace,anti_debugging -o json

{"timestamp":1727372566359065181,"threadStartTime":1727372566357715045,"processorId":23,"processId":253398,"cgroupId":15795,"threadId":253398,"parentProcessId":250785,"hostProcessId":253398,"hostThreadId":253398,"hostParentProcessId":250785,"userId":1000,"mountNamespace":4026531841,"pidNamespace":4026531836,"processName":"strace","executable":{"path":""},"hostName":"hb0","containerId":"","container":{},"kubernetes":{},"eventId":"101","eventName":"ptrace","matchedPolicies":[""],"argsNum":4,"returnValue":80,"syscall":"ptrace","stackAddresses":null,"contextFlags":{"containerStarted":false,"isCompat":false},"threadEntityId":1514910604,"processEntityId":1514910604,"parentEntityId":1331977861,"args":[{"name":"request","type":"long","value":16910},{"name":"pid","type":"pid_t","value":253400},{"name":"addr","type":"void*","value":88},{"name":"data","type":"void*","value":140729822389936}]}
{"timestamp":1727372566359036587,"threadStartTime":1727372566359015597,"processorId":18,"processId":253400,"cgroupId":15795,"threadId":253400,"parentProcessId":253398,"hostProcessId":253400,"hostThreadId":253400,"hostParentProcessId":253398,"userId":1000,"mountNamespace":4026531841,"pidNamespace":4026531836,"processName":"strace","executable":{"path":""},"hostName":"hb0","containerId":"","container":{},"kubernetes":{},"eventId":"6018","eventName":"anti_debugging","matchedPolicies":[""],"argsNum":1,"returnValue":0,"syscall":"ptrace","stackAddresses":null,"contextFlags":{"containerStarted":false,"isCompat":false},"threadEntityId":3776954121,"processEntityId":3776954121,"parentEntityId":1514910604,"args":[{"name":"triggeredBy","type":"unknown","value":{"args":[{"name":"request","type":"long","value":0},{"name":"pid","type":"pid_t","value":0},{"name":"addr","type":"void*","value":0},{"name":"data","type":"void*","value":0}],"id":101,"name":"ptrace","returnValue":0}}],"metadata":{"Version":"1","Description":"A process used anti-debugging techniques to block a debugger. Malware use anti-debugging to stay invisible and inhibit analysis of their behavior.","Tags":null,"Properties":{"Category":"defense-evasion","Kubernetes_Technique":"","Severity":1,"Technique":"Debugger Evasion","external_id":"T1622","id":"attack-pattern--e4dc8c01-417f-458d-9ee0-bb0617c1b391","signatureID":"TRC-102","signatureName":"Anti-Debugging detected"}}}

-e ptrace,anti_debugging -o json -o option:parse-arguments

{"timestamp":1727372641521767935,"threadStartTime":1727372641521707790,"processorId":3,"processId":254357,"cgroupId":15795,"threadId":254357,"parentProcessId":254355,"hostProcessId":254357,"hostThreadId":254357,"hostParentProcessId":254355,"userId":1000,"mountNamespace":4026531841,"pidNamespace":4026531836,"processName":"strace","executable":{"path":""},"hostName":"hb0","containerId":"","container":{},"kubernetes":{},"eventId":"101","eventName":"ptrace","matchedPolicies":[""],"argsNum":4,"returnValue":0,"syscall":"ptrace","stackAddresses":null,"contextFlags":{"containerStarted":false,"isCompat":false},"threadEntityId":991543686,"processEntityId":991543686,"parentEntityId":706525229,"args":[{"name":"request","type":"string","value":"PTRACE_TRACEME"},{"name":"pid","type":"pid_t","value":0},{"name":"addr","type":"void*","value":"0x0"},{"name":"data","type":"void*","value":"0x0"}]}
{"timestamp":1727372641521767935,"threadStartTime":1727372641521707790,"processorId":3,"processId":254357,"cgroupId":15795,"threadId":254357,"parentProcessId":254355,"hostProcessId":254357,"hostThreadId":254357,"hostParentProcessId":254355,"userId":1000,"mountNamespace":4026531841,"pidNamespace":4026531836,"processName":"strace","executable":{"path":""},"hostName":"hb0","containerId":"","container":{},"kubernetes":{},"eventId":"6018","eventName":"anti_debugging","matchedPolicies":[""],"argsNum":1,"returnValue":0,"syscall":"ptrace","stackAddresses":null,"contextFlags":{"containerStarted":false,"isCompat":false},"threadEntityId":991543686,"processEntityId":991543686,"parentEntityId":706525229,"args":[{"name":"triggeredBy","type":"unknown","value":{"args":[{"name":"request","type":"long","value":0},{"name":"pid","type":"pid_t","value":0},{"name":"addr","type":"void*","value":0},{"name":"data","type":"void*","value":0}],"id":101,"name":"ptrace","returnValue":0}}],"metadata":{"Version":"1","Description":"A process used anti-debugging techniques to block a debugger. Malware use anti-debugging to stay invisible and inhibit analysis of their behavior.","Tags":null,"Properties":{"Category":"defense-evasion","Kubernetes_Technique":"","Severity":1,"Technique":"Debugger Evasion","external_id":"T1622","id":"attack-pattern--e4dc8c01-417f-458d-9ee0-bb0617c1b391","signatureID":"TRC-102","signatureName":"Anti-Debugging detected"}}}

-e clone -o json

{"timestamp":1727373613518714532,"threadStartTime":1727359148914395690,"processorId":18,"processId":56508,"cgroupId":13230,"threadId":56508,"parentProcessId":16017,"hostProcessId":56508,"hostThreadId":56508,"hostParentProcessId":16017,"userId":1000,"mountNamespace":4026531841,"pidNamespace":4026531836,"processName":"Isolated Web Co","executable":{"path":""},"hostName":"hb0","containerId":"","container":{},"kubernetes":{},"eventId":"56","eventName":"clone","matchedPolicies":[""],"argsNum":5,"returnValue":266682,"syscall":"clone","stackAddresses":null,"contextFlags":{"containerStarted":false,"isCompat":false},"threadEntityId":1636448302,"processEntityId":1636448302,"parentEntityId":77461819,"args":[{"name":"flags","type":"unsigned long","value":4001536},{"name":"stack","type":"void*","value":139882651930416},{"name":"parent_tid","type":"int*","value":139882651933072},{"name":"child_tid","type":"int*","value":139882651933072},{"name":"tls","type":"unsigned long","value":139882651932352}]}

-e clone -o json -o option:parse-arguments

{"timestamp":1727373700925146906,"threadStartTime":1727373700925174018,"processorId":2,"processId":17283,"cgroupId":13230,"threadId":267890,"parentProcessId":16017,"hostProcessId":17283,"hostThreadId":267890,"hostParentProcessId":16017,"userId":1000,"mountNamespace":4026531841,"pidNamespace":4026531836,"processName":"Isolated Web Co","executable":{"path":""},"hostName":"hb0","containerId":"","container":{},"kubernetes":{},"eventId":"56","eventName":"clone","matchedPolicies":[""],"argsNum":5,"returnValue":0,"syscall":"clone","stackAddresses":null,"contextFlags":{"containerStarted":false,"isCompat":false},"threadEntityId":691270545,"processEntityId":3906119074,"parentEntityId":77461819,"args":[{"name":"flags","type":"string","value":"CLONE_VM|CLONE_FS|CLONE_FILES|CLONE_SIGHAND|CLONE_THREAD|CLONE_SYSVSEM|CLONE_SETTLS|CLONE_PARENT_SETTID|CLONE_CHILD_CLEARTID"},{"name":"stack","type":"void*","value":"0x7f096eb7cf30"},{"name":"parent_tid","type":"int*","value":"0x7f096eb7d990"},{"name":"child_tid","type":"int*","value":"0x7f096eb7d990"},{"name":"tls","type":"unsigned long","value":139678488975040}]}

Analyze mode (requires events with raw args)

-e ptrace -o json:output.json
analyze -e anti_debugging output.json

{"level":"info","ts":1728558831.3532736,"msg":"Signatures loaded","total":1,"signatures":["Anti-Debugging detected"]}
{"timestamp":1728622986623810048,"threadStartTime":1728622986623762297,"processorId":6,"processId":531875,"cgroupId":20475,"threadId":531875,"parentProcessId":531873,"hostProcessId":531875,"hostThreadId":531875,"hostParentProcessId":531873,"userId":1000,"mountNamespace":4026531841,"pidNamespace":4026531836,"processName":"strace","executable":{"path":""},"hostName":"hb0","containerId":"","container":{},"kubernetes":{},"eventId":"6000","eventName":"anti_debugging","argsNum":1,"returnValue":0,"syscall":"ptrace","stackAddresses":null,"contextFlags":{"containerStarted":false,"isCompat":false},"threadEntityId":2721268392,"processEntityId":2721268392,"parentEntityId":2984027261,"args":[{"name":"triggeredBy","type":"unknown","value":{"args":[{"name":"request","type":"long","value":0},{"name":"pid","type":"pid_t","value":0},{"name":"addr","type":"void*","value":0},{"name":"data","type":"void*","value":0}],"id":101,"name":"ptrace","returnValue":0}}],"metadata":{"Version":"1","Description":"A process used anti-debugging techniques to block a debugger. Malware use anti-debugging to stay invisible and inhibit analysis of their behavior.","Tags":null,"Properties":{"Category":"defense-evasion","Kubernetes_Technique":"","Severity":1,"Technique":"Debugger Evasion","external_id":"T1622","id":"attack-pattern--e4dc8c01-417f-458d-9ee0-bb0617c1b391","signatureID":"TRC-102","signatureName":"Anti-Debugging detected"}}}

3. Other comments

go.mod Outdated Show resolved Hide resolved
@geyslan geyslan marked this pull request as ready for review September 26, 2024 18:16
@geyslan geyslan force-pushed the nondefault_parse_args branch 2 times, most recently from 10f7b81 to f5a2cc5 Compare September 27, 2024 00:02
pkg/ebpf/signature_engine.go Show resolved Hide resolved
NDStrahilevitz and others added 6 commits October 9, 2024 18:04
Co-authored-by: Geyslan Gregório <geyslan@gmail.com>
Removing default argument parsing will break rego signatures, whose
implementation depends on parsed arguments. In order to keep the option
of readability in REGO signatures, events will be parsed by default in
the context of evaluating these kind of signatures.
This will also ensure that they will not be broken depending on the
selection of parse-arguments.

Co-authored-by: Geyslan Gregório <geyslan@gmail.com>
Refactor 'event feeding to engine' logic to copy the event before
parsing it, cloning its arguments.
@geyslan geyslan force-pushed the nondefault_parse_args branch from a0de6c0 to 47451f5 Compare October 9, 2024 21:05
@geyslan
Copy link
Member Author

geyslan commented Oct 9, 2024

/fast-forward

@github-actions github-actions bot merged commit 47451f5 into aquasecurity:main Oct 9, 2024
31 checks passed
@geyslan
Copy link
Member Author

geyslan commented Oct 10, 2024

Addendum:

Analyze mode (requires events with raw args)

-e ptrace -o json:output.json
analyze -e anti_debugging output.json

{"level":"info","ts":1728558831.3532736,"msg":"Signatures loaded","total":1,"signatures":["Anti-Debugging detected"]}
{"timestamp":1728622986623810048,"threadStartTime":1728622986623762297,"processorId":6,"processId":531875,"cgroupId":20475,"threadId":531875,"parentProcessId":531873,"hostProcessId":531875,"hostThreadId":531875,"hostParentProcessId":531873,"userId":1000,"mountNamespace":4026531841,"pidNamespace":4026531836,"processName":"strace","executable":{"path":""},"hostName":"hb0","containerId":"","container":{},"kubernetes":{},"eventId":"6000","eventName":"anti_debugging","argsNum":1,"returnValue":0,"syscall":"ptrace","stackAddresses":null,"contextFlags":{"containerStarted":false,"isCompat":false},"threadEntityId":2721268392,"processEntityId":2721268392,"parentEntityId":2984027261,"args":[{"name":"triggeredBy","type":"unknown","value":{"args":[{"name":"request","type":"long","value":0},{"name":"pid","type":"pid_t","value":0},{"name":"addr","type":"void*","value":0},{"name":"data","type":"void*","value":0}],"id":101,"name":"ptrace","returnValue":0}}],"metadata":{"Version":"1","Description":"A process used anti-debugging techniques to block a debugger. Malware use anti-debugging to stay invisible and inhibit analysis of their behavior.","Tags":null,"Properties":{"Category":"defense-evasion","Kubernetes_Technique":"","Severity":1,"Technique":"Debugger Evasion","external_id":"T1622","id":"attack-pattern--e4dc8c01-417f-458d-9ee0-bb0617c1b391","signatureID":"TRC-102","signatureName":"Anti-Debugging detected"}}}

Comment on lines +621 to +622
// Parse args here if the rule engine is NOT enabled (parsed there if it is).
if t.config.Output.ParseArguments && !t.config.EngineConfig.Enabled {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Does this still hold?
If I understand correctly, parse arguments is no longer "always on" when the rule engine is enabled.
So shouldn't the condition be if t.config.Output.ParseArguments only?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

TODO: #4368

Comment on lines +84 to +89
if t.config.Output.ParseArguments {
// shallow clone the event arguments before parsing them (new slice is created),
// to keep the eventCopy with raw arguments.
eventCopy.Args = slices.Clone(event.Args)

err := t.parseArguments(event)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why do we need to parse the arguments here anyway?

  1. If signatures are now using raw arguments - won't this be a bug?
  2. Shouldn't we leave data parsing to the sink stage?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agree with you, but we still need it here until the internal migration is finalised.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we have a "todo" opened so we won't forget to remove it once finalised?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

TODO: #4368

pkg/events/derive/derive.go Show resolved Hide resolved
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Remove need for parse-arguments
3 participants