diff --git a/build-scripts/compile_profiles.py b/build-scripts/compile_profiles.py
index 0967252348f..d1ce8984b2f 100644
--- a/build-scripts/compile_profiles.py
+++ b/build-scripts/compile_profiles.py
@@ -3,6 +3,7 @@
import argparse
import sys
import os.path
+from copy import deepcopy
from glob import glob
import ssg.build_yaml
@@ -36,7 +37,8 @@ def resolve(self, all_profiles):
updated_variables.update(self.variables)
self.variables = updated_variables
- updated_refinements = dict(extended_profile.refine_rules)
+ extended_refinements = deepcopy(extended_profile.refine_rules)
+ updated_refinements = self._subtract_refinements(extended_refinements)
updated_refinements.update(self.refine_rules)
self.refine_rules = updated_refinements
@@ -50,6 +52,18 @@ def resolve(self, all_profiles):
self.resolved = True
+ def _subtract_refinements(self, extended_refinements):
+ """
+ Given a dict of rule refinements from the extended profile,
+ "undo" every refinement prefixed with '!' in this profile.
+ """
+ for rule, refinements in list(self.refine_rules.items()):
+ if rule.startswith("!"):
+ for prop, val in refinements:
+ extended_refinements[rule[1:]].remove((prop, val))
+ del self.refine_rules[rule]
+ return extended_refinements
+
def create_parser():
parser = argparse.ArgumentParser()
diff --git a/linux_os/guide/system/bootloader-zipl/zipl_audit_argument/rule.yml b/linux_os/guide/system/bootloader-zipl/zipl_audit_argument/rule.yml
index 624b4e7041a..b1307ef3f2e 100644
--- a/linux_os/guide/system/bootloader-zipl/zipl_audit_argument/rule.yml
+++ b/linux_os/guide/system/bootloader-zipl/zipl_audit_argument/rule.yml
@@ -20,6 +20,9 @@ rationale: |-
severity: medium
+identifiers:
+ cce@rhel8: 83321-0
+
ocil_clause: 'auditing is not enabled at boot time'
ocil: |-
@@ -28,3 +31,9 @@ ocil: |-
No line should be returned, each line returned is a boot entry that doesn't enable audit.
platform: machine
+
+template:
+ name: zipl_bls_entries_option
+ vars:
+ arg_name: audit
+ arg_value: '1'
diff --git a/linux_os/guide/system/bootloader-zipl/zipl_audit_argument/tests/correct_option.pass.sh b/linux_os/guide/system/bootloader-zipl/zipl_audit_argument/tests/correct_option.pass.sh
new file mode 100644
index 00000000000..7a828837fee
--- /dev/null
+++ b/linux_os/guide/system/bootloader-zipl/zipl_audit_argument/tests/correct_option.pass.sh
@@ -0,0 +1,15 @@
+#!/bin/bash
+# platform = multi_platform_fedora,Red Hat Enterprise Linux 8
+
+# Make sure boot loader entries contain audit=1
+for file in /boot/loader/entries/*.conf
+do
+ if ! grep -q '^options.*audit=1.*$' "$file" ; then
+ sed -i '/^options / s/$/ audit=1/' "$file"
+ fi
+done
+
+# Make sure /etc/kernel/cmdline contains audit=1
+if ! grep -qs '^(.*\s)?audit=1(\s.*)?$' /etc/kernel/cmdline ; then
+ echo "audit=1" >> /etc/kernel/cmdline
+fi
diff --git a/linux_os/guide/system/bootloader-zipl/zipl_audit_argument/tests/missing_in_cmdline.fail.sh b/linux_os/guide/system/bootloader-zipl/zipl_audit_argument/tests/missing_in_cmdline.fail.sh
new file mode 100644
index 00000000000..3af83d30d8c
--- /dev/null
+++ b/linux_os/guide/system/bootloader-zipl/zipl_audit_argument/tests/missing_in_cmdline.fail.sh
@@ -0,0 +1,13 @@
+#!/bin/bash
+# platform = multi_platform_fedora,Red Hat Enterprise Linux 8
+
+# Make sure boot loader entries contain audit=1
+for file in /boot/loader/entries/*.conf
+do
+ if ! grep -q '^options.*audit=1.*$' "$file" ; then
+ sed -i '/^options / s/$/ audit=1/' "$file"
+ fi
+done
+
+# Make sure /etc/kernel/cmdline doesn't contain audit=1
+sed -Ei 's/(^.*)audit=1(.*?)$/\1\2/' /etc/kernel/cmdline || true
diff --git a/linux_os/guide/system/bootloader-zipl/zipl_audit_argument/tests/missing_in_entry.fail.sh b/linux_os/guide/system/bootloader-zipl/zipl_audit_argument/tests/missing_in_entry.fail.sh
new file mode 100644
index 00000000000..5650cc0a745
--- /dev/null
+++ b/linux_os/guide/system/bootloader-zipl/zipl_audit_argument/tests/missing_in_entry.fail.sh
@@ -0,0 +1,13 @@
+#!/bin/bash
+# platform = multi_platform_fedora,Red Hat Enterprise Linux 8
+
+# Remove audit=1 from all boot entries
+sed -Ei 's/(^options.*\s)audit=1(.*?)$/\1\2/' /boot/loader/entries/*
+# But make sure one boot loader entry contains audit=1
+sed -i '/^options / s/$/ audit=1/' /boot/loader/entries/*rescue.conf
+sed -Ei 's/(^options.*\s)\$kernelopts(.*?)$/\1\2/' /boot/loader/entries/*rescue.conf
+
+# Make sure /etc/kernel/cmdline contains audit=1
+if ! grep -qs '^(.*\s)?audit=1(\s.*)?$' /etc/kernel/cmdline ; then
+ echo "audit=1" >> /etc/kernel/cmdline
+fi
diff --git a/linux_os/guide/system/bootloader-zipl/zipl_audit_backlog_limit_argument/rule.yml b/linux_os/guide/system/bootloader-zipl/zipl_audit_backlog_limit_argument/rule.yml
index faf114591a4..18391bee6c2 100644
--- a/linux_os/guide/system/bootloader-zipl/zipl_audit_backlog_limit_argument/rule.yml
+++ b/linux_os/guide/system/bootloader-zipl/zipl_audit_backlog_limit_argument/rule.yml
@@ -19,12 +19,21 @@ rationale: |-
severity: medium
+identifiers:
+ cce@rhel8: 83341-8
+
ocil_clause: 'audit backlog limit is not configured'
ocil: |-
To check that all boot entries extend the backlog limit;
Check that all boot entries extend the log events queue:
-
sudo grep -L "^options\s+.*\baudit_backlog_limit=0\b" /boot/loader/entries/*.conf
+ sudo grep -L "^options\s+.*\baudit_backlog_limit=8192\b" /boot/loader/entries/*.conf
No line should be returned, each line returned is a boot entry that does not extend the log events queue.
platform: machine
+
+template:
+ name: zipl_bls_entries_option
+ vars:
+ arg_name: audit_backlog_limit
+ arg_value: '8192'
diff --git a/linux_os/guide/system/bootloader-zipl/zipl_page_poison_argument/rule.yml b/linux_os/guide/system/bootloader-zipl/zipl_page_poison_argument/rule.yml
index 866664c01bd..7ffea8ce6a3 100644
--- a/linux_os/guide/system/bootloader-zipl/zipl_page_poison_argument/rule.yml
+++ b/linux_os/guide/system/bootloader-zipl/zipl_page_poison_argument/rule.yml
@@ -20,6 +20,9 @@ rationale: |-
severity: medium
+identifiers:
+ cce@rhel8: 83351-7
+
ocil_clause: 'page allocator poisoning is not enabled'
ocil: |-
@@ -28,3 +31,9 @@ ocil: |-
No line should be returned, each line returned is a boot entry that doesn't enable page poisoning.
platform: machine
+
+template:
+ name: zipl_bls_entries_option
+ vars:
+ arg_name: page_poison
+ arg_value: '1'
diff --git a/linux_os/guide/system/bootloader-zipl/zipl_pti_argument/rule.yml b/linux_os/guide/system/bootloader-zipl/zipl_pti_argument/rule.yml
index 2f02d9668c9..6fd10822926 100644
--- a/linux_os/guide/system/bootloader-zipl/zipl_pti_argument/rule.yml
+++ b/linux_os/guide/system/bootloader-zipl/zipl_pti_argument/rule.yml
@@ -19,6 +19,9 @@ rationale: |-
severity: medium
+identifiers:
+ cce@rhel8: 83361-6
+
ocil_clause: 'Kernel page-table isolation is not enabled'
ocil: |-
@@ -27,3 +30,9 @@ ocil: |-
No line should be returned, each line returned is a boot entry that doesn't enable page-table isolation .
platform: machine
+
+template:
+ name: zipl_bls_entries_option
+ vars:
+ arg_name: pti
+ arg_value: 'on'
diff --git a/linux_os/guide/system/bootloader-zipl/zipl_slub_debug_argument/rule.yml b/linux_os/guide/system/bootloader-zipl/zipl_slub_debug_argument/rule.yml
index 0cb10d3cd83..c499140c35b 100644
--- a/linux_os/guide/system/bootloader-zipl/zipl_slub_debug_argument/rule.yml
+++ b/linux_os/guide/system/bootloader-zipl/zipl_slub_debug_argument/rule.yml
@@ -8,7 +8,7 @@ description: |-
To enable poisoning of SLUB/SLAB objects,
check that all boot entries in /boot/loader/entries/*.conf have slub_debug=P
included in its options.
- To ensure that new kernels and boot entries continue to extend the audit log events queue,
+ To ensure that new kernels and boot entries continue to enable poisoning of SLUB/SLAB objects,
add slub_debug=P to /etc/kernel/cmdline.
rationale: |-
@@ -20,6 +20,9 @@ rationale: |-
severity: medium
+identifiers:
+ cce@rhel8: 83371-5
+
ocil_clause: 'SLUB/SLAB poisoning is not enabled'
ocil: |-
@@ -28,3 +31,9 @@ ocil: |-
No line should be returned, each line returned is a boot entry that does not enable poisoning.
platform: machine
+
+template:
+ name: zipl_bls_entries_option
+ vars:
+ arg_name: slub_debug
+ arg_value: 'P'
diff --git a/linux_os/guide/system/bootloader-zipl/zipl_vsyscall_argument/rule.yml b/linux_os/guide/system/bootloader-zipl/zipl_vsyscall_argument/rule.yml
index f79adeb0838..7edd43074f3 100644
--- a/linux_os/guide/system/bootloader-zipl/zipl_vsyscall_argument/rule.yml
+++ b/linux_os/guide/system/bootloader-zipl/zipl_vsyscall_argument/rule.yml
@@ -17,6 +17,9 @@ rationale: |-
severity: medium
+identifiers:
+ cce@rhel8: 83381-4
+
ocil_clause: 'vsyscalls are enabled'
ocil: |-
@@ -25,3 +28,9 @@ ocil: |-
No line should be returned, each line returned is a boot entry that doesn't disable virtual syscalls.
platform: machine
+
+template:
+ name: zipl_bls_entries_option
+ vars:
+ arg_name: vsyscall
+ arg_value: 'none'
diff --git a/rhel8/profiles/ospp.profile b/rhel8/profiles/ospp.profile
index 80e4b71fff6..d3732fa8054 100644
--- a/rhel8/profiles/ospp.profile
+++ b/rhel8/profiles/ospp.profile
@@ -419,3 +419,11 @@ selections:
# zIPl specific rules
- zipl_bls_entries_only
- zipl_bootmap_is_up_to_date
+ - zipl_audit_argument
+ - zipl_audit_backlog_limit_argument
+ - zipl_slub_debug_argument
+ - zipl_page_poison_argument
+ - zipl_vsyscall_argument
+ - zipl_vsyscall_argument.role=unscored
+ - zipl_vsyscall_argument.severity=info
+ - zipl_pti_argument
diff --git a/rhel8/profiles/stig.profile b/rhel8/profiles/stig.profile
index cfc2160be16..53647475aa0 100644
--- a/rhel8/profiles/stig.profile
+++ b/rhel8/profiles/stig.profile
@@ -49,3 +49,11 @@ selections:
# Unselect zIPL rules from OSPP
- "!zipl_bls_entries_only"
- "!zipl_bootmap_is_up_to_date"
+ - "!zipl_audit_argument"
+ - "!zipl_audit_backlog_limit_argument"
+ - "!zipl_page_poison_argument"
+ - "!zipl_pti_argument"
+ - "!zipl_slub_debug_argument"
+ - "!zipl_vsyscall_argument"
+ - "!zipl_vsyscall_argument.role=unscored"
+ - "!zipl_vsyscall_argument.severity=info"
diff --git a/shared/references/cce-redhat-avail.txt b/shared/references/cce-redhat-avail.txt
index 3df70caa779..0fa6651e10d 100644
--- a/shared/references/cce-redhat-avail.txt
+++ b/shared/references/cce-redhat-avail.txt
@@ -22,7 +22,6 @@ CCE-83317-8
CCE-83318-6
CCE-83319-4
CCE-83320-2
-CCE-83321-0
CCE-83322-8
CCE-83327-7
CCE-83328-5
@@ -32,7 +31,6 @@ CCE-83333-5
CCE-83336-8
CCE-83339-2
CCE-83340-0
-CCE-83341-8
CCE-83342-6
CCE-83343-4
CCE-83344-2
@@ -40,14 +38,12 @@ CCE-83345-9
CCE-83346-7
CCE-83349-1
CCE-83350-9
-CCE-83351-7
CCE-83352-5
CCE-83353-3
CCE-83354-1
CCE-83355-8
CCE-83356-6
CCE-83358-2
-CCE-83361-6
CCE-83362-4
CCE-83363-2
CCE-83364-0
@@ -57,7 +53,6 @@ CCE-83367-3
CCE-83368-1
CCE-83369-9
CCE-83370-7
-CCE-83371-5
CCE-83372-3
CCE-83373-1
CCE-83374-9
@@ -66,7 +61,6 @@ CCE-83376-4
CCE-83377-2
CCE-83378-0
CCE-83379-8
-CCE-83381-4
CCE-83382-2
CCE-83383-0
CCE-83384-8
diff --git a/shared/templates/template_ANSIBLE_zipl_bls_entries_option b/shared/templates/template_ANSIBLE_zipl_bls_entries_option
new file mode 100644
index 00000000000..bccad2267c1
--- /dev/null
+++ b/shared/templates/template_ANSIBLE_zipl_bls_entries_option
@@ -0,0 +1,52 @@
+# platform = Red Hat Enterprise Linux 8
+# reboot = true
+# strategy = configure
+# complexity = medium
+# disruption = low
+
+- name: "Ensure BLS boot entries options contain {{{ ARG_NAME_VALUE }}}"
+ block:
+ - name: "Check how many boot entries exist "
+ find:
+ paths: "/boot/loader/entries/"
+ patterns: "*.conf"
+ register: n_entries
+
+ - name: "Check how many boot entries set {{{ ARG_NAME_VALUE }}}"
+ find:
+ paths: "/boot/loader/entries/"
+ contains: "^options .*{{{ ARG_NAME_VALUE }}}.*$"
+ patterns: "*.conf"
+ register: n_entries_options
+
+ - name: "Update boot entries options"
+ command: grubby --update-kernel=ALL --args="{{{ ARG_NAME_VALUE }}}"
+ when: n_entries is defined and n_entries_options is defined and n_entries.matched != n_entries_options.matched
+
+ - name: "Check if /etc/kernel/cmdline exists"
+ stat:
+ path: /etc/kernel/cmdline
+ register: cmdline_stat
+
+ - name: "Check if /etc/kernel/cmdline contains {{{ ARG_NAME_VALUE }}}"
+ find:
+ paths: "/etc/kernel/"
+ patterns: "cmdline"
+ contains: "^.*{{{ ARG_NAME_VALUE }}}.*$"
+ register: cmdline_find
+
+ - name: "Add /etc/kernel/cmdline contains {{{ ARG_NAME_VALUE }}}"
+ lineinfile:
+ create: yes
+ path: "/etc/kernel/cmdline"
+ line: '{{{ ARG_NAME_VALUE }}}'
+ when: cmdline_stat is defined and not cmdline_stat.stat.exists
+
+ - name: "Append /etc/kernel/cmdline contains {{{ ARG_NAME_VALUE }}}"
+ lineinfile:
+ path: "/etc/kernel/cmdline"
+ backrefs: yes
+ regexp: "^(.*)$"
+ line: '\1 {{{ ARG_NAME_VALUE }}}'
+ when: cmdline_stat is defined and cmdline_stat.stat.exists and cmdline_find is defined and cmdline_find.matched == 0
+
diff --git a/shared/templates/template_BASH_zipl_bls_entries_option b/shared/templates/template_BASH_zipl_bls_entries_option
new file mode 100644
index 00000000000..dde8c948f7a
--- /dev/null
+++ b/shared/templates/template_BASH_zipl_bls_entries_option
@@ -0,0 +1,11 @@
+# platform = Red Hat Enterprise Linux 8
+
+# Correct BLS option using grubby, which is a thin wrapper around BLS operations
+grubby --update-kernel=ALL --args="{{{ ARG_NAME_VALUE }}}"
+
+# Ensure new kernels and boot entries retain the boot option
+if [ ! -f /etc/kernel/cmdline ]; then
+ echo "{{{ ARG_NAME_VALUE }}}" >> /etc/kernel/cmdline
+elif ! grep -q '^(.*\s)?{{{ ARG_NAME_VALUE }}}(\s.*)?$' /etc/kernel/cmdline; then
+ sed -Ei 's/^(.*)$/\1 {{{ ARG_NAME_VALUE }}}/' /etc/kernel/cmdline
+fi
diff --git a/shared/templates/template_OVAL_zipl_bls_entries_option b/shared/templates/template_OVAL_zipl_bls_entries_option
new file mode 100644
index 00000000000..502d5e7d9aa
--- /dev/null
+++ b/shared/templates/template_OVAL_zipl_bls_entries_option
@@ -0,0 +1,47 @@
+
+
+
+ Ensure that BLS-compatible boot loader is configured to run Linux operating system with argument {{{ ARG_NAME_VALUE }}}
+ {{{- oval_affected(products) }}}
+ Ensure {{{ ARG_NAME_VALUE }}} option is configured in the 'options' line in /boot/loader/entries/*.conf.
+
+
+
+
+
+
+
+
+
+
+
+
+
+ ^/boot/loader/entries/.*\.conf$
+ ^options (.*)$
+ 1
+
+
+
+
+
+
+
+ /etc/kernel/cmdline
+ ^(.*)$
+ 1
+
+
+
+ ^(?:.*\s)?{{{ ESCAPED_ARG_NAME_VALUE }}}(?:\s.*)?$
+
+
diff --git a/ssg/templates.py b/ssg/templates.py
index 2795267abd3..a27fbb6cb61 100644
--- a/ssg/templates.py
+++ b/ssg/templates.py
@@ -375,6 +375,11 @@ def bls_entries_option(data, lang):
return data
+@template(["ansible", "bash", "oval"])
+def zipl_bls_entries_option(data, lang):
+ return bls_entries_option(data, lang)
+
+
class Builder(object):
"""
Class for building all templated content for a given product.
diff --git a/tests/data/profile_stability/rhel8/ospp.profile b/tests/data/profile_stability/rhel8/ospp.profile
index 08dcccf24cb..5aa35924961 100644
--- a/tests/data/profile_stability/rhel8/ospp.profile
+++ b/tests/data/profile_stability/rhel8/ospp.profile
@@ -168,6 +168,7 @@ selections:
- service_rngd_enabled
- service_systemd-coredump_disabled
- service_usbguard_enabled
+- ssh_client_rekey_limit
- sshd_disable_empty_passwords
- sshd_disable_gssapi_auth
- sshd_disable_kerb_auth
@@ -213,8 +214,14 @@ selections:
- sysctl_user_max_user_namespaces
- timer_dnf-automatic_enabled
- usbguard_allow_hid_and_hub
+- zipl_audit_argument
+- zipl_audit_backlog_limit_argument
- zipl_bls_entries_only
- zipl_bootmap_is_up_to_date
+- zipl_page_poison_argument
+- zipl_pti_argument
+- zipl_slub_debug_argument
+- zipl_vsyscall_argument
- var_sshd_set_keepalive=0
- var_rekey_limit_size=1G
- var_rekey_limit_time=1hour
@@ -238,11 +245,12 @@ selections:
- var_accounts_passwords_pam_faillock_deny=3
- var_accounts_passwords_pam_faillock_fail_interval=900
- var_accounts_passwords_pam_faillock_unlock_time=never
+- var_ssh_client_rekey_limit_size=1G
+- var_ssh_client_rekey_limit_time=1hour
- grub2_vsyscall_argument.role=unscored
- grub2_vsyscall_argument.severity=info
- sysctl_user_max_user_namespaces.role=unscored
- sysctl_user_max_user_namespaces.severity=info
-- ssh_client_rekey_limit
-- var_ssh_client_rekey_limit_size=1G
-- var_ssh_client_rekey_limit_time=1hour
+- zipl_vsyscall_argument.role=unscored
+- zipl_vsyscall_argument.severity=info
title: Protection Profile for General Purpose Operating Systems