Merge branch 'next-general' of git://git.kernel.org/pub/scm/linux/kernel/git/jmorris/linux-security

Pull security subsystem updates from James Morris:

 - kstrdup() return value fix from Eric Biggers

 - Add new security_load_data hook to differentiate security checking of
   kernel-loaded binaries in the case of there being no associated file
   descriptor, from Mimi Zohar.

 - Add ability to IMA to specify a policy at build-time, rather than
   just via command line params or by loading a custom policy, from
   Mimi.

 - Allow IMA and LSMs to prevent sysfs firmware load fallback (e.g. if
   using signed firmware), from Mimi.

 - Allow IMA to deny loading of kexec kernel images, as they cannot be
   measured by IMA, from Mimi.

* 'next-general' of git://git.kernel.org/pub/scm/linux/kernel/git/jmorris/linux-security:
  security: check for kstrdup() failure in lsm_append()
  security: export security_kernel_load_data function
  ima: based on policy warn about loading firmware (pre-allocated buffer)
  module: replace the existing LSM hook in init_module
  ima: add build time policy
  ima: based on policy require signed firmware (sysfs fallback)
  firmware: add call to LSM hook before firmware sysfs fallback
  ima: based on policy require signed kexec kernel images
  kexec: add call to LSM hook in original kexec_load syscall
  security: define new LSM hook named security_kernel_load_data
  MAINTAINERS: remove the outdated "LINUX SECURITY MODULE (LSM) FRAMEWORK" entry
This commit is contained in:
Linus Torvalds
2018-08-15 10:25:26 -07:00
14 changed files with 248 additions and 23 deletions

View File

@@ -156,6 +156,64 @@ config IMA_APPRAISE
<http://linux-ima.sourceforge.net>
If unsure, say N.
config IMA_APPRAISE_BUILD_POLICY
bool "IMA build time configured policy rules"
depends on IMA_APPRAISE && INTEGRITY_ASYMMETRIC_KEYS
default n
help
This option defines an IMA appraisal policy at build time, which
is enforced at run time without having to specify a builtin
policy name on the boot command line. The build time appraisal
policy rules persist after loading a custom policy.
Depending on the rules configured, this policy may require kernel
modules, firmware, the kexec kernel image, and/or the IMA policy
to be signed. Unsigned files might prevent the system from
booting or applications from working properly.
config IMA_APPRAISE_REQUIRE_FIRMWARE_SIGS
bool "Appraise firmware signatures"
depends on IMA_APPRAISE_BUILD_POLICY
default n
help
This option defines a policy requiring all firmware to be signed,
including the regulatory.db. If both this option and
CFG80211_REQUIRE_SIGNED_REGDB are enabled, then both signature
verification methods are necessary.
config IMA_APPRAISE_REQUIRE_KEXEC_SIGS
bool "Appraise kexec kernel image signatures"
depends on IMA_APPRAISE_BUILD_POLICY
default n
help
Enabling this rule will require all kexec'ed kernel images to
be signed and verified by a public key on the trusted IMA
keyring.
Kernel image signatures can not be verified by the original
kexec_load syscall. Enabling this rule will prevent its
usage.
config IMA_APPRAISE_REQUIRE_MODULE_SIGS
bool "Appraise kernel modules signatures"
depends on IMA_APPRAISE_BUILD_POLICY
default n
help
Enabling this rule will require all kernel modules to be signed
and verified by a public key on the trusted IMA keyring.
Kernel module signatures can only be verified by IMA-appraisal,
via the finit_module syscall. Enabling this rule will prevent
the usage of the init_module syscall.
config IMA_APPRAISE_REQUIRE_POLICY_SIGS
bool "Appraise IMA policy signature"
depends on IMA_APPRAISE_BUILD_POLICY
default n
help
Enabling this rule will require the IMA policy to be signed and
and verified by a key on the trusted IMA keyring.
config IMA_APPRAISE_BOOTPARAM
bool "ima_appraise boot parameter"
depends on IMA_APPRAISE

