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

aucoalesce: CoalesceMessages fails with "missing syscall message in compound event" #127

Open
stephen-fox opened this issue Feb 16, 2023 · 3 comments · May be fixed by #148
Open

aucoalesce: CoalesceMessages fails with "missing syscall message in compound event" #127

stephen-fox opened this issue Feb 16, 2023 · 3 comments · May be fixed by #148
Labels
bug Team:Security-External Integrations Label for the Security External Integrations team

Comments

@stephen-fox
Copy link

Hello,

While experimenting with this library on flatcar Linux, I noticed that the aucoalesce.CoalesceMessages function returns the following error when it encounters certain audit events: missing syscall message in compound event

If I supply the same events to the aureport tool (installed as a part of auditd package on Ubuntu), it appears to successfully parse those events - at least in the sense it does not produce error messages or exit with a non-zero status. It looks like commit 666ff1c introduced the formerly-mentioned error - but it does not reference any Linux audit documentation or code that contextualizes the check.

tl;dr - I am not sure if this check is required - or if the audit logs I happened to encounter are just broken. Any kind of guidance would be appreciated :)

Below are the three audit events and the aureport stderr/out for them. For reference, the --debug argument should result in error messages if any events cannot be parsed and -e generates a report about events:

Failure 1

root@x:~# cat avc-failure-audit.log
type=AVC msg=audit(1668179838.476:649407): avc:  denied  { search } for  pid=4059486 comm="cephcsi" name="crypto" dev="proc" ino=475090959 scontext=system_u:system_r:svirt_lxc_net_t:s0:c222,c955 tcontext=system_u:object_r:sysctl_crypto_t:s0 tclass=dir permissive=1
type=AVC msg=audit(1668179838.476:649407): avc:  denied  { read } for  pid=4059486 comm="cephcsi" name="fips_enabled" dev="proc" ino=475090960 scontext=system_u:system_r:svirt_lxc_net_t:s0:c222,c955 tcontext=system_u:object_r:sysctl_crypto_t:s0 tclass=file permissive=1
type=AVC msg=audit(1668179838.476:649407): avc:  denied  { open } for  pid=4059486 comm="cephcsi" path="/proc/sys/crypto/fips_enabled" dev="proc" ino=475090960 scontext=system_u:system_r:svirt_lxc_net_t:s0:c222,c955 tcontext=system_u:object_r:sysctl_crypto_t:s0 tclass=file permissive=1
root@x:~# aureport -if avc-failure-audit.log --debug -e 

Event Report
===================================
# date time event type auid success
===================================
1. 11/11/2022 15:17:18 649407 AVC -2 no
root@x:~# echo $?
0

Failure 2

root@x:~# cat execve-uname-failure-audit.log
type=EXECVE msg=audit(1671230062.742:657491): argc=2 a0="uname" a1="-p"
type=CWD msg=audit(1671230062.742:657491): cwd="/root"
type=PATH msg=audit(1671230062.742:657491): item=0 name="/usr/bin/uname" inode=76040 dev=fe:00 mode=0100755 ouid=0 ogid=0 rdev=00:00 obj=system_u:object_r:unlabeled_t:s0 nametype=NORMAL cap_fp=0 cap_fi=0 cap_fe=0 cap_fver=0 cap_frootid=0
type=PATH msg=audit(1671230062.742:657491): item=1 name="/lib64/ld-linux-x86-64.so.2" inode=98548 dev=fe:00 mode=0100755 ouid=0 ogid=0 rdev=00:00 obj=system_u:object_r:unlabeled_t:s0 nametype=NORMAL cap_fp=0 cap_fi=0 cap_fe=0 cap_fver=0 cap_frootid=0
type=PROCTITLE msg=audit(1671230062.742:657491): proctitle=756E616D65002D70
root@x:~# aureport -if execve-uname-failure-audit.log --debug -e

Event Report
===================================
# date time event type auid success
===================================
1. 12/16/2022 22:34:22 657491 EXECVE -2 unset
root@x:~# echo $?
0

Failure 3

root@x:~# cat execve-ethtool-failure-audit.log
type=EXECVE msg=audit(1671230063.745:657579): argc=3 a0="/usr/sbin/ethtool" a1="-T" a2="lxc61be96845005"
type=CWD msg=audit(1671230063.745:657579): cwd="/root"
type=PATH msg=audit(1671230063.745:657579): item=0 name="/usr/sbin/ethtool" inode=162594 dev=fe:00 mode=0100755 ouid=0 ogid=0 rdev=00:00 obj=system_u:object_r:unlabeled_t:s0 nametype=NORMAL cap_fp=0 cap_fi=0 cap_fe=0 cap_fver=0 cap_frootid=0
type=PATH msg=audit(1671230063.745:657579): item=1 name="/lib64/ld-linux-x86-64.so.2" inode=98548 dev=fe:00 mode=0100755 ouid=0 ogid=0 rdev=00:00 obj=system_u:object_r:unlabeled_t:s0 nametype=NORMAL cap_fp=0 cap_fi=0 cap_fe=0 cap_fver=0 cap_frootid=0
type=PROCTITLE msg=audit(1671230063.745:657579): proctitle=2F7573722F7362696E2F657468746F6F6C002D54006C7863363162653936383435303035
root@x:~# aureport -if execve-ethtool-failure-audit.log --debug -e

