Skip to content

Commit

Permalink
x-pack/auditbeat/module/system/socket: defend against exec with zero …
Browse files Browse the repository at this point in the history
…arguments

execve can have a zero-length argv so fall back to using /proc/comm, or path base.
  • Loading branch information
efd6 committed Feb 28, 2022
1 parent e9e86a8 commit aa7298f
Show file tree
Hide file tree
Showing 2 changed files with 25 additions and 2 deletions.
1 change: 1 addition & 0 deletions CHANGELOG.next.asciidoc
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,7 @@ https://github.com/elastic/beats/compare/v7.0.0-alpha2...main[Check the HEAD dif
*Auditbeat*

- auditd: Add error.message to events when processing fails. {pull}30009[30009]
- Fix handling of execve call events which have no argument. {issue}30585[30585] {pull}30586[30586]

*Filebeat*

Expand Down
26 changes: 24 additions & 2 deletions x-pack/auditbeat/module/system/socket/events.go
Original file line number Diff line number Diff line change
Expand Up @@ -888,6 +888,8 @@ func (e *execveCall) getProcess() *process {
if idx := bytes.IndexByte(e.Path[:], 0); idx >= 0 {
// Fast path if we already have the path.
p.path = string(e.Path[:idx])
// Keep the basename in case we can't get the process name.
p.name = filepath.Base(p.path)
} else {
// Attempt to get the path from the /prox/<pid>/exe symlink.
var err error
Expand All @@ -896,9 +898,13 @@ func (e *execveCall) getProcess() *process {
if pe, ok := err.(*os.PathError); ok && strings.Contains(pe.Path, "(deleted)") {
// Keep the deleted path from the PathError.
p.path = pe.Path
// Keep the basename in case we can't get the process name.
p.name = filepath.Base(strings.TrimSuffix(p.path, " (deleted)"))
} else {
// Fallback to the truncated path.
p.path = string(e.Path[:]) + " ..."
// Don't trim the ellipsis to indicate this may be incorrect.
p.name = filepath.Base(p.path)
}
}
}
Expand Down Expand Up @@ -943,8 +949,24 @@ func (e *execveCall) getProcess() *process {
}
}

// Get name from first argument.
p.name = filepath.Base(p.args[0])
// Carefully get the process name; we may have zero arguments.
if len(p.args) != 0 {
// Get name from first argument.
p.name = filepath.Base(p.args[0])
} else {
// Attempt to get name from /proc/<pid>/comm — only available since 2.6.33.
comm, err := os.ReadFile(fmt.Sprintf("/proc/%d/comm", e.Meta.PID))
if err == nil {
p.name = strings.TrimRight(string(comm), "\x00")
if len(p.name) == 16 {
// The name may have been truncated if it is TASK_COMM_LEN long.
p.name += "..."
}
} else if p.name == "" {
// This should never happen.
p.name = "(unknown)"
}
}

if e.creds != nil {
p.hasCreds = true
Expand Down

0 comments on commit aa7298f

Please # to comment.