View File

@@ -232,6 +232,7 @@ int ima_policy_show(struct seq_file *m, void *v);
#define IMA_APPRAISE_MODULES 0x08
#define IMA_APPRAISE_FIRMWARE 0x10
#define IMA_APPRAISE_POLICY 0x20
#define IMA_APPRAISE_KEXEC 0x40
#ifdef CONFIG_IMA_APPRAISE
int ima_appraise_measurement(enum ima_hooks func,

View File

@@ -429,16 +429,14 @@ void ima_post_path_mknod(struct dentry *dentry)
*/
int ima_read_file(struct file *file, enum kernel_read_file_id read_id)
{
bool sig_enforce = is_module_sig_enforced();
if (!file && read_id == READING_MODULE) {
if (!sig_enforce && (ima_appraise & IMA_APPRAISE_MODULES) &&
(ima_appraise & IMA_APPRAISE_ENFORCE)) {
pr_err("impossible to appraise a module without a file descriptor. sig_enforce kernel parameter might help\n");
return -EACCES; /* INTEGRITY_UNKNOWN */
}
return 0; /* We rely on module signature checking */
}
/*
* READING_FIRMWARE_PREALLOC_BUFFER
*
* Do devices using pre-allocated memory run the risk of the
* firmware being accessible to the device prior to the completion
* of IMA's signature verification any more than when using two
* buffers?
*/
return 0;
}
@@ -472,14 +470,13 @@ int ima_post_read_file(struct file *file, void *buf, loff_t size,
if (!file && read_id == READING_FIRMWARE) {
if ((ima_appraise & IMA_APPRAISE_FIRMWARE) &&
(ima_appraise & IMA_APPRAISE_ENFORCE))
(ima_appraise & IMA_APPRAISE_ENFORCE)) {
pr_err("Prevent firmware loading_store.\n");
return -EACCES; /* INTEGRITY_UNKNOWN */
}
return 0;
}
if (!file && read_id == READING_MODULE) /* MODULE_SIG_FORCE enabled */
return 0;
/* permit signed certs */
if (!file && read_id == READING_X509_CERTIFICATE)
return 0;
@@ -496,6 +493,49 @@ int ima_post_read_file(struct file *file, void *buf, loff_t size,
MAY_READ, func);
}
/**
* ima_load_data - appraise decision based on policy
* @id: kernel load data caller identifier
*
* Callers of this LSM hook can not measure, appraise, or audit the
* data provided by userspace. Enforce policy rules requring a file
* signature (eg. kexec'ed kernel image).
*
* For permission return 0, otherwise return -EACCES.
*/
int ima_load_data(enum kernel_load_data_id id)
{
bool sig_enforce;
if ((ima_appraise & IMA_APPRAISE_ENFORCE) != IMA_APPRAISE_ENFORCE)
return 0;
switch (id) {
case LOADING_KEXEC_IMAGE:
if (ima_appraise & IMA_APPRAISE_KEXEC) {
pr_err("impossible to appraise a kernel image without a file descriptor; try using kexec_file_load syscall.\n");
return -EACCES; /* INTEGRITY_UNKNOWN */
}
break;
case LOADING_FIRMWARE:
if (ima_appraise & IMA_APPRAISE_FIRMWARE) {
pr_err("Prevent firmware sysfs fallback loading.\n");
return -EACCES; /* INTEGRITY_UNKNOWN */
}
break;
case LOADING_MODULE:
sig_enforce = is_module_sig_enforced();
if (!sig_enforce && (ima_appraise & IMA_APPRAISE_MODULES)) {
pr_err("impossible to appraise a module without a file descriptor. sig_enforce kernel parameter might help\n");
return -EACCES; /* INTEGRITY_UNKNOWN */
}
default:
break;
}
return 0;
}
static int __init init_ima(void)
{
int error;

View File

@@ -49,6 +49,7 @@
int ima_policy_flag;
static int temp_ima_appraise;
static int build_ima_appraise __ro_after_init;
#define MAX_LSM_RULES 6
enum lsm_rule_types { LSM_OBJ_USER, LSM_OBJ_ROLE, LSM_OBJ_TYPE,
@@ -162,6 +163,25 @@ static struct ima_rule_entry default_appraise_rules[] __ro_after_init = {
#endif
};
static struct ima_rule_entry build_appraise_rules[] __ro_after_init = {
#ifdef CONFIG_IMA_APPRAISE_REQUIRE_MODULE_SIGS
{.action = APPRAISE, .func = MODULE_CHECK,
.flags = IMA_FUNC | IMA_DIGSIG_REQUIRED},
#endif
#ifdef CONFIG_IMA_APPRAISE_REQUIRE_FIRMWARE_SIGS
{.action = APPRAISE, .func = FIRMWARE_CHECK,
.flags = IMA_FUNC | IMA_DIGSIG_REQUIRED},
#endif
#ifdef CONFIG_IMA_APPRAISE_REQUIRE_KEXEC_SIGS
{.action = APPRAISE, .func = KEXEC_KERNEL_CHECK,
.flags = IMA_FUNC | IMA_DIGSIG_REQUIRED},
#endif
#ifdef CONFIG_IMA_APPRAISE_REQUIRE_POLICY_SIGS
{.action = APPRAISE, .func = POLICY_CHECK,
.flags = IMA_FUNC | IMA_DIGSIG_REQUIRED},
#endif
};
static struct ima_rule_entry secure_boot_rules[] __ro_after_init = {
{.action = APPRAISE, .func = MODULE_CHECK,
.flags = IMA_FUNC | IMA_DIGSIG_REQUIRED},
@@ -435,7 +455,7 @@ void ima_update_policy_flag(void)
ima_policy_flag |= entry->action;
}
ima_appraise |= temp_ima_appraise;
ima_appraise |= (build_ima_appraise | temp_ima_appraise);
if (!ima_appraise)
ima_policy_flag &= ~IMA_APPRAISE;
}
@@ -448,6 +468,8 @@ static int ima_appraise_flag(enum ima_hooks func)
return IMA_APPRAISE_FIRMWARE;
else if (func == POLICY_CHECK)
return IMA_APPRAISE_POLICY;
else if (func == KEXEC_KERNEL_CHECK)
return IMA_APPRAISE_KEXEC;
return 0;
}
@@ -486,8 +508,8 @@ void __init ima_init_policy(void)
}
/*
* Insert the appraise rules requiring file signatures, prior to
* any other appraise rules.
* Insert the builtin "secure_boot" policy rules requiring file
* signatures, prior to any other appraise rules.
*/
for (i = 0; i < secure_boot_entries; i++) {
list_add_tail(&secure_boot_rules[i].list, &ima_default_rules);
@@ -495,6 +517,26 @@ void __init ima_init_policy(void)
ima_appraise_flag(secure_boot_rules[i].func);
}
/*
* Insert the build time appraise rules requiring file signatures
* for both the initial and custom policies, prior to other appraise
* rules.
*/
for (i = 0; i < ARRAY_SIZE(build_appraise_rules); i++) {
struct ima_rule_entry *entry;
if (!secure_boot_entries)
list_add_tail(&build_appraise_rules[i].list,
&ima_default_rules);
entry = kmemdup(&build_appraise_rules[i], sizeof(*entry),
GFP_KERNEL);
if (entry)
list_add_tail(&entry->list, &ima_policy_rules);
build_ima_appraise |=
ima_appraise_flag(build_appraise_rules[i].func);
}
for (i = 0; i < appraise_entries; i++) {
list_add_tail(&default_appraise_rules[i].list,
&ima_default_rules);