Wazuh System Calls - Linux Audit Monitoring

Wazuh monitors system calls on Linux endpoints through integration with the Linux Audit subsystem (auditd). The Wazuh agent installs and configures audit rules on endpoints, collects system call events, and forwards them to the server for analysis. System call monitoring enables detection of suspicious kernel-level activity: privileged command execution, access to critical files, network connections, and privilege escalation attempts.

Monitoring Architecture

The system call monitoring architecture consists of the following components:

  1. Linux Audit (auditd) - kernel subsystem that intercepts system calls
  2. Audit rules - rules defining which calls to monitor
  3. Wazuh agent - collects audit logs from /var/log/audit/audit.log
  4. Wazuh server - analyzes events and generates alerts

Audit log collection configuration on the agent:

<localfile>
  <log_format>audit</log_format>
  <location>/var/log/audit/audit.log</location>
</localfile>

Audit Rule Types

Linux Audit supports three types of rules:

File System Rules

Monitor operations on files and directories:

# Monitor changes to /etc/passwd
auditctl -w /etc/passwd -p wa -k passwd_changes

# Monitor access to SSH configuration
auditctl -w /etc/ssh/sshd_config -p rwxa -k sshd_config

# Monitor the /etc/sudoers.d directory
auditctl -w /etc/sudoers.d/ -p wa -k sudoers_changes

Permission flags:

  • r - read
  • w - write
  • x - execute
  • a - attribute change

System Call Rules

Monitor specific system calls:

# Monitor program execution (execve)
auditctl -a always,exit -F arch=b64 -S execve -k program_execution

# Monitor network connections (connect)
auditctl -a always,exit -F arch=b64 -S connect -k network_connections

# Monitor file opening (open/openat)
auditctl -a always,exit -F arch=b64 -S open -S openat -F auid>=1000 -k file_access

# Monitor permission changes (chmod/chown)
auditctl -a always,exit -F arch=b64 -S chmod -S fchmod -S chown -k permission_changes

Control Rules

Configure the behavior of the audit subsystem:

# Set buffer size
auditctl -b 8192

# Lock audit configuration (until reboot)
auditctl -e 2

# Delete all rules
auditctl -D

Persistent Audit Rules

Rules set with auditctl are active only until reboot. For persistent application, add rules to /etc/audit/rules.d/wazuh.rules:

# Monitor program execution
-a always,exit -F arch=b64 -S execve -k exec_commands

# Monitor critical files
-w /etc/passwd -p wa -k identity_changes
-w /etc/group -p wa -k identity_changes
-w /etc/shadow -p wa -k identity_changes

# Monitor network connections
-a always,exit -F arch=b64 -S connect -S accept -k network_activity

# Monitor kernel module loading
-a always,exit -F arch=b64 -S init_module -S finit_module -k kernel_modules

# Monitor filesystem mounting
-a always,exit -F arch=b64 -S mount -S umount2 -k mount_operations

# Monitor time changes
-a always,exit -F arch=b64 -S adjtimex -S settimeofday -S clock_settime -k time_changes

# Monitor file deletion
-a always,exit -F arch=b64 -S unlink -S unlinkat -S rename -S renameat -F auid>=1000 -k file_deletion

Apply the rules:

augenrules --load
systemctl restart auditd

Who-data for FIM

Integration with Linux Audit enables the File Integrity Monitoring (FIM) module to obtain extended information about who and which process modified a file. This is called who-data.

Configuring Who-data

In the FIM configuration on the agent, enable whodata mode:

<syscheck>
  <directories check_all="yes" whodata="yes">/etc</directories>
  <directories check_all="yes" whodata="yes">/usr/bin</directories>
  <directories check_all="yes" whodata="yes">/usr/sbin</directories>
</syscheck>

When whodata="yes" is enabled, Wazuh automatically creates audit rules for the specified directories. FIM alerts will contain additional fields:

  • audit.user.id - UID of the user who modified the file
  • audit.user.name - username
  • audit.process.id - PID of the process
  • audit.process.name - process name
  • audit.process.ppid - parent process PID

Who-data Alert Example

{
  "rule": {
    "id": "550",
    "level": 7,
    "description": "Integrity checksum changed"
  },
  "syscheck": {
    "path": "/etc/hosts",
    "audit": {
      "user": {
        "id": "0",
        "name": "root"
      },
      "process": {
        "id": "1234",
        "name": "vim",
        "ppid": "5678"
      }
    }
  }
}

Monitoring Specific System Calls

execve - Program Execution

The execve system call records every program launch in the system. It is one of the most informative sources for detecting malicious activity.

-a always,exit -F arch=b64 -S execve -F auid>=1000 -F auid!=4294967295 -k user_commands

Wazuh rule for detecting execution of suspicious commands:

