Verify Permissions on /etc/audit/audit.rules
Ensures /etc/audit/audit.rules is not writable by group/other, not readable by other, and free of executable, setuid, setgid or sticky bits.
Checked against the content of a persistent configuration file, the source of truth that survives reboots.
A mapping is a cross-reference to where each standard places this requirement, anchored and cross-validated, not a claim of equivalence. A passing check is evidence toward these references, how to read it.
Why this rule matters
/etc/audit/audit.rules is the compiled, active auditd ruleset (generated by augenrules from the rules.d fragments). It defines exactly which events are recorded. If it is writable by group or other, an attacker can erase the rules that would log their activity; if readable by other, they learn precisely what is monitored and can route around it. Keeping it root-only protects the integrity and confidentiality of the audit policy that underpins incident detection and attribution.
What Pavois checks
Pavois inspects the real inode permissions of /etc/audit/audit.rules with the InSpec file resource (a stat), under only_if so non-auditd hosts are skipped. It requires an effective mode no looser than 0640 root:root, no group/other write, no other read, no special bits. Reading the live permissions catches a file that was re-generated or edited after install, which a check against a packaging default would miss.
only_if { file('/etc/audit/audit.rules').exist? }
describe file('/etc/audit/audit.rules') do
it { should_not be_executable.by('owner') }
it { should_not be_setuid }
it { should_not be_executable.by('group') }
it { should_not be_writable.by('group') }
it { should_not be_setgid }
it { should_not be_executable.by('other') }
it { should_not be_writable.by('other') }
it { should_not be_readable.by('other') }
it { should_not be_sticky }
endHow to verify it is applied
Run stat -c '%a %U %G' /etc/audit/audit.rules. Expected output is mode 640 (or stricter) owned by root root, e.g. 640 root root. Any group-write, other-read or special bit fails the rule.
Inspect & investigate
auditd loads this file at start; confirm with auditctl -l (active rules) and journalctl -u auditd. Tampering and config changes appear in /var/log/audit/audit.log (grep CONFIG_CHANGE). After regenerating the file, reload with augenrules --load.
Remediation
No automated remediation is defined, so apply it manually: chmod u-x,g-wx,o-rwx /etc/audit/audit.rules && chown root:root /etc/audit/audit.rules (target 0640 root:root). Note that on systems using augenrules, this file is regenerated, so also tighten the rules.d fragments (see fileperm-etc-audit-rulesd) to keep the result.
Pavois applies this with its own harden engine, the plan below, not a shell script:
| mode | 0640 |
|---|---|
| path | /etc/audit/audit.rules |
| resource | file |
pavois harden plan localwhere the target is local, a user@host SSH alias, or a container , Docs
Impact & precautions
The change is low-risk: auditd reads the file as root and needs no broader access. Precaution: if your distro regenerates audit.rules via augenrules, a manual chmod may be undone on the next reload, fix the source fragments too. Verify with auditctl -l that rules remain loaded. Leaving the file group/other-writable lets an unprivileged user disable auditing without detection.
Standards mapping
| Standard | Reference | Type | Version | Confidence |
|---|---|---|---|---|
| CIS | 6.2.4.5, 6.3.4.5 | direct | per OS, see the benchmark table | high |
| DISA STIG | UBTU-22-653065, UBTU-24-900040 | direct | per OS STIG release | high |
Each reference is a cross-reference anchored in the upstream benchmark and cross-validated against the SCAP Security Guide and ansible-lockdown, not a claim of equivalence. Direct = a prescriptive, line-level requirement; supporting = an abstract control family (NIST) the check provides evidence toward. How to read a mapping.