Skip to content

Commit

Permalink
Imporving fileless execution detection and removing paths from senset…
Browse files Browse the repository at this point in the history
…ive paths

Signed-off-by: Amit Schendel <[email protected]>
  • Loading branch information
amitschendel committed Feb 20, 2025
1 parent 963c7ef commit 7533b2e
Show file tree
Hide file tree
Showing 5 changed files with 42 additions and 30 deletions.
4 changes: 0 additions & 4 deletions pkg/ruleengine/v1/helpers.go
Original file line number Diff line number Diff line change
Expand Up @@ -20,10 +20,6 @@ import (
// SensitiveFiles is a list of sensitive files that should not be accessed by the application unexpectedly.
var SensitiveFiles = []string{
"/etc/shadow",
"/etc/sudoers",
"/etc/ssh/sshd_config",
"/etc/ssh/ssh_config",
"/etc/pam.d",
}

var (
Expand Down
1 change: 0 additions & 1 deletion pkg/ruleengine/v1/r1000_exec_from_malicious_source.go
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,6 @@ func (rule *R1000ExecFromMaliciousSource) ProcessEvent(eventType utils.EventType

var maliciousExecPathPrefixes = []string{
"/dev/shm",
"/proc/self",
}

execPath := GetExecFullPathFromEvent(execEvent)
Expand Down
40 changes: 33 additions & 7 deletions pkg/ruleengine/v1/r1000_exec_from_malicious_source_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -39,13 +39,6 @@ func TestR1000ExecFromMaliciousSource(t *testing.T) {
t.Errorf("Expected ruleResult to be nil since test is not a malicious exec")
}

e.Comm = "/proc/self/fd/3"

ruleResult = r.ProcessEvent(utils.ExecveEventType, e, &RuleObjectCacheMock{})
if ruleResult == nil {
t.Errorf("Expected ruleResult since exec is malicious")
}

e.Cwd = "/"

e.Comm = "/run.sh"
Expand Down Expand Up @@ -90,4 +83,37 @@ func TestR1000ExecFromMaliciousSource(t *testing.T) {
if ruleResult == nil {
t.Errorf("Expected ruleResult since exec is malicious")
}

// Create an exec event simulating the motd scenario
e = &events.ExecEvent{
Event: tracerexectype.Event{
Event: eventtypes.Event{
CommonData: eventtypes.CommonData{
K8s: eventtypes.K8sMetadata{
BasicK8sMetadata: eventtypes.BasicK8sMetadata{
ContainerName: "test",
},
},
},
},
Comm: "50-motd-news",
Args: []string{"/bin/sh", "/etc/update-motd.d/50-motd-news", "--force"},
ExePath: "/bin/sh", // The actual executable
Cwd: "/",
},
}

// This should not trigger a rule failure
ruleResult = r.ProcessEvent(utils.ExecveEventType, e, &RuleObjectCacheMock{})
if ruleResult != nil {
t.Errorf("Got false positive alert for legitimate motd execution:\nCwd: %s\nExePath: %s\nArgs: %v",
e.Cwd, e.ExePath, e.Args)
}

// For comparison, test a real malicious case
e.ExePath = "/dev/shm/malicious"
ruleResult = r.ProcessEvent(utils.ExecveEventType, e, &RuleObjectCacheMock{})
if ruleResult == nil {
t.Errorf("Failed to detect actually malicious execution from /dev/shm")
}
}
6 changes: 5 additions & 1 deletion pkg/ruleengine/v1/r1005_fileless_execution.go
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,10 @@ func (rule *R1005FilelessExecution) ProcessEvent(eventType utils.EventType, even
}

func (rule *R1005FilelessExecution) handleExecveEvent(execEvent *events.ExecEvent) ruleengine.RuleFailure {
if !strings.Contains(execEvent.ExePath, "memfd") {
return nil
}

execFullPath := GetExecFullPathFromEvent(execEvent)
execPathDir := filepath.Dir(execFullPath)

Expand Down Expand Up @@ -111,7 +115,7 @@ func (rule *R1005FilelessExecution) handleExecveEvent(execEvent *events.ExecEven
},
TriggerEvent: execEvent.Event.Event,
RuleAlert: apitypes.RuleAlert{
RuleDescription: fmt.Sprintf("Fileless execution detected: exec call \"%s\" is from a malicious source \"/proc/*/fd\"", execPathDir),
RuleDescription: fmt.Sprintf("Fileless execution detected: exec call \"%s\" is from a malicious source %s", execPathDir, execEvent.ExePath),
},
RuntimeAlertK8sDetails: apitypes.RuntimeAlertK8sDetails{
PodName: execEvent.GetPod(),
Expand Down
21 changes: 4 additions & 17 deletions pkg/ruleengine/v1/r1005_fileless_execution_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ func TestHandleExecveEvent(t *testing.T) {
t.Run("Test with /proc/self/fd prefix", func(t *testing.T) {
event := &tracerexectype.Event{
Cwd: "/proc/self/fd",
ExePath: "memfd:",
UpperLayer: false,
Ppid: 123,
Pcomm: "test",
Expand All @@ -30,23 +31,7 @@ func TestHandleExecveEvent(t *testing.T) {
t.Run("Test with /proc/<pid>/fd pattern", func(t *testing.T) {
event := &tracerexectype.Event{
Cwd: "/proc/1/fd/7",
UpperLayer: false,
Ppid: 123,
Pcomm: "test",
Comm: "test",
Gid: 123,
Pid: 123,
Uid: 123,
}
execEvent := events.ExecEvent{Event: *event}
result := rule.handleExecveEvent(&execEvent)
assert.NotNil(t, result)
})

t.Run("Test with /proc/<pid>/fd in ExePath", func(t *testing.T) {
event := &tracerexectype.Event{
Cwd: "/normal/path",
ExePath: "/proc/1234/fd/3",
ExePath: "memfd:",
UpperLayer: false,
Ppid: 123,
Pcomm: "test",
Expand Down Expand Up @@ -111,6 +96,7 @@ func TestHandleExecveEvent(t *testing.T) {
t.Run("Test with absolute path", func(t *testing.T) {
event := &tracerexectype.Event{
Cwd: "/absolute/path",
ExePath: "memfd:",
UpperLayer: false,
Ppid: 123,
Pcomm: "test",
Expand All @@ -127,6 +113,7 @@ func TestHandleExecveEvent(t *testing.T) {
t.Run("Test with deep /proc/<pid>/fd nested path", func(t *testing.T) {
event := &tracerexectype.Event{
Cwd: "/proc/12345/fd/123/nested/path",
ExePath: "memfd:",
UpperLayer: false,
Ppid: 123,
Pcomm: "test",
Expand Down

0 comments on commit 7533b2e

Please sign in to comment.