Event Report
===================================
# date time event type auid success
===================================
1. 12/16/2022 22:34:23 657579 EXECVE -2 unset
root@x:~# echo $?
0

Other notes

I commented out the code that returns the error and tried running the project's Go tests with go test ./.... The tests ran successfully. Based on the test result and the error being generated with errors.New - it appears to be both untested and not programmatically checkable (e.g., errors.As).

@drewr
Copy link

drewr commented Mar 6, 2023

👋 @v1v @andrewkroh!! I work with @stephen-fox. Think you could give this a quick look and see what may be involved here? We could maybe contribute a fix for it. Thanks!

@andrewkroh
Copy link
Member

Hi @drewr 😄 , it looks like the assumption that a type=SYSCALL message is always present when there is more than one message with the same sequence number may be wrong. This assumption looks particularly wrong with respect to failure case 1 where you have multiple AVC messages which will not be tied in with a particular syscall.

For failure cases 2 and 3, what auditd rules were used to generate those groups of messages? If you were auditing execve then I would have expected one type=SYSCALL along with the others. It is possible to have a filter applied that could have discarded that SYSCALL message, but I would say to not do that.

I think it should possible to relax the requirement on having a type=SYSCALL when there is more than one message and still have today's test cases pass.

One other problem I see is with failure case 1. Normally the key/value pairs are dumped into the data map, but with three of the same message types there will be key collisions. So perhaps special handling will be required for AVC message (like we have for type=PATH). The same issue popped up for type=NETFILTER_CFG in #71 and it has not been addressed.

@stephen-fox
Copy link
Author

Hi @andrewkroh! Thank you for the explanation. All three examples came from a single computer that has the following /etc/audit/audit.rules:

