mirror of
https://git.proxmox.com/git/mirror_ubuntu-kernels.git
synced 2025-11-27 00:43:16 +00:00
Define a new structure for EVM-specific metadata, called evm_iint_cache, and embed it in the inode security blob. Introduce evm_iint_inode() to retrieve metadata, and register evm_inode_alloc_security() for the inode_alloc_security LSM hook, to initialize the structure (before splitting metadata, this task was done by iint_init_always()). Keep the non-NULL checks after calling evm_iint_inode() except in evm_inode_alloc_security(), to take into account inodes for which security_inode_alloc() was not called. When using shared metadata, obtaining a NULL pointer from integrity_iint_find() meant that the file wasn't in the IMA policy. Now, because IMA and EVM use disjoint metadata, the EVM status has to be stored for every inode regardless of the IMA policy. Given that from now on EVM relies on its own metadata, remove the iint parameter from evm_verifyxattr(). Also, directly retrieve the iint in evm_verify_hmac(), called by both evm_verifyxattr() and evm_verify_current_integrity(), since now there is no performance penalty in retrieving EVM metadata (constant time). Replicate the management of the IMA_NEW_FILE flag, by introducing evm_post_path_mknod() and evm_file_release() to respectively set and clear the newly introduced flag EVM_NEW_FILE, at the same time IMA does. Like for IMA, select CONFIG_SECURITY_PATH when EVM is enabled, to ensure that files are marked as new. Unlike ima_post_path_mknod(), evm_post_path_mknod() cannot check if a file must be appraised. Thus, it marks all affected files. Also, it does not clear EVM_NEW_FILE depending on i_version, but that is not a problem because IMA_NEW_FILE is always cleared when set in ima_check_last_writer(). Move the EVM-specific flag EVM_IMMUTABLE_DIGSIG to security/integrity/evm/evm.h, since that definition is now unnecessary in the common integrity layer. Finally, switch to the LSM reservation mechanism for the EVM xattr, and consequently decrement by one the number of xattrs to allocate in security_inode_init_security(). Signed-off-by: Roberto Sassu <roberto.sassu@huawei.com> Reviewed-by: Casey Schaufler <casey@schaufler-ca.com> Reviewed-by: Stefan Berger <stefanb@linux.ibm.com> Reviewed-by: Mimi Zohar <zohar@linux.ibm.com> Acked-by: Mimi Zohar <zohar@linux.ibm.com> Signed-off-by: Paul Moore <paul@paul-moore.com>
87 lines
2.1 KiB
C
87 lines
2.1 KiB
C
/* SPDX-License-Identifier: GPL-2.0-only */
|
|
/*
|
|
* Copyright (C) 2005-2010 IBM Corporation
|
|
*
|
|
* Authors:
|
|
* Mimi Zohar <zohar@us.ibm.com>
|
|
* Kylene Hall <kjhall@us.ibm.com>
|
|
*
|
|
* File: evm.h
|
|
*/
|
|
|
|
#ifndef __INTEGRITY_EVM_H
|
|
#define __INTEGRITY_EVM_H
|
|
|
|
#include <linux/xattr.h>
|
|
#include <linux/security.h>
|
|
|
|
#include "../integrity.h"
|
|
|
|
#define EVM_INIT_HMAC 0x0001
|
|
#define EVM_INIT_X509 0x0002
|
|
#define EVM_ALLOW_METADATA_WRITES 0x0004
|
|
#define EVM_SETUP_COMPLETE 0x80000000 /* userland has signaled key load */
|
|
|
|
#define EVM_KEY_MASK (EVM_INIT_HMAC | EVM_INIT_X509)
|
|
#define EVM_INIT_MASK (EVM_INIT_HMAC | EVM_INIT_X509 | EVM_SETUP_COMPLETE | \
|
|
EVM_ALLOW_METADATA_WRITES)
|
|
|
|
struct xattr_list {
|
|
struct list_head list;
|
|
char *name;
|
|
bool enabled;
|
|
};
|
|
|
|
#define EVM_NEW_FILE 0x00000001
|
|
#define EVM_IMMUTABLE_DIGSIG 0x00000002
|
|
|
|
/* EVM integrity metadata associated with an inode */
|
|
struct evm_iint_cache {
|
|
unsigned long flags;
|
|
enum integrity_status evm_status:4;
|
|
};
|
|
|
|
extern struct lsm_blob_sizes evm_blob_sizes;
|
|
|
|
static inline struct evm_iint_cache *evm_iint_inode(const struct inode *inode)
|
|
{
|
|
if (unlikely(!inode->i_security))
|
|
return NULL;
|
|
|
|
return inode->i_security + evm_blob_sizes.lbs_inode;
|
|
}
|
|
|
|
extern int evm_initialized;
|
|
|
|
#define EVM_ATTR_FSUUID 0x0001
|
|
|
|
extern int evm_hmac_attrs;
|
|
|
|
/* List of EVM protected security xattrs */
|
|
extern struct list_head evm_config_xattrnames;
|
|
|
|
struct evm_digest {
|
|
struct ima_digest_data hdr;
|
|
char digest[IMA_MAX_DIGEST_SIZE];
|
|
} __packed;
|
|
|
|
int evm_protected_xattr(const char *req_xattr_name);
|
|
|
|
int evm_init_key(void);
|
|
int evm_update_evmxattr(struct dentry *dentry,
|
|
const char *req_xattr_name,
|
|
const char *req_xattr_value,
|
|
size_t req_xattr_value_len);
|
|
int evm_calc_hmac(struct dentry *dentry, const char *req_xattr_name,
|
|
const char *req_xattr_value,
|
|
size_t req_xattr_value_len, struct evm_digest *data);
|
|
int evm_calc_hash(struct dentry *dentry, const char *req_xattr_name,
|
|
const char *req_xattr_value,
|
|
size_t req_xattr_value_len, char type,
|
|
struct evm_digest *data);
|
|
int evm_init_hmac(struct inode *inode, const struct xattr *xattrs,
|
|
char *hmac_val);
|
|
int evm_init_secfs(void);
|
|
|
|
#endif
|