diff --git a/manifests/shared-workarounds.yaml b/manifests/shared-workarounds.yaml index 500582942b..a0457797b4 100644 --- a/manifests/shared-workarounds.yaml +++ b/manifests/shared-workarounds.yaml @@ -1,2 +1,4 @@ # This manifest is a list of shared workarounds that are needed in both Fedora CoreOS # and downstreams (i.e. Red Hat CoreOS). +ostree-layers: + - overlay/07fix-selinux-labels diff --git a/overlay.d/07fix-selinux-labels/usr/lib/systemd/system-preset/40-fix-selinux-labels.preset b/overlay.d/07fix-selinux-labels/usr/lib/systemd/system-preset/40-fix-selinux-labels.preset new file mode 100644 index 0000000000..d7d1d2ba0a --- /dev/null +++ b/overlay.d/07fix-selinux-labels/usr/lib/systemd/system-preset/40-fix-selinux-labels.preset @@ -0,0 +1,8 @@ +# Fix incorrect SELinux labels in /boot and /sysroot +# - https://github.com/coreos/fedora-coreos-tracker/issues/1772 +# - https://github.com/coreos/fedora-coreos-tracker/issues/1771 +# We need this for both FCOS and RHCOS and it needs to live for +# some time (not just a single FCOS barrier release) so that we +# can ensure RHCOS 4.16 aleph nodes and some early 4.17 aleph +# nodes have been fixed. +enable coreos-fix-selinux-labels.service diff --git a/overlay.d/07fix-selinux-labels/usr/lib/systemd/system/coreos-fix-selinux-labels.service b/overlay.d/07fix-selinux-labels/usr/lib/systemd/system/coreos-fix-selinux-labels.service new file mode 100644 index 0000000000..38683b5e60 --- /dev/null +++ b/overlay.d/07fix-selinux-labels/usr/lib/systemd/system/coreos-fix-selinux-labels.service @@ -0,0 +1,16 @@ +[Unit] +Description=Fix mislabeled or unlabeled SELinux contexts on files +Documentation=https://github.com/coreos/fedora-coreos-tracker/issues/1771 +Documentation=https://github.com/coreos/fedora-coreos-tracker/issues/1772 +ConditionPathExists=!/var/lib/coreos-fix-selinux-labels.stamp + +[Service] +Type=oneshot +# Don't run this more than once, even if it fails +ExecStartPre=/bin/touch /var/lib/coreos-fix-selinux-labels.stamp +ExecStart=/usr/libexec/coreos-fix-selinux-labels +RemainAfterExit=yes +MountFlags=slave + +[Install] +WantedBy=multi-user.target diff --git a/overlay.d/07fix-selinux-labels/usr/libexec/coreos-fix-selinux-labels b/overlay.d/07fix-selinux-labels/usr/libexec/coreos-fix-selinux-labels new file mode 100755 index 0000000000..c819eb49d2 --- /dev/null +++ b/overlay.d/07fix-selinux-labels/usr/libexec/coreos-fix-selinux-labels @@ -0,0 +1,149 @@ +#!/usr/bin/bash + +# Script to help fix selinux labels on systems that were created with +# OSBuild before https://github.com/coreos/coreos-assembler/commit/d3302e0fc9bedec2d4e935e3528eb5abd44e7ae8 +# was put in place to ensure images didn't get created with unlabeled +# or mislabeled files. See also +# - https://github.com/coreos/fedora-coreos-tracker/issues/1771 +# - https://github.com/coreos/fedora-coreos-tracker/issues/1772 +# +# Also handle /boot/.root_uuid and /boot/grub2/bootuuid.cfg created +# by rdcore for some time without labels. +# - https://github.com/coreos/fedora-coreos-tracker/issues/1770 +# - https://github.com/coreos/fedora-coreos-config/pull/3155 + +set -eu -o pipefail + +print_header() { + echo '------------------------------------' + echo "$1" + echo +} + +get_context() { + path=$1 + getfattr -n security.selinux --absolute-name --only-values "${path}" | \ + tr -d '\0' # Trim the null byte from the ouptut to prevent bash warning +} + +path_unlabeled() { + test -e "$1" || return 1 # no exist so not unlabeled + if [ "$(get_context "$1")" == "system_u:object_r:unlabeled_t:s0" ]; then + return 0 + else + return 1 + fi +} + +any_unlabeled() { + # shellcheck disable=SC2068 + for file in $@; do + path_unlabeled "${file}" && return 0 + done + return 1 # none were unlabeled +} + +# Check a few known paths. If /sysroot is unlabeled then we need to +# clean up the mess that OSBuild left behind #1771,#1772. If /boot/.root_uuid +# or /boot/grub2/bootuuid.cfg are unlabeled we need to fix those two #1770. +if ! any_unlabeled '/sysroot' '/boot/.root_uuid' '/boot/grub2/bootuuid.cfg'; then + echo "This CoreOS installation is properly labeled. Exiting" + exit 0 +fi + +print_header "Remounting filesystems read/write" +# Note we don't need to remount them read-only later +# because we are running with MountFlags=slave so +# changes here won't propagate to the rest of the system +mount -v -o remount,rw /boot +mount -v -o remount,rw /sysroot + +# Fix the few ones we know about. Some of these are from #1770 +# and some from #1772, but it's easier to just combine the code. +print_header "Fixing label for files on the /boot filesystem" +for file in '.root_uuid' 'grub2/bootuuid.cfg' 'lost+found'; do + if path_unlabeled "/boot/${file}"; then + context=$(matchpathcon -n "/boot/${file}") + echo "Changing context of /boot/${file} to ${context}" + /usr/bin/chcon -h -v "${context}" "/boot/${file}" + fi +done +# Also handle coreos/platforms.json, which could have the wrong label +if [ -e "/boot/coreos/platforms.json" ]; then + restorecon -v "/boot/coreos/platforms.json" +fi + +if ! path_unlabeled "/sysroot"; then + # We don't need to go further with the other fixes since + # this system doesn't appear to be affected by #1771,#1772. + echo "coreos-fix-selinux-labels finished successfully" > /var/lib/coreos-fix-selinux-labels.stamp + exit 0 +fi + +print_header "Mounting boot partition separately to check shadowed /boot/efi" +boot_mount_point=$(mktemp --directory) +mount -v /dev/disk/by-partlabel/boot "$boot_mount_point" +if path_unlabeled "${boot_mount_point}/efi"; then + echo "Fixing label on shadowed /boot/efi" + context=$(matchpathcon -n "/boot/efi") + echo "Changing context of /boot/efi to ${context}" + /usr/bin/chcon -h -v "${context}" "${boot_mount_point}/efi" +fi +umount -v "$boot_mount_point" +rmdir "$boot_mount_point" + + +# The underlying /boot directory on the root filesystem can be wrong +print_header "Mounting root partition separately to check shadowed /boot" +root_mount_point=$(mktemp --directory) +mount -v /dev/disk/by-partlabel/root "$root_mount_point" +if path_unlabeled "${root_mount_point}/boot"; then + echo "Fixing the label for the /boot mount point on the root filesystem" + context=$(matchpathcon -n "/boot/") + echo "Changing context of /sysroot/boot to ${context}" + /usr/bin/chcon -h -v "${context}" "${root_mount_point}/boot" +fi +umount -v "$root_mount_point" +rmdir "$root_mount_point" + +# Fix unlabeled files. The find commands are hand crafted to try +# to catch all unlabeled files, but not touch any objects in the +# ostree repo and also not traverse too deep in the filesystem, +# which could take more time than we'd like. +# +# - /ostree/repo/refs/ to capture the container/blob/ files +# - /ostree/boot* to capture boot.x and bootx.x files +# - /ostree/repo/{.lock,config} - two known offenders +# - .aleph-version.json, .coreos-aleph-version.json - two more +# - -type l -or -type d - all directories of symlinks in the repo +# - -type f -regex '.*\.\(commitmeta\|commit\|dirmeta\|dirtree\|origin\)' +# - all .commitmeta, .commit, .dirmeta, .dirtree, .origin +# files in the repo and no other files (objects) +# +# Note some of these are left unquoted to allow for shell expansion. +# +context=$(matchpathcon -n "/") +print_header "Changing context of unlabeled files to ${context}" +( + find "/sysroot/ostree/repo/refs" \ + "/sysroot/.aleph-version.json" \ + "/sysroot/.coreos-aleph-version.json" \ + /sysroot/ostree/repo/{.lock,config} \ + /sysroot/ostree/boot* \ + -context '*:unlabeled_t:*'; + find "/sysroot/" -maxdepth 7 -context '*:unlabeled_t:*' \ + \( \ + -type l -or -type d -or \ + \( -type f -regex '.*\.\(commitmeta\|commit\|dirmeta\|dirtree\|origin\)' \) \ + \) +) | xargs -I{} chcon -v -h "${context}" {} | wc -l | xargs -I{} echo "Relabeled {} files to ${context}" + +print_header "Checking the repository for consistency" +if ! ostree fsck; then + echo "OSTree fsck found corruption. Please reprovision if you can or" 1>&2 + echo "ask for help at https://discussion.fedoraproject.org/tag/coreos" 1>&2 + echo "coreos-fix-selinux-labels finished with failure" > /var/lib/coreos-fix-selinux-labels.stamp + exit 1 +fi + +echo "coreos-fix-selinux-labels finished successfully" > /var/lib/coreos-fix-selinux-labels.stamp diff --git a/overlay.d/README.md b/overlay.d/README.md index 9597731fdf..5717586c4c 100644 --- a/overlay.d/README.md +++ b/overlay.d/README.md @@ -10,6 +10,17 @@ This overlay matches `fedora-coreos-base.yaml`; core Ignition+ostree bits. This overlay is shared with RHCOS/SCOS 9. +07fix-selinux-labels +-------------------- + +Fix incorrect SELinux labels in /boot and /sysroot +- https://github.com/coreos/fedora-coreos-tracker/issues/1772 +- https://github.com/coreos/fedora-coreos-tracker/issues/1771 +We need this for both FCOS and RHCOS and it needs to live for +some time (not just a single FCOS barrier release) so that we +can ensure RHCOS 4.16 aleph nodes and some early 4.17 aleph +nodes have been fixed. + 08nouveau ---------