## This file is automatically generated from /etc/audit/rules.d
-D
-b 32768
-f 1
--backlog_wait_time 60000
--loginuid-immutable
-a always,exit -F arch=b32 -S init_module,finit_module -F key=module-load
-a always,exit -F arch=b64 -S init_module,finit_module -F key=module-load
-a always,exit -F arch=b32 -S delete_module -F key=module-unload
-a always,exit -F arch=b64 -S delete_module -F key=module-unload 
-a always,exit -F arch=b32 -S openat,open_by_handle_at -F a2&03 -F path=/etc/passwd -F auid>=1000 -F auid!=unset -F key=user-modify
-a always,exit -F arch=b64 -S openat,open_by_handle_at -F a2&03 -F path=/etc/passwd -F auid>=1000 -F auid!=unset -F key=user-modify
-a always,exit -F arch=b32 -S openat,open_by_handle_at -F a2&03 -F path=/etc/passwd -F auid=500 -F auid!=unset -F key=user-modify
-a always,exit -F arch=b64 -S openat,open_by_handle_at -F a2&03 -F path=/etc/passwd -F auid=500 -F auid!=unset -F key=user-modify
-a always,exit -F arch=b32 -S open -F a1&03 -F path=/etc/passwd -F auid>=1000 -F auid!=unset -F key=user-modify
-a always,exit -F arch=b64 -S open -F a1&03 -F path=/etc/passwd -F auid>=1000 -F auid!=unset -F key=user-modify
-a always,exit -F arch=b32 -S open -F a1&03 -F path=/etc/passwd -F auid=500 -F auid!=unset -F key=user-modify
-a always,exit -F arch=b64 -S open -F a1&03 -F path=/etc/passwd -F auid=500 -F auid!=unset -F key=user-modify
-a always,exit -F arch=b32 -S openat,open_by_handle_at -F a2&03 -F path=/etc/shadow -F auid>=1000 -F auid!=unset -F key=user-modify
-a always,exit -F arch=b64 -S openat,open_by_handle_at -F a2&03 -F path=/etc/shadow -F auid>=1000 -F auid!=unset -F key=user-modify
-a always,exit -F arch=b32 -S openat,open_by_handle_at -F a2&03 -F path=/etc/shadow -F auid=500 -F auid!=unset -F key=user-modify
-a always,exit -F arch=b64 -S openat,open_by_handle_at -F a2&03 -F path=/etc/shadow -F auid=500 -F auid!=unset -F key=user-modify
-a always,exit -F arch=b32 -S open -F a1&03 -F path=/etc/shadow -F auid>=1000 -F auid!=unset -F key=user-modify
-a always,exit -F arch=b64 -S open -F a1&03 -F path=/etc/shadow -F auid>=1000 -F auid!=unset -F key=user-modify
-a always,exit -F arch=b32 -S open -F a1&03 -F path=/etc/shadow -F auid=500 -F auid!=unset -F key=user-modify
-a always,exit -F arch=b64 -S open -F a1&03 -F path=/etc/shadow -F auid=500 -F auid!=unset -F key=user-modify
-a always,exit -F path=/etc/passwd -F perm=wa -F auid>=1000 -F auid!=unset -F key=user-modify
-a always,exit -F path=/etc/shadow -F perm=wa -F auid>=1000 -F auid!=unset -F key=user-modify
-a always,exit -F path=/etc/group -F perm=wa -F auid>=1000 -F auid!=unset -F key=group-modify
-a always,exit -F path=/etc/gshadow -F perm=wa -F auid>=1000 -F auid!=unset -F key=group-modify
-a always,exit -F path=/etc/passwd -F perm=wa -F auid=500 -F auid!=unset -F key=user-modify
-a always,exit -F path=/etc/shadow -F perm=wa -F auid=500 -F auid!=unset -F key=user-modify
-a always,exit -F path=/etc/group -F perm=wa -F auid=500 -F auid!=unset -F key=group-modify
-a always,exit -F path=/etc/gshadow -F perm=wa -F auid=500 -F auid!=unset -F key=group-modify
-a always,exit -F path=/usr/sbin/unix_chkpwd -F perm=x -F auid>=1000 -F auid!=unset -F key=special-config-changes
-a always,exit -F path=/usr/bin/mount -F perm=x -F auid>=1000 -F auid!=unset -F key=special-config-changes
-a always,exit -F path=/usr/bin/newgrp -F perm=x -F auid>=1000 -F auid!=unset -F key=special-config-changes
-a always,exit -F path=/usr/bin/newuidmap -F perm=x -F auid>=1000 -F auid!=unset -F key=special-config-changes
-a always,exit -F path=/usr/bin/gpasswd -F perm=x -F auid>=1000 -F auid!=unset -F key=special-config-changes
-a always,exit -F path=/usr/bin/newgidmap -F perm=x -F auid>=1000 -F auid!=unset -F key=special-config-changes
-a always,exit -F path=/usr/bin/umount -F perm=x -F auid>=1000 -F auid!=unset -F key=special-config-changes
-a always,exit -F path=/usr/bin/passwd -F perm=x -F auid>=1000 -F auid!=unset -F key=special-config-changes
-a always,exit -F path=/usr/sbin/unix_chkpwd -F perm=x -F auid=500 -F auid!=unset -F key=special-config-changes
-a always,exit -F path=/usr/bin/mount -F perm=x -F auid=500 -F auid!=unset -F key=special-config-changes
-a always,exit -F path=/usr/bin/newgrp -F perm=x -F auid=500 -F auid!=unset -F key=special-config-changes
-a always,exit -F path=/usr/bin/newuidmap -F perm=x -F auid=500 -F auid!=unset -F key=special-config-changes
-a always,exit -F path=/usr/bin/gpasswd -F perm=x -F auid=500 -F auid!=unset -F key=special-config-changes
-a always,exit -F path=/usr/bin/newgidmap -F perm=x -F auid=500 -F auid!=unset -F key=special-config-changes
-a always,exit -F path=/usr/bin/umount -F perm=x -F auid=500 -F auid!=unset -F key=special-config-changes
-a always,exit -F path=/usr/bin/passwd -F perm=x -F auid=500 -F auid!=unset -F key=special-config-changes
-a always,exit -F path=/etc/sudoers -F perm=wa -F key=special-config-changes
-a always,exit -F dir=/etc/sudoers.d/ -F perm=wa -F key=special-config-changes
-a always,exit -F dir=/var/log/audit/ -F perm=r -F auid>=1000 -F auid!=unset -F key=access-audit-trail
-a always,exit -F dir=/var/log/audit/ -F perm=r -F auid=500 -F auid!=unset -F key=access-audit-trail
-a always,exit -F path=/var/run/utmp -F perm=wa -F auid>=1000 -F auid!=unset -F key=session
-a always,exit -F path=/var/log/btmp -F perm=wa -F auid>=1000 -F auid!=unset -F key=session
-a always,exit -F path=/var/log/wtmp -F perm=wa -F auid>=1000 -F auid!=unset -F key=session
-a always,exit -F path=/var/run/utmp -F perm=wa -F auid=500 -F auid!=unset -F key=session
-a always,exit -F path=/var/log/btmp -F perm=wa -F auid=500 -F auid!=unset -F key=session
-a always,exit -F path=/var/log/wtmp -F perm=wa -F auid=500 -F auid!=unset -F key=session
-a always,exit -F dir=/etc/selinux/ -F perm=wa -F auid>=1000 -F auid!=unset -F key=MAC-policy
-a always,exit -F dir=/etc/selinux/ -F perm=wa -F auid=500 -F auid!=unset -F key=MAC-policy
-a always,exit -F path=/bin/crictl -F perm=x -F auid>=1000 -F auid!=unset -F key=container-management
-a always,exit -F path=/bin/crictl -F perm=x -F auid=500 -F auid!=unset -F key=container-management
-a always,exit -F path=/bin/docker -F perm=x -F auid>=1000 -F auid!=unset -F key=container-management
-a always,exit -F path=/bin/docker -F perm=x -F auid=500 -F auid!=unset -F key=container-management
-a always,exit -F path=/opt/bin/argocd -F perm=x -F auid>=1000 -F auid!=unset -F key=container-management
-a always,exit -F path=/opt/bin/argocd -F perm=x -F auid=500 -F auid!=unset -F key=container-management
-a always,exit -F path=/opt/bin/crictl -F perm=x -F auid>=1000 -F auid!=unset -F key=container-management
-a always,exit -F path=/opt/bin/crictl -F perm=x -F auid=500 -F auid!=unset -F key=container-management
-a always,exit -F path=/opt/bin/kubeadm -F perm=x -F auid>=1000 -F auid!=unset -F key=container-management
-a always,exit -F path=/opt/bin/kubeadm -F perm=x -F auid=500 -F auid!=unset -F key=container-management
-a always,exit -F path=/opt/bin/kubectl -F perm=x -F auid>=1000 -F auid!=unset -F key=container-management
-a always,exit -F path=/opt/bin/kubectl -F perm=x -F auid=500 -F auid!=unset -F key=container-management
-a always,exit -F path=/opt/bin/kubectl -F perm=x -F auid=0 -F auid!=unset -F key=container-management
-a always,exit -F path=/opt/bin/nerdctl -F perm=x -F auid>=1000 -F auid!=unset -F key=container-management
-a always,exit -F path=/opt/bin/nerdctl -F perm=x -F auid=500 -F auid!=unset -F key=container-management
-a always,exit -F path=/opt/bin/nerdctl -F perm=x -F auid=0 -F auid!=unset -F key=container-management
-r 60
-a exit,always -F arch=b64 -S execve -F key=auditcmd -F auid=500
-a exit,always -F arch=b32 -S execve -F key=auditcmd -F auid=500
-e 1