<rule id="100400" level="10">
  <if_sid>80792</if_sid>
  <field name="audit.command">nc|ncat|netcat|socat|nmap</field>
  <description>Suspicious network tool executed: $(audit.command)</description>
  <mitre>
    <id>T1046</id>
  </mitre>
  <group>audit,syscall,network_scan,</group>
</rule>

connect - Network Connections

Monitoring outbound network connections:

-a always,exit -F arch=b64 -S connect -F a0!=0x2 -k outbound_connections

open/openat - File Access

Monitoring access to sensitive files:

-a always,exit -F arch=b64 -S open -S openat -F dir=/etc/ssl/private -k ssl_key_access
-a always,exit -F arch=b64 -S open -S openat -F dir=/root/.ssh -k ssh_key_access

ptrace - Process Debugging

Monitoring ptrace calls, which are used for process debugging and injection:

-a always,exit -F arch=b64 -S ptrace -k process_injection

socket - Socket Creation

-a always,exit -F arch=b64 -S socket -F a0=0x2 -k ipv4_socket
-a always,exit -F arch=b64 -S socket -F a0=0xa -k ipv6_socket

SELinux and AppArmor Events

SELinux

Wazuh collects SELinux events from the audit log. Typical events include:

  • AVC denial - access denied by SELinux policy
  • MAC_POLICY_LOAD - new policy loaded
  • MAC_STATUS - mode change (enforcing/permissive)
  • MAC_CONFIG_CHANGE - configuration change

Detection rule for SELinux switching to permissive mode:

<rule id="100410" level="12">
  <if_sid>80700</if_sid>
  <match>MAC_STATUS</match>
  <field name="audit.selinux.enforcing">0</field>
  <description>SELinux switched to permissive mode</description>
  <mitre>
    <id>T1562.001</id>
  </mitre>
  <group>audit,selinux,defense_evasion,</group>
</rule>

AppArmor

AppArmor events are also collected through the audit subsystem:

  • APPARMOR_ALLOWED - action permitted by profile
  • APPARMOR_DENIED - action blocked by profile
  • APPARMOR_STATUS - profile status change
<rule id="100411" level="8">
  <if_sid>80700</if_sid>
  <match>apparmor="DENIED"</match>
  <description>AppArmor denied action: $(audit.apparmor.operation)</description>
  <group>audit,apparmor,access_denied,</group>
</rule>

Comparison with Other Solutions

CapabilityWazuh + auditdSysdigFalco
Syscall monitoringVia Linux AuditCustom kernel driver / eBPFeBPF / kernel module
Container supportThrough host-level auditNativeNative
Detection rulesWazuh XML rulesChisel Lua scriptsYAML rules
Event correlationYes (built-in engine)LimitedThrough integrations
FIM with who-dataYesNo (different approach)No
MITRE ATT&CK mappingYesNoYes
CostFree (open source)Commercial (Sysdig Secure)Free (open source)
Performance impactModerateLow (eBPF)Low (eBPF)

Configuration Recommendations

Minimal Audit Rule Set

The following set is recommended as a starting point:

# Program execution
-a always,exit -F arch=b64 -S execve -F auid>=1000 -F auid!=4294967295 -k exec

# Critical files
-w /etc/passwd -p wa -k identity
-w /etc/shadow -p wa -k identity
-w /etc/sudoers -p wa -k sudoers

# Network activity
-a always,exit -F arch=b64 -S connect -k network

# Kernel module loading
-a always,exit -F arch=b64 -S init_module -S finit_module -k modules

Managing Event Volume

Monitoring execve on busy servers generates a significant volume of events. Optimization recommendations:

  • Use the auid>=1000 filter to exclude system processes
  • Add exclusions for trusted applications
  • Set the audit buffer size (auditctl -b) according to workload
  • Monitor event loss via auditctl -s (the lost field)

More about FIM: Wazuh Use Cases

Troubleshooting

Audit Events Not Collected

  • Verify auditd is installed and running: systemctl status auditd
  • Check that audit rules are applied: auditctl -l
  • Confirm the Wazuh agent is configured to read /var/log/audit/audit.log
  • Verify <log_format>audit</log_format> is set in the localfile block

Audit Event Loss

  • Increase the buffer size: auditctl -b 16384
  • Check current losses: auditctl -s | grep lost
  • Reduce audit rules to the necessary minimum
  • Consider using auditd with write_logs = no under high load

Who-data Not Working for FIM

  • Verify auditd is installed and running
  • Confirm whodata="yes" is specified in the syscheck configuration
  • Check that Wazuh automatically created rules: auditctl -l | grep wazuh
  • Review /var/ossec/logs/ossec.log for FIM errors

High CPU Load

  • Reduce the number of monitored system calls
  • Add exclusions via -F exe!= for known safe processes
  • Use -F auid>=1000 to filter system services
  • Increase the FIM scan interval when using who-data

More about architecture: Wazuh Architecture

More about command monitoring: Command Monitoring

Last updated on