IPE is designed to provide system level trust guarantees, this usually implies that trust starts from bootup with a hardware root of trust, which validates the bootloader. After this, the bootloader verifies the kernel and the initramfs. As there's no currently supported integrity method for initramfs, and it's typically already verified by the bootloader. This patch introduces a new IPE property `boot_verified` which allows author of IPE policy to indicate trust for files from initramfs. The implementation of this feature utilizes the newly added `initramfs_populated` hook. This hook marks the superblock of the rootfs after the initramfs has been unpacked into it. Before mounting the real rootfs on top of the initramfs, initramfs script will recursively remove all files and directories on the initramfs. This is typically implemented by using switch_root(8) (https://man7.org/linux/man-pages/man8/switch_root.8.html). Therefore the initramfs will be empty and not accessible after the real rootfs takes over. It is advised to switch to a different policy that doesn't rely on the `boot_verified` property after this point. This ensures that the trust policies remain relevant and effective throughout the system's operation. Signed-off-by: Deven Bowers <deven.desai@linux.microsoft.com> Signed-off-by: Fan Wu <wufan@linux.microsoft.com> Signed-off-by: Paul Moore <paul@paul-moore.com>
57 lines
1.3 KiB
C
57 lines
1.3 KiB
C
// SPDX-License-Identifier: GPL-2.0
|
|
/*
|
|
* Copyright (C) 2020-2024 Microsoft Corporation. All rights reserved.
|
|
*/
|
|
#include <uapi/linux/lsm.h>
|
|
|
|
#include "ipe.h"
|
|
#include "eval.h"
|
|
#include "hooks.h"
|
|
|
|
static struct lsm_blob_sizes ipe_blobs __ro_after_init = {
|
|
.lbs_superblock = sizeof(struct ipe_superblock),
|
|
};
|
|
|
|
static const struct lsm_id ipe_lsmid = {
|
|
.name = "ipe",
|
|
.id = LSM_ID_IPE,
|
|
};
|
|
|
|
struct ipe_superblock *ipe_sb(const struct super_block *sb)
|
|
{
|
|
return sb->s_security + ipe_blobs.lbs_superblock;
|
|
}
|
|
|
|
static struct security_hook_list ipe_hooks[] __ro_after_init = {
|
|
LSM_HOOK_INIT(bprm_check_security, ipe_bprm_check_security),
|
|
LSM_HOOK_INIT(mmap_file, ipe_mmap_file),
|
|
LSM_HOOK_INIT(file_mprotect, ipe_file_mprotect),
|
|
LSM_HOOK_INIT(kernel_read_file, ipe_kernel_read_file),
|
|
LSM_HOOK_INIT(kernel_load_data, ipe_kernel_load_data),
|
|
LSM_HOOK_INIT(initramfs_populated, ipe_unpack_initramfs),
|
|
};
|
|
|
|
/**
|
|
* ipe_init() - Entry point of IPE.
|
|
*
|
|
* This is called at LSM init, which happens occurs early during kernel
|
|
* start up. During this phase, IPE registers its hooks and loads the
|
|
* builtin boot policy.
|
|
*
|
|
* Return:
|
|
* * %0 - OK
|
|
* * %-ENOMEM - Out of memory (OOM)
|
|
*/
|
|
static int __init ipe_init(void)
|
|
{
|
|
security_add_hooks(ipe_hooks, ARRAY_SIZE(ipe_hooks), &ipe_lsmid);
|
|
|
|
return 0;
|
|
}
|
|
|
|
DEFINE_LSM(ipe) = {
|
|
.name = "ipe",
|
|
.init = ipe_init,
|
|
.blobs = &ipe_blobs,
|
|
};
|