stephen-fox pushed a commit to metal-toolbox/go-libaudit that referenced this issue Mar 13, 2023
The CoalesceMessages function takes one or more audit messages and
creates an Event object. An Event containing more than one message
is known as a "compound event".

Prior to this commit, the compound event parsing logic required that
a "syscall" message be included in the slice passed to the function.
This requirement may be a little over-zealous. In GitHub issue 127,
we discovered examples of audit events that did not include a syscall
message. [1] This resulted in CoalesceMessages returning an error.

This commit modifies the syscall message check to only return an
error if both the "special" and syscall audit messages are missing.
In such a case, a new (testable) error is returned.

1. elastic/go-libaudit#127
stephen-fox pushed a commit to metal-toolbox/audito-maldito that referenced this issue Mar 13, 2023
stephen-fox pushed a commit to metal-toolbox/audito-maldito that referenced this issue Mar 13, 2023
stephen-fox pushed a commit to metal-toolbox/audito-maldito that referenced this issue Mar 14, 2023
stephen-fox pushed a commit to metal-toolbox/audito-maldito that referenced this issue Mar 14, 2023
stephen-fox pushed a commit to metal-toolbox/audito-maldito that referenced this issue Mar 14, 2023
stephen-fox pushed a commit to metal-toolbox/audito-maldito that referenced this issue Mar 14, 2023
stephen-fox pushed a commit to metal-toolbox/audito-maldito that referenced this issue Mar 14, 2023
JAORMX pushed a commit to metal-toolbox/audito-maldito that referenced this issue Mar 14, 2023
@andrewkroh andrewkroh added bug Team:Security-External Integrations Label for the Security External Integrations team labels Aug 23, 2023
andrewkroh added a commit to andrewkroh/go-libaudit that referenced this issue Aug 29, 2023
@andrewkroh andrewkroh linked a pull request Jan 3, 2024 that will close this issue
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Team:Security-External Integrations Label for the Security External Integrations team
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants