Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

repo: Add an option to label /usr/etc as /etc #3063

Merged
merged 1 commit into from
Oct 12, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions man/ostree-commit.xml
Original file line number Diff line number Diff line change
Expand Up @@ -184,6 +184,14 @@ License along with this library. If not, see <https://www.gnu.org/licenses/>.
</para></listitem>
</varlistentry>

<varlistentry>
<term><option>--selinux-labeling-epoch</option>0 | 1</term>

<listitem><para>
When SELinux labeling is enabled, epoch <literal>1</literal> ensures that <literal>/usr/etc</literal> is labeled as if it was <literal>/etc</literal>.
</para></listitem>
</varlistentry>

<varlistentry>
<term><option>--bootable</option></term>
<listitem><para>
Expand Down
9 changes: 8 additions & 1 deletion src/libostree/ostree-repo-commit.c
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@
#include <gio/gunixoutputstream.h>
#include <glib-unix.h>
#include <glib/gprintf.h>
#include <stdbool.h>
#include <sys/ioctl.h>
#include <sys/statvfs.h>
#include <sys/xattr.h>
Expand Down Expand Up @@ -3272,8 +3273,14 @@ get_final_xattrs (OstreeRepo *self, OstreeRepoCommitModifier *modifier, const ch
if (modifier && modifier->sepolicy)
{
g_autofree char *label = NULL;
const char *path_for_labeling = relpath;

if (!ostree_sepolicy_get_label (modifier->sepolicy, relpath,
bool using_v1 = (modifier->flags & OSTREE_REPO_COMMIT_MODIFIER_FLAGS_SELINUX_LABEL_V1) > 0;
bool is_usretc = g_str_equal (relpath, "/usr/etc") || g_str_has_prefix (relpath, "/usr/etc/");
if (using_v1 && is_usretc)
path_for_labeling += strlen ("/usr");

if (!ostree_sepolicy_get_label (modifier->sepolicy, path_for_labeling,
g_file_info_get_attribute_uint32 (file_info, "unix::mode"),
&label, cancellable, error))
return FALSE;
Expand Down
3 changes: 3 additions & 0 deletions src/libostree/ostree-repo.h
Original file line number Diff line number Diff line change
Expand Up @@ -517,6 +517,8 @@ typedef OstreeRepoCommitFilterResult (*OstreeRepoCommitFilter) (OstreeRepo *repo
* 2017.13
* @OSTREE_REPO_COMMIT_MODIFIER_FLAGS_DEVINO_CANONICAL: If a devino cache hit is found, skip
* modifier filters (non-directories only); Since: 2017.14
* @OSTREE_REPO_COMMIT_MODIFIER_FLAGS_SELINUX_LABEL_V1: For SELinux and other systems, label
* /usr/etc as if it was /etc.
*
* Flags modifying commit behavior. In bare-user-only mode,
* @OSTREE_REPO_COMMIT_MODIFIER_FLAGS_CANONICAL_PERMISSIONS and
Expand All @@ -532,6 +534,7 @@ typedef enum
OSTREE_REPO_COMMIT_MODIFIER_FLAGS_ERROR_ON_UNLABELED = (1 << 3),
OSTREE_REPO_COMMIT_MODIFIER_FLAGS_CONSUME = (1 << 4),
OSTREE_REPO_COMMIT_MODIFIER_FLAGS_DEVINO_CANONICAL = (1 << 5),
OSTREE_REPO_COMMIT_MODIFIER_FLAGS_SELINUX_LABEL_V1 = (1 << 6),
} OstreeRepoCommitModifierFlags;

/**
Expand Down
18 changes: 18 additions & 0 deletions src/ostree/ot-builtin-commit.c
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@ static char *opt_tar_pathname_filter;
static gboolean opt_no_xattrs;
static char *opt_selinux_policy;
static gboolean opt_selinux_policy_from_base;
static int opt_selinux_labeling_epoch;
static gboolean opt_canonical_permissions;
static gboolean opt_ro_executables;
static gboolean opt_consume;
Expand Down Expand Up @@ -134,6 +135,10 @@ static GOptionEntry options[] = {
"Set SELinux labels based on policy in root filesystem PATH (may be /)", "PATH" },
{ "selinux-policy-from-base", 'P', 0, G_OPTION_ARG_NONE, &opt_selinux_policy_from_base,
"Set SELinux labels based on first --tree argument", NULL },
{ "selinux-labeling-epoch", 0, 0, G_OPTION_ARG_INT, &opt_selinux_labeling_epoch,
"Configure the default SELinux labeling rules; 0 is the default, 1 enables labeling /usr/etc "
"as /etc",
NULL },
{ "link-checkout-speedup", 0, 0, G_OPTION_ARG_NONE, &opt_link_checkout_speedup,
"Optimize for commits of trees composed of hardlinks into the repository", NULL },
{ "devino-canonical", 'I', 0, G_OPTION_ARG_NONE, &opt_devino_canonical,
Expand Down Expand Up @@ -597,6 +602,19 @@ ostree_builtin_commit (int argc, char **argv, OstreeCommandInvocation *invocatio
flags |= OSTREE_REPO_COMMIT_MODIFIER_FLAGS_SKIP_XATTRS;
if (opt_consume)
flags |= OSTREE_REPO_COMMIT_MODIFIER_FLAGS_CONSUME;
switch (opt_selinux_labeling_epoch)
{
case 0:
break;
case 1:
flags |= OSTREE_REPO_COMMIT_MODIFIER_FLAGS_SELINUX_LABEL_V1;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A bit unsure about the epoch approach. Do you envision many more SELinux options that fall in the "clearly right, but needs ratcheting" category?

We could always add epochs later on that just combine the flags if that happens.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Right the background for this is that today there's ostree admin init-fs --modern and I actually wanted to change the defaults there to do something else, and then it gets weird because it'd be need to be called like --really-modern or something 😄

You're probably right we wouldn't change things again (and if we did we'd probably arguably want to change the policy defaults).

But still, no harm done in making this a bit more future proof right?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

But still, no harm done in making this a bit more future proof right?

Just trying to keep out unnecessary complexity (YAGNI and all that). :)
But not strongly against.

break;
default:
{
glnx_throw (error, "Unknown SELinux labeling epoch: %d", opt_selinux_labeling_epoch);
goto out;
}
}
if (opt_devino_canonical)
{
opt_link_checkout_speedup = TRUE; /* Imply this */
Expand Down
15 changes: 15 additions & 0 deletions tests/kolainst/destructive/itest-label-selinux.sh
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,21 @@ ostree refs --delete testbranch
rm co -rf
echo "ok commit with sepolicy"

ostree ls -X ${host_refspec} /usr/etc/sysctl.conf > ls.txt
if grep -qF ':etc_t:' ls.txt; then
ostree checkout -H ${host_refspec} co
ostree commit -b testbranch --link-checkout-speedup \
--selinux-policy co --tree=dir=co --selinux-labeling-epoch=1
ostree ls -X testbranch /usr/etc/sysctl.conf > ls.txt
assert_file_has_content ls.txt ':system_conf_t:'
rm co ls.txt -rf
ostree refs --delete testbranch
else
echo 'Already using --selinux-labeling-epoch > 0 on host, hopefully!'
fi

echo "ok --selinux-labeling-epoch=1"

# Now let's check that selinux policy labels can be applied on checkout

rm rootfs -rf
Expand Down
Loading