diff --git a/.github/ISSUE_TEMPLATE/bug_report.md b/.github/ISSUE_TEMPLATE/bug_report.md new file mode 100644 index 00000000..3a19c72b --- /dev/null +++ b/.github/ISSUE_TEMPLATE/bug_report.md @@ -0,0 +1,32 @@ +--- +name: Report Issue +about: Create a bug issue ticket to help us improve +title: '' +labels: bug +assignees: '' + +--- + +**Describe the Issue** +A clear and concise description of what the bug is. + +**Expected Behavior** +A clear and concise description of what you expected to happen. + +**Actual Behavior** +A clear and concise description of what's happening. + +**Control(s) Affected** +What controls are being affected by the issue + +**Environment (please complete the following information):** + - Ansible Version: [e.g. 2.10] + - Host Python Version: [e.g. Python 3.7.6] + - Ansible Server Python Version: [e.g. Python 3.7.6] + - Additional Details: + +**Additional Notes** +Anything additional goes here + +**Possible Solution** +Enter a suggested fix here diff --git a/.github/ISSUE_TEMPLATE/feature-request-or-enhancement.md b/.github/ISSUE_TEMPLATE/feature-request-or-enhancement.md new file mode 100644 index 00000000..bf457005 --- /dev/null +++ b/.github/ISSUE_TEMPLATE/feature-request-or-enhancement.md @@ -0,0 +1,21 @@ +--- +name: Feature Request or Enhancement +about: Suggest an idea for this project +title: '' +labels: enhancement +assignees: '' + +--- + +**Feature Request or Enhancement** + - Feature [] + - Enhancement [] + +**Summary of Request** +A clear and concise description of what you want to happen. + +**Describe alternatives you've considered** +A clear and concise description of any alternative solutions or features you've considered. + +**Suggested Code** +Please provide any code you have in mind to fulfill the request diff --git a/.github/ISSUE_TEMPLATE/question.md b/.github/ISSUE_TEMPLATE/question.md new file mode 100644 index 00000000..cbab6e73 --- /dev/null +++ b/.github/ISSUE_TEMPLATE/question.md @@ -0,0 +1,17 @@ +--- +name: Question +about: Ask away....... +title: '' +labels: question +assignees: '' + +--- + +**Question** +Pose question here. + +**Environment (please complete the following information):** + - Ansible Version: [e.g. 2.10] + - Host Python Version: [e.g. Python 3.7.6] + - Ansible Server Python Version: [e.g. Python 3.7.6] + - Additional Details: diff --git a/.github/pull_request_template.md b/.github/pull_request_template.md new file mode 100644 index 00000000..05dadb6b --- /dev/null +++ b/.github/pull_request_template.md @@ -0,0 +1,12 @@ +**Overall Review of Changes:** +A general description of the changes made that are being requested for merge + +**Issue Fixes:** +Please list (using linking) any open issues this PR addresses + +**Enhancements:** +Please list any enhancements/features that are not open issue tickets + +**How has this been tested?:** +Please give an overview of how these changes were tested. If they were not please use N/A + diff --git a/.github/workflows/develtomain.yml b/.github/workflows/develtomain.yml index f166faf8..86336cb4 100644 --- a/.github/workflows/develtomain.yml +++ b/.github/workflows/develtomain.yml @@ -10,6 +10,7 @@ on: branches: [ main ] # A workflow run is made up of one or more jobs that can run sequentially or in parallel + jobs: # This workflow contains a single job called "build" build: diff --git a/.yamllint b/.yamllint index d3493a2e..fdea6296 100644 --- a/.yamllint +++ b/.yamllint @@ -8,16 +8,16 @@ ignore: | extends: default rules: - indentation: - # Requiring 4 space indentation - spaces: 4 - # Requiring consistent indentation within a file, either indented or not - indent-sequences: consistent - truthy: disable - braces: - max-spaces-inside: 1 - level: error - brackets: - max-spaces-inside: 1 - level: error - line-length: disable \ No newline at end of file + indentation: + # Requiring 4 space indentation + spaces: 4 + # Requiring consistent indentation within a file, either indented or not + indent-sequences: consistent + truthy: disable + braces: + max-spaces-inside: 1 + level: error + brackets: + max-spaces-inside: 1 + level: error + line-length: disable diff --git a/Changelog.md b/Changelog.md index db5b1872..1d14c1c1 100644 --- a/Changelog.md +++ b/Changelog.md @@ -1,47 +1,68 @@ # Changes to rhel8CIS +## 1.3.1 +- CIS 1.0.1 updates +- Added Issue and PR templates +- Added better reboot logic +- Added options to ensure idempotence +- Enhanced flush handlers +- Typo fixes +- mount check improvements +- Linting fixes +- Added systemd tmp mount +- Added systemd tmpfs block +- #110 tmp.mount support + - thanks to @erpadmin + + +## 1.3 + +- extentions to LE audit capability +- more lint and layout changes +- sugroup assertion added 5.7 +- added extra logic variable to authselect/config section 5.3 related +- AlmaLinux and Rocky tested (comments in readme - also rsyslog installed at build or will fail) +- section 1.1 mount work has been rewritten and systemd tmp mount options added + +## 1.2.3 + +- #117 sugroup enhancements + - thanks to @ihotz +- #112 use of dnf module not shell + - thanks to @wolskie + ## 1.2.2 - #33 mkgrub missing variable issues - efi and bios path resolution - - thanks to mrampant & mickey1928geo + - thanks to @mrampant & @mickey1928geo - #102 2.2.2 xorg pkg removal extended - - thanks to RosarioVinoth + - thanks to @RosarioVinoth - #104 5.4.1 pwquality logic - - thanks to RosarioVinoth + - thanks to @RosarioVinoth - #107 Idempotence improvement for 4.1.1.3 and 4.1.1.4 - - thanks to andreyzher - + - thanks to @andreyzher - lint changes and updates to sync with ansible-galaxy ## v1.2.1 - bootloader and default variables - empty strings lint updates - -### 87 - +- #87 - rule 6.1.1 - audit only - outputs file discrepancies to {{ rhel8cis_rpm_audit_file }} - -### 88 - +- #88 - checkmode_improvements added to relevant tasks - -### PR #96 - +- PR #96 - crypto policy idempotency ## v1.2.0 -### 86 - +- #86 - Adding on the goss auditing tool - remove deprecated warnings - format and layout - general improvements - readme updates - use ansible package_facts - -### 90 - +- #90 - cis fix - nfs-server not nfs - Thanks to danderemer diff --git a/README.md b/README.md index 1710af32..e654fe1c 100644 --- a/README.md +++ b/README.md @@ -5,13 +5,13 @@ RHEL 8 CIS ![Build Status](https://img.shields.io/github/workflow/status/ansible-lockdown/RHEL8-CIS/DevelToMain?label=Main%20Build%20Status&style=plastic) ![Release](https://img.shields.io/github/v/release/ansible-lockdown/RHEL8-CIS?style=plastic) - Configure RHEL/Centos 8 machine to be [CIS](https://www.cisecurity.org/cis-benchmarks/) compliant -Based on [CIS RedHat Enterprise Linux 8 Benchmark v1.0.0 - 09-30-2019 ](https://www.cisecurity.org/cis-benchmarks/) +Based on [CIS RedHat Enterprise Linux 8 Benchmark v1.0.1 - 05-19-2021 ](https://www.cisecurity.org/cis-benchmarks/) Caution(s) ------- + This role **will make changes to the system** which may have unintended concequences. This is not an auditing tool but rather a remediation tool to be used after an audit has been conducted. This role was developed against a clean install of the Operating System. If you are implimenting to an existing system please review this role for any site specific changes that are needed. @@ -20,12 +20,13 @@ To use release version please point to main branch Documentation ------------- -[Getting Started](https://www.lockdownenterprise.com/docs/getting-started-with-lockdown)
-[Customizing Roles](https://www.lockdownenterprise.com/docs/customizing-lockdown-enterprise)
-[Per-Host Configuration](https://www.lockdownenterprise.com/docs/per-host-lockdown-enterprise-configuration)
-[Getting the Most Out of the Role](https://www.lockdownenterprise.com/docs/get-the-most-out-of-lockdown-enterprise)
-[Wiki](https://github.com/ansible-lockdown/RHEL8-CIS/wiki)
-[Repo GitHub Page](https://ansible-lockdown.github.io/RHEL8-CIS/)
+ +- [Getting Started](https://www.lockdownenterprise.com/docs/getting-started-with-lockdown) +- [Customizing Roles](https://www.lockdownenterprise.com/docs/customizing-lockdown-enterprise) +- [Per-Host Configuration](https://www.lockdownenterprise.com/docs/per-host-lockdown-enterprise-configuration) +- [Getting the Most Out of the Role](https://www.lockdownenterprise.com/docs/get-the-most-out-of-lockdown-enterprise) +- [Wiki](https://github.com/ansible-lockdown/RHEL8-CIS/wiki) +- [Repo GitHub Page](https://ansible-lockdown.github.io/RHEL8-CIS/) Auditing (new) -------------- @@ -39,24 +40,27 @@ This audit will not only check the config has the correct setting but aims to ca Refer to [RHEL8-CIS-Audit](https://github.com/ansible-lockdown/RHEL8-CIS-Audit). - Requirements ------------ -RHEL 8 or CentOS 8 - Other versions are not supported. -Access to download or add the goss binary and content to the system if using auditing. options are available on how to get the content to the system. +RHEL/AlmaLinux/CentOS/Rocky 8 - Other versions are not supported. + +- AlmaLinux/Rocky Has been tested on 8.4(enabling crypto (sections 1.10&1.11) breaks updating or installs 01Jul2021 +- Access to download or add the goss binary and content to the system if using auditing (other options are available on how to get the content to the system.) **General:** + - Basic knowledge of Ansible, below are some links to the Ansible documentation to help get started if you are unfamiliar with Ansible - [Main Ansible documentation page](https://docs.ansible.com) - [Ansible Getting Started](https://docs.ansible.com/ansible/latest/user_guide/intro_getting_started.html) - [Tower User Guide](https://docs.ansible.com/ansible-tower/latest/html/userguide/index.html) - [Ansible Community Info](https://docs.ansible.com/ansible/latest/community/index.html) -- Functioning Ansible and/or Tower Installed, configured, and running. This includes all of the base Ansible/Tower configurations, needed packages installed, and infrastructure setup. +- Functioning Ansible and/or Tower Installed, configured, and running. This includes all of the base Ansible/Tower configurations, needed packages installed, and infrastructure setup. - Please read through the tasks in this role to gain an understanding of what each control is doing. Some of the tasks are disruptive and can have unintended consiquences in a live production system. Also familiarize yourself with the variables in the defaults/main.yml file or the [Main Variables Wiki Page](https://github.com/ansible-lockdown/RHEL8-CIS/wiki/Main-Variables). Dependencies ------------ + - Python3 - Ansible 2.9+ - python-def (should be included in RHEL/CentOS 8) @@ -64,15 +68,17 @@ Dependencies Role Variables -------------- -This role is designed that the end user should not have to edit the tasks themselves. All customizing should be done via the defaults/main.yml file or with extra vars within the project, job, workflow, etc. These variables can be found [here](https://github.com/ansible-lockdown/RHEL8-CIS/wiki/Main-Variables) in the Main Variables Wiki page. All variables are listed there along with descriptions. +This role is designed that the end user should not have to edit the tasks themselves. All customizing should be done via the defaults/main.yml file or with extra vars within the project, job, workflow, etc. These variables can be found [here](https://github.com/ansible-lockdown/RHEL8-CIS/wiki/Main-Variables) in the Main Variables Wiki page. All variables are listed there along with descriptions. Tags ---- -There are many tags available for added control precision. Each control has it's own set of tags noting what level, if it's scored/notscored, what OS element it relates to, if it's a patch or audit, and the rule number. -Below is an example of the tag section from a control within this role. Using this example if you set your run to skip all controls with the tag services, this task will be skipped. The opposite can also happen where you run only controls tagged with services. -``` +There are many tags available for added control precision. Each control has it's own set of tags noting what level, if it's scored/notscored, what OS element it relates to, if it's a patch or audit, and the rule number. + +Below is an example of the tag section from a control within this role. Using this example if you set your run to skip all controls with the tag services, this task will be skipped. The opposite can also happen where you run only controls tagged with services. + +```txt tags: - level1-server - level1-workstation @@ -88,7 +94,9 @@ Example Audit Summary This is based on a vagrant image with selections enabled. e.g. No Gui or firewall. Note: More tests are run during audit as we check config and running state. -```` + +```txt + ok: [default] => { "msg": [ "The pre remediation results are: ['Total Duration: 5.454s', 'Count: 338, Failed: 47, Skipped: 5'].", @@ -100,18 +108,21 @@ ok: [default] => { PLAY RECAP ******************************************************************************************************************************************* default : ok=270 changed=23 unreachable=0 failed=0 skipped=140 rescued=0 ignored=0 -```` +``` + Branches ------- -**devel** - This is the default branch and the working development branch. Community pull requests will pull into this branch
-**main** - This is the release branch
-**reports** - This is a protected branch for our scoring reports, no code should ever go here
-**all other branches** - Individual community member branches
+ +- devel - This is the default branch and the working development branch. Community pull requests will pull into this branch +- main - This is the release branch +- reports - This is a protected branch for our scoring reports, no code should ever go here +- all other branches** - Individual community member branches Community Contribution ---------------------- -We encourage you (the community) to contribute to this role. Please read the rules below. +We encourage you (the community) to contribute to this role. Please read the rules below. + - Your work is done in your own individual branch. Make sure to Signed-off and GPG sign all commits you intend to merge. - All community Pull Requests are pulled into the devel branch - Pull Requests into devel will confirm your commits have a GPG signature, Signed-off, and a functional test before being approved diff --git a/defaults/main.yml b/defaults/main.yml index 5e47bd5e..ff73cf2d 100644 --- a/defaults/main.yml +++ b/defaults/main.yml @@ -1,5 +1,5 @@ --- -# defaults file for rhel8-CIS +# defaults file for rhel8-cis rhel8cis_skip_for_travis: false rhel8cis_system_is_container: false @@ -29,14 +29,31 @@ python2_bin: /bin/python2.7 # The audit variable found at the base benchmark: RHEL8-CIS -# Enable goss binary download -rhel8cis_setup_audit: false -# Options are downoad from github or copy from pre downloaded location -# copy or download +# Whether to skip the reboot +rhel8cis_skip_reboot: true + +#### Basic external goss audit enablement settings #### +#### Precise details - per setting can be found at the bottom of this file #### + +### Goss is required on the remote host +setup_audit: false +# How to retrive goss +# Options are copy or download - detailed settings at the bottom of this file +# you will need to access to either github or the file already dowmloaded get_goss_file: download -# Enable audits to run -rhel8cis_run_audit: false +# how to get audit files onto host options +# options are git/copy/get_url - use local if already available to to the host (adjust paths accordingly) +audit_content: git + +# enable audits to run - this runs the audit and get the latest content +run_audit: false + +# Timeout for those cmds that take longer to run where timeout set +audit_cmd_timeout: 30000 + +### End Goss enablements #### +#### Detailed settings found at the end of this document #### # These variables correspond with the CIS rule IDs or paragraph numbers defined in # the CIS benchmark documents. @@ -170,10 +187,12 @@ rhel8cis_rule_3_4_4_1_1: true rhel8cis_rule_3_4_4_1_2: true rhel8cis_rule_3_4_4_1_3: true rhel8cis_rule_3_4_4_1_4: true +rhel8cis_rule_3_4_4_1_5: true rhel8cis_rule_3_4_4_2_1: true rhel8cis_rule_3_4_4_2_2: true rhel8cis_rule_3_4_4_2_3: true rhel8cis_rule_3_4_4_2_4: true +rhel8cis_rule_3_4_4_2_5: true rhel8cis_rule_3_5: true rhel8cis_rule_3_6: true @@ -437,7 +456,7 @@ rhel8cis_nft_tables_autonewtable: true rhel8cis_nft_tables_tablename: filter # 3.4.3.3 Set nftables new chain create -rhel8cis_nft_tables_autoChainCreate: true +rhel8cis_nft_tables_autochaincreate: true # Warning Banner Content (issue, issue.net, motd) rhel8cis_warning_banner: | @@ -495,16 +514,18 @@ rhel8cis_ssh_maxsessions: 4 rhel8cis_inactivelock: lock_days: 30 -# 5.3.1/5.3.2 Custon authselect profile settings. Settings in place now will fail, they are place holders from the control example +# 5.3.1/5.3.2 Custom authselect profile settings. Settings in place now will fail, they are place holders from the control example +# Due to the way many multiple options and ways to configure this control needs to be enabled and settings adjusted to minimise risk +rhel8cis_use_authconfig: false rhel8cis_authselect: custom_profile_name: custom-profile default_file_to_copy: "sssd --symlink-meta" options: with-sudo with-faillock without-nullok -# 5.3.1 Enable automation to creat custom profile settings, using the setings above +# 5.3.1 Enable automation to create custom profile settings, using the settings above rhel8cis_authselect_custom_profile_create: false -# 5.3.2 Enable autmoation to select custom profile options, using the settings above +# 5.3.2 Enable automation to select custom profile options, using the settings above rhel8cis_authselect_custom_profile_select: false rhel8cis_pass: @@ -513,7 +534,7 @@ rhel8cis_pass: warn_age: 7 # Syslog system - either rsyslog or syslog-ng rhel8cis_syslog: rsyslog -rhel8cis_rsyslog_ansibleManaged: true +rhel8cis_rsyslog_ansiblemanaged: true rhel8cis_vartmp: source: /tmp @@ -551,45 +572,52 @@ rhel8cis_rpm_audit_file: /var/tmp/rpm_file_check # RHEL-08_6.1.10 Allow ansible to adjust world-writable files. False will just display world-writable files, True will remove world-writable rhel8cis_no_world_write_adjust: true rhel8cis_passwd_label: "{{ (this_item | default(item)).id }}: {{ (this_item | default(item)).dir }}" -rhel8cis_dotperm_ansibleManaged: true +# 6.2.9 +rhel8cis_dotperm_ansiblemanaged: true +#### Goss Configuration Settings #### -# Goss Audit Variables -# how to get audit files onto host options -# options are git/copy/get_url -rhel8cis_audit_content: git +### Goss binary settings ### +goss_version: + release: v0.3.16 + checksum: 'sha256:827e354b48f93bce933f5efcd1f00dc82569c42a179cf2d384b040d8a80bfbfb' +audit_bin_path: /usr/local/bin/ +audit_bin: "{{ audit_bin_path }}goss" +audit_format: json + +# if get_goss_file == download change accordingly +goss_url: "https://github.com/aelsabbahy/goss/releases/download/{{ goss_version.release }}/goss-linux-amd64" + +## if get_goss_file - copy the following needs to be updated for your environment +## it is expected that it will be copied from somewhere accessible to the control node +## e.g copy from ansible control node to remote host +copy_goss_from_path: /some/accessible/path +### Goss Audit Benchmark file ### +## managed by the control rhel8cis_audit_content # git rhel8cis_audit_file_git: "https://github.com/ansible-lockdown/{{ benchmark }}-Audit.git" rhel8cis_audit_git_version: main # copy: -# rhel8cis_audit_local_copy: "some path to copy from" +rhel8cis_audit_local_copy: "some path to copy from" # get_url: -# rhel8cis_audit_files_url: "some url maybe s3?" - - -## audit controls ## -goss_version: - release: v0.3.16 - checksum: 'sha256:827e354b48f93bce933f5efcd1f00dc82569c42a179cf2d384b040d8a80bfbfb' - -### Audit Settings ### -# goss_checksum: "checksum_{{ goss_version }}" -goss_path: /usr/local/bin/ -goss_bin: "{{ goss_path }}goss" -goss_format: documentation -goss_url: "https://github.com/aelsabbahy/goss/releases/download/{{ goss_version.release }}/goss-linux-amd64" - -## Goss tests information -goss_audit_dir: "/var/tmp/{{ benchmark }}-Audit/" -goss_file: "{{ goss_audit_dir }}goss.yml" -goss_vars_path: "{{ goss_audit_dir }}/vars/{{ ansible_hostname }}.yml" -goss_out_dir: '/var/tmp' -pre_audit_outfile: "{{ goss_out_dir }}/{{ ansible_hostname }}_pre_scan_{{ ansible_date_time.epoch }}" -post_audit_outfile: "{{ goss_out_dir }}/{{ ansible_hostname }}_post_scan_{{ ansible_date_time.epoch }}" - -Audit_results: | +rhel8cis_audit_files_url: "some url maybe s3?" + +# Where the goss audit configuration will be stored +rhel8cis_audit_files: "/var/tmp/{{ benchmark }}-Audit/" + +## Goss configuration information +# Where the goss configs and outputs are stored +audit_out_dir: '/var/tmp' +audit_conf_dir: "{{ audit_out_dir }}/{{ benchmark }}-Audit/" +pre_audit_outfile: "{{ audit_out_dir }}/{{ ansible_hostname }}_pre_scan_{{ ansible_date_time.epoch }}.{{ audit_format }}" +post_audit_outfile: "{{ audit_out_dir }}/{{ ansible_hostname }}_post_scan_{{ ansible_date_time.epoch }}.{{ audit_format }}" + +## The following should not need changing +goss_file: "{{ audit_conf_dir }}goss.yml" +audit_vars_path: "{{ audit_conf_dir }}/vars/{{ ansible_hostname }}.yml" +audit_results: | The pre remediation results are: {{ pre_audit_summary }}. The post remediation results are: {{ post_audit_summary }}. - Full breakdown can be found in {{ goss_out_dir }} \ No newline at end of file + Full breakdown can be found in {{ audit_out_dir }} diff --git a/handlers/main.yml b/handlers/main.yml index f8635154..fe7b5da7 100644 --- a/handlers/main.yml +++ b/handlers/main.yml @@ -100,3 +100,7 @@ service: name: syslog-ng state: restarted + +- name: systemd_daemon_reload + systemd: + daemon-reload: yes diff --git a/meta/main.yml b/meta/main.yml index 5f04b77b..797cd408 100644 --- a/meta/main.yml +++ b/meta/main.yml @@ -1,6 +1,6 @@ --- galaxy_info: - author: "Sam Doran, Josh Springer, Daniel Shepherd, Bas Meijeri, James Cassell, Mike Renfro, DFed, George Nalen" + author: "Sam Doran, Josh Springer, Daniel Shepherd, Bas Meijeri, James Cassell, Mike Renfro, DFed, George Nalen, Mark Bolwell" description: "Apply the DISA RHEL 8 CIS" company: "MindPoint Group" license: MIT @@ -13,6 +13,6 @@ galaxy_info: galaxy_tags: - system - security - - CIS + - cis - hardening dependencies: [] diff --git a/tasks/LE_audit_setup.yml b/tasks/LE_audit_setup.yml index 54b95b36..61a4cdf1 100644 --- a/tasks/LE_audit_setup.yml +++ b/tasks/LE_audit_setup.yml @@ -1,9 +1,9 @@ --- -- name: Download goss binary +- name: Download audit binary get_url: url: "{{ goss_url }}" - dest: "{{ goss_bin }}" + dest: "{{ audit_bin }}" owner: root group: root checksum: "{{ goss_version.checksum }}" @@ -11,10 +11,10 @@ when: - get_goss_file == 'download' -- name: copy goss binary +- name: copy audit binary copy: src: - dest: "{{ goss_bin }}" + dest: "{{ audit_bin }}" mode: 0555 owner: root group: root diff --git a/tasks/main.yml b/tasks/main.yml index cdad25cd..6595b052 100644 --- a/tasks/main.yml +++ b/tasks/main.yml @@ -20,7 +20,7 @@ assert: that: rhel8cis_crypto_policy in rhel8cis_allowed_crypto_policies -- name: Check rhel7cis_bootloader_password_hash variable has been changed +- name: Check rhel8cis_bootloader_password_hash variable has been changed assert: that: rhel8cis_bootloader_password_hash != 'grub.pbkdf2.sha512.changethispassword' msg: "This role will not be able to run single user password commands as rhel8cis_bootloader_password_hash variable has not been set" @@ -28,15 +28,35 @@ - rhel8cis_set_boot_pass - rhel8cis_rule_1_5_2 +- name: "check sugroup exists if used" + block: + - name: "Check su group exists if defined" + shell: grep -w "{{ rhel8cis_sugroup }}" /etc/group + register: sugroup_exists + changed_when: false + failed_when: sugroup_exists.rc >= 2 + tags: + - skip_ansible_lint + + - name: Check sugroup if defined exists before continuing + assert: + that: sugroup_exists.rc == 0 + msg: "The variable rhel8cis_sugroup is defined but does not exist please rectify" + when: + - rhel8cis_sugroup is defined + - rhel8cis_rule_5_7 + tags: + - rule_5.7 + - include: prelim.yml become: yes tags: - prelim_tasks - always -- import_tasks: pre_LE_audit.yml +- import_tasks: pre_remediation_audit.yml when: - - rhel8cis_run_audit + - run_audit - name: Gather the package facts package_facts: @@ -80,15 +100,12 @@ - post_tasks - always -- name: flush handlers - meta: flush_handlers - -- import_tasks: post_LE_audit.yml +- import_tasks: post_remediation_audit.yml when: - - rhel8cis_run_audit + - run_audit - name: Show Audit Summary debug: - msg: "{{ Audit_results.split('\n') }}" + msg: "{{ audit_results.split('\n') }}" when: - - rhel8cis_run_audit + - run_audit diff --git a/tasks/post.yml b/tasks/post.yml index d5a44ad8..3c3ced3f 100644 --- a/tasks/post.yml +++ b/tasks/post.yml @@ -2,7 +2,14 @@ # Post tasks - name: Perform DNF package cleanup - dnf: - autoremove: yes + dnf: + autoremove: yes changed_when: no - ignore_errors: yes + +- name: flush handlers + meta: flush_handlers + +- name: Reboot host + reboot: + when: + - not rhel8cis_skip_reboot diff --git a/tasks/post_LE_audit.yml b/tasks/post_remediation_audit.yml similarity index 83% rename from tasks/post_LE_audit.yml rename to tasks/post_remediation_audit.yml index 98431573..6bfa7719 100644 --- a/tasks/post_LE_audit.yml +++ b/tasks/post_remediation_audit.yml @@ -2,12 +2,14 @@ - name: "Run post_remediation {{ benchmark }} audit" goss: - goss_path: "{{ goss_bin }}" + goss_path: "{{ audit_bin }}" path: "{{ goss_file }}" - vars_path: "{{ goss_vars_path }}" - format: "{{ goss_format }}" + vars_path: "{{ audit_vars_path }}" + format: "{{ audit_format }}" output_file: "{{ post_audit_outfile }}" failed_when: false + environment: + GOSS_FMT_OPTIONS: Pretty - name: ensure audit files readable by users file: @@ -31,7 +33,7 @@ vars: summary: 'summary."summary-line"' when: - - goss_format == "json" + - audit_format == "json" - name: Capture audit data if documentation format block: @@ -44,4 +46,4 @@ set_fact: post_audit_summary: "{{ post_audit.stdout_lines }}" when: - - goss_format == "documentation" + - audit_format == "documentation" diff --git a/tasks/pre_LE_audit.yml b/tasks/pre_LE_audit.yml deleted file mode 100644 index d7fb3db3..00000000 --- a/tasks/pre_LE_audit.yml +++ /dev/null @@ -1,108 +0,0 @@ ---- - -- name: Setup the LE audit - include_tasks: LE_audit_setup.yml - when: - - rhel8cis_setup_audit - tags: - - setup_audit - -- name: "Ensure {{ goss_audit_dir }} exists" - file: - path: "{{ goss_audit_dir }}" - state: directory - mode: '0755' - -- name: If using git for content set up - block: - - name: Install git - package: - name: git - state: present - - - name: retrieve audit content files from git - git: - repo: "{{ rhel8cis_audit_file_git }}" - dest: "{{ goss_audit_dir }}" - version: "{{ rhel8cis_audit_git_version }}" - when: - - rhel8cis_audit_content == 'git' - -- name: copy to audit content files to server - copy: - src: "{{ rhel8cis_audit_local_copy }}" - dest: "{{ goss_audit_dir }}" - owner: root - group: root - mode: 0640 - when: - - rhel8cis_audit_content == 'copy' - -- name: get audit content from url - get_url: - url: "{{ rhel8cis_audit_files_url }}" - dest: "{{ goss_audit_dir }}" - when: - - rhel8cis_audit_content == 'get_url' - -- name: Check Goss is available - block: - - name: Check for goss file - stat: - path: "{{ goss_bin }}" - register: goss_available - - - name: If audit ensure goss is available - assert: - msg: "Audit has been selected: unable to find goss binary at {{ goss_bin }}" - when: - - not goss_available.stat.exists - when: - - rhel8cis_run_audit - -- name: Copy ansible default vars values to test audit - template: - src: ansible_vars_goss.yml.j2 - dest: "{{ goss_vars_path }}" - mode: 0600 - when: - - rhel8cis_run_audit - tags: - - goss_template - -- name: "Run pre_remediation {{ benchmark }} audit" - goss: - goss_path: "{{ goss_bin }}" - path: "{{ goss_file }}" - vars_path: "{{ goss_vars_path }}" - format: "{{ goss_format }}" - output_file: "{{ pre_audit_outfile }}" - failed_when: false - -- name: Capture audit data if json format - block: - - name: "capture data {{ pre_audit_outfile }}" - command: "cat {{ pre_audit_outfile }}" - register: pre_audit - changed_when: false - - - name: Capture pre-audit result - set_fact: - pre_audit_summary: "{{ pre_audit.stdout | from_json |json_query(summary) }}" - vars: - summary: 'summary."summary-line"' - when: - - goss_format == "json" - -- name: Capture audit data if documentation format - block: - - name: "capture data {{ pre_audit_outfile }}" - command: "tail -2 {{ pre_audit_outfile }}" - register: pre_audit - changed_when: false - - - name: Capture pre-audit result - set_fact: - pre_audit_summary: "{{ pre_audit.stdout_lines }}" - when: - - goss_format == "documentation" diff --git a/tasks/pre_remediation_audit.yml b/tasks/pre_remediation_audit.yml new file mode 100644 index 00000000..201b996d --- /dev/null +++ b/tasks/pre_remediation_audit.yml @@ -0,0 +1,124 @@ +--- + +- name: Setup the audit + include_tasks: LE_audit_setup.yml + when: + - setup_audit + tags: + - setup_audit + +- name: "Ensure {{ audit_conf_dir }} exists" + file: + path: "{{ audit_conf_dir }}" + state: directory + mode: '0755' + +- name: If using git for content set up + block: + - name: Install git (rh8 python3) + package: + name: git + state: present + when: ansible_distribution_major_version == 8 + + - name: Install git (rh7 python2) + package: + name: git + state: present + vars: + ansible_python_interpreter: "{{ python2_bin }}" + when: ansible_distribution_major_version == 7 + + - name: retrieve audit content files from git + git: + repo: "{{ rhel8cis_audit_file_git }}" + dest: "{{ audit_conf_dir }}" + version: "{{ rhel8cis_audit_git_version }}" + when: + - audit_content == 'git' + +- name: copy to audit content files to server + copy: + src: "{{ rhel8cis_audit_local_copy }}" + dest: "{{ audit_conf_dir }}" + mode: 0644 + when: + - audit_content == 'copy' + +- name: get audit content from url + get_url: + url: "{{ rhel8cis_audit_files_url }}" + dest: "{{ audit_conf_dir }}" + when: + - audit_content == 'get_url' + +- name: Check Goss is available + block: + - name: Check for goss file + stat: + path: "{{ audit_bin }}" + register: goss_available + + - name: If audit ensure goss is available + assert: + msg: "Audit has been selected: unable to find goss binary at {{ audit_bin }}" + when: + - not goss_available.stat.exists + when: + - run_audit + +- name: "Check whether machine is UEFI-based" + stat: + path: /sys/firmware/efi + register: rhel8_efi_boot + tags: + - goss_template + +- name: Copy ansible default vars values to test audit + template: + src: ansible_vars_goss.yml.j2 + dest: "{{ audit_vars_path }}" + mode: 0600 + when: + - run_audit + tags: + - goss_template + +- name: "Run pre_remediation {{ benchmark }} audit" + goss: + goss_path: "{{ audit_bin }}" + path: "{{ goss_file }}" + vars_path: "{{ audit_vars_path }}" + format: "{{ audit_format }}" + output_file: "{{ pre_audit_outfile }}" + failed_when: false + environment: + GOSS_FMT_OPTIONS: Pretty + +- name: Capture audit data if json format + block: + - name: "capture data {{ pre_audit_outfile }}" + command: "cat {{ pre_audit_outfile }}" + register: pre_audit + changed_when: false + + - name: Capture pre-audit result + set_fact: + pre_audit_summary: "{{ pre_audit.stdout | from_json |json_query(summary) }}" + vars: + summary: 'summary."summary-line"' + when: + - audit_format == "json" + +- name: Capture audit data if documentation format + block: + - name: "capture data {{ pre_audit_outfile }}" + command: "tail -2 {{ pre_audit_outfile }}" + register: pre_audit + changed_when: false + + - name: Capture pre-audit result + set_fact: + pre_audit_summary: "{{ pre_audit.stdout_lines }}" + when: + - audit_format == "documentation" diff --git a/tasks/prelim.yml b/tasks/prelim.yml index 7c65e235..885cd408 100644 --- a/tasks/prelim.yml +++ b/tasks/prelim.yml @@ -33,10 +33,22 @@ check_mode: no register: system_wide_crypto_policy +- name: "PRELIM | if systemd coredump" + stat: + path: /etc/systemd/coredump.conf + register: systemd_coredump + when: + - rhel8cis_rule_1_6_1 + +- name: "PRELIM | Section 1.1 | Create list of mount points" + set_fact: + mount_names: "{{ ansible_mounts | map(attribute='mount') | list }}" + - name: "PRELIM | Section 4.1 | Configure System Accounting (auditd)" package: name: audit state: present + when: rhel8cis_level_2 - name: "PRELIM | Section 5.1 | Configure cron" package: @@ -48,6 +60,7 @@ name: authconfig state: present when: + - rhel8cis_use_authconfig - rhel8cis_rule_5_3_1 or rhel8cis_rule_5_3_2 or rhel8cis_rule_5_3_3 diff --git a/tasks/section_1/cis_1.1.1.x.yml b/tasks/section_1/cis_1.1.1.x.yml index 1b8efcd3..b6dffa91 100644 --- a/tasks/section_1/cis_1.1.1.x.yml +++ b/tasks/section_1/cis_1.1.1.x.yml @@ -1,7 +1,8 @@ --- -- name: "SCORED | 1.1.1.1 | PATCH | Ensure mounting of cramfs filesystems is disabled" + +- name: "1.1.1.1 | L1 | PATCH | Ensure mounting of cramfs filesystems is disabled" block: - - name: "SCORED | 1.1.1.1 | PATCH | Ensure mounting of cramfs filesystems is disabled | Edit modprobe config" + - name: "1.1.1.1 | L1 | PATCH | Ensure mounting of cramfs filesystems is disabled | Edit modprobe config" lineinfile: dest: /etc/modprobe.d/CIS.conf regexp: "^(#)?install cramfs(\\s|$)" @@ -9,7 +10,7 @@ create: yes mode: 0600 - - name: "SCORED | 1.1.1.1 | PATCH | Remove cramfs module | Disable cramfs" + - name: "1.1.1.1 | L1 | PATCH | Ensure mounting of cramfs filesystems is disabled | Disable cramfs" modprobe: name: cramfs state: absent @@ -24,9 +25,9 @@ - rule_1.1.1.1 - cramfs -- name: "NOT SCORED | 1.1.1.2 | PATCH | Ensure mounting of vFAT filesystems is limited" +- name: "1.1.1.2 | L2 | PATCH | Ensure mounting of vFAT filesystems is limited" block: - - name: "NOT SCORED | 1.1.1.2 | PATCH | Ensure mounting of vFAT filesystems is limited | Edit modprobe config" + - name: "1.1.1.2 | L2 | PATCH | Ensure mounting of vFAT filesystems is limited | Edit modprobe config" lineinfile: dest: /etc/modprobe.d/CIS.conf regexp: "^(#)?install vfat(\\s|$)" @@ -34,7 +35,7 @@ create: yes mode: 0600 - - name: "NOT SCORED | 1.1.1.2 | PATCH | Ensure mounting of vFAT filesystems is limited | Disable vFAT" + - name: "1.1.1.2 | L2 | PATCH | Ensure mounting of vFAT filesystems is limited | Disable vFAT" modprobe: name: vfat state: absent @@ -50,9 +51,9 @@ - rule_1.1.1.2 - vfat -- name: "SCORED | 1.1.1.3 | PATCH | Ensure mounting of squashfs filesystems is disabled" +- name: "1.1.1.3 | L1 | PATCH | Ensure mounting of squashfs filesystems is disabled" block: - - name: "SCORED | 1.1.1.3 | PATCH | Ensure mounting of squashfs filesystems is disabled | Edit modprobe config" + - name: "1.1.1.3 | L1 | PATCH | Ensure mounting of squashfs filesystems is disabled | Edit modprobe config" lineinfile: dest: /etc/modprobe.d/CIS.conf regexp: "^(#)?install squashfs(\\s|$)" @@ -60,7 +61,7 @@ create: yes mode: 0600 - - name: "SCORED | 1.1.1.3 | PATCH | Ensure mounting of squashfs filesystems is disabled | Disable squashfs" + - name: "1.1.1.3 | L1 | PATCH | Ensure mounting of squashfs filesystems is disabled | Disable squashfs" modprobe: name: squashfs state: absent @@ -75,9 +76,9 @@ - rule_1.1.1.3 - squashfs -- name: "SCORED | 1.1.1.4 | PATCH | Ensure mounting of udf filesystems is disabled" +- name: "1.1.1.4 | L1 | PATCH | Ensure mounting of udf filesystems is disabled" block: - - name: "SCORED | 1.1.1.4 | PATCH | Ensure mounting of udf filesystems is disable | Edit modprobe config" + - name: "1.1.1.4 | L1 | PATCH | Ensure mounting of udf filesystems is disable | Edit modprobe config" lineinfile: dest: /etc/modprobe.d/CIS.conf regexp: "^(#)?install udf(\\s|$)" @@ -85,7 +86,7 @@ create: yes mode: 0600 - - name: "SCORED | 1.1.1.4 | PATCH | Ensure mounting of udf filesystems is disable | Disable udf" + - name: "1.1.1.4 | L1 | PATCH | Ensure mounting of udf filesystems is disable | Disable udf" modprobe: name: udf state: absent diff --git a/tasks/section_1/cis_1.1.x.yml b/tasks/section_1/cis_1.1.x.yml index ade4ca62..adeb29b3 100644 --- a/tasks/section_1/cis_1.1.x.yml +++ b/tasks/section_1/cis_1.1.x.yml @@ -5,6 +5,7 @@ "SCORED | 1.1.3 | PATCH | Ensure nodev option set on /tmp partition" "SCORED | 1.1.4 | PATCH | Ensure nosuid option set on /tmp partition" "SCORED | 1.1.5 | PATCH | Ensure noexec option set on /tmp partition" + "via fstab" mount: name: /tmp src: "{{ item.device }}" @@ -30,16 +31,53 @@ - rule_1.1.4 - rule_1.1.5 -- name: "SCORED | 1.1.6 | PATCH | Ensure separate partition exists for /var" - mount: - name: /var - src: "{{ item.device }}" - fstype: "{{ item.fstype }}" - state: present - loop: "{{ ansible_mounts }}" +- name: | + "SCORED | 1.1.2 | PATCH | Ensure /tmp is configured" + "SCORED | 1.1.3 | PATCH | Ensure nodev option set on /tmp partition" + "SCORED | 1.1.4 | PATCH | Ensure nosuid option set on /tmp partition" + "SCORED | 1.1.5 | PATCH | Ensure noexec option set on /tmp partition" + "via systemd" + template: + src: etc/systemd/system/tmp.mount.j2 + dest: /etc/systemd/system/tmp.mount + owner: root + group: root + mode: 0644 + notify: systemd restart tmp.mount + when: + - rhel8cis_tmp_svc + - rhel8cis_rule_1_1_2 or + rhel8cis_rule_1_1_3 or + rhel8cis_rule_1_1_4 or + rhel8cis_rule_1_1_5 + tags: + - level1-server + - level1-workstation + - scored + - patch + - mounts + - rule_1.1.3 + - rule_1.1.4 + - rule_1.1.5 + +- name: "1.1.6 | L2 | AUDIT | Ensure separate partition exists for /var" + block: + - name: "1.1.6 | L2 | AUDIT | Ensure separate partition exists for /var | Absent" + debug: + msg: "Warning! {{ required_mount }} doesn't exist. This is a manual task" + register: var_mount_absent + changed_when: var_mount_absent.skipped is undefined + when: + - required_mount not in mount_names + - name: "1.1.6 | L2 | AUDIT | Ensure separate partition exists for /var | Present" + debug: + msg: "Congratulations: {{ required_mount }} exists." + when: + - required_mount in mount_names + vars: + required_mount: '/var' when: - rhel8cis_rule_1_1_6 - - item.mount == "/var" tags: - level2-server - level2-workstation @@ -47,32 +85,38 @@ - patch - mounts - rule_1.1.6 - - skip_ansible_lint -- name: "SCORED | 1.1.7 | PATCH | Ensure separate partition exists for /var/tmp" - mount: - name: /var/tmp - src: "{{ item.device }}" - fstype: "{{ item.fstype }}" - state: present - opts: defaults,{% if rhel8cis_rule_1_1_10 %}noexec,{% endif %}{% if rhel8cis_rule_1_1_8 %}nodev,{% endif %}{% if rhel8cis_rule_1_1_9 %}nosuid{% endif %} - loop: "{{ ansible_mounts }}" +- name: "1.1.7 | L2 | AUDIT | Ensure separate partition exists for /var/tmp | skips if mount absent" + block: + - name: "1.1.7 | L2 | AUDIT | Ensure separate partition exists for /var/tmp | Absent" + debug: + msg: "Warning! {{ required_mount }} doesn't exist. This is a manual task" + register: var_tmp_mount_absent + changed_when: var_tmp_mount_absent.skipped is undefined + when: + - required_mount not in mount_names + - name: "1.1.7 | L2 | AUDIT | Ensure separate partition exists for /var/tmp | Present" + debug: + msg: "Congratulations: {{ required_mount }} exists." + register: var_tmp_mount_present + when: + - required_mount in mount_names + vars: + required_mount: '/var/tmp' when: - rhel8cis_rule_1_1_7 - - item.mount == "/var/tmp" tags: - level2-server - level2-workstation - scored - - patch + - audit - mounts - rule_1.1.7 - - skip_ansible_lint - name: | - "SCORED | 1.1.8 | PATCH | Ensure nodev option set on /var/tmp partition | - SCORED | 1.1.9 | PATCH | Ensure nosuid option set on /var/tmp partition | - SCORED | 1.1.10 | PATCH | Ensure noexec option set on /var/tmp partition" + "1.1.8 | L1 | PATCH | Ensure nodev option set on /var/tmp partition | skips if mount absent" + "1.1.9 | L1 | PATCH | Ensure nosuid option set on /var/tmp partition | skips if mount absent" + "1.1.10 | L1 | PATCH | Ensure noexec option set on /var/tmp partition | skips if mount absent" mount: name: /var/tmp src: "{{ item.device }}" @@ -81,8 +125,9 @@ opts: defaults,{% if rhel8cis_rule_1_1_10 %}noexec,{% endif %}{% if rhel8cis_rule_1_1_8 %}nodev,{% endif %}{% if rhel8cis_rule_1_1_9 %}nosuid{% endif %} loop: "{{ ansible_mounts }}" when: + - var_tmp_mount_present is defined - item.mount == "/var/tmp" - - rhel8cis_rule_1_1_7 + - rhel8cis_rule_1_1_7 # This is required so the check takes place - rhel8cis_rule_1_1_8 or rhel8cis_rule_1_1_9 or rhel8cis_rule_1_1_10 @@ -92,48 +137,91 @@ - scored - patch - mounts + - skip_ansible_lint -- name: "SCORED | 1.1.11 | PATCH | Ensure separate partition exists for /var/log" - mount: - name: /var/log - src: "{{ item.device }}" - fstype: "{{ item.fstype }}" - state: present - loop: "{{ ansible_mounts }}" +- name: "1.1.11 | L2 | AUDIT | Ensure separate partition exists for /var/log" + block: + - name: "1.1.11 | L2 | AUDIT | Ensure separate partition exists for /var/log | Absent" + debug: + msg: "Warning! {{ required_mount }} doesn't exist. This is a manual task" + register: var_log_mount_absent + changed_when: var_log_mount_absent.skipped is undefined + when: + - required_mount not in mount_names + - name: "1.1.11 | L2 | AUDIT | Ensure separate partition exists for /var/log | Present" + debug: + msg: "Congratulations: {{ required_mount }} exists." + when: + - required_mount in mount_names + vars: + required_mount: '/var/log' when: - rhel8cis_rule_1_1_11 - - item.mount == "/var/log" tags: - level2-server - level2-workstation - scored - - patch + - audit - mounts - rule_1.1.11 - skip_ansible_lint -- name: "SCORED | 1.1.12 | PATCH | Ensure separate partition exists for /var/log/audit" - mount: - name: /var/log/audit - src: "{{ item.device }}" - fstype: "{{ item.fstype }}" - state: present - loop: "{{ ansible_mounts }}" +- name: "1.1.12 | L2 | AUDIT | Ensure separate partition exists for /var/log/audit" + block: + - name: "1.1.12 | L2 | AUDIT | Ensure separate partition exists for /var/log/audit | Absent" + debug: + msg: "Warning! {{ required_mount }} doesn't exist. This is a manual task" + register: var_log_audit_mount_absent + changed_when: var_log_audit_mount_absent.skipped is undefined + when: + - required_mount not in mount_names + - name: "1.1.12 | L2 | AUDIT | Ensure separate partition exists for /var/log/audit | Present" + debug: + msg: "Congratulations: {{ required_mount }} exists." + when: + - required_mount in mount_names + vars: + required_mount: '/var/log/audit' when: - rhel8cis_rule_1_1_12 - - item.mount == "/var/log/audit" tags: - level2-server - level2-workstation - scored - - patch + - audit - mounts - rule_1.1.12 + + +- name: "1.1.13 | L2 | AUDIT | Ensure separate partition exists for /home" + block: + - name: "1.1.13 | L2 | AUDIT | Ensure separate partition exists for /home | Absent" + debug: + msg: "Warning! {{ required_mount }} doesn't exist. This is a manual task" + register: home_mount_absent + changed_when: home_mount_absent.skipped is undefined + when: + - required_mount not in mount_names + - name: "1.1.13 | L2 | AUDIT | Ensure separate partition exists for /home | Present" + debug: + msg: "Congratulations: {{ required_mount }} exists." + register: home_mount_present + when: + - required_mount in mount_names + vars: + required_mount: '/home' + when: + - rhel8cis_rule_1_1_13 + tags: + - level2-server + - level2-workstation + - scored + - audit + - mounts + - rule_1.1.13 - skip_ansible_lint -- name: | - "SCORED | 1.1.13 | AUDIT | Ensure separate partition exists for /home" - "SCORED | 1.1.14 | PATCH | Ensure nodev option set on /home partition" +- name: "1.1.14 | L1 | PATCH | Ensure nodev option set on /home partition | skips if mount absent" mount: name: /home src: "{{ item.device }}" @@ -142,31 +230,44 @@ opts: defaults,{% if rhel8cis_rule_1_1_14 %}nodev{% endif %} loop: "{{ ansible_mounts }}" when: + - home_mount_present is defined - item.mount == "/home" - - rhel8cis_rule_1_1_13 or - rhel8cis_rule_1_1_14 + - rhel8cis_rule_1_1_14 tags: - - level2-server - - level2-workstation + - level1-server + - level1-workstation - scored - - audit + - patch - mounts - rule_1.1.13 - skip_ansible_lint - name: | - "SCORED | 1.1.15 | PATCH | Ensure nodev option set on /dev/shm partition | - SCORED | 1.1.16 | PATCH | Ensure nosuid option set on /dev/shm partition | - SCORED | 1.1.17 | PATCH | Ensure noexec option set on /dev/shm partition" - mount: - name: /dev/shm - src: "{{ item.device }}" - fstype: tmpfs - state: present - opts: defaults,{% if rhel8cis_rule_1_1_17 %}noexec,{% endif %}{% if rhel8cis_rule_1_1_15 %}nodev,{% endif %}{% if rhel8cis_rule_1_1_16 %}nosuid{% endif %} - loop: "{{ ansible_mounts }}" + "1.1.15 | L1 | PATCH | Ensure nodev option set on /dev/shm partition | skips if mount absent + 1.1.16 | L1 | PATCH | Ensure nosuid option set on /dev/shm partition | skips if mount absent + 1.1.17 | L1 | PATCH | Ensure noexec option set on /dev/shm partition | skips if mount absent" + block: + - name: | + "1.1.15 | L1 | AUDIT | Ensure nodev option set on /dev/shm partition | Check for /dev/shm existence + 1.1.16 | L1 | AUDIT | Ensure nosuid option set on /dev/shm partition | Check for /dev/shm existence + 1.1.17 | L1 | AUDIT | Ensure noexec option set on /dev/shm partition | Check for /dev/shm existence" + shell: mount -l | grep -E '\s/dev/shm\s' + changed_when: false + failed_when: false + register: rhel8cis_1_1_15_dev_shm_status + + - name: | + "1.1.15 | L1 | PATCH | Ensure nodev option set on /dev/shm partition | skips if mount absent + 1.1.16 | L1 | PATCH | Ensure nosuid option set on /dev/shm partition | skips if mount absent + 1.1.17 | L1 | PATCH | Ensure noexec option set on /dev/shm partition | skips if mount absent" + mount: + name: /dev/shm + src: tmpfs + fstype: tmpfs + state: mounted + opts: defaults,{% if rhel8cis_rule_1_1_17 %}noexec,{% endif %}{% if rhel8cis_rule_1_1_15 %}nodev,{% endif %}{% if rhel8cis_rule_1_1_16 %}nosuid{% endif %} + when: "'dev/shm' in rhel8cis_1_1_15_dev_shm_status.stdout" when: - - item.mount == "/dev/shm" - rhel8cis_rule_1_1_15 or rhel8cis_rule_1_1_16 or rhel8cis_rule_1_1_17 @@ -181,9 +282,9 @@ - rule_1.1.17 - name: | - "NOTSCORED | 1.1.18 | AUDIT | Ensure nodev option set on removable media partitions" - "NOTSCORED | 1.1.19 | AUDIT | Ensure nosuid option set on removable media partitions" - "NOTSCORED | 1.1.20 | AUDIT | Ensure noexec option set on removable media partitions" + "1.1.18 | L1 | PATCH | Ensure nodev option set on removable media partitions" + "1.1.19 | L1 | PATCH | Ensure nosuid option set on removable media partitions" + "1.1.20 | L1 | PATCH | Ensure noexec option set on removable media partitions" debug: msg: "--> Not relevant" changed_when: false @@ -201,7 +302,7 @@ - rule_1.1.19 - rule_1.1.20 -- name: "SCORED | 1.1.21 | PATCH | Ensure sticky bit is set on all world-writable directories" +- name: "1.1.21 | L1 | PATCH | Ensure sticky bit is set on all world-writable directories" shell: df --local -P | awk {'if (NR!=1) print $6'} | xargs -I '{}' find '{}' -xdev -type d -perm -0002 2>/dev/null | xargs chmod a+t args: warn: no @@ -218,7 +319,7 @@ - permissons - rule_1.1.21 -- name: "SCORED | 1.1.22 | PATCH | Disable Automounting" +- name: "1.1.22 | L1 | PATCH | Disable Automounting" service: name: autofs enabled: no @@ -234,9 +335,9 @@ - automounting - rule_1.1.22 -- name: "SCORED | 1.1.23 | PATCH | Disable USB Storage" +- name: "1.1.23 | L1 | PATCH | Disable USB Storage" block: - - name: "SCORED | 1.1.23 | PATCH | Disable USB Storage | Edit modprobe config" + - name: "1.1.23 | L1 | PATCH | Disable USB Storage | Edit modprobe config" lineinfile: dest: /etc/modprobe.d/CIS.conf regexp: "^(#)?install usb-storage(\\s|$)" @@ -246,7 +347,7 @@ group: root mode: 0640 - - name: "SCORED | 1.1.23 | PATCH | Disable USB Storage | Edit modprobe config" + - name: "1.1.23 | L1 | PATCH | Disable USB Storage | Edit modprobe config" modprobe: name: usb-storage state: absent diff --git a/tasks/section_1/cis_1.10.yml b/tasks/section_1/cis_1.10.yml index c5339ae9..56d72fe6 100644 --- a/tasks/section_1/cis_1.10.yml +++ b/tasks/section_1/cis_1.10.yml @@ -1,6 +1,6 @@ --- -- name: "SCORED | 1.10 | PATCH | Ensure system-wide crypto policy is not legacy" +- name: "1.10 | L1 | PATCH | Ensure system-wide crypto policy is not legacy" shell: | update-crypto-policies --set "{{ rhel8cis_crypto_policy }}" update-crypto-policies diff --git a/tasks/section_1/cis_1.11.yml b/tasks/section_1/cis_1.11.yml index 48367702..2b6cf917 100644 --- a/tasks/section_1/cis_1.11.yml +++ b/tasks/section_1/cis_1.11.yml @@ -1,6 +1,6 @@ --- -- name: "SCORED | 1.11 | PATCH | Ensure system-wide crypto policy is FUTURE or FIPS" +- name: "1.11 | L2 | PATCH | Ensure system-wide crypto policy is FUTURE or FIPS" shell: | update-crypto-policies --set "{{ rhel8cis_crypto_policy }}" update-crypto-policies diff --git a/tasks/section_1/cis_1.2.x.yml b/tasks/section_1/cis_1.2.x.yml index 8b951bcb..6d40beab 100644 --- a/tasks/section_1/cis_1.2.x.yml +++ b/tasks/section_1/cis_1.2.x.yml @@ -1,11 +1,12 @@ --- -- name: "NOTSCORED | 1.2.1 | PATCH | Ensure Red Hat Subscription Manager connection is configured" +- name: "1.2.1 | L1 | PATCH | Ensure Red Hat Subscription Manager connection is configured" redhat_subscription: state: present username: "{{ rhel8cis_rh_sub_user }}" password: "{{ rhel8cis_rh_sub_password }}" auto_attach: true + no_log: true when: - ansible_distribution == "RedHat" - rhel8cis_rhnsd_required @@ -16,8 +17,9 @@ - notscored - patch - rule_1.2.1 + - skip_ansible_lint # Added as no_log still errors on ansuible-lint -- name: "NOTSCORED | 1.2.2 | PATCH | Disable the rhnsd Daemon" +- name: "1.2.2 | L1 | PATCH | Disable the rhnsd Daemon" service: name: rhnsd state: stopped @@ -33,7 +35,7 @@ - patch - rule_1.2.2 -- name: "NOTSCORED | 1.2.3 | PATCH | Ensure GPG keys are configured" +- name: "1.2.3 | L1 | AUDIT | Ensure GPG keys are configured" command: gpg --quiet --with-fingerprint /etc/pki/rpm-gpg/RPM-GPG-KEY-{{ ansible_distribution|lower }}-release when: - rhel8cis_rule_1_2_3 @@ -45,16 +47,16 @@ - patch - rule_1.2.3 -- name: "SCORED | 1.2.4 | PATCH | Ensure gpgcheck is globally activated" +- name: "1.2.4 | L1 | PATCH | Ensure gpgcheck is globally activated" block: - - name: "SCORED | 1.2.4 | AUDIT | Ensure gpgcheck is globally activated | Find repos" + - name: "1.2.4 | L1 | AUDIT | Ensure gpgcheck is globally activated | Find repos" find: paths: /etc/yum.repos.d patterns: "*.repo" register: yum_repos changed_when: false - - name: "SCORED | 1.2.4 | PATCH | Ensure gpgcheck is globally activated | Update yum.repos" + - name: "1.2.4 | L1 | PATCH | Ensure gpgcheck is globally activated | Update yum.repos" replace: name: "{{ item.path }}" regexp: "^gpgcheck=0" @@ -70,9 +72,9 @@ - patch - rule_1.2.4 -- name: "NOTSCORED | 1.2.5 | PATCH | Ensure package manager repositories are configured" +- name: "1.2.5 | L1 | Ensure package manager repositories are configured" block: - - name: "NOTSCORED | 1.2.5 | PATCH | Ensure package manager repositories are configured | Get repo list" + - name: "1.2.5 | L1 | AUDIT | Ensure package manager repositories are configured | Get repo list" command: dnf repolist changed_when: false failed_when: false @@ -81,10 +83,10 @@ args: warn: false - - name: "NOTSCORED | 1.2.5 | PATCH | Ensure package manager repositories are configured | Display repo list" + - name: "1.2.5 | L1 | AUDIT | Ensure package manager repositories are configured | Display repo list" debug: msg: - - "Alert! Below are the configured repos. Please review and make sure all allign with site policy" + - "Alert! Below are the configured repos. Please review and make sure all align with site policy" - "{{ dnf_configured.stdout_lines }}" when: - rhel8cis_rule_1_2_5 diff --git a/tasks/section_1/cis_1.3.x.yml b/tasks/section_1/cis_1.3.x.yml index f6d6d910..6b2826f9 100644 --- a/tasks/section_1/cis_1.3.x.yml +++ b/tasks/section_1/cis_1.3.x.yml @@ -1,6 +1,6 @@ --- -- name: "SCORED | 1.3.1 | PATCH | Ensure sudo is installed" +- name: "1.3.1 | L1 | PATCH | Ensure sudo is installed" package: name: sudo state: present @@ -14,7 +14,7 @@ - patch - rule_1.3.1 -- name: "SCORED | 1.3.2 | PATCH | Ensure sudo commands use pty" +- name: "1.3.2 | L1 | PATCH | Ensure sudo commands use pty" lineinfile: dest: /etc/sudoers line: "Defaults use_pty" @@ -28,14 +28,14 @@ - patch - rule_1.3.2 -- name: "SCORED | 1.3.3 | PATCH | Ensure sudo log file exists" +- name: "1.3.3 | L1 | PATCH | Ensure sudo log file exists" lineinfile: dest: /etc/sudoers regexp: '^Defaults logfile=' line: 'Defaults logfile="{{ rhel8cis_varlog_location }}"' state: present when: - - rhel8cis_rule_1_3_1 + - rhel8cis_rule_1_3_3 tags: - level1-server - level1-workstation diff --git a/tasks/section_1/cis_1.4.x.yml b/tasks/section_1/cis_1.4.x.yml index ef482b75..7eff30a5 100644 --- a/tasks/section_1/cis_1.4.x.yml +++ b/tasks/section_1/cis_1.4.x.yml @@ -1,13 +1,13 @@ --- -- name: "SCORED | 1.4.1 | PATCH | Ensure AIDE is installed" +- name: "1.4.1 | L1 | PATCH | Ensure AIDE is installed" block: - - name: "SCORED | 1.4.1 | PATCH | Ensure AIDE is installed | Install AIDE" + - name: "1.4.1 | L1 | PATCH | Ensure AIDE is installed | Install AIDE" package: name: aide state: present - - name: "SCORED | 1.4.1 | PATCH | Ensure AIDE is installed | Configure AIDE" + - name: "1.4.1 | L1 | PATCH | Ensure AIDE is installed | Configure AIDE" command: /usr/sbin/aide --init -B 'database_out=file:/var/lib/aide/aide.db.gz' changed_when: false failed_when: false @@ -27,7 +27,7 @@ - patch - rule_1.4.1 -- name: "SCORED | 1.4.2 | PATCH | Ensure filesystem integrity is regularly checked" +- name: "1.4.2 | L1 | PATCH | Ensure filesystem integrity is regularly checked" cron: name: Run AIDE integrity check cron_file: "{{ rhel8cis_aide_cron['cron_file'] }}" diff --git a/tasks/section_1/cis_1.5.x.yml b/tasks/section_1/cis_1.5.x.yml index 5b4def04..e9e84f65 100644 --- a/tasks/section_1/cis_1.5.x.yml +++ b/tasks/section_1/cis_1.5.x.yml @@ -1,11 +1,26 @@ --- -- name: "SCORED | 1.5.1 | PATCH | Ensure permissions on bootloader config are configured" - file: - path: "{{ grub_cfg.stat.lnk_source }}" - owner: root - group: root - mode: 0600 +- name: "1.5.1 | L1 | PATCH | Ensure permissions on bootloader config are configured" + block: + - name: "1.5.1 | L1 | PATCH | Ensure permissions on bootloader config are configured" + file: + path: "{{ grub_cfg.stat.lnk_source }}" + owner: root + group: root + mode: 0600 + + - name: "1.5.1 | L1 | PATCH | Ensure permissions on bootloader config are configured | UEFI" + mount: + name: /boot/efi + src: "UUID={{ item.uuid }}" + fstype: vfat + state: present + opts: defaults,umask=0027,fmask=0077,uid=0,gid=0 + passno: '0' + loop: "{{ ansible_mounts }}" + when: + - not rhel8cis_legacy_boot + - item.mount == "/boot/efi" when: - rhel8cis_rule_1_5_1 - grub_cfg.stat.exists @@ -18,7 +33,7 @@ - patch - rule_1.5.1 -- name: "SCORED | 1.5.2 | PATCH | Ensure bootloader password is set" +- name: "1.5.2 | L1 | PATCH | Ensure bootloader password is set" copy: dest: /boot/grub2/user.cfg content: "GRUB2_PASSWORD={{ rhel8cis_bootloader_password_hash }}" @@ -39,22 +54,21 @@ - patch - rule_1.5.2 -- name: "NOTSCORED | 1.5.3 | PATCH | Ensure authentication required for single user mode" +- name: "1.5.3 | L1 | PATCH | Ensure authentication required for single user mode" block: - - name: "NOTSCORED | 1.5.3 | PATCH | Ensure authentication required for single user mode | Emergency service" + - name: "1.5.3 | L1 | PATCH | Ensure authentication required for single user mode | Emergency service" lineinfile: dest: /usr/lib/systemd/system/emergency.service regexp: '/sbin/sulogin' line: 'ExecStart=-/usr/lib/systemd/systemd-sulogin-shell emergency' - - name: "NOTSCORED | 1.5.3 | PATCH | Ensure authentication required for single user mode | Rescue service" + - name: "1.5.3 | L1 | PATCH | Ensure authentication required for single user mode | Rescue service" lineinfile: dest: /usr/lib/systemd/system/rescue.service regexp: '/sbin/sulogin' line: 'ExecStart=-/usr/lib/systemd/systemd-sulogin-shell rescue' when: - rhel8cis_rule_1_5_3 - - ansible_distribution_major_version == 8 tags: - level1-server - level1-workstation diff --git a/tasks/section_1/cis_1.6.x.yml b/tasks/section_1/cis_1.6.x.yml index 1e5130df..0a456e75 100644 --- a/tasks/section_1/cis_1.6.x.yml +++ b/tasks/section_1/cis_1.6.x.yml @@ -1,8 +1,8 @@ --- -- name: "SCORED | 1.6.1 | PATCH | Ensure core dumps are restricted" +- name: "1.6.1 | L1 | PATCH | Ensure core dumps are restricted" block: - - name: "SCORED | 1.6.1 | PATCH | Ensure core dumps are restricted | Update limits.conf file" + - name: "1.6.1 | L1 | Ensure core dumps are restricted | Update limits.conf file" lineinfile: state: present dest: /etc/security/limits.conf @@ -10,7 +10,7 @@ line: '* hard core 0' insertbefore: '^# End of file' - - name: "SCORED | 1.6.1 | PATCH | Ensure core dumps are restricted | Set active kernel parameter" + - name: "1.6.1 | L1 | PATCH | Ensure core dumps are restricted | Set active kernel parameter" sysctl: name: fs.suid_dumpable value: '0' @@ -18,6 +18,20 @@ reload: yes sysctl_set: yes ignoreerrors: yes + + - name: "1.6.1 | L1 | PATCH | Ensure core dumps are restricted | if systemd coredump" + lineinfile: + path: /etc/systemd/coredump.conf + regexp: "{{ item.regexp }}" + line: "{{ item.regexp }}{{ item.line }}" + state: present + with_items: + - {'regexp': 'Storage=', 'line': 'none'} + - {'regexp': 'ProcessSizeMax=', 'line': '0'} + notify: + - systemd_daemon_reload + when: + - systemd_coredump.stat.exists when: - rhel8cis_rule_1_6_1 tags: @@ -28,7 +42,7 @@ - patch - rule_1.6.1 -- name: "SCORED | 1.6.2 | PATCH | Ensure address space layout randomization (ASLR) is enabled" +- name: "1.6.2 | L1 | PATCH | Ensure address space layout randomization (ASLR) is enabled" sysctl: name: kernel.randomize_va_space value: '2' diff --git a/tasks/section_1/cis_1.7.1.x.yml b/tasks/section_1/cis_1.7.1.x.yml index 8debe526..e09a156f 100644 --- a/tasks/section_1/cis_1.7.1.x.yml +++ b/tasks/section_1/cis_1.7.1.x.yml @@ -1,6 +1,6 @@ --- -- name: "SCORED | 1.7.1.1 | PATCH | Ensure SELinux is installed" +- name: "1.7.1.1 | L2 | PATCH | Ensure SELinux is installed" package: name: libselinux state: present @@ -13,7 +13,7 @@ - patch - rule_1.7.1.1 -- name: "SCORED | 1.7.1.2 | PATCH | Ensure SELinux is not disabled in bootloader configuration" +- name: "1.7.1.2 | L2 | PATCH | Ensure SELinux is not disabled in bootloader configuration" replace: dest: /etc/default/grub regexp: '(selinux|enforcing)\s*=\s*0\s*' @@ -30,7 +30,7 @@ - patch - rule_1.7.1.2 -- name: "SCORED | 1.7.1.3 | PATCH | Ensure SELinux policy is configured" +- name: "1.7.1.3 | L2 | PATCH | Ensure SELinux policy is configured" selinux: conf: /etc/selinux/config policy: "{{ rhel8cis_selinux_pol }}" @@ -46,7 +46,7 @@ - patch - rule_1.7.1.3 -- name: "SCORED | 1.7.1.4 | PATCH | Ensure the SELinux state is enforcing" +- name: "1.7.1.4 | L2 | PATCH | Ensure the SELinux state is enforcing" selinux: conf: /etc/selinux/config policy: "{{ rhel8cis_selinux_pol }}" @@ -62,20 +62,20 @@ - patch - rule_1.7.1.4 -- name: "SCORED | 1.7.1.5 | AUDIT | Ensure no unconfined daemons exist" +- name: "1.7.1.5 | L2 | AUDIT | Ensure no unconfined daemons exist" block: - - name: "SCORED | 1.7.1.5 | AUDIT | Ensure no unconfined daemons exist | Find the unconfined daemons" + - name: "1.7.1.5 | L2 | AUDIT | Ensure no unconfined daemons exist | Find the unconfined daemons" shell: ps -eZ | grep unconfined_service_t | egrep -vw "tr|ps|egrep|bash|awk" | tr ':' ' ' | awk '{ print $NF }' register: rhelcis_1_7_1_5_unconf_daemons failed_when: false changed_when: false - - name: "SCORED | 1.7.1.5 | AUDIT | Ensure no unconfined daemons exist | Message on no unconfined daemones" + - name: "1.7.1.5 | L2 | AUDIT | Ensure no unconfined daemons exist | Message on no unconfined daemones" debug: msg: "Good News! There are no unconfined daemons found on your system" when: rhelcis_1_7_1_5_unconf_daemons.stdout | length == 0 - - name: "SCORED | 1.7.1.5 | AUDIT | Ensure no unconfined daemons exist | Message on unconfined daemones" + - name: "1.7.1.5 | L2 | AUDIT | Ensure no unconfined daemons exist | Message on unconfined daemones" debug: msg: "Warning! You have unconfined daemons: {{ rhelcis_1_7_1_5_unconf_daemons.stdout_lines }}" when: rhelcis_1_7_1_5_unconf_daemons.stdout | length > 0 @@ -87,7 +87,7 @@ - audit - rule_1.7.1.5 -- name: "SCORED | 1.7.1.6 | PATCH | Ensure SETroubleshoot is not installed" +- name: "1.7.1.6 | L2 | PATCH | Ensure SETroubleshoot is not installed" package: name: setroubleshoot state: absent @@ -101,7 +101,7 @@ - patch - rule_1.7.1.6 -- name: "SCORED | 1.7.1.7 | PATCH | Ensure the MCS Translation Service (mcstrans) is not installed" +- name: "1.7.1.7 | L2 | PATCH | Ensure the MCS Translation Service (mcstrans) is not installed" package: name: mcstrans state: absent diff --git a/tasks/section_1/cis_1.8.1.x.yml b/tasks/section_1/cis_1.8.1.x.yml index bd228cdb..ab8e3de8 100644 --- a/tasks/section_1/cis_1.8.1.x.yml +++ b/tasks/section_1/cis_1.8.1.x.yml @@ -1,13 +1,12 @@ --- -- name: "SCORED | 1.8.1.1 | PATCH | Ensure message of the day is configured properly" +- name: "1.8.1.1 | L1 | PATCH | Ensure message of the day is configured properly" template: src: etc/motd.j2 dest: /etc/motd owner: root group: root mode: 0644 - when: - rhel8cis_rule_1_8_1_1 tags: @@ -17,7 +16,7 @@ - patch - rule_1.8.1.1 -- name: "SCORED | 1.8.1.2 | PATCH | Ensure local login warning banner is configured properly" +- name: "1.8.1.2 | L1 | PATCH | Ensure local login warning banner is configured properly" template: src: etc/issue.j2 dest: /etc/issue @@ -32,7 +31,7 @@ - patch - rule_1.8.1.2 -- name: "SCORED | 1.8.1.3 | PATCH | Ensure remote login warning banner is configured properly" +- name: "1.8.1.3 | L1 | PATCH | Ensure remote login warning banner is configured properly" template: src: etc/issue.net.j2 dest: /etc/issue.net @@ -48,7 +47,7 @@ - patch - rule_1.8.1.3 -- name: "SCORED | 1.8.1.4 | PATCH | Ensure permissions on /etc/motd are configured" +- name: "1.8.1.4 | L1 | PATCH | Ensure permissions on /etc/motd are configured" file: dest: /etc/motd state: file @@ -64,7 +63,7 @@ - patch - rule_1.8.1.4 -- name: "SCORED | 1.8.1.5 | PATCH | Ensure permissions on /etc/issue are configured" +- name: "1.8.1.5 | L1 | PATCH | Ensure permissions on /etc/issue are configured" file: dest: /etc/issue state: file @@ -80,7 +79,7 @@ - patch - rule_1.8.1.5 -- name: "NOTSCORED | 1.8.1.6 | PATCH | Ensure permissions on /etc/issue.net are configured" +- name: "1.8.1.6 | L1 | PATCH | Ensure permissions on /etc/issue.net are configured" file: dest: /etc/issue.net state: file diff --git a/tasks/section_1/cis_1.8.2.yml b/tasks/section_1/cis_1.8.2.yml index a044c7b5..0f3593d2 100644 --- a/tasks/section_1/cis_1.8.2.yml +++ b/tasks/section_1/cis_1.8.2.yml @@ -1,6 +1,6 @@ --- -- name: "SCORED | 1.8.2 | PATCH | Ensure GDM login banner is configured" +- name: "1.8.2 | L1 | PATCH | Ensure GDM login banner is configured" lineinfile: dest: "{{ item.file }}" regexp: "{{ item.regexp }}" diff --git a/tasks/section_1/cis_1.9.yml b/tasks/section_1/cis_1.9.yml index 93e26390..f413c2cb 100644 --- a/tasks/section_1/cis_1.9.yml +++ b/tasks/section_1/cis_1.9.yml @@ -1,6 +1,6 @@ --- -- name: "SCORED | 1.9 | PATCH | Ensure updates, patches, and additional security software are installed" +- name: "1.9 | L1 | PATCH | Ensure updates, patches, and additional security software are installed" package: name: "*" state: latest diff --git a/tasks/section_2/cis_2.1.1.yml b/tasks/section_2/cis_2.1.1.yml index 62e265de..74352ae0 100644 --- a/tasks/section_2/cis_2.1.1.yml +++ b/tasks/section_2/cis_2.1.1.yml @@ -1,6 +1,6 @@ --- -- name: "SCORED | 2.1.1 | PATCH | Ensure xinetd is not installed" +- name: "2.1.1 | L1 | PATCH | Ensure xinetd is not installed" package: name: xinetd state: absent diff --git a/tasks/section_2/cis_2.2.1.x.yml b/tasks/section_2/cis_2.2.1.x.yml index 0d421086..57ad1c6c 100644 --- a/tasks/section_2/cis_2.2.1.x.yml +++ b/tasks/section_2/cis_2.2.1.x.yml @@ -1,6 +1,6 @@ --- -- name: "NOTSCORED | 2.2.1.1 | PATCH | Ensure time synchronization is in use - service install" +- name: "2.2.1.1 | L1 | PATCH | Ensure time synchronization is in use - service install" package: name: "{{ rhel8cis_time_synchronization }}" state: present @@ -13,9 +13,9 @@ - patch - rule_2.2.1.1 -- name: "SCORED | 2.2.1.2 | PATCH | Ensure chrony is configured" +- name: "2.2.1.2 | L1 | PATCH | Ensure chrony is configured" block: - - name: "SCORED | 2.2.1.2 | PATCH | Ensure chrony is configured | Set configuration" + - name: "2.2.1.2 | L1 | PATCH | Ensure chrony is configured | Set configuration" template: src: chrony.conf.j2 dest: /etc/chrony.conf @@ -23,7 +23,7 @@ group: root mode: 0644 - - name: "SCORED | 2.2.1.2 | PATCH | Ensure chrony is configured | modify /etc/sysconfig/chronyd | 1" + - name: "2.2.1.2 | L1 | PATCH | Ensure chrony is configured | modify /etc/sysconfig/chronyd | 1" lineinfile: dest: /etc/sysconfig/chronyd regexp: "^(#)?OPTIONS" diff --git a/tasks/section_2/cis_2.2.x.yml b/tasks/section_2/cis_2.2.x.yml index ce6939cc..a71b84f8 100644 --- a/tasks/section_2/cis_2.2.x.yml +++ b/tasks/section_2/cis_2.2.x.yml @@ -1,8 +1,8 @@ --- -- name: "SCORED | 2.2.2 | PATCH | Ensure X Window System is not installed" +- name: "2.2.2 | L1 | PATCH | Ensure X Window System is not installed" block: - - name: "SCORED | 2.2.2 | AUDIT | Ensure X Window System is not installed | capture xorg-x11 packages" + - name: "2.2.2 | L1 | AUDIT | Ensure X Window System is not installed | capture xorg-x11 packages" shell: rpm -qa | grep xorg-x11 args: warn: no @@ -11,7 +11,7 @@ changed_when: false register: xorg_x11_installed - - name: "SCORED | 2.2.2 | PATCH | Ensure X Window System is not installed | remove packages if found" + - name: "2.2.2 | L1 | PATCH | Ensure X Window System is not installed | remove packages if found" shell: "dnf remove {{ item }}" args: warn: no @@ -28,7 +28,7 @@ - patch - rule_2.2.2 -- name: "SCORED | 2.2.3 | PATCH | Ensure rsync service is not enabled " +- name: "2.2.3 | L1 | PATCH | Ensure rsync service is not enabled " service: name: rsyncd state: stopped @@ -43,7 +43,7 @@ - patch - rule_2.2.3 -- name: "SCORED | 2.2.4 | PATCH | Ensure Avahi Server is not enabled" +- name: "2.2.4 | L1 | PATCH | Ensure Avahi Server is not enabled" service: name: avahi-daemon state: stopped @@ -61,7 +61,7 @@ - patch - rule_2.2.4 -- name: "SCORED | 2.2.5 | PATCH | Ensure SNMP Server is not enabled" +- name: "2.2.5 | L1 | PATCH | Ensure SNMP Server is not enabled" service: name: snmpd state: stopped @@ -76,7 +76,7 @@ - patch - rule_2.2.5 -- name: "SCORED | 2.2.6 | PATCH | Ensure HTTP Proxy Server is not enabled" +- name: "2.2.6 | L1 | PATCH | Ensure HTTP Proxy Server is not enabled" service: name: squid state: stopped @@ -91,7 +91,7 @@ - patch - rule_2.2.6 -- name: "SCORED | 2.2.7 | PATCH | Ensure Samba is not enabled" +- name: "2.2.7 | L1 | PATCH | Ensure Samba is not enabled" service: name: smb state: stopped @@ -106,7 +106,7 @@ - patch - rule_2.2.7 -- name: "SCORED | 2.2.8 | PATCH | Ensure IMAP and POP3 server is not enabled" +- name: "2.2.8 | L1 | PATCH | Ensure IMAP and POP3 server is not enabled" service: name: dovecot state: stopped @@ -121,7 +121,7 @@ - patch - rule_2.2.8 -- name: "SCORED | 2.2.9 | PATCH | Ensure HTTP server is not enabled" +- name: "2.2.9 | L1 | PATCH | Ensure HTTP server is not enabled" service: name: httpd state: stopped @@ -136,7 +136,7 @@ - patch - rule_2.2.9 -- name: "SCORED | 2.2.10 | PATCH | Ensure FTP Server is not enabled" +- name: "2.2.10 | L1 | PATCH | Ensure FTP Server is not enabled" service: name: vsftpd state: stopped @@ -151,7 +151,7 @@ - patch - rule_2.2.10 -- name: "SCORED | 2.2.11 | PATCH | Ensure DNS Server is not enabled" +- name: "2.2.11 | L1 | PATCH | Ensure DNS Server is not enabled" service: name: named state: stopped @@ -166,7 +166,7 @@ - patch - rule_2.2.11 -- name: "SCORED | 2.2.12 | PATCH | Ensure NFS is not enabled" +- name: "2.2.12 | L1 | PATCH | Ensure NFS is not enabled" service: name: nfs-server state: stopped @@ -184,7 +184,7 @@ - patch - rule_2.2.12 -- name: "SCORED | 2.2.13 | PATCH | Ensure RPC is not enabled" +- name: "2.2.13 | L1 | PATCH | Ensure RPC is not enabled" service: name: rpcbind state: stopped @@ -202,7 +202,7 @@ - patch - rule_2.2.7 -- name: "SCORED | 2.2.14 | PATCH | Ensure LDAP server is not enabled" +- name: "2.2.14 | L1 | PATCH | Ensure LDAP server is not enabled" service: name: slapd state: stopped @@ -220,7 +220,7 @@ - patch - rule_2.2.6 -- name: "SCORED | 2.2.15 | PATCH | Ensure DHCP Server is not enabled" +- name: "2.2.15 | L1 | PATCH | Ensure DHCP Server is not enabled" service: name: dhcpd state: stopped @@ -238,7 +238,7 @@ - patch - rule_2.2.15 -- name: "SCORED | 2.2.16 | PATCH | Ensure CUPS is not enabled" +- name: "2.2.16 | L1 | PATCH | Ensure CUPS is not enabled" service: name: cups state: stopped @@ -256,7 +256,7 @@ - patch - rule_2.2.16 -- name: "SCORED | 2.2.17 | PATCH | Ensure NIS Server is not enabled" +- name: "2.2.17 | L1 | PATCH | Ensure NIS Server is not enabled" service: name: ypserv state: stopped @@ -271,7 +271,7 @@ - patch - rule_2.2.17 -- name: "SCORED | 2.2.18 | PATCH | Ensure mail transfer agent is configured for local-only mode" +- name: "2.2.18 | L1 | PATCH | Ensure mail transfer agent is configured for local-only mode" lineinfile: dest: /etc/postfix/main.cf regexp: "^(#)?inet_interfaces" diff --git a/tasks/section_2/cis_2.3.x.yml b/tasks/section_2/cis_2.3.x.yml index 8f508729..00e91f08 100644 --- a/tasks/section_2/cis_2.3.x.yml +++ b/tasks/section_2/cis_2.3.x.yml @@ -1,6 +1,6 @@ --- -- name: "SCORED | 2.3.1 | PATCH | Ensure NIS Client is not installed" +- name: "2.3.1 | L1 | PATCH | Ensure NIS Client is not installed" package: name: ypbind state: absent @@ -14,7 +14,7 @@ - patch - rule_2.3.1 -- name: "SCORED | 2.3.2 | PATCH | Ensure telnet client is not installed" +- name: "2.3.2 | L1 | PATCH | Ensure telnet client is not installed" package: name: telnet state: absent @@ -28,7 +28,7 @@ - patch - rule_2.3.2 -- name: "SCORED | 2.3.3 | PATCH | Ensure LDAP client is not installed" +- name: "2.3.3 | L1 | PATCH | Ensure LDAP client is not installed" package: name: openldap-clients state: absent diff --git a/tasks/section_3/cis_3.1.x.yml b/tasks/section_3/cis_3.1.x.yml index 63f6be7c..b2f532e6 100644 --- a/tasks/section_3/cis_3.1.x.yml +++ b/tasks/section_3/cis_3.1.x.yml @@ -1,8 +1,8 @@ --- -- name: "SCORED | 3.1.1 | PATCH | Ensure IP forwarding is disabled" +- name: "3.1.1 | L1 | PATCH | Ensure IP forwarding is disabled" block: - - name: "SCORED | 3.1.1 | PATCH | Ensure IP forwarding is disabled | Disable IPv4 forwarding" + - name: "3.1.1 | L1 | PATCH | Ensure IP forwarding is disabled | Disable IPv4 forwarding" sysctl: name: net.ipv4.ip_forward value: '0' @@ -11,7 +11,7 @@ ignoreerrors: yes notify: sysctl flush ipv4 route table - - name: "SCORED | 3.1.1 | PATCH | Ensure IP forwarding is disabled | Disable IPv6 forwarding" + - name: "3.1.1 | L1 | PATCH | Ensure IP forwarding is disabled | Disable IPv6 forwarding" sysctl: name: net.ipv6.conf.all.forwarding value: '0' @@ -30,7 +30,7 @@ - patch - rule_3.1.1 -- name: "SCORED | 3.1.2 | PATCH | Ensure packet redirect sending is disabled" +- name: "3.1.2 | L1 | PATCH | Ensure packet redirect sending is disabled" sysctl: name: '{{ item.name }}' value: '{{ item.value }}' diff --git a/tasks/section_3/cis_3.2.x.yml b/tasks/section_3/cis_3.2.x.yml index c6945b88..4eb33b32 100644 --- a/tasks/section_3/cis_3.2.x.yml +++ b/tasks/section_3/cis_3.2.x.yml @@ -1,8 +1,8 @@ --- -- name: "SCORED | 3.2.1 | PATCH | Ensure source routed packets are not accepted" +- name: "3.2.1 | L1 | PATCH | Ensure source routed packets are not accepted" block: - - name: "SCORED | 3.2.1 | PATCH | Ensure source routed packets are not accepted | Set routed packets IPv4" + - name: "3.2.1 | L1 | PATCH | Ensure source routed packets are not accepted | Set routed packets IPv4" sysctl: name: '{{ item.name }}' value: '{{ item.value }}' @@ -15,7 +15,7 @@ - { name: net.ipv4.conf.all.accept_source_route, value: 0 } - { name: net.ipv4.conf.default.accept_source_route, value: 0 } - - name: "SCORED | 3.2.1 | PATCH | Ensure source routed packets are not accepted | Set routed packets IPv6" + - name: "3.2.1 | L1 | PATCH | Ensure source routed packets are not accepted | Set routed packets IPv6" sysctl: name: '{{ item.name }}' value: '{{ item.value }}' @@ -36,9 +36,9 @@ - patch - rule_3.2.1 -- name: "SCORED | 3.2.2 | PATCH | Ensure ICMP redirects are not accepted" +- name: "3.2.2 | L1 | PATCH | Ensure ICMP redirects are not accepted" block: - - name: "SCORED | 3.2.2 | PATCH | Ensure ICMP redirects are not accepted | Set ICMP redirects IPv4" + - name: "3.2.2 | L1 | PATCH | Ensure ICMP redirects are not accepted | Set ICMP redirects IPv4" sysctl: name: '{{ item.name }}' value: '{{ item.value }}' @@ -51,7 +51,7 @@ - { name: net.ipv4.conf.all.accept_redirects, value: 0 } - { name: net.ipv4.conf.default.accept_redirects, value: 0 } - - name: "SCORED | 3.2.2 | PATCH | Ensure ICMP redirects are not accepted | Set ICMP redirects IPv6" + - name: "3.2.2 | L1 | PATCH | Ensure ICMP redirects are not accepted | Set ICMP redirects IPv6" sysctl: name: '{{ item.name }}' value: '{{ item.value }}' @@ -59,7 +59,7 @@ state: present reload: yes ignoreerrors: yes - notify: sysctl flush ipv4 route table + notify: sysctl flush ipv6 route table with_items: - { name: net.ipv6.conf.all.accept_redirects, value: 0 } - { name: net.ipv6.conf.default.accept_redirects, value: 0 } @@ -73,7 +73,7 @@ - patch - rule_3.2.2 -- name: "SCORED | 3.2.3 | PATCH | Ensure secure ICMP redirects are not accepted" +- name: "3.2.3 | L1 | PATCH | Ensure secure ICMP redirects are not accepted" sysctl: name: '{{ item.name }}' value: '{{ item.value }}' @@ -94,7 +94,7 @@ - patch - rule_3.2.3 -- name: "SCORED | 3.2.4 | PATCH | Ensure suspicious packets are logged" +- name: "3.2.4 | L1 | PATCH | Ensure suspicious packets are logged" sysctl: name: '{{ item.name }}' value: '{{ item.value }}' @@ -115,7 +115,7 @@ - patch - rule_3.2.4 -- name: "SCORED | 3.2.5 | PATCH | Ensure broadcast ICMP requests are ignored" +- name: "3.2.5 | L1 | PATCH | Ensure broadcast ICMP requests are ignored" sysctl: name: net.ipv4.icmp_echo_ignore_broadcasts value: '1' @@ -132,7 +132,7 @@ - patch - rule_3.2.5 -- name: "SCORED | 3.2.6 | PATCH | Ensure bogus ICMP responses are ignored" +- name: "3.2.6 | L1 | PATCH | Ensure bogus ICMP responses are ignored" sysctl: name: net.ipv4.icmp_ignore_bogus_error_responses value: '1' @@ -149,7 +149,7 @@ - patch - rule_3.2.6 -- name: "SCORED | 3.2.7 | PATCH | Ensure Reverse Path Filtering is enabled" +- name: "3.2.7 | L1 | PATCH | Ensure Reverse Path Filtering is enabled" sysctl: name: net.ipv4.conf.default.rp_filter value: '1' @@ -167,7 +167,7 @@ - patch - rule_3.2.7 -- name: "SCORED | 3.2.8 | PATCH | Ensure TCP SYN Cookies is enabled" +- name: "3.2.8 | L1 | PATCH | Ensure TCP SYN Cookies is enabled" sysctl: name: net.ipv4.tcp_syncookies value: '1' @@ -184,7 +184,7 @@ - patch - rule_3.2.8 -- name: "SCORED | 3.2.9 | PATCH | Ensure IPv6 router advertisements are not accepted" +- name: "3.2.9 | L2 | PATCH | Ensure IPv6 router advertisements are not accepted" sysctl: name: '{{ item.name }}' value: '{{ item.value }}' diff --git a/tasks/section_3/cis_3.3.x.yml b/tasks/section_3/cis_3.3.x.yml index 2296262d..130af2ce 100644 --- a/tasks/section_3/cis_3.3.x.yml +++ b/tasks/section_3/cis_3.3.x.yml @@ -1,6 +1,6 @@ --- -- name: "SCORED | 3.3.1 | PATCH | Ensure DCCP is disabled" +- name: "3.3.1 | L2 | PATCH | Ensure DCCP is disabled" lineinfile: dest: /etc/modprobe.d/CIS.conf regexp: "^(#)?install dccp(\\s|$)" @@ -15,7 +15,7 @@ - patch - rule_3.3.1 -- name: "SCORED | 3.3.2 | PATCH | Ensure SCTP is disabled" +- name: "3.3.2 | L2 | PATCH | Ensure SCTP is disabled" lineinfile: dest: /etc/modprobe.d/CIS.conf regexp: "^(#)?install sctp(\\s|$)" @@ -30,7 +30,7 @@ - patch - rule_3.3.2 -- name: "SCORED | 3.3.3 | PATCH | Ensure RDS is disabled" +- name: "3.3.3 | L2 | PATCH | Ensure RDS is disabled" lineinfile: dest: /etc/modprobe.d/CIS.conf regexp: "^(#)?install rds(\\s|$)" @@ -45,7 +45,7 @@ - patch - rule_3.3.3 -- name: "SCORED | 3.3.4 | PATCH | Ensure TIPC is disabled" +- name: "3.3.4 | L2 | PATCH | Ensure TIPC is disabled" lineinfile: dest: /etc/modprobe.d/CIS.conf regexp: "^(#)?install tipc(\\s|$)" diff --git a/tasks/section_3/cis_3.4.1.1.yml b/tasks/section_3/cis_3.4.1.1.yml index cbeb86fc..9b79813a 100644 --- a/tasks/section_3/cis_3.4.1.1.yml +++ b/tasks/section_3/cis_3.4.1.1.yml @@ -1,12 +1,10 @@ --- -- name: "SCORED | 3.4.1.1 | PATCH | Ensure a Firewall package is installed" +- name: "3.4.1.1 | L1 | PATCH | Ensure a Firewall package is installed" package: name: "{{ rhel8cis_firewall }}" state: present - notify: restart {{ rhel8cis_firewall }} when: - - rhel8cis_firewall == "firewalld" - rhel8cis_rule_3_4_1_1 tags: - level1-server diff --git a/tasks/section_3/cis_3.4.2.x.yml b/tasks/section_3/cis_3.4.2.x.yml index ee4b5524..d273876c 100644 --- a/tasks/section_3/cis_3.4.2.x.yml +++ b/tasks/section_3/cis_3.4.2.x.yml @@ -1,6 +1,6 @@ --- -- name: "SCORED | 3.4.2.1 | PATCH | Ensure firewalld service is enabled and running" +- name: "3.4.2.1 | L1 | PATCH | Ensure firewalld service is enabled and running" service: name: firewalld state: started @@ -14,7 +14,7 @@ - patch - rule_3_4_2_1 -- name: "SCORED | 3.4.2.2 | PATCH | Ensure iptables is not enabled" +- name: "3.4.2.2 | L1 | PATCH | Ensure iptables is not enabled with firewalld" systemd: name: iptables enabled: false @@ -30,7 +30,7 @@ - patch - rule_3_4_2_2 -- name: "SCORED | 3.4.2.3 | PATCH | Ensure nftables is not enabled" +- name: "3.4.2.3 | L1 | PATCH | Ensure nftables is not enabled with firewalld" systemd: name: nftables enabled: false @@ -44,7 +44,7 @@ - patch - rule_3_4_2_3 -- name: "SCORED | 3.4.2.4 | PATCH | Ensure default zone is set" +- name: "3.4.2.4 | L1 | PATCH | Ensure default zone is set" command: firewall-cmd --set-default-zone="{{ rhel8cis_default_zone }}" when: - rhel8cis_firewall == "firewalld" @@ -55,16 +55,16 @@ - patch - rule_3.4.2.4 -- name: "SCORED | 3.4.2.5 | AUDIT | Ensure network interfaces are assigned to appropriate zone" +- name: "3.4.2.5 | L1 | AUDIT | Ensure network interfaces are assigned to appropriate zone" block: - - name: "SCORED | 3.4.2.5 | AUDIT | Ensure network interfaces are assigned to appropriate zone | Get list of interfaces and polocies" + - name: "3.4.2.5 | L1 | AUDIT | Ensure network interfaces are assigned to appropriate zone | Get list of interfaces and polocies" shell: "nmcli -t connection show | awk -F: '{ if($4){print $4} }' | while read INT; do firewall-cmd --get-active-zones | grep -B1 $INT; done" changed_when: false failed_when: false check_mode: no register: rhel8cis_3_4_2_5_interfacepolicy - - name: "SCORED | 3.4.2.5 | AUDIT | Ensure network interfaces are assigned to appropriate zone | Get list of interfaces and polocies | Show the interface to policy" + - name: "3.4.2.5 | L1 | AUDIT | Ensure network interfaces are assigned to appropriate zone | Get list of interfaces and polocies | Show the interface to policy" debug: msg: - "The items below are the policies tied to the interfaces, please correct as needed" @@ -78,16 +78,16 @@ - audit - rule_3.4.2.5 -- name: "SCORED | 3.4.2.6 | AUDIT | Ensure unnecessary services and ports are not accepted" +- name: "3.4.2.6 | L1 | AUDIT | Ensure firewalld drops unnecessary services and ports" block: - - name: "SCORED | 3.4.2.6 | AUDIT | Ensure unnecessary services and ports are not accepted | Get list of services and ports" + - name: "3.4.2.6 | L1 | AUDIT | Ensure firewalld drops unnecessary services and ports | Get list of services and ports" shell: "firewall-cmd --get-active-zones | awk '!/:/ {print $1}' | while read ZN; do firewall-cmd --list-all --zone=$ZN; done" changed_when: false failed_when: false check_mode: no register: rhel8cis_3_4_2_6_servicesport - - name: "SCORED | 3.4.2.6 | AUDIT | Ensure unnecessary services and ports are not accepted | Show services adn ports" + - name: "3.4.2.6 | L1 | AUDIT | Ensure firewalld drops unnecessary services and ports | Show services and ports" debug: msg: - "The items below are the services and ports that are accepted, please correct as needed" diff --git a/tasks/section_3/cis_3.4.3.x.yml b/tasks/section_3/cis_3.4.3.x.yml index 26243fa3..3b7467db 100644 --- a/tasks/section_3/cis_3.4.3.x.yml +++ b/tasks/section_3/cis_3.4.3.x.yml @@ -1,6 +1,6 @@ --- -- name: "NOTSCORED | 3.4.3.1 | PATCH | Ensure iptables are flushed" +- name: "3.4.3.1 | L1 | PATCH | Ensure iptables are flushed with nftables" command: ip6tables -F when: - rhel8cis_rule_3_4_3_1 @@ -12,22 +12,22 @@ - patch - rule_3.4.3.1 -- name: "SCORED | 3.4.3.2 | PATCH | Ensure a table exists" +- name: "3.4.3.2 | L1 | AUDIT | Ensure an nftables table exists" block: - - name: "SCORED | 3.4.3.2 | AUDIT | Ensure a table exists | Check for tables" + - name: "3.4.3.2 | L1 | AUDIT | Ensure a table exists | Check for tables" command: nft list tables changed_when: false failed_when: false register: rhel8cis_3_4_3_2_nft_tables - - name: "SCORED | 3.4.3.2 | AUDIT | Ensure a table exists | Show existing tables" + - name: "3.4.3.2 | L1 | AUDIT | Ensure an nftables table exists | Show existing tables" debug: msg: - "Below are the current nft tables, please review" - "{{ rhel8cis_3_4_3_2_nft_tables.stdout_lines }}" when: rhel8cis_3_4_3_2_nft_tables.stdout | length > 0 - - name: "SCORED | 3.4.3.2 | AUDIT | Ensure a table exists | Alert on no tables" + - name: "3.4.3.2 | L1 | AUDIT | Ensure an nftables table exists | Alert on no tables" debug: msg: - "Warning! You currently have no nft tables, please review your setup" @@ -36,7 +36,7 @@ - rhel8cis_3_4_3_2_nft_tables.stdout | length == 0 - not rhel8cis_nft_tables_autonewtable - - name: "SCORED | 3.4.3.2 | PATCH | Ensure a table exists | Create table if needed" + - name: "3.4.3.2 | L1 | PATCH | Ensure a table exists | Create table if needed" command: nft create table inet "{{ rhel8cis_nft_tables_tablename }}" failed_when: no when: rhel8cis_nft_tables_autonewtable @@ -49,27 +49,27 @@ - patch - rule_3.4.3.2 -- name: "SCORED | 3.4.3.3 | PATCH | Ensure base chains exist" +- name: "3.4.3.3 | L1 | PATCH | Ensure nftables base chains exist" block: - - name: "SCORED | 3.4.3.3 | AUDIT | Ensure base chains exist | Get current chains for INPUT" + - name: "3.4.3.3 | L1 | Ensure nftables base chains exist | Get current chains for INPUT" shell: nft list ruleset | grep 'hook input' changed_when: false failed_when: false register: rhel8cis_3_4_3_3_input_chains - - name: "SCORED | 3.4.3.3 | AUDIT | Ensure base chains exist | Get current chains for FORWARD" + - name: "3.4.3.3 | L1 | AUDIT | Ensure nftables base chains exist | Get current chains for FORWARD" shell: nft list ruleset | grep 'hook forward' changed_when: false failed_when: false register: rhel8cis_3_4_3_3_forward_chains - - name: "SCORED | 3.4.3.3 | AUDIT | Ensure base chains exist | Get current chains for OUTPUT" + - name: "3.4.3.3 | L1 | AUDIT | Ensure nftables base chains exist | Get current chains for OUTPUT" shell: nft list ruleset | grep 'hook output' changed_when: false failed_when: false register: rhel8cis_3_4_3_3_output_chains - - name: "SCORED | 3.4.3.3 | AUDIT | Ensure base chains exist | Display chains for review" + - name: "3.4.3.3 | L1 | AUDIT | Ensure nftables base chains exist | Display chains for review" debug: msg: - "Below are the current INPUT chains" @@ -78,9 +78,9 @@ - "{{ rhel8cis_3_4_3_3_forward_chains.stdout_lines }}" - "Below are teh current OUTPUT chains" - "{{ rhel8cis_3_4_3_3_output_chains.stdout_lines }}" - when: not rhel8cis_nft_tables_autoChainCreate + when: not rhel8cis_nft_tables_autochaincreate - - name: "SCORED | 3.4.3.3 | PATCH | Ensure base chains exist | Create chains if needed" + - name: "3.4.3.3 | L1 | PATCH | Ensure nftables base chains exist | Create chains if needed" shell: "{{ item }}" args: warn: no @@ -89,45 +89,45 @@ - nft create chain inet "{{ rhel8cis_nft_tables_tablename }}" input { type filter hook input priority 0 \; } - nft create chain inet "{{ rhel8cis_nft_tables_tablename }}" forward { type filter hook forward priority 0 \; } - nft create chain inet "{{ rhel8cis_nft_tables_tablename }}" output { type filter hook output priority 0 \; } - when: rhel8cis_nft_tables_autoChainCreate + when: rhel8cis_nft_tables_autochaincreate when: - rhel8cis_firewall == "nftables" - - rhel8cis_rule_3_4_3_2 + - rhel8cis_rule_3_4_3_3 tags: - level1-server - level1-workstation - patch - rule_3.4.3.3 -- name: "SCORED | 3.4.3.4 | PATCH | Ensure loopback traffic is configured" +- name: "3.4.3.4 | L1 | PATCH | Ensure nftables loopback traffic is configured" block: - - name: "SCORED | 3.4.3.4 | AUDIT | Ensure loopback traffic is configured | Gather iif lo accept existence" + - name: "3.4.3.4 | L1 | AUDIT | Ensure nftables loopback traffic is configured | Gather iif lo accept existence" shell: nft list ruleset | awk '/hook input/,/}/' | grep 'iif "lo" accept' changed_when: false failed_when: false register: rhel8cis_3_4_3_4_iiflo - - name: "SCORED | 3.4.3.4 | AUDIT | Ensure loopback traffic is configured | Gather ip saddr existence" + - name: "3.4.3.4 | L1 | AUDIT | Ensure nftables loopback traffic is configured | Gather ip saddr existence" shell: nft list ruleset | awk '/hook input/,/}/' | grep 'ip saddr' changed_when: false failed_when: false register: rhel8cis_3_4_3_4_ipsaddr - - name: "SCORED | 3.4.3.4 | AUDIT | Ensure loopback traffic is configured | Gather ip6 saddr existence" + - name: "3.4.3.4 | L1 | AUDIT | Ensure nftables loopback traffic is configured | Gather ip6 saddr existence" shell: nft list ruleset | awk '/hook input/,/}/' | grep 'ip6 saddr' changed_when: false failed_when: false register: rhel8cis_3_4_3_4_ip6saddr - - name: "SCORED | 3.4.3.4 | PATCH | Ensure loopback traffic is configured | Set iif lo accept rule" + - name: "3.4.3.4 | L1 | PATCH | Ensure nftables loopback traffic is configured | Set iif lo accept rule" command: nft add rule inet "{{ rhel8cis_nft_tables_tablename }}" input iif lo accept when: '"iif \"lo\" accept" not in rhel8cis_3_4_3_4_iiflo.stdout' - - name: "SCORED | 3.4.3.4 | PATCH | Ensure loopback traffic is configured | Set ip sddr rule" + - name: "3.4.3.4 | L1 | PATCH | Ensure nftables loopback traffic is configured | Set ip sddr rule" command: nft add rule inet "{{ rhel8cis_nft_tables_tablename }}" input ip saddr 127.0.0.0/8 counter drop when: '"ip saddr 127.0.0.0/8 counter packets 0 bytes 0 drop" not in rhel8cis_3_4_3_4_ipsaddr.stdout' - - name: "SCORED | 3.4.3.4 | PATCH | Ensure loopback traffic is configured | Set ip6 saddr rule" + - name: "3.4.3.4 | L1 | PATCH | Ensure nftables loopback traffic is configured | Set ip6 saddr rule" command: nft add rule inet "{{ rhel8cis_nft_tables_tablename }}" input ip6 saddr ::1 counter drop when: '"ip6 saddr ::1 counter packets 0 bytes 0 drop" not in rhel8cis_3_4_3_4_ip6saddr.stdout' when: @@ -139,41 +139,41 @@ - patch - rule_3.4.3.4 -- name: "NOTSCORED | 3.4.3.5 | PATCH | Ensure outbound and established connections are configured" +- name: "3.4.3.5 | L1 | PATCH | Ensure nftables outbound and established connections are configured" block: - - name: "NOTSCORED | 3.4.3.5 | AUDIT | Ensure outbound and established connections are configured | Gather incoming connection rules" + - name: "3.4.3.5 | L1 | AUDIT | Ensure nftables outbound and established connections are configured | Gather incoming connection rules" shell: nft list ruleset | awk '/hook input/,/}/' | grep -E 'ip protocol (tcp|udp|icmp) ct state' changed_when: false failed_when: false register: rhel8cis_3_4_3_5_inconnectionrule - - name: "NOTSCORED | 3.4.3.5 | AUDIT | Ensure outbound and established connections are configured | Gather outbound connection rules" + - name: "3.4.3.5 | L1 | AUDIT | Ensure nftables outbound and established connections are configured | Gather outbound connection rules" shell: nft list ruleset | awk '/hook output/,/}/' | grep -E 'ip protocol (tcp|udp|icmp) ct state' changed_when: false failed_when: false register: rhel8cis_3_4_3_5_outconnectionrule - - name: "NOTSCORED | 3.4.3.5 | PATCH | Ensure outbound and established connections are configured | Add input tcp established accpet policy" + - name: "3.4.3.5 | L1 | PATCH | Ensure nftables outbound and established connections are configured | Add input tcp established accept policy" command: nft add rule inet "{{ rhel8cis_nft_tables_tablename }}" input ip protocol tcp ct state established accept when: '"ip protocol tcp ct state established accept" not in rhel8cis_3_4_3_5_inconnectionrule.stdout' - - name: "NOTSCORED | 3.4.3.5 | PATCH | Ensure outbound and established connections are configured | Add input udp established accpet policy" + - name: "3.4.3.5 | L1 | PATCH | Ensure nftables outbound and established connections are configured | Add input udp established accept policy" command: nft add rule inet "{{ rhel8cis_nft_tables_tablename }}" input ip protocol udp ct state established accept when: '"ip protocol udp ct state established accept" not in rhel8cis_3_4_3_5_inconnectionrule.stdout' - - name: "NOTSCORED | 3.4.3.5 | PATCH | Ensure outbound and established connections are configured | Add input icmp established accpet policy" + - name: "3.4.3.5 | L1 | PATCH | Ensure nftables outbound and established connections are configured | Add input icmp established accept policy" command: nft add rule inet "{{ rhel8cis_nft_tables_tablename }}" input ip protocol icmp ct state established accept when: '"ip protocol icmp ct state established accept" not in rhel8cis_3_4_3_5_inconnectionrule.stdout' - - name: "NOTSCORED | 3.4.3.5 | PATCH | Ensure outbound and established connections are configured | Add output tcp new, related, established accpet policy" + - name: "3.4.3.5 | L1 | PATCH | Ensure nftables outbound and established connections are configured | Add output tcp new, related, established accept policy" command: nft add rule inet "{{ rhel8cis_nft_tables_tablename }}" output ip protocol tcp ct state new,related,established accept when: '"ip protocol tcp ct state established,related,new accept" not in rhel8cis_3_4_3_5_outconnectionrule.stdout' - - name: "NOTSCORED | 3.4.3.5 | PATCH | Ensure outbound and established connections are configured | Add output udp new, related, established accpet policy" + - name: "3.4.3.5 | L1 | PATCH | Ensure nftables outbound and established connections are configured | Add output udp new, related, established accept policy" command: nft add rule inet "{{ rhel8cis_nft_tables_tablename }}" output ip protocol udp ct state new,related,established accept when: '"ip protocol udp ct state established,related,new accept" not in rhel8cis_3_4_3_5_outconnectionrule.stdout' - - name: "NOTSCORED | 3.4.3.5 | PATCH | Ensure outbound and established connections are configured | Add output icmp new, related, established accpet policy" + - name: "3.4.3.5 | L1 | PATCH | Ensure nftables outbound and established connections are configured | Add output icmp new, related, established accept policy" command: nft add rule inet "{{ rhel8cis_nft_tables_tablename }}" output ip protocol icmp ct state new,related,established accept when: '"ip protocol icmp ct state established,related,new accept" not in rhel8cis_3_4_3_5_outconnectionrule.stdout' when: @@ -185,45 +185,45 @@ - patch - rule_3.4.3.5 -- name: "SCORED | 3.4.3.6 | PATCH | Ensure default deny firewall policy" +- name: "3.4.3.6 | L1 | PATCH | Ensure nftables default deny firewall policy" block: - - name: "SCORED | 3.4.3.6 | AUDIT | Ensure default deny firewall policy | Check for hook input deny policy" + - name: "3.4.3.6 | L1 | AUDIT | Ensure nftables default deny firewall policy | Check for hook input deny policy" shell: nft list table inet "{{ rhel8cis_nft_tables_tablename }}" | grep 'hook input' failed_when: false changed_when: false register: rhel8cis_3_4_3_6_inputpolicy - - name: "SCORED | 3.4.3.6 | AUDIT | Ensure default deny firewall policy | Check for hook forward deny policy" + - name: "3.4.3.6 | L1 | AUDIT | Ensure nftables default deny firewall policy | Check for hook forward deny policy" shell: nft list table inet "{{ rhel8cis_nft_tables_tablename }}" | grep 'hook forward' failed_when: false changed_when: false register: rhel8cis_3_4_3_6_forwardpolicy - - name: "SCORED | 3.4.3.6 | AUDIT | Ensure default deny firewall policy | Check for hook output deny policy" + - name: "3.4.3.6 | L1 | AUDIT | Ensure nftables default deny firewall policy | Check for hook output deny policy" shell: nft list table inet "{{ rhel8cis_nft_tables_tablename }}" | grep 'hook output' failed_when: false changed_when: false register: rhel8cis_3_4_3_6_outputpolicy - - name: "SCORED | 3.4.3.6 | AUDIT | Ensure default deny firewall policy | Check for SSH allow" + - name: "3.4.3.6 | L1 | AUDIT | Ensure nftables default deny firewall policy | Check for SSH allow" shell: nft list table inet "{{ rhel8cis_nft_tables_tablename }}" | grep 'ssh' failed_when: false changed_when: false register: rhel8cis_3_4_3_6_sshallowcheck - - name: "SCORED | 3.4.3.6 | PATCH | Ensure default deny firewall policy | Enable SSH traffic" + - name: "3.4.3.6 | L1 | PATCH | Ensure nftables default deny firewall policy | Enable SSH traffic" command: nft add rule inet "{{ rhel8cis_nft_tables_tablename }}" input tcp dport ssh accept when: '"tcp dport ssh accept" not in rhel8cis_3_4_3_6_sshallowcheck.stdout' - - name: "SCORED | 3.4.3.6 | PATCH | Ensure default deny firewall policy | Set hook input deny policy" + - name: "3.4.3.6 | L1 | PATCH | Ensure nftables default deny firewall policy | Set hook input deny policy" command: nft chain inet "{{ rhel8cis_nft_tables_tablename }}" input { policy drop \; } when: '"type filter hook input priority 0; policy drop;" not in rhel8cis_3_4_3_6_inputpolicy.stdout' - - name: "SCORED | 3.4.3.6 | PATCH | Ensure default deny firewall policy | Create hook forward deny policy" + - name: "3.4.3.6 | L1 | PATCH | Ensure nftables default deny firewall policy | Create hook forward deny policy" command: nft chain inet "{{ rhel8cis_nft_tables_tablename }}" forward { policy drop \; } when: '"type filter hook forward priority 0; policy drop;" not in rhel8cis_3_4_3_6_forwardpolicy.stdout' - - name: "SCORED | 3.4.3.6 | PATCH | Ensure default deny firewall policy | Create hook output deny policy" + - name: "3.4.3.6 | L1 | PATCH | Ensure nftables default deny firewall policy | Create hook output deny policy" command: nft chain inet "{{ rhel8cis_nft_tables_tablename }}" output { policy drop \; } when: '"type filter hook output priority 0; policy drop;" not in rhel8cis_3_4_3_6_outputpolicy.stdout' when: @@ -235,7 +235,7 @@ - patch - rule_3.4.3.6 -- name: "SCORED | 3.4.3.7 | PATCH | Ensure nftables service is enabled | Check if nftables is enabled" +- name: "3.4.3.7 | L1 | PATCH | Ensure nftables service is enabled | Check if nftables is enabled" service: name: nftables enabled: yes @@ -248,7 +248,7 @@ - patch - rule_3.4.3.7 -- name: "SCORED | 3.4.3.8 | PATCH | Ensure nftables rules are permanent" +- name: "3.4.3.8 | L1 | PATCH | Ensure nftables rules are permanent" lineinfile: path: /etc/sysconfig/nftables.conf state: present @@ -256,7 +256,7 @@ line: include "/etc/nftables/inet-{{ rhel8cis_nft_tables_tablename }}" when: - rhel8cis_firewall == "nftables" - - rhel8cis_rule_3_4_3_7 + - rhel8cis_rule_3_4_3_8 tags: - level1-server - level1-workstation diff --git a/tasks/section_3/cis_3.4.4.1.x.yml b/tasks/section_3/cis_3.4.4.1.x.yml index d6774890..8e82a51d 100644 --- a/tasks/section_3/cis_3.4.4.1.x.yml +++ b/tasks/section_3/cis_3.4.4.1.x.yml @@ -1,15 +1,15 @@ --- -- name: "SCORED | 3.4.4.1.1 | PATCH | Ensure default deny firewall policy" +- name: "3.4.4.1.1 | L1 | PATCH | Ensure iptables default deny firewall policy" block: - - name: "SCORED | 3.4.4.1.1 | PATCH | Ensure default deny firewall policy | Configure ssh to be allowed" + - name: "3.4.4.1.1 | L1 | PATCH | Ensure iptables default deny firewall policy | Configure ssh to be allowed" iptables: chain: INPUT protocol: tcp destination_port: "22" jump: ACCEPT - - name: "SCORED | 3.4.4.1.1 | PATCH | Ensure default deny firewall policy | Set drop items" + - name: "3.4.4.1.1 | L1 | PATCH | Ensure iptables default deny firewall policy | Set drop items" iptables: policy: DROP chain: "{{ item }}" @@ -26,23 +26,23 @@ - patch - rule_3.4.4.1.1 -- name: "SCORED | 3.4.4.1.2 | PATCH | Ensure loopback traffic is configured" +- name: "3.4.4.1.2 | L1 | PATCH | Ensure iptables loopback traffic is configured" block: - - name: "SCORED | 3.4.4.1.2 | PATCH | Ensure loopback traffic is configured | INPUT Loopback ACCEPT" + - name: "3.4.4.1.2 | L1 | Ensure iptables loopback traffic is configured | INPUT Loopback ACCEPT" iptables: action: append chain: INPUT in_interface: lo jump: ACCEPT - - name: "SCORED | 3.4.4.1.2 | PATCH | Ensure loopback traffic is configured | OUTPUT Loopback ACCEPT" + - name: "3.4.4.1.2 | L1 | PATCH | Ensure iptables loopback traffic is configured | OUTPUT Loopback ACCEPT" iptables: action: append chain: OUTPUT out_interface: lo jump: ACCEPT - - name: "SCORED | 3.4.4.1.2 | PATCH | Ensure loopback traffic is configured | INPUT Loopback 127.0.0.0/8" + - name: "3.4.4.1.2 | L1 | PATCH | Ensure iptables loopback traffic is configured | INPUT Loopback 127.0.0.0/8" iptables: action: append chain: INPUT @@ -57,7 +57,7 @@ - patch - rule_3.4.4.1.2 -- name: "NOTSCORED | 3.4.4.1.3 | PATCH | Ensure outbound and established connections are configured" +- name: "3.4.4.1.3 | L1 | PATCH | Ensure iptables outbound and established connections are configured" iptables: action: append chain: '{{ item.chain }}' @@ -81,21 +81,21 @@ - patch - rule_3.4.4.1.3 -- name: "SCORED | 3.4.4.1.4 | PATCH | Ensure firewall rules exist for all open ports" +- name: "3.4.4.1.4 | L1 | PATCH | Ensure iptables firewall rules exist for all open ports" block: - - name: "SCORED | 3.4.4.1.4 | AUDIT | Ensure firewall rules exist for all open ports | Get list of TCP open ports" + - name: "3.4.4.1.4 | L1 | AUDIT | Ensure iptables firewall rules exist for all open ports | Get list of TCP open ports" shell: netstat -ant |grep "tcp.*LISTEN" | awk '{ print $4 }'| sed 's/.*://' changed_when: false failed_when: false register: rhel8cis_3_4_4_1_4_otcp - - name: "SCORED | 3.4.4.1.4| AUDIT | Ensure firewall rules exist for all open ports | Get the list of udp open ports" + - name: "3.4.4.1.4 | L1 | AUDIT | Ensure iptables firewall rules exist for all open ports | Get the list of udp open ports" shell: netstat -ant |grep "udp.*LISTEN" | awk '{ print $4 }'| sed 's/.*://' changed_when: false failed_when: false register: rhel8cis_3_4_4_1_4_oudp - - name: "SCORED | 3.4.4.1.4 | PATCH | Ensure firewall rules exist for all open ports| Adjust open tcp ports" + - name: "3.4.4.1.4 | L1 | PATCH | Ensure iptables firewall rules exist for all open ports | Adjust open tcp ports" iptables: action: append chain: INPUT @@ -108,7 +108,7 @@ - "{{ rhel8cis_3_4_4_1_4_otcp.stdout_lines }}" when: rhel8cis_3_4_4_1_4_otcp.stdout is defined - - name: "SCORED | 3.4.4.1.4 | PATCH | Ensure firewall rules exist for all open ports | Adjust open udp ports" + - name: "3.4.4.1.4 | L1 | PATCH | Ensure iptables firewall rules exist for all open ports | Adjust open udp ports" iptables: action: append chain: INPUT @@ -128,3 +128,17 @@ - level1-workstation - patch - rule_3.4.4.1.4 + +- name: "3.4.4.1.5 | L1 | PATCH | Ensure iptables service is enabled and active | Check if iptables is enabled" + service: + name: iptables + enabled: yes + state: started + when: + - rhel8cis_firewall == "iptables" + - rhel8cis_rule_3_4_4_1_5 + tags: + - level1-server + - level1-workstation + - patch + - rule_3.4.4.1.5 diff --git a/tasks/section_3/cis_3.4.4.2.x.yml b/tasks/section_3/cis_3.4.4.2.x.yml index 95d2b3e4..f42ab714 100644 --- a/tasks/section_3/cis_3.4.4.2.x.yml +++ b/tasks/section_3/cis_3.4.4.2.x.yml @@ -1,8 +1,8 @@ --- -- name: "SCORED | 3.4.4.2.1 | PATCH | Ensure IPv6 default deny firewall policy" +- name: "3.4.4.2.1 | L1 | PATCH | Ensure ip6tables default deny firewall policy" block: - - name: "SCORED | 3.4.4.2.1 | PATCH | Ensure IPv6 default deny firewall policy | Configure ssh to be allowed" + - name: "3.4.4.2.1 | L1 | Ensure ip6tables default deny firewall policy | Configure ssh to be allowed" iptables: chain: INPUT protocol: tcp @@ -10,7 +10,7 @@ jump: ACCEPT ip_version: ipv6 - - name: "SCORED | 3.4.4.2.1 | PATCH | Ensure IPv6 default deny firewall policy | Set drop items" + - name: "3.4.4.2.1 | L1 | PATCH | Ensure ip6tables default deny firewall policy | Set drop items" iptables: policy: DROP chain: "{{ item }}" @@ -29,9 +29,9 @@ - patch - rule_3.4.4.2.1 -- name: "SCORED | 3.4.4.2.2 | PATCH | Ensure IPv6 loopback traffic is configured" +- name: "3.4.4.2.2 | L1 | PATCH | Ensure ip6tables loopback traffic is configured" block: - - name: "SCORED | 3.4.4.2.2 | PATCH | Ensure IPv6 loopback traffic is configured | INPUT Loopback ACCEPT" + - name: "3.4.4.2.2 | L1 | PATCH | Ensure ip6tables loopback traffic is configured | INPUT Loopback ACCEPT" iptables: action: append chain: INPUT @@ -39,7 +39,7 @@ jump: ACCEPT ip_version: ipv6 - - name: "SCORED | 3.4.4.2.2 | PATCH | Ensure IPv6 loopback traffic is configured | OUTPUT Loopback ACCEPT" + - name: "3.4.4.2.2 | L1 | PATCH | Ensure ip6tables loopback traffic is configured | OUTPUT Loopback ACCEPT" iptables: action: append chain: OUTPUT @@ -47,7 +47,7 @@ jump: ACCEPT ip_version: ipv6 - - name: "SCORED | 3.4.4.2.2 | PATCH | Ensure IPv6 loopback traffic is configured | INPUT Loopback 127.0.0.0/8" + - name: "3.4.4.2.2 | L1 | PATCH | Ensure ip6tables loopback traffic is configured | INPUT Loopback 127.0.0.0/8" iptables: action: append chain: INPUT @@ -64,7 +64,7 @@ - patch - rule_3.4.4.2.2 -- name: "NOTSCORED | 3.4.4.2.3 | PATCH | Ensure IPv6 outbound and established connections are configured" +- name: "3.4.4.2.3 | L1 | PATCH | Ensure ip6tables outbound and established connections are configured" iptables: action: append chain: '{{ item.chain }}' @@ -90,15 +90,15 @@ - patch - rule_3.4.4.2.3 -- name: "NOTSCORED | 3.4.4.2.4 | PATCH | Ensure IPV6 firewall rules exist for all open ports" +- name: "3.4.4.2.4 | L1 | PATCH | Ensure ip6tables firewall rules exist for all open ports" block: - - name: "NOTSCORED | 3.4.4.2.4 | AUDIT | Ensure IPv6 firewall rules exist for all open ports | Get list of TCP6 open ports" + - name: "3.4.4.2.4 | L1 | AUDIT | Ensure ip6tables firewall rules exist for all open ports | Get list of TCP6 open ports" shell: netstat -ant |grep "tcp6.*LISTEN" | awk '{ print $4 }'| sed 's/.*://' changed_when: false failed_when: false register: rhel8cis_3_4_4_2_4_otcp - - name: "NOTSCORED | 3.4.4.2.4 | PATCH | Ensure IPv6 firewall rules exist for all open ports| Adjust open tcp6 ports" + - name: "3.4.4.2.4 | L1 | PATCH |Ensure ip6tables firewall rules exist for all open ports| Adjust open tcp6 ports" iptables: action: append chain: INPUT @@ -120,3 +120,17 @@ - level1-workstation - patch - rule_3.4.4.2.4 + +- name: "3.4.4.2.5 | L1 | PATCH | Ensure ip6tables service is enabled and active | Check if ip6tables is enabled" + service: + name: ip6tables + enabled: yes + state: started + when: + - rhel8cis_firewall == "iptables" + - rhel8cis_rule_3_4_4_2_5 + tags: + - level1-server + - level1-workstation + - patch + - rule_3.4.4.2.5 diff --git a/tasks/section_3/cis_3.5.yml b/tasks/section_3/cis_3.5.yml index 910c12c6..361c6109 100644 --- a/tasks/section_3/cis_3.5.yml +++ b/tasks/section_3/cis_3.5.yml @@ -1,8 +1,8 @@ --- -- name: "SCORED | 3.5 | PATCH | Ensure wireless interfaces are disabled" +- name: "3.5 | L1 | PATCH | Ensure wireless interfaces are disabled" block: - - name: "SCORED | 3.5 | AUDIT | Ensure wireless interfaces are disabled | Check if nmcli command is available" + - name: "3.5 | L1 | AUDIT | Ensure wireless interfaces are disabled | Check if nmcli command is available" command: rpm -q NetworkManager changed_when: false failed_when: false @@ -11,14 +11,14 @@ warn: no register: rhel_08_nmcli_available - - name: "SCORED | 3.5 | AUDIT | Ensure wireless interfaces are disabled | Check if wifi is enabled" - command: nmcli radio all + - name: "3.5 | L1 | AUDIT | Ensure wireless interfaces are disabled | Check if wifi is enabled" + command: nmcli radio wifi register: rhel_08_wifi_enabled changed_when: rhel_08_wifi_enabled.stdout != "disabled" failed_when: false when: rhel_08_nmcli_available.rc == 0 - - name: "SCORED | 3.5 | PATCH | Ensure wireless interfaces are disabled | Disable wifi if enabled" + - name: "3.5 | L1 | PATCH | Ensure wireless interfaces are disabled | Disable wifi if enabled" command: nmcli radio all off changed_when: false failed_when: false diff --git a/tasks/section_3/cis_3.6.yml b/tasks/section_3/cis_3.6.yml index 2bb3dc1b..89ccd907 100644 --- a/tasks/section_3/cis_3.6.yml +++ b/tasks/section_3/cis_3.6.yml @@ -1,6 +1,6 @@ --- -- name: "NOTSCORED | 3.6 | PATCH | Disable IPv6" +- name: "3.6 | L2 | PATCH | Disable IPv6" replace: dest: /etc/default/grub regexp: '(^GRUB_CMDLINE_LINUX\s*\=\s*)(?:")(.+)(?/dev/null; done changed_when: false failed_when: false check_mode: no register: priv_procs - - name: "SCORED | 4.1.12 | PATCH | Ensure successful file system mounts are collected" + - name: "4.1.12 | L2 | PATCH | Ensure successful file system mounts are collected" template: src: audit/rhel8cis_rule_4_1_12.rules.j2 dest: /etc/audit/rules.d/rhel8cis_rule_4_1_12.rules @@ -179,7 +179,7 @@ - patch - rule_4.1.12 -- name: "SCORED | 4.1.13 | PATCH | Ensure use of privileged commands is collected" +- name: "4.1.13 | L2 | PATCH | Ensure use of privileged commands is collected" template: src: audit/rhel8cis_rule_4_1_13.rules.j2 dest: /etc/audit/rules.d/rhel8cis_rule_4_1_13.rules @@ -196,7 +196,7 @@ - patch - rule_4.1.13 -- name: "SCORED | 4.1.14 | PATCH | Ensure file deletion events by users are collected" +- name: "4.1.14 | L2 | PATCH | Ensure file deletion events by users are collected" template: src: audit/rhel8cis_rule_4_1_14.rules.j2 dest: /etc/audit/rules.d/rhel8cis_rule_4_1_14.rules @@ -213,7 +213,7 @@ - patch - rule_4.1.14 -- name: "SCORED | 4.1.15 | PATCH | Ensure kernel module loading and unloading is collected" +- name: "4.1.15 | L2 | PATCH | Ensure kernel module loading and unloading is collected" template: src: audit/rhel8cis_rule_4_1_15.rules.j2 dest: /etc/audit/rules.d/rhel8cis_rule_4_1_15.rules @@ -230,7 +230,7 @@ - patch - rule_4.1.15 -- name: "SCORED | 4.1.16 | PATCH | Ensure system administrator actions (sudolog) are collected" +- name: "4.1.16 | L2 | PATCH | Ensure system administrator actions (sudolog) are collected" template: src: audit/rhel8cis_rule_4_1_16.rules.j2 dest: /etc/audit/rules.d/rhel8cis_rule_4_1_16.rules @@ -247,7 +247,7 @@ - patch - rule_4.1.16 -- name: "SCORED | 4.1.17 | PATCH | Ensure the audit configuration is immutable" +- name: "4.1.17 | L2 | PATCH | Ensure the audit configuration is immutable" template: src: audit/rhel8cis_rule_4_1_17.rules.j2 dest: /etc/audit/rules.d/rhel8cis_rule_4_1_17.rules diff --git a/tasks/section_4/cis_4.2.1.x.yml b/tasks/section_4/cis_4.2.1.x.yml index 47b229db..836d47d0 100644 --- a/tasks/section_4/cis_4.2.1.x.yml +++ b/tasks/section_4/cis_4.2.1.x.yml @@ -1,10 +1,11 @@ --- -- name: "SCORED | 4.2.1.1 | PATCH | Ensure rsyslog or syslog-ng is installed" +- name: "4.2.1.1 | L1 | PATCH | Ensure rsyslog installed" package: - name: "{{ rhel8cis_syslog }}" + name: rsyslog state: present when: + - "'rsyslog' not in ansible_facts.packages" - rhel8cis_rule_4_2_1_1 tags: - level1-server @@ -12,13 +13,12 @@ - patch - rule_4.2.1.1 -- name: "SCORED | 4.2.1.2 | PATCH | Ensure rsyslog Service is enabled" +- name: "4.2.1.2 | L1 | PATCH | Ensure rsyslog Service is enabled" service: name: rsyslog enabled: yes when: - rhel8cis_rule_4_2_1_2 - - rhel8cis_syslog == 'rsyslog' tags: - level1-server - level1-workstation @@ -26,7 +26,7 @@ - rsyslog - rule_4.2.1.2 -- name: "SCORED | 4.2.1.3 | PATCH | Ensure rsyslog default file permissions configured" +- name: "4.2.1.3 | L1 | PATCH | Ensure rsyslog default file permissions configured" lineinfile: dest: /etc/rsyslog.conf regexp: '^\$FileCreateMode' @@ -40,22 +40,22 @@ - patch - rule_4.2.1.3 -- name: "NOTSCORED | 4.2.1.4 | PATCH | Ensure logging is configured" +- name: "4.2.1.4 | L1 | PATCH | Ensure logging is configured" block: - - name: "NOTSCORED | 4.2.1.4 | AUDIT | Ensure logging is configured | rsyslog current config message out" + - name: "4.2.1.4 | L1 | AUDIT | Ensure logging is configured | rsyslog current config message out" command: cat /etc/rsyslog.conf become: yes changed_when: false failed_when: no register: rhel_08_4_2_1_4_audit - - name: "NOTSCORED | 4.2.1.4 | AUDIT | Ensure logging is configured | rsyslog current config message out" + - name: "4.2.1.4 | L1 | AUDIT | Ensure logging is configured | rsyslog current config message out" debug: msg: - "These are the current logging configurations for rsyslog, please review:" - "{{ rhel_08_4_2_1_4_audit.stdout_lines }}" - - name: "NOTSCORED | 4.2.1.4 | PATCH | Ensure logging is configured | mail.* log setting" + - name: "4.2.1.4 | L1 | PATCH | Ensure logging is configured | mail.* log setting" blockinfile: path: /etc/rsyslog.conf state: present @@ -68,9 +68,9 @@ mail.err /var/log/mail.err insertafter: '# Log all the mail messages in one place.' notify: restart rsyslog - when: rhel8cis_rsyslog_ansibleManaged + when: rhel8cis_rsyslog_ansiblemanaged - - name: "NOTSCORED | 4.2.1.4 | PATCH | Ensure logging is configured | news.crit log setting" + - name: "4.2.1.4 | L1 | PATCH | Ensure logging is configured | news.crit log setting" blockinfile: path: /etc/rsyslog.conf state: present @@ -81,9 +81,9 @@ news.notice -/var/log/news/news.crit insertafter: '# Save news errors of level crit and higher in a special file.' notify: restart rsyslog - when: rhel8cis_rsyslog_ansibleManaged + when: rhel8cis_rsyslog_ansiblemanaged - - name: "NOTSCORED | 4.2.1.4 | PATCH | Ensure logging is configured | Misc. log setting" + - name: "4.2.1.4 | L1 | PATCH | Ensure logging is configured | Misc. log setting" blockinfile: path: /etc/rsyslog.conf state: present @@ -95,9 +95,9 @@ *.*;mail.none;news.none /var/log/messages insertafter: '#### RULES ####' notify: restart rsyslog - when: rhel8cis_rsyslog_ansibleManaged + when: rhel8cis_rsyslog_ansiblemanaged - - name: "NOTSCORED | 4.2.1.4 | PATCH | Ensure logging is configured | Local log settings" + - name: "4.2.1.4 | L1 | PATCH | Ensure logging is configured | Local log settings" blockinfile: path: /etc/rsyslog.conf state: present @@ -120,7 +120,7 @@ - rsyslog - rule_4.2.1.4 -- name: "SCORED | 4.2.1.5 | PATCH | Ensure rsyslog is configured to send logs to a remote log host" +- name: "4.2.1.5 | L1 | PATCH | Ensure rsyslog is configured to send logs to a remote log host" blockinfile: path: /etc/rsyslog.conf state: present @@ -143,9 +143,9 @@ - rule_4.2.1.5 - rsyslog -- name: "NOTSCORED | 4.2.1.6 | PATCH | Ensure remote rsyslog messages are only accepted on designated log hosts." +- name: "4.2.1.6 | L1 | PATCH | Ensure remote rsyslog messages are only accepted on designated log hosts." block: - - name: "NOTSCORED | 4.2.1.6 | PATCH | Ensure remote rsyslog messages are only accepted on designated log hosts. | When not log host" + - name: "4.2.1.6 | L1 | PATCH | Ensure remote rsyslog messages are only accepted on designated log hosts. | When not log host" replace: path: /etc/rsyslog.conf regexp: '({{ item }})' @@ -156,7 +156,7 @@ - '^(\$InputTCPServerRun)' when: not rhel8cis_system_is_log_server - - name: "NOTSCORED | 4.2.1.6 | PATCH | Ensure remote rsyslog messages are only accepted on designated log hosts. | When log host" + - name: "4.2.1.6 | L1 | PATCH | Ensure remote rsyslog messages are only accepted on designated log hosts. | When log host" replace: path: /etc/rsyslog.conf regexp: '^#(.*{{ item }}.*)' diff --git a/tasks/section_4/cis_4.2.2.x.yml b/tasks/section_4/cis_4.2.2.x.yml index 1b096d98..49ce75fd 100644 --- a/tasks/section_4/cis_4.2.2.x.yml +++ b/tasks/section_4/cis_4.2.2.x.yml @@ -1,6 +1,6 @@ --- -- name: "SCORED | 4.2.2.1 | PATCH | Ensure journald is configured to send logs to rsyslog" +- name: "4.2.2.1 | L1 | PATCH | Ensure journald is configured to send logs to rsyslog" lineinfile: dest: /etc/systemd/journald.conf regexp: "^#ForwardToSyslog=|^ForwardToSyslog=" @@ -14,7 +14,7 @@ - patch - rule_4.2.2.1 -- name: "SCORED | 4.2.2.2 | PATCH | Ensure journald is configured to compress large log files" +- name: "4.2.2.2 | L1 | PATCH | Ensure journald is configured to compress large log files" lineinfile: dest: /etc/systemd/journald.conf regexp: "^#Compress=|^Compress=" @@ -28,7 +28,7 @@ - patch - rule_4.2.2.2 -- name: "SCORED | 4.2.2.3 | PATCH | Ensure journald is configured to write logfiles to persistent disk" +- name: "4.2.2.3 | L1 | PATCH | Ensure journald is configured to write logfiles to persistent disk" lineinfile: dest: /etc/systemd/journald.conf regexp: "^#Storage=|^Storage=" diff --git a/tasks/section_4/cis_4.2.3.yml b/tasks/section_4/cis_4.2.3.yml index 1fec057d..c5105030 100644 --- a/tasks/section_4/cis_4.2.3.yml +++ b/tasks/section_4/cis_4.2.3.yml @@ -1,7 +1,7 @@ --- -- name: "SCORED | 4.2.3 | PATCH | Ensure permissions on all logfiles are configured" - command: find /var/log -type f -exec chmod g-wx,o-rwx {} + -o -type d -exec chmod g-w,o-rwx "{}" + +- name: "4.2.3 | L1 | PATCH | Ensure permissions on all logfiles are configured" + command: find /var/log/ -type f -perm /g+wx,o+rwx -exec chmod g-wx,o-rwx "{}" + changed_when: false failed_when: false when: diff --git a/tasks/section_4/cis_4.3.yml b/tasks/section_4/cis_4.3.yml index f124e9ca..2d60dac8 100644 --- a/tasks/section_4/cis_4.3.yml +++ b/tasks/section_4/cis_4.3.yml @@ -1,13 +1,13 @@ --- -- name: "NOTSCORED | 4.3 | PATCH | Ensure logrotate is configured" +- name: "4.3 | L1 | PATCH | Ensure logrotate is configured" block: - - name: "NOTSCORED | 4.3 | PATCH | Ensure logrotate is configured | Get logrotate settings" + - name: "4.3 | L1 | AUDIT | Ensure logrotate is configured | Get logrotate settings" find: paths: /etc/logrotate.d/ register: log_rotates - - name: "NOTSCORED | 4.3 | PATCH | Ensure logrotate is configured" + - name: "4.3 | L1 | PATCH | Ensure logrotate is configured" replace: path: "{{ item.path }}" regexp: '^(\s*)(daily|weekly|monthly|yearly)$' diff --git a/tasks/section_4/main.yml b/tasks/section_4/main.yml index 1fd3af3e..f3a95004 100644 --- a/tasks/section_4/main.yml +++ b/tasks/section_4/main.yml @@ -11,6 +11,7 @@ - name: "SECTION | 4.2.x| Configure Logging" include: cis_4.2.1.x.yml + when: rhel8cis_syslog == 'rsyslog' - name: "SECTION | 4.2.2.x| Configure journald" include: cis_4.2.2.x.yml diff --git a/tasks/section_5/cis_5.1.x.yml b/tasks/section_5/cis_5.1.x.yml index ad54a880..73de68f8 100644 --- a/tasks/section_5/cis_5.1.x.yml +++ b/tasks/section_5/cis_5.1.x.yml @@ -1,6 +1,6 @@ --- -- name: "SCORED | 5.1.1 | PATCH | Ensure cron daemon is enabled" +- name: "5.1.1 | L1 | PATCH | Ensure cron daemon is enabled" service: name: crond enabled: yes @@ -12,7 +12,7 @@ - patch - rule_5.1.1 -- name: "SCORED | 5.1.2 | PATCH | Ensure permissions on /etc/crontab are configured" +- name: "5.1.2 | L1 | PATCH | Ensure permissions on /etc/crontab are configured" file: dest: /etc/crontab owner: root @@ -26,7 +26,7 @@ - patch - rule_5.1.2 -- name: "SCORED | 5.1.3 | PATCH | Ensure permissions on /etc/cron.hourly are configured" +- name: "5.1.3 | L1 | PATCH | Ensure permissions on /etc/cron.hourly are configured" file: dest: /etc/cron.hourly state: directory @@ -41,7 +41,7 @@ - patch - rule_5.1.3 -- name: "SCORED | 5.1.4 | PATCH | Ensure permissions on /etc/cron.daily are configured" +- name: "5.1.4 | L1 | PATCH | Ensure permissions on /etc/cron.daily are configured" file: dest: /etc/cron.daily state: directory @@ -56,7 +56,7 @@ - patch - rule_5.1.4 -- name: "SCORED | 5.1.5 | PATCH | Ensure permissions on /etc/cron.weekly are configured" +- name: "5.1.5 | L1 | PATCH | Ensure permissions on /etc/cron.weekly are configured" file: dest: /etc/cron.weekly state: directory @@ -71,7 +71,7 @@ - patch - rule_5.1.5 -- name: "SCORED | 5.1.6 | PATCH | Ensure permissions on /etc/cron.monthly are configured" +- name: "5.1.6 | L1 | PATCH | Ensure permissions on /etc/cron.monthly are configured" file: dest: /etc/cron.monthly state: directory @@ -86,7 +86,7 @@ - patch - rule_5.1.6 -- name: "SCORED | 5.1.7 | PATCH | Ensure permissions on /etc/cron.d are configured" +- name: "5.1.7 | L1 | PATCH | Ensure permissions on /etc/cron.d are configured" file: dest: /etc/cron.d state: directory @@ -101,19 +101,19 @@ - patch - rule_5.1.7 -- name: "SCORED | 5.1.8 | PATCH | Ensure at/cron is restricted to authorized users" +- name: "5.1.8 | L1 | PATCH | Ensure at/cron is restricted to authorized users" block: - - name: "SCORED | 5.1.8 | PATCH | Ensure at/cron is restricted to authorized users | Remove at.deny" + - name: "5.1.8 | L1 | PATCH | Ensure at/cron is restricted to authorized users | Remove at.deny" file: dest: /etc/at.deny state: absent - - name: "SCORED | 5.1.8 | AUDIT | Ensure at/cron is restricted to authorized users | Check if at.allow exists" + - name: "5.1.8 | L1 | PATCH | Ensure at/cron is restricted to authorized users | Check if at.allow exists" stat: path: "/etc/at.allow" register: p - - name: "SCORED | 5.1.8 | PATCH | Ensure at/cron is restricted to authorized users | Ensure at.allow is restricted to authorized users" + - name: "5.1.8 | L1 | PATCH | Ensure at/cron is restricted to authorized users | Ensure at.allow is restricted to authorized users" file: dest: /etc/at.allow state: '{{ "file" if p.stat.exists else "touch" }}' @@ -121,17 +121,17 @@ group: root mode: 0600 - - name: "SCORED | 5.1.8 | PATCH | Ensure at/cron is restricted to authorized users | Remove cron.deny" + - name: "5.1.8 | L1 | PATCH | Ensure at/cron is restricted to authorized users | Remove cron.deny" file: dest: /etc/cron.deny state: absent - - name: "SCORED | 5.1.8 | PATCH | Ensure at/cron is restricted to authorized users | Check if cron.allow exists" + - name: "5.1.8 | L1 | PATCH | Ensure at/cron is restricted to authorized users | Check if cron.allow exists" stat: path: "/etc/cron.allow" register: p - - name: "SCORED | 5.1.8 | PATCH | Ensure at/cron is restricted to authorized users | Ensure cron.allow is restricted to authorized users" + - name: "5.1.8 | L1 | PATCH | Ensure at/cron is restricted to authorized users | Ensure cron.allow is restricted to authorized users" file: dest: /etc/cron.allow state: '{{ "file" if p.stat.exists else "touch" }}' diff --git a/tasks/section_5/cis_5.2.x.yml b/tasks/section_5/cis_5.2.x.yml index 4b5048e0..96b8d1fc 100644 --- a/tasks/section_5/cis_5.2.x.yml +++ b/tasks/section_5/cis_5.2.x.yml @@ -1,6 +1,6 @@ --- -- name: "SCORED | 5.2.1 | PATCH | Ensure permissions on /etc/ssh/sshd_config are configured" +- name: "5.2.1 | L1 | PATCH | Ensure permissions on /etc/ssh/sshd_config are configured" file: dest: /etc/ssh/sshd_config state: file @@ -15,9 +15,9 @@ - patch - rule_5.2.1 -- name: "SCORED | 5.2.2 | PATCH | Ensure SSH access is limited" +- name: "5.2.2 | L1 | PATCH | Ensure SSH access is limited" block: - - name: "SCORED | 5.2.2 | PATCH | Ensure SSH access is limited | Add line to sshd_config for allowusers" + - name: "5.2.2 | L1 | PATCH | Ensure SSH access is limited | Add line to sshd_config for allowusers" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -26,7 +26,7 @@ notify: restart sshd when: "rhel8cis_sshd['allowusers']|default('') | length > 0" - - name: "SCORED | 5.2.2 | PATCH | Ensure SSH access is limited | Add line to sshd_config for allowgroups" + - name: "5.2.2 | L1 | PATCH | Ensure SSH access is limited | Add line to sshd_config for allowgroups" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -35,7 +35,7 @@ notify: restart sshd when: "rhel8cis_sshd['allowgroups']|default('') | length > 0" - - name: "SCORED | 5.2.2 | PATCH | Ensure SSH access is limited | Add line to sshd_config for denyusers" + - name: "5.2.2 | L1 | PATCH | Ensure SSH access is limited | Add line to sshd_config for denyusers" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -44,7 +44,7 @@ notify: restart sshd when: "rhel8cis_sshd['denyusers']|default('') | length > 0" - - name: "SCORED | 5.2.2 | PATCH | Ensure SSH access is limited | Add line to sshd_config for denygroups" + - name: "5.2.2 | L1 | PATCH | Ensure SSH access is limited | Add line to sshd_config for denygroups" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -60,9 +60,9 @@ - patch - rule_5.2.2 -- name: "SCORED | 5.2.3 | PATCH | Ensure permissions on SSH private host key files are configured" +- name: "5.2.3 | L1 | PATCH | Ensure permissions on SSH private host key files are configured" block: - - name: "SCORED | 5.2.3 | PATCH | Ensure permissions on SSH private host key files are configured | Find the SSH private host keys" + - name: "5.2.3 | L1 | AUDIT | Ensure permissions on SSH private host key files are configured | Find the SSH private host keys" find: paths: /etc/ssh patterns: 'ssh_host_*_key' @@ -70,7 +70,7 @@ file_type: any register: rhel8cis_5_2_3_ssh_private_host_key - - name: "SCORED | 5.2.3 | PATCH | Ensure permissions on SSH private host key files are configured | Set permissions on SSH private host keys" + - name: "5.2.3 | L1 | PATCH | Ensure permissions on SSH private host key files are configured | Set permissions on SSH private host keys" file: path: "{{ item.path }}" owner: root @@ -86,9 +86,9 @@ - patch - rule_5.2.3 -- name: "SCORED | 5.2.4 | PATCH | Ensure permissions on SSH public host key files are configured" +- name: "5.2.4 | L1 | PATCH | Ensure permissions on SSH public host key files are configured" block: - - name: "SCORED | 5.2.4 | PATCH | Ensure permissions on SSH public host key files are configured | Find the SSH public host keys" + - name: "5.2.4 | L1 | AUDIT | Ensure permissions on SSH public host key files are configured | Find the SSH public host keys" find: paths: /etc/ssh patterns: 'ssh_host_*_key.pub' @@ -96,7 +96,7 @@ file_type: any register: rhel8cis_5_2_4_ssh_public_host_key - - name: "SCORED | 5.2.4 | PATCH | Ensure permissions on SSH public host key files are configured | Set permissions on SSH public host keys" + - name: "5.2.4 | L1 | PATCH | Ensure permissions on SSH public host key files are configured | Set permissions on SSH public host keys" file: path: "{{ item.path }}" owner: root @@ -112,7 +112,7 @@ - patch - rule_5.2.4 -- name: "SCORED | 5.2.5 | PATCH | Ensure SSH LogLevel is appropriate" +- name: "5.2.5 | L1 | PATCH | Ensure SSH LogLevel is appropriate" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -126,7 +126,7 @@ - patch - rule_5.2.5 -- name: "SCORED | 5.2.6 | PATCH | Ensure SSH X11 forwarding is disabled" +- name: "5.2.6 | L2 | PATCH | Ensure SSH X11 forwarding is disabled" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -140,7 +140,7 @@ - patch - rule_5.2.6 -- name: "SCORED | 5.2.7 | PATCH | Ensure SSH MaxAuthTries is set to 4 or less" +- name: "5.2.7 | L1 | PATCH | Ensure SSH MaxAuthTries is set to 4 or less" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -154,7 +154,7 @@ - patch - rule_5.2.7 -- name: "SCORED | 5.2.8 | PATCH | Ensure SSH IgnoreRhosts is enabled" +- name: "5.2.8 | L1 | PATCH | Ensure SSH IgnoreRhosts is enabled" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -168,7 +168,7 @@ - patch - rule_5.2.8 -- name: "SCORED | 5.2.9 | PATCH | Ensure SSH HostbasedAuthentication is disabled" +- name: "5.2.9 | L1 | PATCH | Ensure SSH HostbasedAuthentication is disabled" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -182,7 +182,7 @@ - patch - rule_5.2.9 -- name: "SCORED | 5.2.10 | PATCH | Ensure SSH root login is disabled" +- name: "5.2.10 | L1 | PATCH | Ensure SSH root login is disabled" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -196,7 +196,7 @@ - patch - rule_5.2.10 -- name: "SCORED | 5.2.11 | PATCH | Ensure SSH PermitEmptyPasswords is disabled" +- name: "5.2.11 | PATCH | Ensure SSH PermitEmptyPasswords is disabled" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -210,7 +210,7 @@ - patch - rule_5.2.11 -- name: "SCORED | 5.2.12 | PATCH | Ensure SSH PermitUserEnvironment is disabled" +- name: "5.2.12 | L1 | PATCH | Ensure SSH PermitUserEnvironment is disabled" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -224,16 +224,16 @@ - patch - rule_5.2.12 -- name: "SCORED | 5.2.13 | PATCH | Ensure SSH Idle Timeout Interval is configured" +- name: "5.2.13 | L1 | PATCH | Ensure SSH Idle Timeout Interval is configured" block: - - name: "SCORED | 5.2.13 | PATCH | Ensure SSH Idle Timeout Interval is configured | Add line in sshd_config for ClientAliveInterval" + - name: "5.2.13 | L1 | PATCH | Ensure SSH Idle Timeout Interval is configured | Add line in sshd_config for ClientAliveInterval" lineinfile: state: present dest: /etc/ssh/sshd_config regexp: '^ClientAliveInterval' line: "ClientAliveInterval {{ rhel8cis_sshd['clientaliveinterval'] }}" - - name: "SCORED | 5.2.13 | PATCH | Ensure SSH Idle Timeout Interval is configured | Ensure SSH ClientAliveCountMax set to <= 3" + - name: "5.2.13 | L1 | PATCH | Ensure SSH Idle Timeout Interval is configured | Ensure SSH ClientAliveCountMax set to <= 3" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -247,7 +247,7 @@ - patch - rule_5.2.13 -- name: "SCORED | 5.2.14 | PATCH | Ensure SSH LoginGraceTime is set to one minute or less" +- name: "5.2.14 | L1 | PATCH | Ensure SSH LoginGraceTime is set to one minute or less" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -261,7 +261,7 @@ - patch - rule_5.2.14 -- name: "SCORED | 5.2.15 | PATCH | Ensure SSH warning banner is configured" +- name: "5.2.15 | L1 | PATCH | Ensure SSH warning banner is configured" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -275,7 +275,7 @@ - patch - rule_5.2.15 -- name: "SCORED | 5.2.16 | PATCH | Ensure SSH PAM is enabled" +- name: "5.2.16 | L1 | PATCH | Ensure SSH PAM is enabled" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -289,7 +289,7 @@ - patch - rule_5.2.16 -- name: "SCORED | 5.2.17 | PATCH | Ensure SSH AllowTcpForwarding is disabled" +- name: "5.2.17 | L2 | PATCH | Ensure SSH AllowTcpForwarding is disabled" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -303,7 +303,7 @@ - patch - rule_5.2.17 -- name: "SCORED | 5.2.18 | PATCH | Ensure SSH MaxStartups is configured" +- name: "5.2.18 | L1 | PATCH | Ensure SSH MaxStartups is configured" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -317,7 +317,7 @@ - patch - rule_5.2.18 -- name: "SCORED | 5.2.19 | PATCH | Ensure SSH MaxSessions is set to 4 or less" +- name: "5.2.19 | L1 | PATCH | Ensure SSH MaxSessions is set to 4 or less" lineinfile: state: present dest: /etc/ssh/sshd_config @@ -331,7 +331,7 @@ - patch - rule_5.2.19 -- name: "SCORED | 5.2.20 | PATCH | Ensure system-wide crypto policy is not over-ridden" +- name: "5.2.20 | L1 | PATCH | Ensure system-wide crypto policy is not over-ridden" shell: sed -ri "s/^\s*(CRYPTO_POLICY\s*=.*)$/# \1/" /etc/sysconfig/sshd args: warn: no diff --git a/tasks/section_5/cis_5.3.x.yml b/tasks/section_5/cis_5.3.x.yml index 06bc9ec0..a3c7128b 100644 --- a/tasks/section_5/cis_5.3.x.yml +++ b/tasks/section_5/cis_5.3.x.yml @@ -1,21 +1,21 @@ --- -- name: "SCORED | 5.3.1 | PATCH | Create custom authselect profile" +- name: "5.3.1 | L1 | PATCH | Create custom authselect profile" block: - - name: "SCORED | 5.3.1 | AUDIT | Create custom authselect profile | Gather profiles" + - name: "5.3.1 | L1 | PATCH | Create custom authselect profile | Gather profiles" shell: 'authselect current | grep "Profile ID: custom/"' failed_when: false changed_when: false check_mode: no register: rhel8cis_5_3_1_profiles - - name: "SCORED | 5.3.1 | AUDIT | Create custom authselect profile | Show profiles" + - name: "5.3.1 | L1 | AUDIT | Create custom authselect profile | Show profiles" debug: msg: - "Below are the current custom profiles" - "{{ rhel8cis_5_3_1_profiles.stdout_lines }}" - - name: "SCORED | 5.3.1 | PATCH | Create custom authselect profile | Create custom profiles" + - name: "5.3.1 | L1 | PATCH | Create custom authselect profile | Create custom profiles" shell: authselect create-profile {{ rhel8cis_authselect['custom_profile_name'] }} -b {{ rhel8cis_authselect['default_file_to_copy'] }} args: warn: no @@ -29,9 +29,9 @@ - authselect - rule_5.3.1 -- name: "SCORED | 5.3.2 | PATCH | Select authselect profile" +- name: "5.3.2 | L1 | PATCH | Select authselect profile" block: - - name: "SCORED | 5.3.2 | AUDIT | Select authselect profile | Gather profiles and enabled features" + - name: "5.3.2 | L1 | AUDIT | Select authselect profile | Gather profiles and enabled features" shell: "authselect current" args: warn: no @@ -40,13 +40,13 @@ check_mode: no register: rhel8cis_5_3_2_profiles - - name: "SCORED | 5.3.2 | AUDIT | Select authselect profile | Show profiles" + - name: "5.3.2 | L1 | AUDIT | Select authselect profile | Show profiles" debug: msg: - "Below are the current custom profiles" - "{{ rhel8cis_5_3_2_profiles.stdout_lines }}" - - name: "SCORED | 5.3.2 | PATCH | Select authselect profile | Create custom profiles" + - name: "5.3.2 | L1 | PATCH | Select authselect profile | Create custom profiles" shell: "authselect select custom/{{ rhel8cis_authselect['custom_profile_name'] }} {{ rhel8cis_authselect['options'] }}" args: warn: no @@ -60,22 +60,22 @@ - authselect - rule_5.3.2 -- name: "SCORED | 5.3.3 | PATCH | Ensure authselect includes with-faillock" +- name: "5.3.3 | L1 | PATCH | Ensure authselect includes with-faillock" block: - - name: "SCORED | 5.3.3 | AUDIT | Ensure authselect includes with-faillock | Gather profiles and enabled features" + - name: "5.3.3 | L1 | AUDIT | Ensure authselect includes with-faillock | Gather profiles and enabled features" shell: "authselect current | grep with-faillock" failed_when: false changed_when: false check_mode: no register: rhel8cis_5_3_3_profiles_faillock - - name: "SCORED | 5.3.3 | AUDIT | Ensure authselect includes with-faillock| Show profiles" + - name: "5.3.3 | L1 | AUDIT | Ensure authselect includes with-faillock| Show profiles" debug: msg: - "Below are the current custom profiles" - "{{ rhel8cis_5_3_3_profiles_faillock.stdout_lines }}" - - name: "SCORED | 5.3.3 | PATCH | Ensure authselect includes with-faillock | Create custom profiles" + - name: "5.3.3 | L1 | PATCH | Ensure authselect includes with-faillock | Create custom profiles" shell: "authselect select custom/{{ rhel8cis_authselect['custom_profile_name'] }} with-faillock" args: warn: no diff --git a/tasks/section_5/cis_5.4.x.yml b/tasks/section_5/cis_5.4.x.yml index 57e74617..1b0600da 100644 --- a/tasks/section_5/cis_5.4.x.yml +++ b/tasks/section_5/cis_5.4.x.yml @@ -1,12 +1,12 @@ --- - name: | - "SCORED | 5.4.1 | PATCH | Ensure password creation requirements are configured - SCORED | 5.4.2 | PATCH | Ensure lockout for failed password attempts is configured - SCORED | 5.4.3 | PATCH | Ensure password reuse is limited - SCORED | 5.4.4 | PATCH | Ensure password hashing algorithm is SHA-512" + "5.4.1 | L1 | PATCH | Ensure password creation requirements are configured + 5.4.2 | L1 | PATCH | Ensure lockout for failed password attempts is configured + 5.4.3 | L1 | PATCH | Ensure password reuse is limited + 5.4.4 | L1 | PATCH | Ensure password hashing algorithm is SHA-512" block: - - name: "SCORED | 5.4.1 | PATCH | Ensure password creation requirements are configured | Set pwquality config settings" + - name: "5.4.1 | L1 | PATCH | Ensure password creation requirements are configured | Set pwquality config settings" lineinfile: state: present dest: /etc/security/pwquality.conf @@ -18,8 +18,8 @@ when: rhel8cis_rule_5_4_1 - name: | - "SCORED | 5.4.1 | PATCH | Ensure password creation requirements are configured | Set system-auth retry settings - SCORED | 5.4.3 | PATCH | Ensure password reuse is limited | Set system-auth remember settings" + "5.4.1 | L1 | PATCH | Ensure password creation requirements are configured | Set system-auth retry settings + 5.4.3| L1 | PATCH | Ensure password reuse is limited | Set system-auth remember settings" lineinfile: dest: /etc/pam.d/system-auth state: present @@ -30,7 +30,7 @@ - rhel8cis_rule_5_4_1 or rhel8cis_rule_5_4_3 - - name: "SCORED | 5.4.1 | PATCH | Ensure password creation requirements are configured | Set system-auth retry settings" + - name: "5.4.1 | L1 | PATCH | Ensure password creation requirements are configured | Set system-auth retry settings" lineinfile: dest: /etc/pam.d/password-auth state: present @@ -39,7 +39,7 @@ insertbefore: '^#?password ?' when: rhel8cis_rule_5_4_1 - - name: "SCORED | 5.4.2 | PATCH | Ensure lockout for failed password attempts is configured | Add deny count and unlock time for preauth" + - name: "5.4.2 | L1 | PATCH | Ensure lockout for failed password attempts is configured | Add deny count and unlock time for preauth" lineinfile: dest: /etc/pam.d/{{ item }} state: present @@ -51,7 +51,7 @@ - "password-auth" when: rhel8cis_rule_5_4_2 - - name: "SCORED | 5.4.2 | PATCH | Ensure lockout for failed password attempts is configured | Add deny count and unlock times for authfail" + - name: "5.4.2 | L1 | PATCH | Ensure lockout for failed password attempts is configured | Add deny count and unlock times for authfail" lineinfile: dest: /etc/pam.d/{{ item }} state: present @@ -64,8 +64,8 @@ when: rhel8cis_rule_5_4_2 - name: | - "SCORED | 5.4.3 | PATCH | Ensure password reuse is limited | Set system-auth remember remember settings - SCORED | 5.4.4 | PATCH | Ensure password hashing algorithm is SHA-512 | Set system-auth pwhash settings" + "5.4.3 | L1 | PATCH | Ensure password reuse is limited | Set system-auth remember remember settings + 5.4.4 | L1 | PATCH | Ensure password hashing algorithm is SHA-512 | Set system-auth pwhash settings" lineinfile: dest: /etc/pam.d/system-auth state: present @@ -76,7 +76,7 @@ - rhel8cis_rule_5_4_3 or rhel8cis_rule_5_4_4 - - name: "SCORED | 5.4.4 | PATCH | Ensure password hashing algorithm is SHA-512 | Set system-auth pwhash settings" + - name: "5.4.4 | L1 | PATCH | Ensure password hashing algorithm is SHA-512 | Set system-auth pwhash settings" lineinfile: dest: /etc/pam.d/password-auth state: present @@ -88,10 +88,10 @@ # The two steps below were added to keep authconfig from overwritting the above configs. This follows steps from here: https://access.redhat.com/documentation/en-us/red_hat_enterprise_linux/7/html/security_guide/chap-hardening_your_system_with_tools_and_services # With the steps below you will score five (5) points lower due to false positive results - name: | - "SCORED | 5.4.1 | PATCH | Ensure password creation requirements are configured" - SCORED | 5.4.2 | PATCH | Ensure lockout for failed password attempts is configured - SCORED | 5.4.3 | PATCH | Ensure password reuse is limited - SCORED | 5.4.4 | PATCH | Ensure password hashing algorithm is SHA-512" + "5.4.1 | L1 | PATCH | Ensure password creation requirements are configured + 5.4.2 | L1 | PATCH | Ensure lockout for failed password attempts is configured + 5.4.3 | L1 | PATCH | Ensure password reuse is limited + 5.4.4 | L1 | PATCH | Ensure password hashing algorithm is SHA-512" copy: src: /etc/pam.d/{{ item }} dest: /etc/pam.d/{{ item }}-local @@ -104,10 +104,10 @@ - "password-auth" - name: | - "SCORED | 5.4.1 | PATCH | Ensure password creation requirements are configured" - SCORED | 5.4.2 | PATCH | Ensure lockout for failed password attempts is configured - SCORED | 5.4.3 | PATCH | Ensure password reuse is limited - SCORED | 5.4.4 | PATCH | Ensure password hashing algorithm is SHA-512" + "5.4.1 | L1 | PATCH | Ensure password creation requirements are configured + 5.4.2 | L1 | PATCH | Ensure lockout for failed password attempts is configured + 5.4.3 | L1 | PATCH | Ensure password reuse is limited + 5.4.4 | L1 | PATCH | Ensure password hashing algorithm is SHA-512" file: src: /etc/pam.d/{{ item }}-local dest: /etc/pam.d/{{ item }} diff --git a/tasks/section_5/cis_5.5.1.x.yml b/tasks/section_5/cis_5.5.1.x.yml index caebadd5..aa85b598 100644 --- a/tasks/section_5/cis_5.5.1.x.yml +++ b/tasks/section_5/cis_5.5.1.x.yml @@ -1,6 +1,6 @@ --- -- name: "SCORED | 5.5.1.1 | PATCH | Ensure password expiration is 365 days or less" +- name: "5.5.1.1 | L1 | PATCH | Ensure password expiration is 365 days or less" lineinfile: state: present dest: /etc/login.defs @@ -14,7 +14,7 @@ - patch - rule_5.5.1.1 -- name: "SCORED | 5.5.1.2 | PATCH | Ensure minimum days between password changes is 7 or more" +- name: "5.5.1.2 | L1 | PATCH | Ensure minimum days between password changes is 7 or more" lineinfile: state: present dest: /etc/login.defs @@ -28,7 +28,7 @@ - patch - rule_5.5.1.2 -- name: "SCORED | 5.5.1.3 | PATCH | Ensure password expiration warning days is 7 or more" +- name: "5.5.1.3 | L1 | PATCH | Ensure password expiration warning days is 7 or more" lineinfile: state: present dest: /etc/login.defs @@ -42,26 +42,26 @@ - patch - rule_5.5.1.3 -- name: "SCORED | 5.5.1.4 | PATCH | Ensure inactive password lock is 30 days or less" +- name: "5.5.1.4 | L1 | PATCH | Ensure inactive password lock is 30 days or less" block: - - name: "SCORED | 5.5.1.4 | AUDIT | Ensure inactive password lock is 30 days or less | Check current settings" + - name: "5.5.1.4 | L1 | AUDIT | Ensure inactive password lock is 30 days or less | Check current settings" shell: useradd -D | grep INACTIVE={{ rhel8cis_inactivelock.lock_days }} | cut -f2 -d= changed_when: false failed_when: false check_mode: no register: rhel8cis_5_5_1_4_inactive_settings - - name: "SCORED | 5.5.1.4 | PATCH | Ensure inactive password lock is 30 days or less | Set default inactive setting" + - name: "5.5.1.4 | L1 | PATCH | Ensure inactive password lock is 30 days or less | Set default inactive setting" command: useradd -D -f {{ rhel8cis_inactivelock.lock_days }} when: rhel8cis_5_5_1_4_inactive_settings.stdout | length == 0 - - name: "AUDIT | 5.5.1.4 | PATCH | Ensure inactive password lock is 30 days or less | Getting user list" + - name: "5.5.1.4 | L1 | AUDIT | Ensure inactive password lock is 30 days or less | Getting user list" shell: 'egrep ^[^:]+:[^\!*] /etc/shadow | cut -d: -f1' check_mode: no register: rhel_08_5_5_1_4_audit changed_when: false - - name: "SCORED | 5.5.1.4 | PATCH | Ensure inactive password lock is 30 days or less | Apply Inactive setting to existing accounts" + - name: "5.5.1.4 | L1 | PATCH | Ensure inactive password lock is 30 days or less | Apply Inactive setting to existing accounts" command: chage --inactive {{ rhel8cis_inactivelock.lock_days }} "{{ item }}" with_items: - "{{ rhel_08_5_5_1_4_audit.stdout_lines }}" @@ -73,35 +73,35 @@ - patch - rule_5.5.1.4 -- name: "SCORED | 5.5.1.5 | PATCH | Ensure all users last password change date is in the past" +- name: "5.5.1.5 | L1 | PATCH | Ensure all users last password change date is in the past" block: - - name: "SCORED | 5.5.1.5 | AUDIT | Ensure all users last password change date is in the past | Get current date in Unix Time" + - name: "5.5.1.5 | L1 | AUDIT | Ensure all users last password change date is in the past | Get current date in Unix Time" shell: echo $(($(date --utc --date "$1" +%s)/86400)) failed_when: false changed_when: false check_mode: no - register: rhel8cis_5_5_1_5_currentUT + register: rhel8cis_5_5_1_5_currentut - - name: "SCORED | 5.5.1.5 | AUDIT | Ensure all users last password change date is in the past | Get list of users with last changed pw date in the future" - shell: "cat /etc/shadow | awk -F: '{if($3>{{ rhel8cis_5_5_1_5_currentUT.stdout }})print$1}'" + - name: "5.5.1.5 | L1 | AUDIT | Ensure all users last password change date is in the past | Get list of users with last changed pw date in the future" + shell: "cat /etc/shadow | awk -F: '{if($3>{{ rhel8cis_5_5_1_5_currentut.stdout }})print$1}'" changed_when: false failed_when: false check_mode: no register: rhel8cis_5_5_1_5_user_list - - name: "SCORED | 5.5.1.5 | AUDIT | Ensure all users last password change date is in the past | Alert no pw change in the future exist" + - name: "5.5.1.5 | L1 | AUDIT | Ensure all users last password change date is in the past | Alert no pw change in the future exist" debug: msg: "Good News! All accounts have PW change dates that are in the past" when: rhel8cis_5_5_1_5_user_list.stdout | length == 0 - - name: "SCORED | 5.5.1.5 | AUDIT | Ensure all users last password change date is in the past | Alert on accounts with pw change in the future" + - name: "5.5.1.5 | L1 | AUDIT | Ensure all users last password change date is in the past | Alert on accounts with pw change in the future" debug: msg: "Warning! The following accounts have the last PW change date in the future: {{ rhel8cis_5_5_1_5_user_list.stdout_lines }}" when: - rhel8cis_5_5_1_5_user_list.stdout | length > 0 - not rhel8cis_futurepwchgdate_autofix - - name: "SCORED | 5.5.1.5 | PATCH | Ensure all users last password change date is in the past | Fix accounts with pw change in the future" + - name: "5.5.1.5 | L1 | PATCH | Ensure all users last password change date is in the past | Fix accounts with pw change in the future" command: passwd --expire {{ item }} when: - rhel8cis_5_5_1_5_user_list | length > 0 diff --git a/tasks/section_5/cis_5.5.x.yml b/tasks/section_5/cis_5.5.x.yml index c02e49b3..b9e78c45 100644 --- a/tasks/section_5/cis_5.5.x.yml +++ b/tasks/section_5/cis_5.5.x.yml @@ -1,8 +1,8 @@ --- -- name: "SCORED | 5.5.2 | PATCH | Ensure system accounts are secured" +- name: "5.5.2 | L1 | PATCH | Ensure system accounts are secured" block: - - name: "SCORED | 5.5.2 | PATCH | Ensure system accounts are secured | Set nologin" + - name: "5.5.2 | L1 | Ensure system accounts are secured | Set nologin" user: name: "{{ item.id }}" shell: /usr/sbin/nologin @@ -17,7 +17,7 @@ - item.shell != " /bin/false" - item.shell != " /usr/sbin/nologin" - - name: "SCORED | 5.5.2 | PATCH | Ensure system accounts are secured | Lock accounts" + - name: "5.5.2 | L1 | PATCH | Ensure system accounts are secured | Lock accounts" user: name: "{{ item.id }}" password_lock: true @@ -39,7 +39,7 @@ - patch - rule_5.5.2 -- name: "SCORED | 5.5.3 | PATCH | Ensure default user shell timeout is 900 seconds or less" +- name: "5.5.3 | L1 | PATCH | Ensure default user shell timeout is 900 seconds or less" blockinfile: create: yes mode: 0644 @@ -62,7 +62,7 @@ - patch - rule_5.5.3 -- name: "SCORED | 5.5.4 | PATCH | Ensure default group for the root account is GID 0" +- name: "5.5.4 | L1 | PATCH | Ensure default group for the root account is GID 0" command: usermod -g 0 root changed_when: false failed_when: false @@ -73,15 +73,15 @@ - patch - rule_5.5.4 -- name: "SCORED | 5.5.5 | PATCH | Ensure default user umask is 027 or more restrictive" +- name: "5.5.5 | L1 | PATCH | Ensure default user umask is 027 or more restrictive" block: - - name: "SCORED | 5.5.5 | PATCH | Ensure default user umask is 027 or more restrictive | Set umask for /etc/bashrc" + - name: "5.5.5 | L1 | PATCH | Ensure default user umask is 027 or more restrictive | Set umask for /etc/bashrc" replace: path: /etc/bashrc regexp: '(^\s+umask) 002' replace: '\1 027' - - name: "SCORED | 5.5.5 | PATCH | Ensure default user umask is 027 or more restrictive | Set umask for /etc/profile" + - name: "5.5.5 | L1 | PATCH | Ensure default user umask is 027 or more restrictive | Set umask for /etc/profile" replace: path: /etc/profile regexp: '(^\s+umask) 002' diff --git a/tasks/section_5/cis_5.6.yml b/tasks/section_5/cis_5.6.yml index 5d6fc989..9bbfd29a 100644 --- a/tasks/section_5/cis_5.6.yml +++ b/tasks/section_5/cis_5.6.yml @@ -1,27 +1,27 @@ --- # this will just display the list of consoles. The site will need to confirm the allowed consoles are correct and change manually if needed. -- name: "NOTSCORED | 5.6 | AUDIT | Ensure root login is restricted to system console" +- name: "5.6 | L1 | AUDIT | Ensure root login is restricted to system console" block: - - name: "NOTSCORED | 5.6 | AUDIT | Ensure root login is restricted to system console | Check if securetty file exists" + - name: "5.6 | L1 | AUDIT | Ensure root login is restricted to system console | Check if securetty file exists" stat: path: /etc/securetty register: rhel8cis_securetty_check - - name: "NOTSCORED | 5.6 | AUDIT | Ensure root login is restricted to system console | Capture consoles" + - name: "5.6 | L1 | AUDIT | Ensure root login is restricted to system console | Capture consoles" command: cat /etc/securetty changed_when: false register: rhel_08_5_6_audit when: rhel8cis_securetty_check.stat.exists - - name: "NOTSCORED | 5.6 | AUDIT | Ensure root login is restricted to system console | Display Console" + - name: "5.6 | L1 | AUDIT |Ensure root login is restricted to system console | Display Console" debug: msg: - "These are the consoles with root login access, please review:" - "{{ rhel_08_5_6_audit.stdout_lines }}" when: rhel8cis_securetty_check.stat.exists - - name: "NOTSCORED | 5.6 | AUDIT | Ensure root login is restricted to system console | Display that no securetty file exists" + - name: "5.6 | L1 | AUDIT | Ensure root login is restricted to system console | Display that no securetty file exists" debug: msg: - "There is no /etc/securetty file, this has been removed by default in RHEL8" diff --git a/tasks/section_5/cis_5.7.yml b/tasks/section_5/cis_5.7.yml index f258fd9a..45e41dde 100644 --- a/tasks/section_5/cis_5.7.yml +++ b/tasks/section_5/cis_5.7.yml @@ -1,15 +1,15 @@ --- -- name: "SCORED | 5.7 | PATCH | Ensure access to the su command is restricted" +- name: "5.7 | L1 | PATCH | Ensure access to the su command is restricted" block: - - name: "SCORED | 5.7 | PATCH | Ensure access to the su command is restricted | Setting pm_wheel to use_uid" + - name: "5.7 | L1 | PATCH | Ensure access to the su command is restricted | Setting pam_wheel to use_uid" lineinfile: state: present dest: /etc/pam.d/su regexp: '^(#)?auth\s+required\s+pam_wheel\.so' line: 'auth required pam_wheel.so use_uid {% if rhel8cis_sugroup is defined %}group={{ rhel8cis_sugroup }}{% endif %}' - - name: "SCORED | 5.7 | PATCH | Ensure access to the su command is restricted | wheel group contains root" + - name: "5.7 | L1 | PATCH | Ensure access to the su command is restricted | wheel group contains root" user: name: "{{ rhel8cis_sugroup_users }}" groups: "{{ rhel8cis_sugroup | default('wheel') }}" @@ -19,4 +19,4 @@ - level1-server - level1-workstation - patch - - rule_5.7 \ No newline at end of file + - rule_5.7 diff --git a/tasks/section_5/main.yml b/tasks/section_5/main.yml index 886c7568..7d6a2034 100644 --- a/tasks/section_5/main.yml +++ b/tasks/section_5/main.yml @@ -8,6 +8,8 @@ - name: "SECTION | 5.3 | Configure Profiles" include: cis_5.3.x.yml + when: + - rhel8cis_use_authconfig - name: "SECTION | 5.4 | Configure PAM " include: cis_5.4.x.yml diff --git a/tasks/section_6/cis_6.1.x.yml b/tasks/section_6/cis_6.1.x.yml index 36af10fd..ccdc019a 100644 --- a/tasks/section_6/cis_6.1.x.yml +++ b/tasks/section_6/cis_6.1.x.yml @@ -1,8 +1,8 @@ --- -- name: "NOTSCORED | 6.1.1 | PATCH | Audit system file permissions" +- name: "6.1.1 | L2 | AUDIT | Audit system file permissions" block: - - name: "NOTSCORED | 6.1.1 | AUDIT | Audit system file permissions | Audit the packages" + - name: "6.1.1 | L2 | AUDIT | Audit system file permissions | Audit the packages" shell: rpm -Va --nomtime --nosize --nomd5 --nolinkto args: warn: no @@ -10,21 +10,21 @@ failed_when: false register: rhel8cis_6_1_1_packages_rpm - - name: "NOTSCORED | 6.1.1 | AUDIT | Audit system file permissions | Create list and warning" + - name: "6.1.1 | L2 | AUDIT | Audit system file permissions | Create list and warning" block: - - name: "NOTSCORED | 6.1.1 | AUDIT | Audit system file permissions | Add file discrepancy list to system" + - name: "6.1.1 | L2 | Audit system file permissions | Add file discrepancy list to system" copy: dest: "{{ rhel8cis_rpm_audit_file }}" content: "{{ rhel8cis_6_1_1_packages_rpm.stdout }}" - - name: "NOTSCORED | 6.1.1 | AUDIT | Audit system file permissions | Message out alert for package descrepancies" + - name: "6.1.1 | L2 | AUDIT | Audit system file permissions | Message out alert for package descrepancies" debug: msg: | "Warning! You have some package descrepancies issues. The file list can be found in {{ rhel8cis_rpm_audit_file }}" when: rhel8cis_6_1_1_packages_rpm.stdout|length > 0 - - name: "NOTSCORED | 6.1.1 | AUDIT | Audit system file permissions | Message out no package descrepancies" + - name: "6.1.1 | L2 | AUDIT | Audit system file permissions | Message out no package descrepancies" debug: msg: "Good News! There are no package descrepancies" when: rhel8cis_6_1_1_packages_rpm.stdout|length == 0 @@ -33,10 +33,10 @@ tags: - level2-server - level2-workstation - - patch + - audit - rule_6.1.1 -- name: "SCORED | 6.1.2 | PATCH | Ensure permissions on /etc/passwd are configured" +- name: "6.1.2 | L1 | PATCH | Ensure permissions on /etc/passwd are configured" file: dest: /etc/passwd owner: root @@ -50,12 +50,12 @@ - patch - rule_6.1.2 -- name: "SCORED | 6.1.3 | PATCH | Ensure permissions on /etc/shadow are configured" +- name: "6.1.3 | L1 | PATCH | Ensure permissions on /etc/passwd- are configured" file: - dest: /etc/shadow + dest: /etc/passwd- owner: root group: root - mode: 0640 + mode: 0644 when: - rhel8cis_rule_6_1_3 tags: @@ -64,12 +64,12 @@ - patch - rule_6.1.3 -- name: "SCORED | 6.1.4 | PATCH | Ensure permissions on /etc/group are configured" +- name: "6.1.4 | L1 | PATCH | Ensure permissions on /etc/shadow are configured" file: - dest: /etc/group + dest: /etc/shadow owner: root group: root - mode: 0644 + mode: 0000 when: - rhel8cis_rule_6_1_4 tags: @@ -78,12 +78,12 @@ - patch - rule_6.1.4 -- name: "SCORED | 6.1.5 | PATCH | Ensure permissions on /etc/gshadow are configured" +- name: "6.1.5 | L1 | PATCH | Ensure permissions on /etc/shadow- are configured" file: - dest: /etc/gshadow + dest: /etc/shadow- owner: root group: root - mode: 0640 + mode: 0000 when: - rhel8cis_rule_6_1_5 tags: @@ -92,12 +92,12 @@ - patch - rule_6.1.5 -- name: "SCORED | 6.1.6 | PATCH | Ensure permissions on /etc/passwd- are configured" +- name: "6.1.6 | L1 | PATCH | Ensure permissions on /etc/gshadow are configured" file: - dest: /etc/passwd- + dest: /etc/gshadow owner: root group: root - mode: 0600 + mode: 0000 when: - rhel8cis_rule_6_1_6 tags: @@ -106,12 +106,12 @@ - patch - rule_6.1.6 -- name: "SCORED | 6.1.7 | PATCH | Ensure permissions on /etc/shadow- are configured" +- name: "6.1.7 | L1 | PATCH | Ensure permissions on /etc/gshadow- are configured" file: - dest: /etc/shadow- + dest: /etc/gshadow- owner: root group: root - mode: 0600 + mode: 0000 when: - rhel8cis_rule_6_1_7 tags: @@ -120,7 +120,7 @@ - patch - rule_6.1.7 -- name: "SCORED | 6.1.8 | PATCH | Ensure permissions on /etc/group- are configured" +- name: "6.1.8 | L1 | PATCH | Ensure permissions on /etc/group are configured" file: dest: /etc/group- owner: root @@ -134,12 +134,12 @@ - patch - rule_6.1.8 -- name: "SCORED | 6.1.9 | PATCH | Ensure permissions on /etc/gshadow- are configured" +- name: "6.1.9 | L1 | PATCH | Ensure permissions on /etc/group- are configured" file: - dest: /etc/gshadow- + dest: /etc/group- owner: root group: root - mode: 0640 + mode: 0644 when: - rhel8cis_rule_6_1_9 tags: @@ -148,21 +148,21 @@ - patch - rule_6.1.9 -- name: "SCORED | 6.1.10 | PATCH | Ensure no world writable files exist" +- name: "6.1.10 | L1 | PATCH | Ensure no world writable files exist" block: - - name: "SCORED | 6.1.10 | AUDIT | Ensure no world writable files exist | Get list of world-writable files" + - name: "6.1.10 | L1 | AUDIT | Ensure no world writable files exist | Get list of world-writable files" shell: df --local -P | awk {'if (NR!=1) print $6'} | xargs -I '{}' find '{}' -xdev -type f -perm -0002 failed_when: false changed_when: false register: rhel_08_6_1_10_perms_results - - name: "SCORED | 6.1.10 | AUDIT | Ensure no world writable files exist | Alert no world-writable files exist" + - name: "6.1.10 | L1 | AUDIT | Ensure no world writable files exist | Alert no world-writable files exist" debug: msg: "Good news! We have not found any world-writable files on your system" when: - rhel_08_6_1_10_perms_results.stdout is not defined - - name: "SCORED | 6.1.10 | PATCH | Ensure no world writable files exist | Adjust world-writable files if they exist (Configurable)" + - name: "6.1.10 | L1 | PATCH | Ensure no world writable files exist | Adjust world-writable files if they exist (Configurable)" file: path: '{{ item }}' mode: o-w @@ -179,9 +179,9 @@ - patch - rule_6.1.10 -- name: "SCORED | 6.1.11 | PATCH | Ensure no unowned files or directories exist" +- name: "6.1.11 | L1 | AUDIT | Ensure no unowned files or directories exist" block: - - name: "SCORED | 6.1.11 | AUDIT | Ensure no unowned files or directories exist | Finding all unowned files or directories" + - name: "6.1.11 | L1 | AUDIT | Ensure no unowned files or directories exist | Finding all unowned files or directories" command: find "{{ item.mount }}" -xdev -nouser check_mode: false failed_when: false @@ -190,7 +190,7 @@ register: rhel_08_6_1_11_audit when: item['device'].startswith('/dev') and not 'bind' in item['options'] - - name: "SCORED | 6.1.11 | AUDIT | Ensure no unowned files or directories exist | Displaying any unowned files or directories" + - name: "6.1.11 | L1 | AUDIT | Ensure no unowned files or directories exist | Displaying any unowned files or directories" debug: msg: "Manual intervention is required -- missing owner on items in {{ item.item.mount }}: {{ item.stdout_lines | join(', ') }}" with_items: "{{ rhel_08_6_1_11_audit.results }}" @@ -202,12 +202,12 @@ tags: - level1-server - level1-workstation - - patch + - audit - rule_6.1.11 -- name: "SCORED | 6.1.12 | PATCH | Ensure no ungrouped files or directories exist" +- name: "6.1.12 | L1 | AUDIT | Ensure no ungrouped files or directories exist" block: - - name: "SCORED | 6.1.12 | AUDIT | Ensure no ungrouped files or directories exist | Finding all ungrouped files or directories" + - name: "6.1.12 | L1 | AUDIT | Ensure no ungrouped files or directories exist | Finding all ungrouped files or directories" command: find "{{ item.mount }}" -xdev -nogroup check_mode: false failed_when: false @@ -216,7 +216,7 @@ with_items: "{{ ansible_mounts }}" when: item['device'].startswith('/dev') and not 'bind' in item['options'] - - name: "SCORED | 6.1.12 | AUDIT | Ensure no ungrouped files or directories exist | Displaying all ungrouped files or directories" + - name: "6.1.12 | L1 | AUDIT | Ensure no ungrouped files or directories exist | Displaying all ungrouped files or directories" debug: msg: "Manual intervention is required -- missing group on items in {{ item.item.mount }}: {{ item.stdout_lines | join(', ') }}" with_items: "{{ rhel_08_6_1_12_audit.results }}" @@ -231,16 +231,16 @@ - patch - rule_6.1.12 -- name: "NOTSCORED | 6.1.13 | PATCH | Audit SUID executables" +- name: "6.1.13 | L1 | AUDIT | Audit SUID executables" block: - - name: "NOTSCORED | 6.1.13 | AUDIT | Audit SUID executables | Find all SUID executables" + - name: "6.1.13 | L1 | AUDIT | Audit SUID executables | Find all SUID executables" shell: df {{ item.mount }} -P | awk {'if (NR!=1) print $6'} | xargs -I '{}' find '{}' -xdev -type f -perm -4000 failed_when: false changed_when: false register: rhel_08_6_1_13_perms_results with_items: "{{ ansible_mounts }}" - - name: "NOTSCORED | 6.1.13 | AUDIT | Audit SUID executables | Alert no SUID executables exist" + - name: "6.1.13 | L1 | AUDIT | Audit SUID executables | Alert no SUID executables exist" debug: msg: "Good news! We have not found any SUID executable files on your system" failed_when: false @@ -248,7 +248,7 @@ when: - rhel_08_6_1_13_perms_results.stdout is not defined - - name: "NOTSCORED | 6.1.13 | AUDIT | Audit SUID executables | Alert SUID executables exist" + - name: "6.1.13 | L1 | AUDIT | Audit SUID executables | Alert SUID executables exist" debug: msg: "Manual intervention is required -- SUID set on items in {{ item.item.mount }}: {{ item.stout_lines | join(', ') }}" with_items: "{{ rhel_08_6_1_13_perms_results.stdout_lines }}" @@ -259,19 +259,19 @@ tags: - level1-server - level1-workstation - - patch + - audit - rule_6.1.13 -- name: "NOTSCORED | 6.1.14 | PATCH | Audit SGID executables" +- name: "6.1.14 | L1 | AUDIT | Audit SGID executables" block: - - name: "NOTSCORED | 6.1.14 | AUDIT | Audit SGID executables | Find all SGID executables" + - name: "6.1.14 | L1 | AUDIT | Audit SGID executables | Find all SGID executables" shell: df {{ item.mount }} -P | awk {'if (NR!=1) print $6'} | xargs -I '{}' find '{}' -xdev -type f -perm -2000 failed_when: false changed_when: false register: rhel_08_6_1_14_perms_results with_items: "{{ ansible_mounts }}" - - name: "NOTSCORED | 6.1.14 | AUDIT | Audit SGID executables | Alert no SGID executables exist" + - name: "6.1.14 | L1 | AUDIT | Audit SGID executables | Alert no SGID executables exist" debug: msg: "Good news! We have not found any SGID executable files on your system" failed_when: false @@ -279,7 +279,7 @@ when: - rhel_08_6_1_14_perms_results.stdout is not defined - - name: "NOTSCORED | 6.1.14 | AUDIT | Audit SGID executables | Alert SGID executables exist" + - name: "6.1.14 | L1 | AUDIT | Audit SGID executables | Alert SGID executables exist" debug: msg: "Manual intervention is required -- SGID set on items in {{ item.item.mount }}: {{ item.stout_lines | join(', ') }}" with_items: "{{ rhel_08_6_1_14_perms_results.stdout_lines }}" diff --git a/tasks/section_6/cis_6.2.x.yml b/tasks/section_6/cis_6.2.x.yml index 622f189c..55ff8fe7 100644 --- a/tasks/section_6/cis_6.2.x.yml +++ b/tasks/section_6/cis_6.2.x.yml @@ -1,6 +1,6 @@ --- -- name: "SCORED | 6.2.1 | PATCH | Ensure password fields are not empty" +- name: "6.2.1 | L1 | AUDIT | Ensure password fields are not empty" command: passwd -l {{ item }} changed_when: false failed_when: false @@ -14,7 +14,7 @@ - patch - rule_6.2.1 -- name: "SCORED | 6.2.2 | PATCH | Ensure no legacy '+' entries exist in /etc/passwd" +- name: "6.2.2 | L1 | PATCH | Ensure no legacy '+' entries exist in /etc/passwd" command: sed -i '/^+/ d' /etc/passwd changed_when: false failed_when: false @@ -27,37 +27,37 @@ - rule_6.2.2 - skip_ansible_lint -- name: "SCORED | 6.2.3 | PATCH | Ensure root PATH Integrity" +- name: "6.2.3 | L1 | PATCH | Ensure root PATH Integrity" block: - - name: "SCORED | 6.2.3 | AUDIT | Ensure root PATH Integrity | Determine empty value" + - name: "6.2.3 | L1 | AUDIT | Ensure root PATH Integrity | Determine empty value" shell: 'echo $PATH | grep ::' check_mode: no register: path_colon changed_when: False failed_when: path_colon.rc == 0 - - name: "SCORED | 6.2.3 | AUDIT | Ensure root PATH Integrity | Determin colon end" + - name: "6.2.3 | L1 | AUDIT | Ensure root PATH Integrity | Determin colon end" shell: 'echo $PATH | grep :$' check_mode: no register: path_colon_end changed_when: False failed_when: path_colon_end.rc == 0 - - name: "SCORED | 6.2.3 | AUDIT | Ensure root PATH Integrity | Determine dot in path" + - name: "6.2.3 | L1 | AUDIT | Ensure root PATH Integrity | Determine dot in path" shell: "/bin/bash --login -c 'env | grep ^PATH=' | sed -e 's/PATH=//' -e 's/::/:/' -e 's/:$//' -e 's/:/\\n/g'" check_mode: no register: dot_in_path changed_when: False failed_when: '"." in dot_in_path.stdout_lines' - - name: "SCORED | 6.2.3| AUDIT | Ensure root PATH Integrity | Alert on empty value, colon end, and dot in path" + - name: "6.2.3 | L1 | AUDIT | Ensure root PATH Integrity | Alert on empty value, colon end, and dot in path" debug: msg: - "The following paths have an empty value: {{ path_colon.stdout_lines }}" - "The following paths have colon end: {{ path_colon_end.stdout_lines }}" - "The following paths have a dot in the path: {{ dot_in_path.stdout_lines }}" - - name: "SCORED | 6.2.3 | PATCH | Ensure root PATH Integrity (Scored) | Determine rights and owner" + - name: "6.2.3 | L1 | PATCH | Ensure root PATH Integrity (Scored) | Determine rights and owner" file: > path='{{ item }}' follow=yes @@ -73,7 +73,7 @@ - patch - rule_6.2.3 -- name: "SCORED | 6.2.4 | PATCH | Ensure no legacy '+' entries exist in /etc/shadow" +- name: "6.2.4 | L1 | PATCH | Ensure no legacy '+' entries exist in /etc/shadow" command: sed -i '/^+/ d' /etc/shadow changed_when: false failed_when: false @@ -86,7 +86,7 @@ - rule_6.2.4 - skip_ansible_lint -- name: "SCORED | 6.2.5 | PATCH | Ensure no legacy '+' entries exist in /etc/group" +- name: "6.2.5 | L1 | PATCH | Ensure no legacy '+' entries exist in /etc/group" command: sed -i '/^+/ d' /etc/group changed_when: false failed_when: false @@ -99,7 +99,7 @@ - rule_6.2.5 - skip_ansible_lint -- name: "SCORED | 6.2.6 | PATCH | Ensure root is the only UID 0 account" +- name: "6.2.6 | L1 | PATCH | Ensure root is the only UID 0 account" command: passwd -l {{ item }} changed_when: false failed_when: false @@ -113,15 +113,15 @@ - patch - rule_6.2.6 -- name: "SCORED | 6.2.7 | PATCH | Ensure users' home directories permissions are 750 or more restrictive" +- name: "6.2.7 | L1 | PATCH | Ensure users' home directories permissions are 750 or more restrictive" block: - - name: "SCORED | 6.2.7| AUDIT | Ensure users' home directories permissions are 750 or more restrictive" + - name: "6.2.7 | L1 | AUDIT | Ensure users' home directories permissions are 750 or more restrictive" stat: path: "{{ item }}" with_items: "{{ rhel8cis_passwd | selectattr('uid', '>=', rhel8cis_int_gid) | selectattr('uid', '!=', 65534) | map(attribute='dir') | list }}" register: rhel_08_6_2_7_audit - - name: "SCORED | 6.2.7 | AUDIT | Ensure users' home directories permissions are 750 or more restrictive" + - name: "6.2.7 | L1 | AUDIT | Ensure users' home directories permissions are 750 or more restrictive" command: find -H {{ item.0 | quote }} -not -type l -perm /027 check_mode: false changed_when: rhel_08_6_2_7_patch_audit.stdout | length > 0 @@ -135,7 +135,7 @@ loop_control: label: "{{ item.0 }}" - - name: "SCORED | 6.2.7 | AUDIT | Ensure users' home directories permissions are 750 or more restrictive" + - name: "6.2.7 | L1 | PATCH | Ensure users' home directories permissions are 750 or more restrictive" file: path: "{{ item.0 }}" recurse: yes @@ -151,7 +151,7 @@ label: "{{ item.0 }}" # set default ACLs so the homedir has an effective umask of 0027 - - name: "SCORED | 6.2.7 | PATCH | Ensure users' home directories permissions are 750 or more restrictive" + - name: "6.2.7 | L1 | PATCH | Ensure users' home directories permissions are 750 or more restrictive" acl: path: "{{ item.0 }}" default: yes @@ -176,7 +176,7 @@ - patch - rule_6.2.7 -- name: "SCORED | 6.2.8 | PATCH | Ensure users own their home directories" +- name: "6.2.8 | L1 | PATCH | Ensure users own their home directories" file: path: "{{ item.dir }}" owner: "{{ item.id }}" @@ -196,28 +196,28 @@ - patch - rule_6.2.8 -- name: "SCORED | 6.2.9 | PATCH | Ensure users' dot files are not group or world-writable" +- name: "6.2.9 | L1 | PATCH | Ensure users' dot files are not group or world-writable" block: - - name: "SCORED | 6.2.9 | AUDIT | Ensure users' dot files are not group or world-writable | Check for files" + - name: "6.2.9 | L1 | AUDIT | Ensure users' dot files are not group or world-writable | Check for files" shell: find /home/ -name "\.*" -perm /g+w,o+w changed_when: false failed_when: false register: rhel8cis_6_2_9_audit - - name: "SCORED | 6.2.9 | AUDIT | Ensure users' dot files are not group or world-writable | Alert on files found" + - name: "6.2.9 | L1 | AUDIT | Ensure users' dot files are not group or world-writable | Alert on files found" debug: msg: "Good news! We have not found any group or world-writable dot files on your sytem" when: - rhel8cis_6_2_9_audit.stdout is not defined - - name: "SCORED | 6.2.9 | PATCH | Ensure users' dot files are not group or world-writable | Changes files if configured" + - name: "6.2.9 | L1 | PATCH | Ensure users' dot files are not group or world-writable | Changes files if configured" file: path: '{{ item }}' mode: go-w with_items: "{{ rhel8cis_6_2_9_audit.stdout_lines }}" when: - rhel8cis_6_2_9_audit.stdout is defined - - rhel8cis_dotperm_ansibleManaged + - rhel8cis_dotperm_ansiblemanaged when: - rhel8cis_rule_6_2_9 tags: @@ -226,7 +226,7 @@ - patch - rule_6.2.9 -- name: "SCORED | 6.2.10 | PATCH | Ensure no users have .forward files" +- name: "6.2.10 | L1 | PATCH | Ensure no users have .forward files" file: state: absent dest: "~{{ item }}/.forward" @@ -239,7 +239,7 @@ - patch - rule_6.2.10 -- name: "SCORED | 6.2.11 | PATCH | Ensure no users have .netrc files" +- name: "6.2.11 | L1 | PATCH | Ensure no users have .netrc files" file: state: absent dest: "~{{ item }}/.netrc" @@ -252,7 +252,7 @@ - patch - rule_6.2.11 -- name: "SCORED | 6.2.12 | PATCH | Ensure users' .netrc Files are not group or world accessible" +- name: "6.2.12 | L1 | PATCH | Ensure users' .netrc Files are not group or world accessible" command: /bin/true changed_when: false failed_when: false @@ -264,7 +264,7 @@ - patch - rule_6.2.12 -- name: "SCORED | 6.2.13 | PATCH | Ensure no users have .rhosts files" +- name: "6.2.13 | L1 | PATCH | Ensure no users have .rhosts files" file: state: absent dest: "~{{ item }}/.rhosts" @@ -277,21 +277,21 @@ - patch - rule_6.2.13 -- name: "SCORED | 6.2.14 | PATCH | Ensure all groups in /etc/passwd exist in /etc/group" +- name: "6.2.14 | L1 | AUDIT | Ensure all groups in /etc/passwd exist in /etc/group" block: - - name: "SCORED | 6.2.14 | AUDIT | Ensure all groups in /etc/passwd exist in /etc/group | Check /etc/passwd entries" + - name: "6.2.14 | L1 | AUDIT | Ensure all groups in /etc/passwd exist in /etc/group | Check /etc/passwd entries" shell: pwck -r | grep 'no group' | awk '{ gsub("[:\47]",""); print $2}' changed_when: false failed_when: false check_mode: false register: passwd_gid_check - - name: "SCORED | 6.2.14 | AUDIT | Ensure all groups in /etc/passwd exist in /etc/group | Print message that all groups match between passwd and group files" + - name: "6.2.14 | L1 | AUDIT | Ensure all groups in /etc/passwd exist in /etc/group | Print message that all groups match between passwd and group files" debug: msg: "Good News! There are no users that have non-existent GUIDs (Groups)" when: passwd_gid_check.stdout is not defined - - name: "SCORED | 6.2.14 | AUDIT | Ensure all groups in /etc/passwd exist in /etc/group | Print warning about users with invalid GIDs missing GID entries in /etc/group" + - name: "6.2.14 | L1 | AUDIT | Ensure all groups in /etc/passwd exist in /etc/group | Print warning about users with invalid GIDs missing GID entries in /etc/group" debug: msg: "WARNING: The following users have non-existent GIDs (Groups): {{ passwd_gid_check.stdout_lines | join (', ') }}" when: passwd_gid_check.stdout is defined @@ -300,23 +300,23 @@ tags: - level1-server - level1-workstation - - patch + - audit - rule_6.2.14 -- name: "SCORED | 6.2.15 | PATCH | Ensure no duplicate UIDs exist" +- name: "6.2.15 | L1 | AUDIT Ensure no duplicate UIDs exist" block: - - name: "SCORED | 6.2.15 | AUDIT | Ensure no duplicate UIDs exist | Check for duplicate UIDs" + - name: "6.2.15 | L1 | AUDIT | Ensure no duplicate UIDs exist | Check for duplicate UIDs" shell: "pwck -r | awk -F: '{if ($3 in uid) print $1 ; else uid[$3]}' /etc/passwd" changed_when: false failed_when: false register: user_uid_check - - name: "SCORED | 6.2.15 | AUDIT | Ensure no duplicate UIDs exist | Print message that no duplicate UIDs exist" + - name: "6.2.15 | L1 | AUDIT | Ensure no duplicate UIDs exist | Print message that no duplicate UIDs exist" debug: msg: "Good News! There are no duplicate UID's in the system" when: user_uid_check.stdout is not defined - - name: "SCORED | 6.2.15 | AUDIT | Ensure no duplicate UIDs exist | Print warning about users with duplicate UIDs" + - name: "6.2.15 | L1 | AUDIT| Ensure no duplicate UIDs exist | Print warning about users with duplicate UIDs" debug: msg: "Warning: The following users have UIDs that are duplicates: {{ user_uid_check.stdout_lines }}" when: user_uid_check.stdout is defined @@ -328,20 +328,20 @@ - patch - rule_6.2.15 -- name: "SCORED | 6.2.16 | PATCH | Ensure no duplicate GIDs exist" +- name: "6.2.16 | L1 | AUDIT | Ensure no duplicate GIDs exist" block: - - name: "SCORED | 6.2.16 | AUDIT | Ensure no duplicate GIDs exist | Check for duplicate GIDs" + - name: "6.2.16 | L1 | AUDIT | Ensure no duplicate GIDs exist | Check for duplicate GIDs" shell: "pwck -r | awk -F: '{if ($3 in users) print $1 ; else users[$3]}' /etc/group" changed_when: false failed_when: false register: user_user_check - - name: "SCORED | 6.2.16 | AUDIT | Ensure no duplicate GIDs exist | Print message that no duplicate GID's exist" + - name: "6.2.16 | L1 | AUDIT | Ensure no duplicate GIDs exist | Print message that no duplicate GID's exist" debug: msg: "Good News! There are no duplicate GIDs in the system" when: user_user_check.stdout is not defined - - name: "SCORED | 6.2.16 | AUDIT | Ensure no duplicate GIDs exist | Print warning about users with duplicate GIDs" + - name: "6.2.16 | L1 | AUDIT | Ensure no duplicate GIDs exist | Print warning about users with duplicate GIDs" debug: msg: "Warning: The following groups have duplicate GIDs: {{ user_user_check.stdout_lines }}" when: user_user_check.stdout is defined @@ -350,23 +350,23 @@ tags: - level1-server - level1-workstation - - patch + - audit - rule_6.2.16 -- name: "SCORED | 6.2.17 | PATCH | Ensure no duplicate user names exist" +- name: "6.2.17 | L1 | AUDIT | Ensure no duplicate user names exist" block: - - name: "SCORED | 6.2.17 | AUDIT | Ensure no duplicate user names exist | Check for duplicate User Names" + - name: "6.2.17 | L1 | AUDIT | Ensure no duplicate user names exist | Check for duplicate User Names" shell: "pwck -r | awk -F: '{if ($1 in users) print $1 ; else users[$1]}' /etc/passwd" changed_when: false failed_when: false register: user_username_check - - name: "SCORED | 6.2.17 | AUDIT | Ensure no duplicate user names exist | Print message that no duplicate user names exist" + - name: "6.2.17 | L1 | AUDIT | Ensure no duplicate user names exist | Print message that no duplicate user names exist" debug: msg: "Good News! There are no duplicate user names in the system" when: user_username_check.stdout is not defined - - name: "SCORED | 6.2.17 | AUDIT | Ensure no duplicate user names exist | Print warning about users with duplicate User Names" + - name: "6.2.17 | L1 | AUDIT | Ensure no duplicate user names exist | Print warning about users with duplicate User Names" debug: msg: "Warning: The following user names are duplicates: {{ user_username_check.stdout_lines }}" when: user_username_check.stdout is defined @@ -375,24 +375,24 @@ tags: - level1-server - level1-workstation - - patch + - audit - rule_6.2.17 -- name: "SCORED | 6.2.18 | PATCH | Ensure no duplicate group names exist" +- name: "6.2.18 | L1 | AUDIT |Ensure no duplicate group names exist" block: - - name: "SCORED | 6.2.18 | AUDIT | Ensure no duplicate group names exist | Check for duplicate group names" + - name: "6.2.18 | L1 | AUDIT | Ensure no duplicate group names exist | Check for duplicate group names" shell: 'getent passwd | cut -d: -f1 | sort -n | uniq -d' changed_when: false failed_when: false check_mode: no register: group_group_check - - name: "SCORED | 6.2.18 | AUDIT | Ensure no duplicate group names exist | Print message that no duplicate groups exist" + - name: "6.2.18 | L1 | AUDIT | Ensure no duplicate group names exist | Print message that no duplicate groups exist" debug: msg: "Good News! There are no duplicate group names in the system" when: group_group_check.stdout is defined - - name: "SCORED | 6.2.18 | AUDIT | Ensure no duplicate group names exist | Print warning about users with duplicate group names" + - name: "6.2.18 | L1 | AUDIT | Ensure no duplicate group names exist | Print warning about users with duplicate group names" debug: msg: "Warning: The following group names are duplicates: {{ group_group_check.stdout_lines }}" when: group_group_check.stdout is not defined @@ -401,33 +401,33 @@ tags: - level1-server - level1-workstation - - patch + - audit - rule_6.2.18 -- name: "SCORED | 6.2.19 | PATCH | Ensure shadow group is empty" +- name: "6.2.19 | L1 | AUDIT | Ensure shadow group is empty" block: - - name: "SCORED | 6.2.19 | AUDIT | Ensure shadow group is empty | Check for shadow group and pull group id" + - name: "6.2.19 | L1 | AUDIT | Ensure shadow group is empty | Check for shadow group and pull group id" shell: "getent group shadow | cut -d: -f3" changed_when: false failed_when: false check_mode: no register: rhel8cis_shadow_gid - - name: "SCORED | 6.2.19 | AUDIT | Ensure shadow group is empty | Check /etc/group for empty shadow group" + - name: "6.2.19 | L1 | AUDIT | Ensure shadow group is empty | Check /etc/group for empty shadow group" shell: grep ^shadow:[^:]*:[^:]*:[^:]+ /etc/group changed_when: false failed_when: false check_mode: no register: rhel8cis_empty_shadow - - name: "SCORED | 6.2.19 | AUDIT | Ensure shadow group is empty | Check for users assigned to shadow" + - name: "6.2.19 | L1 | AUDIT | Ensure shadow group is empty | Check for users assigned to shadow" shell: "getent passwd | awk -F: '$4 == '{{ rhel8cis_shadow_gid.stdout }}' {print $1}'" changed_when: false failed_when: false check_mode: no register: rhel8cis_shadow_passwd - - name: "SCORED | 6.2.19 | AUDIT | Ensure shadow group is empty | Alert shadow group is empty and no users assigned" + - name: "6.2.19 | L1 | AUDIT | Ensure shadow group is empty | Alert shadow group is empty and no users assigned" debug: msg: - " Good News! The shadow group is empty and there are no users assigned to shadow" @@ -435,14 +435,14 @@ - rhel8cis_empty_shadow.stdout | length == 0 - rhel8cis_shadow_passwd.stdout | length == 0 - - name: "SCORED | 6.2.19 | AUDIT | Ensure shadow group is empty | Alert shadow group is not empty" + - name: "6.2.19 | L1 | AUDIT | Ensure shadow group is empty | Alert shadow group is not empty" debug: msg: - "Alert! The shadow group is not empty" when: - rhel8cis_empty_shadow.stdout | length > 0 - - name: "SCORED | 6.2.19 | AUDIT | Ensure shadow group is empty | Alert users are using shadow group" + - name: "6.2.19 | L1 | AUDIT | Ensure shadow group is empty | Alert users are using shadow group" debug: msg: - "Alert! The following users are assigned to the shadow group, please assing them to the appropriate group" @@ -457,15 +457,15 @@ - audit - rule_6.2.19 -- name: "SCORED | 6.2.20 | PATCH | Ensure users home directories permissions are 750 or more restrictive" +- name: "6.2.20 | L1 | PATCH | Ensure users home directories permissions are 750 or more restrictive" block: - - name: "SCORED | 6.2.20 | AUDIT | Ensure users home directories permissions are 750 or more restrictive" + - name: "6.2.20 | L1 | AUDIT | Ensure users home directories permissions are 750 or more restrictive" stat: path: "{{ item }}" register: rhel_08_6_2_20_audit with_items: "{{ rhel8cis_passwd | selectattr('uid', '>=', rhel8cis_int_gid) | selectattr('uid', '!=', 65534) | map(attribute='dir') | list }}" - - name: "SCORED | 6.2.20 | AUDIT | Ensure users home directories permissions are 750 or more restrictive" + - name: "6.2.20 | L1 | AUDIT | Ensure users home directories permissions are 750 or more restrictive" command: find -H {{ item.0 | quote }} -not -type l -perm /027 check_mode: false changed_when: rhel_08_6_2_20_patch_audit.stdout "| length > 0" @@ -479,7 +479,7 @@ loop_control: label: "{{ item.0 }}" - - name: "SCORED | 6.2.20 | AUDIT | Ensure users home directories permissions are 750 or more restrictive" + - name: "6.2.20 | L1 | PATCH | Ensure users home directories permissions are 750 or more restrictive" file: path: "{{ item.0 }}" recurse: yes @@ -495,7 +495,7 @@ label: "{{ item.0 }}" # set default ACLs so the homedir has an effective umask of 0027 - - name: "SCORED | 6.2.20 | PATCH | Ensure users home directories permissions are 750 or more restrictive" + - name: "6.2.20 | L1 | PATCH | Ensure users home directories permissions are 750 or more restrictive" acl: path: "{{ item.0 }}" default: yes diff --git a/templates/ansible_vars_goss.yml.j2 b/templates/ansible_vars_goss.yml.j2 index b9859093..c3c3efb9 100644 --- a/templates/ansible_vars_goss.yml.j2 +++ b/templates/ansible_vars_goss.yml.j2 @@ -1,13 +1,16 @@ ## metadata for Audit benchmark rhel8cis_benchmark: - "type: CIS" -- "version: '1.0'" +- "version: '1.0.1'" - "os: RHEL 8" - "epoch: {{ ansible_date_time.epoch }}" - "hostname: {{ ansible_hostname }}" rhel8cis_os_distribution: {{ ansible_distribution | lower }} +# timeout for each command to run where set - default = 10seconds/10000ms +timeout_ms: {{ audit_cmd_timeout }} + # Taken from LE rhel8-cis rhel8cis_notauto: {{ rhel8cis_notauto }} rhel8cis_section1: {{ rhel8cis_section1 }} diff --git a/templates/etc/systemd/system/tmp.mount.j2 b/templates/etc/systemd/system/tmp.mount.j2 new file mode 100644 index 00000000..e62d186d --- /dev/null +++ b/templates/etc/systemd/system/tmp.mount.j2 @@ -0,0 +1,28 @@ +# SPDX-License-Identifier: LGPL-2.1+ +# +# This file is part of systemd. +# +# systemd is free software; you can redistribute it and/or modify it +# under the terms of the GNU Lesser General Public License as published by +# the Free Software Foundation; either version 2.1 of the License, or +# (at your option) any later version. + +[Unit] +Description=Temporary Directory (/tmp) +Documentation=man:hier(7) +Documentation=https://www.freedesktop.org/wiki/Software/systemd/APIFileSystems +ConditionPathIsSymbolicLink=!/tmp +DefaultDependencies=no +Conflicts=umount.target +Before=local-fs.target umount.target +After=swap.target + +[Mount] +What=tmpfs +Where=/tmp +Type=tmpfs +Options=mode=1777,strictatime,{% if rhel8cis_rule_1_1_3 %}nodev,{% endif %}{% if rhel8cis_rule_1_1_4 %}nosuid,{% endif %}{% if rhel8cis_rule_1_1_5 %}noexec{% endif %} + +# Make 'systemctl enable tmp.mount' work: +[Install] +WantedBy=local-fs.target \ No newline at end of file