mirror of
https://github.com/torvalds/linux.git
synced 2024-11-21 11:31:31 +00:00
lsm/stable-6.13 PR 20241112
-----BEGIN PGP SIGNATURE----- iQJIBAABCAAyFiEES0KozwfymdVUl37v6iDy2pc3iXMFAmcztFcUHHBhdWxAcGF1 bC1tb29yZS5jb20ACgkQ6iDy2pc3iXPvFQ/+KYwRe3g6gFSu7tRA34okHtUopvpF KGAaic06c8oy85gSX4B2Xk4HINCgXVUuRi9Z+0yExRWvvBXRRdQRUj1Vdbj4KOEG sRsIA1j1YhPU3wyhkAqwpJ97sQE1v9Xb3xizGwTfQKGQkd+cvtHg0QKM08/jPQYq bbbcSxoVsUzh8+idAq1UMfdoTsMh2xeCW7Q1+dbBINJykNzKiqEEc21xgBxeomST lSG9XFP3BJr1RBlb4Ux+J8YL+2G/rDBWZh1sR5+t31kgClSgs3CMBRFdTATvplKk e9vrcUF8wR7xWWnDmmdobHa462qUt6BWifYarX9RTomGBugZfYDOR/C+jpb+xZwd +tZfL6HSOVeBtQ/Zu1bs18eS5i2dj7GxFN7GPY2qXIPvsW5Acwcx1CCK6oNDmX05 1cOaNuZRYBDye4eAnT3yufnJ34VO80UQIfKTE6dqrX0XtCFYomTxb+Km0qM3utl5 ubr3Krp6GmVs65lIvtnIhDKSlcNIBbJfH64vdQNnOn/8FvkovGqp2eaX+0wBhROM 8KgbqntXU4/DgQuDiP01g13mTDeTGdcfyRWKcKMI/CzI/WASPZBpVuqX6xWXh3bs NlZmJ/7+Y48Xp2FvaEchQ/A8ppyIrigMLloZ8yAHf2P1z9g6wBNRCrsScdSQVx63 ArxHLRY44pUOnPs= =m/yY -----END PGP SIGNATURE----- Merge tag 'lsm-pr-20241112' of git://git.kernel.org/pub/scm/linux/kernel/git/pcmoore/lsm Pull lsm updates from Paul Moore: "Thirteen patches, all focused on moving away from the current 'secid' LSM identifier to a richer 'lsm_prop' structure. This move will help reduce the translation that is necessary in many LSMs, offering better performance, and make it easier to support different LSMs in the future" * tag 'lsm-pr-20241112' of git://git.kernel.org/pub/scm/linux/kernel/git/pcmoore/lsm: lsm: remove lsm_prop scaffolding netlabel,smack: use lsm_prop for audit data audit: change context data from secid to lsm_prop lsm: create new security_cred_getlsmprop LSM hook audit: use an lsm_prop in audit_names lsm: use lsm_prop in security_inode_getsecid lsm: use lsm_prop in security_current_getsecid audit: update shutdown LSM data lsm: use lsm_prop in security_ipc_getsecid audit: maintain an lsm_prop in audit_context lsm: add lsmprop_to_secctx hook lsm: use lsm_prop in security_audit_rule_match lsm: add the lsm_prop data structure
This commit is contained in:
commit
5591fd5e03
@ -20804,6 +20804,7 @@ Q: https://patchwork.kernel.org/project/linux-security-module/list
|
||||
B: mailto:linux-security-module@vger.kernel.org
|
||||
P: https://github.com/LinuxSecurityModule/kernel/blob/main/README.md
|
||||
T: git https://git.kernel.org/pub/scm/linux/kernel/git/pcmoore/lsm.git
|
||||
F: include/linux/lsm/
|
||||
F: include/linux/lsm_audit.h
|
||||
F: include/linux/lsm_hook_defs.h
|
||||
F: include/linux/lsm_hooks.h
|
||||
|
17
include/linux/lsm/apparmor.h
Normal file
17
include/linux/lsm/apparmor.h
Normal file
@ -0,0 +1,17 @@
|
||||
/* SPDX-License-Identifier: GPL-2.0 */
|
||||
/*
|
||||
* Linux Security Module interface to other subsystems.
|
||||
* AppArmor presents single pointer to an aa_label structure.
|
||||
*/
|
||||
#ifndef __LINUX_LSM_APPARMOR_H
|
||||
#define __LINUX_LSM_APPARMOR_H
|
||||
|
||||
struct aa_label;
|
||||
|
||||
struct lsm_prop_apparmor {
|
||||
#ifdef CONFIG_SECURITY_APPARMOR
|
||||
struct aa_label *label;
|
||||
#endif
|
||||
};
|
||||
|
||||
#endif /* ! __LINUX_LSM_APPARMOR_H */
|
16
include/linux/lsm/bpf.h
Normal file
16
include/linux/lsm/bpf.h
Normal file
@ -0,0 +1,16 @@
|
||||
/* SPDX-License-Identifier: GPL-2.0 */
|
||||
/*
|
||||
* Linux Security Module interface to other subsystems.
|
||||
* BPF may present a single u32 value.
|
||||
*/
|
||||
#ifndef __LINUX_LSM_BPF_H
|
||||
#define __LINUX_LSM_BPF_H
|
||||
#include <linux/types.h>
|
||||
|
||||
struct lsm_prop_bpf {
|
||||
#ifdef CONFIG_BPF_LSM
|
||||
u32 secid;
|
||||
#endif
|
||||
};
|
||||
|
||||
#endif /* ! __LINUX_LSM_BPF_H */
|
16
include/linux/lsm/selinux.h
Normal file
16
include/linux/lsm/selinux.h
Normal file
@ -0,0 +1,16 @@
|
||||
/* SPDX-License-Identifier: GPL-2.0 */
|
||||
/*
|
||||
* Linux Security Module interface to other subsystems.
|
||||
* SELinux presents a single u32 value which is known as a secid.
|
||||
*/
|
||||
#ifndef __LINUX_LSM_SELINUX_H
|
||||
#define __LINUX_LSM_SELINUX_H
|
||||
#include <linux/types.h>
|
||||
|
||||
struct lsm_prop_selinux {
|
||||
#ifdef CONFIG_SECURITY_SELINUX
|
||||
u32 secid;
|
||||
#endif
|
||||
};
|
||||
|
||||
#endif /* ! __LINUX_LSM_SELINUX_H */
|
17
include/linux/lsm/smack.h
Normal file
17
include/linux/lsm/smack.h
Normal file
@ -0,0 +1,17 @@
|
||||
/* SPDX-License-Identifier: GPL-2.0 */
|
||||
/*
|
||||
* Linux Security Module interface to other subsystems.
|
||||
* Smack presents a pointer into the global Smack label list.
|
||||
*/
|
||||
#ifndef __LINUX_LSM_SMACK_H
|
||||
#define __LINUX_LSM_SMACK_H
|
||||
|
||||
struct smack_known;
|
||||
|
||||
struct lsm_prop_smack {
|
||||
#ifdef CONFIG_SECURITY_SMACK
|
||||
struct smack_known *skp;
|
||||
#endif
|
||||
};
|
||||
|
||||
#endif /* ! __LINUX_LSM_SMACK_H */
|
@ -176,7 +176,8 @@ LSM_HOOK(int, -EOPNOTSUPP, inode_setsecurity, struct inode *inode,
|
||||
const char *name, const void *value, size_t size, int flags)
|
||||
LSM_HOOK(int, 0, inode_listsecurity, struct inode *inode, char *buffer,
|
||||
size_t buffer_size)
|
||||
LSM_HOOK(void, LSM_RET_VOID, inode_getsecid, struct inode *inode, u32 *secid)
|
||||
LSM_HOOK(void, LSM_RET_VOID, inode_getlsmprop, struct inode *inode,
|
||||
struct lsm_prop *prop)
|
||||
LSM_HOOK(int, 0, inode_copy_up, struct dentry *src, struct cred **new)
|
||||
LSM_HOOK(int, -EOPNOTSUPP, inode_copy_up_xattr, struct dentry *src,
|
||||
const char *name)
|
||||
@ -217,6 +218,8 @@ LSM_HOOK(int, 0, cred_prepare, struct cred *new, const struct cred *old,
|
||||
LSM_HOOK(void, LSM_RET_VOID, cred_transfer, struct cred *new,
|
||||
const struct cred *old)
|
||||
LSM_HOOK(void, LSM_RET_VOID, cred_getsecid, const struct cred *c, u32 *secid)
|
||||
LSM_HOOK(void, LSM_RET_VOID, cred_getlsmprop, const struct cred *c,
|
||||
struct lsm_prop *prop)
|
||||
LSM_HOOK(int, 0, kernel_act_as, struct cred *new, u32 secid)
|
||||
LSM_HOOK(int, 0, kernel_create_files_as, struct cred *new, struct inode *inode)
|
||||
LSM_HOOK(int, 0, kernel_module_request, char *kmod_name)
|
||||
@ -235,9 +238,9 @@ LSM_HOOK(int, 0, task_fix_setgroups, struct cred *new, const struct cred * old)
|
||||
LSM_HOOK(int, 0, task_setpgid, struct task_struct *p, pid_t pgid)
|
||||
LSM_HOOK(int, 0, task_getpgid, struct task_struct *p)
|
||||
LSM_HOOK(int, 0, task_getsid, struct task_struct *p)
|
||||
LSM_HOOK(void, LSM_RET_VOID, current_getsecid_subj, u32 *secid)
|
||||
LSM_HOOK(void, LSM_RET_VOID, task_getsecid_obj,
|
||||
struct task_struct *p, u32 *secid)
|
||||
LSM_HOOK(void, LSM_RET_VOID, current_getlsmprop_subj, struct lsm_prop *prop)
|
||||
LSM_HOOK(void, LSM_RET_VOID, task_getlsmprop_obj,
|
||||
struct task_struct *p, struct lsm_prop *prop)
|
||||
LSM_HOOK(int, 0, task_setnice, struct task_struct *p, int nice)
|
||||
LSM_HOOK(int, 0, task_setioprio, struct task_struct *p, int ioprio)
|
||||
LSM_HOOK(int, 0, task_getioprio, struct task_struct *p)
|
||||
@ -256,8 +259,8 @@ LSM_HOOK(void, LSM_RET_VOID, task_to_inode, struct task_struct *p,
|
||||
struct inode *inode)
|
||||
LSM_HOOK(int, 0, userns_create, const struct cred *cred)
|
||||
LSM_HOOK(int, 0, ipc_permission, struct kern_ipc_perm *ipcp, short flag)
|
||||
LSM_HOOK(void, LSM_RET_VOID, ipc_getsecid, struct kern_ipc_perm *ipcp,
|
||||
u32 *secid)
|
||||
LSM_HOOK(void, LSM_RET_VOID, ipc_getlsmprop, struct kern_ipc_perm *ipcp,
|
||||
struct lsm_prop *prop)
|
||||
LSM_HOOK(int, 0, msg_msg_alloc_security, struct msg_msg *msg)
|
||||
LSM_HOOK(void, LSM_RET_VOID, msg_msg_free_security, struct msg_msg *msg)
|
||||
LSM_HOOK(int, 0, msg_queue_alloc_security, struct kern_ipc_perm *perm)
|
||||
@ -294,6 +297,8 @@ LSM_HOOK(int, -EINVAL, setprocattr, const char *name, void *value, size_t size)
|
||||
LSM_HOOK(int, 0, ismaclabel, const char *name)
|
||||
LSM_HOOK(int, -EOPNOTSUPP, secid_to_secctx, u32 secid, char **secdata,
|
||||
u32 *seclen)
|
||||
LSM_HOOK(int, -EOPNOTSUPP, lsmprop_to_secctx, struct lsm_prop *prop,
|
||||
char **secdata, u32 *seclen)
|
||||
LSM_HOOK(int, 0, secctx_to_secid, const char *secdata, u32 seclen, u32 *secid)
|
||||
LSM_HOOK(void, LSM_RET_VOID, release_secctx, char *secdata, u32 seclen)
|
||||
LSM_HOOK(void, LSM_RET_VOID, inode_invalidate_secctx, struct inode *inode)
|
||||
@ -416,7 +421,8 @@ LSM_HOOK(void, LSM_RET_VOID, key_post_create_or_update, struct key *keyring,
|
||||
LSM_HOOK(int, 0, audit_rule_init, u32 field, u32 op, char *rulestr,
|
||||
void **lsmrule, gfp_t gfp)
|
||||
LSM_HOOK(int, 0, audit_rule_known, struct audit_krule *krule)
|
||||
LSM_HOOK(int, 0, audit_rule_match, u32 secid, u32 field, u32 op, void *lsmrule)
|
||||
LSM_HOOK(int, 0, audit_rule_match, struct lsm_prop *prop, u32 field, u32 op,
|
||||
void *lsmrule)
|
||||
LSM_HOOK(void, LSM_RET_VOID, audit_rule_free, void *lsmrule)
|
||||
#endif /* CONFIG_AUDIT */
|
||||
|
||||
|
@ -34,6 +34,10 @@
|
||||
#include <linux/sockptr.h>
|
||||
#include <linux/bpf.h>
|
||||
#include <uapi/linux/lsm.h>
|
||||
#include <linux/lsm/selinux.h>
|
||||
#include <linux/lsm/smack.h>
|
||||
#include <linux/lsm/apparmor.h>
|
||||
#include <linux/lsm/bpf.h>
|
||||
|
||||
struct linux_binprm;
|
||||
struct cred;
|
||||
@ -152,6 +156,16 @@ enum lockdown_reason {
|
||||
LOCKDOWN_CONFIDENTIALITY_MAX,
|
||||
};
|
||||
|
||||
/*
|
||||
* Data exported by the security modules
|
||||
*/
|
||||
struct lsm_prop {
|
||||
struct lsm_prop_selinux selinux;
|
||||
struct lsm_prop_smack smack;
|
||||
struct lsm_prop_apparmor apparmor;
|
||||
struct lsm_prop_bpf bpf;
|
||||
};
|
||||
|
||||
extern const char *const lockdown_reasons[LOCKDOWN_CONFIDENTIALITY_MAX+1];
|
||||
extern u32 lsm_active_cnt;
|
||||
extern const struct lsm_id *lsm_idlist[];
|
||||
@ -269,8 +283,32 @@ static inline const char *kernel_load_data_id_str(enum kernel_load_data_id id)
|
||||
return kernel_load_data_str[id];
|
||||
}
|
||||
|
||||
/**
|
||||
* lsmprop_init - initialize a lsm_prop structure
|
||||
* @prop: Pointer to the data to initialize
|
||||
*
|
||||
* Set all secid for all modules to the specified value.
|
||||
*/
|
||||
static inline void lsmprop_init(struct lsm_prop *prop)
|
||||
{
|
||||
memset(prop, 0, sizeof(*prop));
|
||||
}
|
||||
|
||||
#ifdef CONFIG_SECURITY
|
||||
|
||||
/**
|
||||
* lsmprop_is_set - report if there is a value in the lsm_prop
|
||||
* @prop: Pointer to the exported LSM data
|
||||
*
|
||||
* Returns true if there is a value set, false otherwise
|
||||
*/
|
||||
static inline bool lsmprop_is_set(struct lsm_prop *prop)
|
||||
{
|
||||
const struct lsm_prop empty = {};
|
||||
|
||||
return !!memcmp(prop, &empty, sizeof(*prop));
|
||||
}
|
||||
|
||||
int call_blocking_lsm_notifier(enum lsm_event event, void *data);
|
||||
int register_blocking_lsm_notifier(struct notifier_block *nb);
|
||||
int unregister_blocking_lsm_notifier(struct notifier_block *nb);
|
||||
@ -408,7 +446,7 @@ int security_inode_getsecurity(struct mnt_idmap *idmap,
|
||||
void **buffer, bool alloc);
|
||||
int security_inode_setsecurity(struct inode *inode, const char *name, const void *value, size_t size, int flags);
|
||||
int security_inode_listsecurity(struct inode *inode, char *buffer, size_t buffer_size);
|
||||
void security_inode_getsecid(struct inode *inode, u32 *secid);
|
||||
void security_inode_getlsmprop(struct inode *inode, struct lsm_prop *prop);
|
||||
int security_inode_copy_up(struct dentry *src, struct cred **new);
|
||||
int security_inode_copy_up_xattr(struct dentry *src, const char *name);
|
||||
int security_inode_setintegrity(const struct inode *inode,
|
||||
@ -444,6 +482,7 @@ void security_cred_free(struct cred *cred);
|
||||
int security_prepare_creds(struct cred *new, const struct cred *old, gfp_t gfp);
|
||||
void security_transfer_creds(struct cred *new, const struct cred *old);
|
||||
void security_cred_getsecid(const struct cred *c, u32 *secid);
|
||||
void security_cred_getlsmprop(const struct cred *c, struct lsm_prop *prop);
|
||||
int security_kernel_act_as(struct cred *new, u32 secid);
|
||||
int security_kernel_create_files_as(struct cred *new, struct inode *inode);
|
||||
int security_kernel_module_request(char *kmod_name);
|
||||
@ -463,8 +502,8 @@ int security_task_fix_setgroups(struct cred *new, const struct cred *old);
|
||||
int security_task_setpgid(struct task_struct *p, pid_t pgid);
|
||||
int security_task_getpgid(struct task_struct *p);
|
||||
int security_task_getsid(struct task_struct *p);
|
||||
void security_current_getsecid_subj(u32 *secid);
|
||||
void security_task_getsecid_obj(struct task_struct *p, u32 *secid);
|
||||
void security_current_getlsmprop_subj(struct lsm_prop *prop);
|
||||
void security_task_getlsmprop_obj(struct task_struct *p, struct lsm_prop *prop);
|
||||
int security_task_setnice(struct task_struct *p, int nice);
|
||||
int security_task_setioprio(struct task_struct *p, int ioprio);
|
||||
int security_task_getioprio(struct task_struct *p);
|
||||
@ -482,7 +521,7 @@ int security_task_prctl(int option, unsigned long arg2, unsigned long arg3,
|
||||
void security_task_to_inode(struct task_struct *p, struct inode *inode);
|
||||
int security_create_user_ns(const struct cred *cred);
|
||||
int security_ipc_permission(struct kern_ipc_perm *ipcp, short flag);
|
||||
void security_ipc_getsecid(struct kern_ipc_perm *ipcp, u32 *secid);
|
||||
void security_ipc_getlsmprop(struct kern_ipc_perm *ipcp, struct lsm_prop *prop);
|
||||
int security_msg_msg_alloc(struct msg_msg *msg);
|
||||
void security_msg_msg_free(struct msg_msg *msg);
|
||||
int security_msg_queue_alloc(struct kern_ipc_perm *msq);
|
||||
@ -515,6 +554,7 @@ int security_setprocattr(int lsmid, const char *name, void *value, size_t size);
|
||||
int security_netlink_send(struct sock *sk, struct sk_buff *skb);
|
||||
int security_ismaclabel(const char *name);
|
||||
int security_secid_to_secctx(u32 secid, char **secdata, u32 *seclen);
|
||||
int security_lsmprop_to_secctx(struct lsm_prop *prop, char **secdata, u32 *seclen);
|
||||
int security_secctx_to_secid(const char *secdata, u32 seclen, u32 *secid);
|
||||
void security_release_secctx(char *secdata, u32 seclen);
|
||||
void security_inode_invalidate_secctx(struct inode *inode);
|
||||
@ -531,6 +571,17 @@ int security_bdev_setintegrity(struct block_device *bdev,
|
||||
size_t size);
|
||||
#else /* CONFIG_SECURITY */
|
||||
|
||||
/**
|
||||
* lsmprop_is_set - report if there is a value in the lsm_prop
|
||||
* @prop: Pointer to the exported LSM data
|
||||
*
|
||||
* Returns true if there is a value set, false otherwise
|
||||
*/
|
||||
static inline bool lsmprop_is_set(struct lsm_prop *prop)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
static inline int call_blocking_lsm_notifier(enum lsm_event event, void *data)
|
||||
{
|
||||
return 0;
|
||||
@ -1020,9 +1071,10 @@ static inline int security_inode_listsecurity(struct inode *inode, char *buffer,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline void security_inode_getsecid(struct inode *inode, u32 *secid)
|
||||
static inline void security_inode_getlsmprop(struct inode *inode,
|
||||
struct lsm_prop *prop)
|
||||
{
|
||||
*secid = 0;
|
||||
lsmprop_init(prop);
|
||||
}
|
||||
|
||||
static inline int security_inode_copy_up(struct dentry *src, struct cred **new)
|
||||
@ -1172,6 +1224,10 @@ static inline void security_cred_getsecid(const struct cred *c, u32 *secid)
|
||||
*secid = 0;
|
||||
}
|
||||
|
||||
static inline void security_cred_getlsmprop(const struct cred *c,
|
||||
struct lsm_prop *prop)
|
||||
{ }
|
||||
|
||||
static inline int security_kernel_act_as(struct cred *cred, u32 secid)
|
||||
{
|
||||
return 0;
|
||||
@ -1249,14 +1305,15 @@ static inline int security_task_getsid(struct task_struct *p)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline void security_current_getsecid_subj(u32 *secid)
|
||||
static inline void security_current_getlsmprop_subj(struct lsm_prop *prop)
|
||||
{
|
||||
*secid = 0;
|
||||
lsmprop_init(prop);
|
||||
}
|
||||
|
||||
static inline void security_task_getsecid_obj(struct task_struct *p, u32 *secid)
|
||||
static inline void security_task_getlsmprop_obj(struct task_struct *p,
|
||||
struct lsm_prop *prop)
|
||||
{
|
||||
*secid = 0;
|
||||
lsmprop_init(prop);
|
||||
}
|
||||
|
||||
static inline int security_task_setnice(struct task_struct *p, int nice)
|
||||
@ -1332,9 +1389,10 @@ static inline int security_ipc_permission(struct kern_ipc_perm *ipcp,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline void security_ipc_getsecid(struct kern_ipc_perm *ipcp, u32 *secid)
|
||||
static inline void security_ipc_getlsmprop(struct kern_ipc_perm *ipcp,
|
||||
struct lsm_prop *prop)
|
||||
{
|
||||
*secid = 0;
|
||||
lsmprop_init(prop);
|
||||
}
|
||||
|
||||
static inline int security_msg_msg_alloc(struct msg_msg *msg)
|
||||
@ -1468,7 +1526,14 @@ static inline int security_ismaclabel(const char *name)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline int security_secid_to_secctx(u32 secid, char **secdata, u32 *seclen)
|
||||
static inline int security_secid_to_secctx(u32 secid, char **secdata,
|
||||
u32 *seclen)
|
||||
{
|
||||
return -EOPNOTSUPP;
|
||||
}
|
||||
|
||||
static inline int security_lsmprop_to_secctx(struct lsm_prop *prop,
|
||||
char **secdata, u32 *seclen)
|
||||
{
|
||||
return -EOPNOTSUPP;
|
||||
}
|
||||
@ -2095,7 +2160,8 @@ static inline void security_key_post_create_or_update(struct key *keyring,
|
||||
int security_audit_rule_init(u32 field, u32 op, char *rulestr, void **lsmrule,
|
||||
gfp_t gfp);
|
||||
int security_audit_rule_known(struct audit_krule *krule);
|
||||
int security_audit_rule_match(u32 secid, u32 field, u32 op, void *lsmrule);
|
||||
int security_audit_rule_match(struct lsm_prop *prop, u32 field, u32 op,
|
||||
void *lsmrule);
|
||||
void security_audit_rule_free(void *lsmrule);
|
||||
|
||||
#else
|
||||
@ -2111,8 +2177,8 @@ static inline int security_audit_rule_known(struct audit_krule *krule)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline int security_audit_rule_match(u32 secid, u32 field, u32 op,
|
||||
void *lsmrule)
|
||||
static inline int security_audit_rule_match(struct lsm_prop *prop, u32 field,
|
||||
u32 op, void *lsmrule)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
@ -97,7 +97,7 @@ struct calipso_doi;
|
||||
|
||||
/* NetLabel audit information */
|
||||
struct netlbl_audit {
|
||||
u32 secid;
|
||||
struct lsm_prop prop;
|
||||
kuid_t loginuid;
|
||||
unsigned int sessionid;
|
||||
};
|
||||
|
@ -123,7 +123,7 @@ static u32 audit_backlog_wait_time = AUDIT_BACKLOG_WAIT_TIME;
|
||||
/* The identity of the user shutting down the audit system. */
|
||||
static kuid_t audit_sig_uid = INVALID_UID;
|
||||
static pid_t audit_sig_pid = -1;
|
||||
static u32 audit_sig_sid;
|
||||
static struct lsm_prop audit_sig_lsm;
|
||||
|
||||
/* Records can be lost in several ways:
|
||||
0) [suppressed in audit_alloc]
|
||||
@ -1473,20 +1473,21 @@ static int audit_receive_msg(struct sk_buff *skb, struct nlmsghdr *nlh,
|
||||
}
|
||||
case AUDIT_SIGNAL_INFO:
|
||||
len = 0;
|
||||
if (audit_sig_sid) {
|
||||
err = security_secid_to_secctx(audit_sig_sid, &ctx, &len);
|
||||
if (lsmprop_is_set(&audit_sig_lsm)) {
|
||||
err = security_lsmprop_to_secctx(&audit_sig_lsm, &ctx,
|
||||
&len);
|
||||
if (err)
|
||||
return err;
|
||||
}
|
||||
sig_data = kmalloc(struct_size(sig_data, ctx, len), GFP_KERNEL);
|
||||
if (!sig_data) {
|
||||
if (audit_sig_sid)
|
||||
if (lsmprop_is_set(&audit_sig_lsm))
|
||||
security_release_secctx(ctx, len);
|
||||
return -ENOMEM;
|
||||
}
|
||||
sig_data->uid = from_kuid(&init_user_ns, audit_sig_uid);
|
||||
sig_data->pid = audit_sig_pid;
|
||||
if (audit_sig_sid) {
|
||||
if (lsmprop_is_set(&audit_sig_lsm)) {
|
||||
memcpy(sig_data->ctx, ctx, len);
|
||||
security_release_secctx(ctx, len);
|
||||
}
|
||||
@ -2178,16 +2179,16 @@ void audit_log_key(struct audit_buffer *ab, char *key)
|
||||
|
||||
int audit_log_task_context(struct audit_buffer *ab)
|
||||
{
|
||||
struct lsm_prop prop;
|
||||
char *ctx = NULL;
|
||||
unsigned len;
|
||||
int error;
|
||||
u32 sid;
|
||||
|
||||
security_current_getsecid_subj(&sid);
|
||||
if (!sid)
|
||||
security_current_getlsmprop_subj(&prop);
|
||||
if (!lsmprop_is_set(&prop))
|
||||
return 0;
|
||||
|
||||
error = security_secid_to_secctx(sid, &ctx, &len);
|
||||
error = security_lsmprop_to_secctx(&prop, &ctx, &len);
|
||||
if (error) {
|
||||
if (error != -EINVAL)
|
||||
goto error_path;
|
||||
@ -2404,7 +2405,7 @@ int audit_signal_info(int sig, struct task_struct *t)
|
||||
audit_sig_uid = auid;
|
||||
else
|
||||
audit_sig_uid = uid;
|
||||
security_current_getsecid_subj(&audit_sig_sid);
|
||||
security_current_getlsmprop_subj(&audit_sig_lsm);
|
||||
}
|
||||
|
||||
return audit_signal_info_syscall(t);
|
||||
|
@ -11,6 +11,7 @@
|
||||
|
||||
#include <linux/fs.h>
|
||||
#include <linux/audit.h>
|
||||
#include <linux/security.h>
|
||||
#include <linux/skbuff.h>
|
||||
#include <uapi/linux/mqueue.h>
|
||||
#include <linux/tty.h>
|
||||
@ -81,7 +82,7 @@ struct audit_names {
|
||||
kuid_t uid;
|
||||
kgid_t gid;
|
||||
dev_t rdev;
|
||||
u32 osid;
|
||||
struct lsm_prop oprop;
|
||||
struct audit_cap_data fcap;
|
||||
unsigned int fcap_ver;
|
||||
unsigned char type; /* record type */
|
||||
@ -143,7 +144,7 @@ struct audit_context {
|
||||
kuid_t target_auid;
|
||||
kuid_t target_uid;
|
||||
unsigned int target_sessionid;
|
||||
u32 target_sid;
|
||||
struct lsm_prop target_ref;
|
||||
char target_comm[TASK_COMM_LEN];
|
||||
|
||||
struct audit_tree_refs *trees, *first_trees;
|
||||
@ -160,7 +161,7 @@ struct audit_context {
|
||||
kuid_t uid;
|
||||
kgid_t gid;
|
||||
umode_t mode;
|
||||
u32 osid;
|
||||
struct lsm_prop oprop;
|
||||
int has_perm;
|
||||
uid_t perm_uid;
|
||||
gid_t perm_gid;
|
||||
|
@ -1339,8 +1339,8 @@ int audit_filter(int msgtype, unsigned int listtype)
|
||||
|
||||
for (i = 0; i < e->rule.field_count; i++) {
|
||||
struct audit_field *f = &e->rule.fields[i];
|
||||
struct lsm_prop prop = { };
|
||||
pid_t pid;
|
||||
u32 sid;
|
||||
|
||||
switch (f->type) {
|
||||
case AUDIT_PID:
|
||||
@ -1370,9 +1370,10 @@ int audit_filter(int msgtype, unsigned int listtype)
|
||||
case AUDIT_SUBJ_SEN:
|
||||
case AUDIT_SUBJ_CLR:
|
||||
if (f->lsm_rule) {
|
||||
security_current_getsecid_subj(&sid);
|
||||
result = security_audit_rule_match(sid,
|
||||
f->type, f->op, f->lsm_rule);
|
||||
security_current_getlsmprop_subj(&prop);
|
||||
result = security_audit_rule_match(
|
||||
&prop, f->type, f->op,
|
||||
f->lsm_rule);
|
||||
}
|
||||
break;
|
||||
case AUDIT_EXE:
|
||||
|
@ -100,7 +100,7 @@ struct audit_aux_data_pids {
|
||||
kuid_t target_auid[AUDIT_AUX_PIDS];
|
||||
kuid_t target_uid[AUDIT_AUX_PIDS];
|
||||
unsigned int target_sessionid[AUDIT_AUX_PIDS];
|
||||
u32 target_sid[AUDIT_AUX_PIDS];
|
||||
struct lsm_prop target_ref[AUDIT_AUX_PIDS];
|
||||
char target_comm[AUDIT_AUX_PIDS][TASK_COMM_LEN];
|
||||
int pid_count;
|
||||
};
|
||||
@ -470,7 +470,7 @@ static int audit_filter_rules(struct task_struct *tsk,
|
||||
{
|
||||
const struct cred *cred;
|
||||
int i, need_sid = 1;
|
||||
u32 sid;
|
||||
struct lsm_prop prop = { };
|
||||
unsigned int sessionid;
|
||||
|
||||
if (ctx && rule->prio <= ctx->prio)
|
||||
@ -674,14 +674,16 @@ static int audit_filter_rules(struct task_struct *tsk,
|
||||
* fork()/copy_process() in which case
|
||||
* the new @tsk creds are still a dup
|
||||
* of @current's creds so we can still
|
||||
* use security_current_getsecid_subj()
|
||||
* use
|
||||
* security_current_getlsmprop_subj()
|
||||
* here even though it always refs
|
||||
* @current's creds
|
||||
*/
|
||||
security_current_getsecid_subj(&sid);
|
||||
security_current_getlsmprop_subj(&prop);
|
||||
need_sid = 0;
|
||||
}
|
||||
result = security_audit_rule_match(sid, f->type,
|
||||
result = security_audit_rule_match(&prop,
|
||||
f->type,
|
||||
f->op,
|
||||
f->lsm_rule);
|
||||
}
|
||||
@ -697,14 +699,14 @@ static int audit_filter_rules(struct task_struct *tsk,
|
||||
/* Find files that match */
|
||||
if (name) {
|
||||
result = security_audit_rule_match(
|
||||
name->osid,
|
||||
&name->oprop,
|
||||
f->type,
|
||||
f->op,
|
||||
f->lsm_rule);
|
||||
} else if (ctx) {
|
||||
list_for_each_entry(n, &ctx->names_list, list) {
|
||||
if (security_audit_rule_match(
|
||||
n->osid,
|
||||
&n->oprop,
|
||||
f->type,
|
||||
f->op,
|
||||
f->lsm_rule)) {
|
||||
@ -716,7 +718,7 @@ static int audit_filter_rules(struct task_struct *tsk,
|
||||
/* Find ipc objects that match */
|
||||
if (!ctx || ctx->type != AUDIT_IPC)
|
||||
break;
|
||||
if (security_audit_rule_match(ctx->ipc.osid,
|
||||
if (security_audit_rule_match(&ctx->ipc.oprop,
|
||||
f->type, f->op,
|
||||
f->lsm_rule))
|
||||
++result;
|
||||
@ -1017,7 +1019,7 @@ static void audit_reset_context(struct audit_context *ctx)
|
||||
ctx->target_pid = 0;
|
||||
ctx->target_auid = ctx->target_uid = KUIDT_INIT(0);
|
||||
ctx->target_sessionid = 0;
|
||||
ctx->target_sid = 0;
|
||||
lsmprop_init(&ctx->target_ref);
|
||||
ctx->target_comm[0] = '\0';
|
||||
unroll_tree_refs(ctx, NULL, 0);
|
||||
WARN_ON(!list_empty(&ctx->killed_trees));
|
||||
@ -1091,8 +1093,9 @@ static inline void audit_free_context(struct audit_context *context)
|
||||
}
|
||||
|
||||
static int audit_log_pid_context(struct audit_context *context, pid_t pid,
|
||||
kuid_t auid, kuid_t uid, unsigned int sessionid,
|
||||
u32 sid, char *comm)
|
||||
kuid_t auid, kuid_t uid,
|
||||
unsigned int sessionid, struct lsm_prop *prop,
|
||||
char *comm)
|
||||
{
|
||||
struct audit_buffer *ab;
|
||||
char *ctx = NULL;
|
||||
@ -1106,8 +1109,8 @@ static int audit_log_pid_context(struct audit_context *context, pid_t pid,
|
||||
audit_log_format(ab, "opid=%d oauid=%d ouid=%d oses=%d", pid,
|
||||
from_kuid(&init_user_ns, auid),
|
||||
from_kuid(&init_user_ns, uid), sessionid);
|
||||
if (sid) {
|
||||
if (security_secid_to_secctx(sid, &ctx, &len)) {
|
||||
if (lsmprop_is_set(prop)) {
|
||||
if (security_lsmprop_to_secctx(prop, &ctx, &len)) {
|
||||
audit_log_format(ab, " obj=(none)");
|
||||
rc = 1;
|
||||
} else {
|
||||
@ -1384,19 +1387,17 @@ static void show_special(struct audit_context *context, int *call_panic)
|
||||
audit_log_format(ab, " a%d=%lx", i,
|
||||
context->socketcall.args[i]);
|
||||
break; }
|
||||
case AUDIT_IPC: {
|
||||
u32 osid = context->ipc.osid;
|
||||
|
||||
case AUDIT_IPC:
|
||||
audit_log_format(ab, "ouid=%u ogid=%u mode=%#ho",
|
||||
from_kuid(&init_user_ns, context->ipc.uid),
|
||||
from_kgid(&init_user_ns, context->ipc.gid),
|
||||
context->ipc.mode);
|
||||
if (osid) {
|
||||
if (lsmprop_is_set(&context->ipc.oprop)) {
|
||||
char *ctx = NULL;
|
||||
u32 len;
|
||||
|
||||
if (security_secid_to_secctx(osid, &ctx, &len)) {
|
||||
audit_log_format(ab, " osid=%u", osid);
|
||||
if (security_lsmprop_to_secctx(&context->ipc.oprop,
|
||||
&ctx, &len)) {
|
||||
*call_panic = 1;
|
||||
} else {
|
||||
audit_log_format(ab, " obj=%s", ctx);
|
||||
@ -1416,7 +1417,7 @@ static void show_special(struct audit_context *context, int *call_panic)
|
||||
context->ipc.perm_gid,
|
||||
context->ipc.perm_mode);
|
||||
}
|
||||
break; }
|
||||
break;
|
||||
case AUDIT_MQ_OPEN:
|
||||
audit_log_format(ab,
|
||||
"oflag=0x%x mode=%#ho mq_flags=0x%lx mq_maxmsg=%ld "
|
||||
@ -1558,13 +1559,11 @@ static void audit_log_name(struct audit_context *context, struct audit_names *n,
|
||||
from_kgid(&init_user_ns, n->gid),
|
||||
MAJOR(n->rdev),
|
||||
MINOR(n->rdev));
|
||||
if (n->osid != 0) {
|
||||
if (lsmprop_is_set(&n->oprop)) {
|
||||
char *ctx = NULL;
|
||||
u32 len;
|
||||
|
||||
if (security_secid_to_secctx(
|
||||
n->osid, &ctx, &len)) {
|
||||
audit_log_format(ab, " osid=%u", n->osid);
|
||||
if (security_lsmprop_to_secctx(&n->oprop, &ctx, &len)) {
|
||||
if (call_panic)
|
||||
*call_panic = 2;
|
||||
} else {
|
||||
@ -1780,7 +1779,7 @@ static void audit_log_exit(void)
|
||||
axs->target_auid[i],
|
||||
axs->target_uid[i],
|
||||
axs->target_sessionid[i],
|
||||
axs->target_sid[i],
|
||||
&axs->target_ref[i],
|
||||
axs->target_comm[i]))
|
||||
call_panic = 1;
|
||||
}
|
||||
@ -1789,7 +1788,7 @@ static void audit_log_exit(void)
|
||||
audit_log_pid_context(context, context->target_pid,
|
||||
context->target_auid, context->target_uid,
|
||||
context->target_sessionid,
|
||||
context->target_sid, context->target_comm))
|
||||
&context->target_ref, context->target_comm))
|
||||
call_panic = 1;
|
||||
|
||||
if (context->pwd.dentry && context->pwd.mnt) {
|
||||
@ -2278,7 +2277,7 @@ static void audit_copy_inode(struct audit_names *name,
|
||||
name->uid = inode->i_uid;
|
||||
name->gid = inode->i_gid;
|
||||
name->rdev = inode->i_rdev;
|
||||
security_inode_getsecid(inode, &name->osid);
|
||||
security_inode_getlsmprop(inode, &name->oprop);
|
||||
if (flags & AUDIT_INODE_NOEVAL) {
|
||||
name->fcap_ver = -1;
|
||||
return;
|
||||
@ -2632,7 +2631,7 @@ void __audit_ipc_obj(struct kern_ipc_perm *ipcp)
|
||||
context->ipc.gid = ipcp->gid;
|
||||
context->ipc.mode = ipcp->mode;
|
||||
context->ipc.has_perm = 0;
|
||||
security_ipc_getsecid(ipcp, &context->ipc.osid);
|
||||
security_ipc_getlsmprop(ipcp, &context->ipc.oprop);
|
||||
context->type = AUDIT_IPC;
|
||||
}
|
||||
|
||||
@ -2729,7 +2728,7 @@ void __audit_ptrace(struct task_struct *t)
|
||||
context->target_auid = audit_get_loginuid(t);
|
||||
context->target_uid = task_uid(t);
|
||||
context->target_sessionid = audit_get_sessionid(t);
|
||||
security_task_getsecid_obj(t, &context->target_sid);
|
||||
security_task_getlsmprop_obj(t, &context->target_ref);
|
||||
memcpy(context->target_comm, t->comm, TASK_COMM_LEN);
|
||||
}
|
||||
|
||||
@ -2756,7 +2755,7 @@ int audit_signal_info_syscall(struct task_struct *t)
|
||||
ctx->target_auid = audit_get_loginuid(t);
|
||||
ctx->target_uid = t_uid;
|
||||
ctx->target_sessionid = audit_get_sessionid(t);
|
||||
security_task_getsecid_obj(t, &ctx->target_sid);
|
||||
security_task_getlsmprop_obj(t, &ctx->target_ref);
|
||||
memcpy(ctx->target_comm, t->comm, TASK_COMM_LEN);
|
||||
return 0;
|
||||
}
|
||||
@ -2777,7 +2776,7 @@ int audit_signal_info_syscall(struct task_struct *t)
|
||||
axp->target_auid[axp->pid_count] = audit_get_loginuid(t);
|
||||
axp->target_uid[axp->pid_count] = t_uid;
|
||||
axp->target_sessionid[axp->pid_count] = audit_get_sessionid(t);
|
||||
security_task_getsecid_obj(t, &axp->target_sid[axp->pid_count]);
|
||||
security_task_getlsmprop_obj(t, &axp->target_ref[axp->pid_count]);
|
||||
memcpy(axp->target_comm[axp->pid_count], t->comm, TASK_COMM_LEN);
|
||||
axp->pid_count++;
|
||||
|
||||
|
@ -1538,7 +1538,7 @@ int __init netlbl_unlabel_defconf(void)
|
||||
/* Only the kernel is allowed to call this function and the only time
|
||||
* it is called is at bootup before the audit subsystem is reporting
|
||||
* messages so don't worry to much about these values. */
|
||||
security_current_getsecid_subj(&audit_info.secid);
|
||||
security_current_getlsmprop_subj(&audit_info.prop);
|
||||
audit_info.loginuid = GLOBAL_ROOT_UID;
|
||||
audit_info.sessionid = 0;
|
||||
|
||||
|
@ -98,10 +98,9 @@ struct audit_buffer *netlbl_audit_start_common(int type,
|
||||
from_kuid(&init_user_ns, audit_info->loginuid),
|
||||
audit_info->sessionid);
|
||||
|
||||
if (audit_info->secid != 0 &&
|
||||
security_secid_to_secctx(audit_info->secid,
|
||||
&secctx,
|
||||
&secctx_len) == 0) {
|
||||
if (lsmprop_is_set(&audit_info->prop) &&
|
||||
security_lsmprop_to_secctx(&audit_info->prop, &secctx,
|
||||
&secctx_len) == 0) {
|
||||
audit_log_format(audit_buf, " subj=%s", secctx);
|
||||
security_release_secctx(secctx, secctx_len);
|
||||
}
|
||||
|
@ -32,7 +32,7 @@
|
||||
*/
|
||||
static inline void netlbl_netlink_auditinfo(struct netlbl_audit *audit_info)
|
||||
{
|
||||
security_current_getsecid_subj(&audit_info->secid);
|
||||
security_current_getlsmprop_subj(&audit_info->prop);
|
||||
audit_info->loginuid = audit_get_loginuid(current);
|
||||
audit_info->sessionid = audit_get_sessionid(current);
|
||||
}
|
||||
|
@ -264,13 +264,13 @@ int aa_audit_rule_known(struct audit_krule *rule)
|
||||
return 0;
|
||||
}
|
||||
|
||||
int aa_audit_rule_match(u32 sid, u32 field, u32 op, void *vrule)
|
||||
int aa_audit_rule_match(struct lsm_prop *prop, u32 field, u32 op, void *vrule)
|
||||
{
|
||||
struct aa_audit_rule *rule = vrule;
|
||||
struct aa_label *label;
|
||||
int found = 0;
|
||||
|
||||
label = aa_secid_to_label(sid);
|
||||
label = prop->apparmor.label;
|
||||
|
||||
if (!label)
|
||||
return -ENOENT;
|
||||
|
@ -202,6 +202,6 @@ static inline int complain_error(int error)
|
||||
void aa_audit_rule_free(void *vrule);
|
||||
int aa_audit_rule_init(u32 field, u32 op, char *rulestr, void **vrule, gfp_t gfp);
|
||||
int aa_audit_rule_known(struct audit_krule *rule);
|
||||
int aa_audit_rule_match(u32 sid, u32 field, u32 op, void *vrule);
|
||||
int aa_audit_rule_match(struct lsm_prop *prop, u32 field, u32 op, void *vrule);
|
||||
|
||||
#endif /* __AA_AUDIT_H */
|
||||
|
@ -26,6 +26,8 @@ extern int apparmor_display_secid_mode;
|
||||
|
||||
struct aa_label *aa_secid_to_label(u32 secid);
|
||||
int apparmor_secid_to_secctx(u32 secid, char **secdata, u32 *seclen);
|
||||
int apparmor_lsmprop_to_secctx(struct lsm_prop *prop, char **secdata,
|
||||
u32 *seclen);
|
||||
int apparmor_secctx_to_secid(const char *secdata, u32 seclen, u32 *secid);
|
||||
void apparmor_release_secctx(char *secdata, u32 seclen);
|
||||
|
||||
|
@ -982,17 +982,20 @@ static void apparmor_bprm_committed_creds(const struct linux_binprm *bprm)
|
||||
return;
|
||||
}
|
||||
|
||||
static void apparmor_current_getsecid_subj(u32 *secid)
|
||||
static void apparmor_current_getlsmprop_subj(struct lsm_prop *prop)
|
||||
{
|
||||
struct aa_label *label = __begin_current_label_crit_section();
|
||||
*secid = label->secid;
|
||||
|
||||
prop->apparmor.label = label;
|
||||
__end_current_label_crit_section(label);
|
||||
}
|
||||
|
||||
static void apparmor_task_getsecid_obj(struct task_struct *p, u32 *secid)
|
||||
static void apparmor_task_getlsmprop_obj(struct task_struct *p,
|
||||
struct lsm_prop *prop)
|
||||
{
|
||||
struct aa_label *label = aa_get_task_label(p);
|
||||
*secid = label->secid;
|
||||
|
||||
prop->apparmor.label = label;
|
||||
aa_put_label(label);
|
||||
}
|
||||
|
||||
@ -1503,8 +1506,9 @@ static struct security_hook_list apparmor_hooks[] __ro_after_init = {
|
||||
|
||||
LSM_HOOK_INIT(task_free, apparmor_task_free),
|
||||
LSM_HOOK_INIT(task_alloc, apparmor_task_alloc),
|
||||
LSM_HOOK_INIT(current_getsecid_subj, apparmor_current_getsecid_subj),
|
||||
LSM_HOOK_INIT(task_getsecid_obj, apparmor_task_getsecid_obj),
|
||||
LSM_HOOK_INIT(current_getlsmprop_subj,
|
||||
apparmor_current_getlsmprop_subj),
|
||||
LSM_HOOK_INIT(task_getlsmprop_obj, apparmor_task_getlsmprop_obj),
|
||||
LSM_HOOK_INIT(task_setrlimit, apparmor_task_setrlimit),
|
||||
LSM_HOOK_INIT(task_kill, apparmor_task_kill),
|
||||
LSM_HOOK_INIT(userns_create, apparmor_userns_create),
|
||||
@ -1517,6 +1521,7 @@ static struct security_hook_list apparmor_hooks[] __ro_after_init = {
|
||||
#endif
|
||||
|
||||
LSM_HOOK_INIT(secid_to_secctx, apparmor_secid_to_secctx),
|
||||
LSM_HOOK_INIT(lsmprop_to_secctx, apparmor_lsmprop_to_secctx),
|
||||
LSM_HOOK_INIT(secctx_to_secid, apparmor_secctx_to_secid),
|
||||
LSM_HOOK_INIT(release_secctx, apparmor_release_secctx),
|
||||
|
||||
|
@ -61,10 +61,10 @@ struct aa_label *aa_secid_to_label(u32 secid)
|
||||
return xa_load(&aa_secids, secid);
|
||||
}
|
||||
|
||||
int apparmor_secid_to_secctx(u32 secid, char **secdata, u32 *seclen)
|
||||
static int apparmor_label_to_secctx(struct aa_label *label, char **secdata,
|
||||
u32 *seclen)
|
||||
{
|
||||
/* TODO: cache secctx and ref count so we don't have to recreate */
|
||||
struct aa_label *label = aa_secid_to_label(secid);
|
||||
int flags = FLAG_VIEW_SUBNS | FLAG_HIDDEN_UNCONFINED | FLAG_ABS_ROOT;
|
||||
int len;
|
||||
|
||||
@ -90,6 +90,23 @@ int apparmor_secid_to_secctx(u32 secid, char **secdata, u32 *seclen)
|
||||
return 0;
|
||||
}
|
||||
|
||||
int apparmor_secid_to_secctx(u32 secid, char **secdata, u32 *seclen)
|
||||
{
|
||||
struct aa_label *label = aa_secid_to_label(secid);
|
||||
|
||||
return apparmor_label_to_secctx(label, secdata, seclen);
|
||||
}
|
||||
|
||||
int apparmor_lsmprop_to_secctx(struct lsm_prop *prop, char **secdata,
|
||||
u32 *seclen)
|
||||
{
|
||||
struct aa_label *label;
|
||||
|
||||
label = prop->apparmor.label;
|
||||
|
||||
return apparmor_label_to_secctx(label, secdata, seclen);
|
||||
}
|
||||
|
||||
int apparmor_secctx_to_secid(const char *secdata, u32 seclen, u32 *secid)
|
||||
{
|
||||
struct aa_label *label;
|
||||
|
@ -369,7 +369,7 @@ static inline void ima_process_queued_keys(void) {}
|
||||
|
||||
/* LIM API function definitions */
|
||||
int ima_get_action(struct mnt_idmap *idmap, struct inode *inode,
|
||||
const struct cred *cred, u32 secid, int mask,
|
||||
const struct cred *cred, struct lsm_prop *prop, int mask,
|
||||
enum ima_hooks func, int *pcr,
|
||||
struct ima_template_desc **template_desc,
|
||||
const char *func_data, unsigned int *allowed_algos);
|
||||
@ -400,8 +400,8 @@ const char *ima_d_path(const struct path *path, char **pathbuf, char *filename);
|
||||
|
||||
/* IMA policy related functions */
|
||||
int ima_match_policy(struct mnt_idmap *idmap, struct inode *inode,
|
||||
const struct cred *cred, u32 secid, enum ima_hooks func,
|
||||
int mask, int flags, int *pcr,
|
||||
const struct cred *cred, struct lsm_prop *prop,
|
||||
enum ima_hooks func, int mask, int flags, int *pcr,
|
||||
struct ima_template_desc **template_desc,
|
||||
const char *func_data, unsigned int *allowed_algos);
|
||||
void ima_init_policy(void);
|
||||
@ -555,7 +555,7 @@ static inline void ima_filter_rule_free(void *lsmrule)
|
||||
{
|
||||
}
|
||||
|
||||
static inline int ima_filter_rule_match(u32 secid, u32 field, u32 op,
|
||||
static inline int ima_filter_rule_match(struct lsm_prop *prop, u32 field, u32 op,
|
||||
void *lsmrule)
|
||||
{
|
||||
return -EINVAL;
|
||||
|
@ -165,7 +165,7 @@ err_out:
|
||||
* @idmap: idmap of the mount the inode was found from
|
||||
* @inode: pointer to the inode associated with the object being validated
|
||||
* @cred: pointer to credentials structure to validate
|
||||
* @secid: secid of the task being validated
|
||||
* @prop: properties of the task being validated
|
||||
* @mask: contains the permission mask (MAY_READ, MAY_WRITE, MAY_EXEC,
|
||||
* MAY_APPEND)
|
||||
* @func: caller identifier
|
||||
@ -187,7 +187,7 @@ err_out:
|
||||
*
|
||||
*/
|
||||
int ima_get_action(struct mnt_idmap *idmap, struct inode *inode,
|
||||
const struct cred *cred, u32 secid, int mask,
|
||||
const struct cred *cred, struct lsm_prop *prop, int mask,
|
||||
enum ima_hooks func, int *pcr,
|
||||
struct ima_template_desc **template_desc,
|
||||
const char *func_data, unsigned int *allowed_algos)
|
||||
@ -196,7 +196,7 @@ int ima_get_action(struct mnt_idmap *idmap, struct inode *inode,
|
||||
|
||||
flags &= ima_policy_flag;
|
||||
|
||||
return ima_match_policy(idmap, inode, cred, secid, func, mask,
|
||||
return ima_match_policy(idmap, inode, cred, prop, func, mask,
|
||||
flags, pcr, template_desc, func_data,
|
||||
allowed_algos);
|
||||
}
|
||||
|
@ -73,13 +73,13 @@ bool is_ima_appraise_enabled(void)
|
||||
int ima_must_appraise(struct mnt_idmap *idmap, struct inode *inode,
|
||||
int mask, enum ima_hooks func)
|
||||
{
|
||||
u32 secid;
|
||||
struct lsm_prop prop;
|
||||
|
||||
if (!ima_appraise)
|
||||
return 0;
|
||||
|
||||
security_current_getsecid_subj(&secid);
|
||||
return ima_match_policy(idmap, inode, current_cred(), secid,
|
||||
security_current_getlsmprop_subj(&prop);
|
||||
return ima_match_policy(idmap, inode, current_cred(), &prop,
|
||||
func, mask, IMA_APPRAISE | IMA_HASH, NULL,
|
||||
NULL, NULL, NULL);
|
||||
}
|
||||
|
@ -206,8 +206,8 @@ static void ima_file_free(struct file *file)
|
||||
}
|
||||
|
||||
static int process_measurement(struct file *file, const struct cred *cred,
|
||||
u32 secid, char *buf, loff_t size, int mask,
|
||||
enum ima_hooks func)
|
||||
struct lsm_prop *prop, char *buf, loff_t size,
|
||||
int mask, enum ima_hooks func)
|
||||
{
|
||||
struct inode *real_inode, *inode = file_inode(file);
|
||||
struct ima_iint_cache *iint = NULL;
|
||||
@ -232,7 +232,7 @@ static int process_measurement(struct file *file, const struct cred *cred,
|
||||
* bitmask based on the appraise/audit/measurement policy.
|
||||
* Included is the appraise submask.
|
||||
*/
|
||||
action = ima_get_action(file_mnt_idmap(file), inode, cred, secid,
|
||||
action = ima_get_action(file_mnt_idmap(file), inode, cred, prop,
|
||||
mask, func, &pcr, &template_desc, NULL,
|
||||
&allowed_algos);
|
||||
violation_check = ((func == FILE_CHECK || func == MMAP_CHECK ||
|
||||
@ -443,23 +443,23 @@ out:
|
||||
static int ima_file_mmap(struct file *file, unsigned long reqprot,
|
||||
unsigned long prot, unsigned long flags)
|
||||
{
|
||||
u32 secid;
|
||||
struct lsm_prop prop;
|
||||
int ret;
|
||||
|
||||
if (!file)
|
||||
return 0;
|
||||
|
||||
security_current_getsecid_subj(&secid);
|
||||
security_current_getlsmprop_subj(&prop);
|
||||
|
||||
if (reqprot & PROT_EXEC) {
|
||||
ret = process_measurement(file, current_cred(), secid, NULL,
|
||||
ret = process_measurement(file, current_cred(), &prop, NULL,
|
||||
0, MAY_EXEC, MMAP_CHECK_REQPROT);
|
||||
if (ret)
|
||||
return ret;
|
||||
}
|
||||
|
||||
if (prot & PROT_EXEC)
|
||||
return process_measurement(file, current_cred(), secid, NULL,
|
||||
return process_measurement(file, current_cred(), &prop, NULL,
|
||||
0, MAY_EXEC, MMAP_CHECK);
|
||||
|
||||
return 0;
|
||||
@ -488,9 +488,9 @@ static int ima_file_mprotect(struct vm_area_struct *vma, unsigned long reqprot,
|
||||
char *pathbuf = NULL;
|
||||
const char *pathname = NULL;
|
||||
struct inode *inode;
|
||||
struct lsm_prop prop;
|
||||
int result = 0;
|
||||
int action;
|
||||
u32 secid;
|
||||
int pcr;
|
||||
|
||||
/* Is mprotect making an mmap'ed file executable? */
|
||||
@ -498,13 +498,13 @@ static int ima_file_mprotect(struct vm_area_struct *vma, unsigned long reqprot,
|
||||
!(prot & PROT_EXEC) || (vma->vm_flags & VM_EXEC))
|
||||
return 0;
|
||||
|
||||
security_current_getsecid_subj(&secid);
|
||||
security_current_getlsmprop_subj(&prop);
|
||||
inode = file_inode(vma->vm_file);
|
||||
action = ima_get_action(file_mnt_idmap(vma->vm_file), inode,
|
||||
current_cred(), secid, MAY_EXEC, MMAP_CHECK,
|
||||
current_cred(), &prop, MAY_EXEC, MMAP_CHECK,
|
||||
&pcr, &template, NULL, NULL);
|
||||
action |= ima_get_action(file_mnt_idmap(vma->vm_file), inode,
|
||||
current_cred(), secid, MAY_EXEC,
|
||||
current_cred(), &prop, MAY_EXEC,
|
||||
MMAP_CHECK_REQPROT, &pcr, &template, NULL,
|
||||
NULL);
|
||||
|
||||
@ -541,16 +541,16 @@ static int ima_file_mprotect(struct vm_area_struct *vma, unsigned long reqprot,
|
||||
static int ima_bprm_check(struct linux_binprm *bprm)
|
||||
{
|
||||
int ret;
|
||||
u32 secid;
|
||||
struct lsm_prop prop;
|
||||
|
||||
security_current_getsecid_subj(&secid);
|
||||
ret = process_measurement(bprm->file, current_cred(), secid, NULL, 0,
|
||||
MAY_EXEC, BPRM_CHECK);
|
||||
security_current_getlsmprop_subj(&prop);
|
||||
ret = process_measurement(bprm->file, current_cred(),
|
||||
&prop, NULL, 0, MAY_EXEC, BPRM_CHECK);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
security_cred_getsecid(bprm->cred, &secid);
|
||||
return process_measurement(bprm->file, bprm->cred, secid, NULL, 0,
|
||||
security_cred_getlsmprop(bprm->cred, &prop);
|
||||
return process_measurement(bprm->file, bprm->cred, &prop, NULL, 0,
|
||||
MAY_EXEC, CREDS_CHECK);
|
||||
}
|
||||
|
||||
@ -566,10 +566,10 @@ static int ima_bprm_check(struct linux_binprm *bprm)
|
||||
*/
|
||||
static int ima_file_check(struct file *file, int mask)
|
||||
{
|
||||
u32 secid;
|
||||
struct lsm_prop prop;
|
||||
|
||||
security_current_getsecid_subj(&secid);
|
||||
return process_measurement(file, current_cred(), secid, NULL, 0,
|
||||
security_current_getlsmprop_subj(&prop);
|
||||
return process_measurement(file, current_cred(), &prop, NULL, 0,
|
||||
mask & (MAY_READ | MAY_WRITE | MAY_EXEC |
|
||||
MAY_APPEND), FILE_CHECK);
|
||||
}
|
||||
@ -768,7 +768,7 @@ static int ima_read_file(struct file *file, enum kernel_read_file_id read_id,
|
||||
bool contents)
|
||||
{
|
||||
enum ima_hooks func;
|
||||
u32 secid;
|
||||
struct lsm_prop prop;
|
||||
|
||||
/*
|
||||
* Do devices using pre-allocated memory run the risk of the
|
||||
@ -788,9 +788,9 @@ static int ima_read_file(struct file *file, enum kernel_read_file_id read_id,
|
||||
|
||||
/* Read entire file for all partial reads. */
|
||||
func = read_idmap[read_id] ?: FILE_CHECK;
|
||||
security_current_getsecid_subj(&secid);
|
||||
return process_measurement(file, current_cred(), secid, NULL,
|
||||
0, MAY_READ, func);
|
||||
security_current_getlsmprop_subj(&prop);
|
||||
return process_measurement(file, current_cred(), &prop, NULL, 0,
|
||||
MAY_READ, func);
|
||||
}
|
||||
|
||||
const int read_idmap[READING_MAX_ID] = {
|
||||
@ -818,7 +818,7 @@ static int ima_post_read_file(struct file *file, char *buf, loff_t size,
|
||||
enum kernel_read_file_id read_id)
|
||||
{
|
||||
enum ima_hooks func;
|
||||
u32 secid;
|
||||
struct lsm_prop prop;
|
||||
|
||||
/* permit signed certs */
|
||||
if (!file && read_id == READING_X509_CERTIFICATE)
|
||||
@ -831,8 +831,8 @@ static int ima_post_read_file(struct file *file, char *buf, loff_t size,
|
||||
}
|
||||
|
||||
func = read_idmap[read_id] ?: FILE_CHECK;
|
||||
security_current_getsecid_subj(&secid);
|
||||
return process_measurement(file, current_cred(), secid, buf, size,
|
||||
security_current_getlsmprop_subj(&prop);
|
||||
return process_measurement(file, current_cred(), &prop, buf, size,
|
||||
MAY_READ, func);
|
||||
}
|
||||
|
||||
@ -967,7 +967,7 @@ int process_buffer_measurement(struct mnt_idmap *idmap,
|
||||
int digest_hash_len = hash_digest_size[ima_hash_algo];
|
||||
int violation = 0;
|
||||
int action = 0;
|
||||
u32 secid;
|
||||
struct lsm_prop prop;
|
||||
|
||||
if (digest && digest_len < digest_hash_len)
|
||||
return -EINVAL;
|
||||
@ -990,9 +990,9 @@ int process_buffer_measurement(struct mnt_idmap *idmap,
|
||||
* buffer measurements.
|
||||
*/
|
||||
if (func) {
|
||||
security_current_getsecid_subj(&secid);
|
||||
security_current_getlsmprop_subj(&prop);
|
||||
action = ima_get_action(idmap, inode, current_cred(),
|
||||
secid, 0, func, &pcr, &template,
|
||||
&prop, 0, func, &pcr, &template,
|
||||
func_data, NULL);
|
||||
if (!(action & IMA_MEASURE) && !digest)
|
||||
return -ENOENT;
|
||||
|
@ -557,7 +557,7 @@ static bool ima_match_rule_data(struct ima_rule_entry *rule,
|
||||
* @idmap: idmap of the mount the inode was found from
|
||||
* @inode: a pointer to an inode
|
||||
* @cred: a pointer to a credentials structure for user validation
|
||||
* @secid: the secid of the task to be validated
|
||||
* @prop: LSM properties of the task to be validated
|
||||
* @func: LIM hook identifier
|
||||
* @mask: requested action (MAY_READ | MAY_WRITE | MAY_APPEND | MAY_EXEC)
|
||||
* @func_data: func specific data, may be NULL
|
||||
@ -567,7 +567,7 @@ static bool ima_match_rule_data(struct ima_rule_entry *rule,
|
||||
static bool ima_match_rules(struct ima_rule_entry *rule,
|
||||
struct mnt_idmap *idmap,
|
||||
struct inode *inode, const struct cred *cred,
|
||||
u32 secid, enum ima_hooks func, int mask,
|
||||
struct lsm_prop *prop, enum ima_hooks func, int mask,
|
||||
const char *func_data)
|
||||
{
|
||||
int i;
|
||||
@ -635,7 +635,7 @@ static bool ima_match_rules(struct ima_rule_entry *rule,
|
||||
return false;
|
||||
for (i = 0; i < MAX_LSM_RULES; i++) {
|
||||
int rc = 0;
|
||||
u32 osid;
|
||||
struct lsm_prop prop = { };
|
||||
|
||||
if (!lsm_rule->lsm[i].rule) {
|
||||
if (!lsm_rule->lsm[i].args_p)
|
||||
@ -649,15 +649,15 @@ retry:
|
||||
case LSM_OBJ_USER:
|
||||
case LSM_OBJ_ROLE:
|
||||
case LSM_OBJ_TYPE:
|
||||
security_inode_getsecid(inode, &osid);
|
||||
rc = ima_filter_rule_match(osid, lsm_rule->lsm[i].type,
|
||||
security_inode_getlsmprop(inode, &prop);
|
||||
rc = ima_filter_rule_match(&prop, lsm_rule->lsm[i].type,
|
||||
Audit_equal,
|
||||
lsm_rule->lsm[i].rule);
|
||||
break;
|
||||
case LSM_SUBJ_USER:
|
||||
case LSM_SUBJ_ROLE:
|
||||
case LSM_SUBJ_TYPE:
|
||||
rc = ima_filter_rule_match(secid, lsm_rule->lsm[i].type,
|
||||
rc = ima_filter_rule_match(&prop, lsm_rule->lsm[i].type,
|
||||
Audit_equal,
|
||||
lsm_rule->lsm[i].rule);
|
||||
break;
|
||||
@ -720,7 +720,7 @@ static int get_subaction(struct ima_rule_entry *rule, enum ima_hooks func)
|
||||
* @inode: pointer to an inode for which the policy decision is being made
|
||||
* @cred: pointer to a credentials structure for which the policy decision is
|
||||
* being made
|
||||
* @secid: LSM secid of the task to be validated
|
||||
* @prop: LSM properties of the task to be validated
|
||||
* @func: IMA hook identifier
|
||||
* @mask: requested action (MAY_READ | MAY_WRITE | MAY_APPEND | MAY_EXEC)
|
||||
* @flags: IMA actions to consider (e.g. IMA_MEASURE | IMA_APPRAISE)
|
||||
@ -737,8 +737,8 @@ static int get_subaction(struct ima_rule_entry *rule, enum ima_hooks func)
|
||||
* than writes so ima_match_policy() is classical RCU candidate.
|
||||
*/
|
||||
int ima_match_policy(struct mnt_idmap *idmap, struct inode *inode,
|
||||
const struct cred *cred, u32 secid, enum ima_hooks func,
|
||||
int mask, int flags, int *pcr,
|
||||
const struct cred *cred, struct lsm_prop *prop,
|
||||
enum ima_hooks func, int mask, int flags, int *pcr,
|
||||
struct ima_template_desc **template_desc,
|
||||
const char *func_data, unsigned int *allowed_algos)
|
||||
{
|
||||
@ -756,7 +756,7 @@ int ima_match_policy(struct mnt_idmap *idmap, struct inode *inode,
|
||||
if (!(entry->action & actmask))
|
||||
continue;
|
||||
|
||||
if (!ima_match_rules(entry, idmap, inode, cred, secid,
|
||||
if (!ima_match_rules(entry, idmap, inode, cred, prop,
|
||||
func, mask, func_data))
|
||||
continue;
|
||||
|
||||
|
@ -2726,16 +2726,15 @@ int security_inode_listsecurity(struct inode *inode,
|
||||
EXPORT_SYMBOL(security_inode_listsecurity);
|
||||
|
||||
/**
|
||||
* security_inode_getsecid() - Get an inode's secid
|
||||
* security_inode_getlsmprop() - Get an inode's LSM data
|
||||
* @inode: inode
|
||||
* @secid: secid to return
|
||||
* @prop: lsm specific information to return
|
||||
*
|
||||
* Get the secid associated with the node. In case of failure, @secid will be
|
||||
* set to zero.
|
||||
* Get the lsm specific information associated with the node.
|
||||
*/
|
||||
void security_inode_getsecid(struct inode *inode, u32 *secid)
|
||||
void security_inode_getlsmprop(struct inode *inode, struct lsm_prop *prop)
|
||||
{
|
||||
call_void_hook(inode_getsecid, inode, secid);
|
||||
call_void_hook(inode_getlsmprop, inode, prop);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -3275,6 +3274,21 @@ void security_cred_getsecid(const struct cred *c, u32 *secid)
|
||||
}
|
||||
EXPORT_SYMBOL(security_cred_getsecid);
|
||||
|
||||
/**
|
||||
* security_cred_getlsmprop() - Get the LSM data from a set of credentials
|
||||
* @c: credentials
|
||||
* @prop: destination for the LSM data
|
||||
*
|
||||
* Retrieve the security data of the cred structure @c. In case of
|
||||
* failure, @prop will be cleared.
|
||||
*/
|
||||
void security_cred_getlsmprop(const struct cred *c, struct lsm_prop *prop)
|
||||
{
|
||||
lsmprop_init(prop);
|
||||
call_void_hook(cred_getlsmprop, c, prop);
|
||||
}
|
||||
EXPORT_SYMBOL(security_cred_getlsmprop);
|
||||
|
||||
/**
|
||||
* security_kernel_act_as() - Set the kernel credentials to act as secid
|
||||
* @new: credentials
|
||||
@ -3494,33 +3508,33 @@ int security_task_getsid(struct task_struct *p)
|
||||
}
|
||||
|
||||
/**
|
||||
* security_current_getsecid_subj() - Get the current task's subjective secid
|
||||
* @secid: secid value
|
||||
* security_current_getlsmprop_subj() - Current task's subjective LSM data
|
||||
* @prop: lsm specific information
|
||||
*
|
||||
* Retrieve the subjective security identifier of the current task and return
|
||||
* it in @secid. In case of failure, @secid will be set to zero.
|
||||
* it in @prop.
|
||||
*/
|
||||
void security_current_getsecid_subj(u32 *secid)
|
||||
void security_current_getlsmprop_subj(struct lsm_prop *prop)
|
||||
{
|
||||
*secid = 0;
|
||||
call_void_hook(current_getsecid_subj, secid);
|
||||
lsmprop_init(prop);
|
||||
call_void_hook(current_getlsmprop_subj, prop);
|
||||
}
|
||||
EXPORT_SYMBOL(security_current_getsecid_subj);
|
||||
EXPORT_SYMBOL(security_current_getlsmprop_subj);
|
||||
|
||||
/**
|
||||
* security_task_getsecid_obj() - Get a task's objective secid
|
||||
* security_task_getlsmprop_obj() - Get a task's objective LSM data
|
||||
* @p: target task
|
||||
* @secid: secid value
|
||||
* @prop: lsm specific information
|
||||
*
|
||||
* Retrieve the objective security identifier of the task_struct in @p and
|
||||
* return it in @secid. In case of failure, @secid will be set to zero.
|
||||
* return it in @prop.
|
||||
*/
|
||||
void security_task_getsecid_obj(struct task_struct *p, u32 *secid)
|
||||
void security_task_getlsmprop_obj(struct task_struct *p, struct lsm_prop *prop)
|
||||
{
|
||||
*secid = 0;
|
||||
call_void_hook(task_getsecid_obj, p, secid);
|
||||
lsmprop_init(prop);
|
||||
call_void_hook(task_getlsmprop_obj, p, prop);
|
||||
}
|
||||
EXPORT_SYMBOL(security_task_getsecid_obj);
|
||||
EXPORT_SYMBOL(security_task_getlsmprop_obj);
|
||||
|
||||
/**
|
||||
* security_task_setnice() - Check if setting a task's nice value is allowed
|
||||
@ -3732,17 +3746,17 @@ int security_ipc_permission(struct kern_ipc_perm *ipcp, short flag)
|
||||
}
|
||||
|
||||
/**
|
||||
* security_ipc_getsecid() - Get the sysv ipc object's secid
|
||||
* security_ipc_getlsmprop() - Get the sysv ipc object LSM data
|
||||
* @ipcp: ipc permission structure
|
||||
* @secid: secid pointer
|
||||
* @prop: pointer to lsm information
|
||||
*
|
||||
* Get the secid associated with the ipc object. In case of failure, @secid
|
||||
* will be set to zero.
|
||||
* Get the lsm information associated with the ipc object.
|
||||
*/
|
||||
void security_ipc_getsecid(struct kern_ipc_perm *ipcp, u32 *secid)
|
||||
|
||||
void security_ipc_getlsmprop(struct kern_ipc_perm *ipcp, struct lsm_prop *prop)
|
||||
{
|
||||
*secid = 0;
|
||||
call_void_hook(ipc_getsecid, ipcp, secid);
|
||||
lsmprop_init(prop);
|
||||
call_void_hook(ipc_getlsmprop, ipcp, prop);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -4313,6 +4327,27 @@ int security_secid_to_secctx(u32 secid, char **secdata, u32 *seclen)
|
||||
}
|
||||
EXPORT_SYMBOL(security_secid_to_secctx);
|
||||
|
||||
/**
|
||||
* security_lsmprop_to_secctx() - Convert a lsm_prop to a secctx
|
||||
* @prop: lsm specific information
|
||||
* @secdata: secctx
|
||||
* @seclen: secctx length
|
||||
*
|
||||
* Convert a @prop entry to security context. If @secdata is NULL the
|
||||
* length of the result will be returned in @seclen, but no @secdata
|
||||
* will be returned. This does mean that the length could change between
|
||||
* calls to check the length and the next call which actually allocates
|
||||
* and returns the @secdata.
|
||||
*
|
||||
* Return: Return 0 on success, error on failure.
|
||||
*/
|
||||
int security_lsmprop_to_secctx(struct lsm_prop *prop, char **secdata,
|
||||
u32 *seclen)
|
||||
{
|
||||
return call_int_hook(lsmprop_to_secctx, prop, secdata, seclen);
|
||||
}
|
||||
EXPORT_SYMBOL(security_lsmprop_to_secctx);
|
||||
|
||||
/**
|
||||
* security_secctx_to_secid() - Convert a secctx to a secid
|
||||
* @secdata: secctx
|
||||
@ -5572,7 +5607,7 @@ void security_audit_rule_free(void *lsmrule)
|
||||
|
||||
/**
|
||||
* security_audit_rule_match() - Check if a label matches an audit rule
|
||||
* @secid: security label
|
||||
* @prop: security label
|
||||
* @field: LSM audit field
|
||||
* @op: matching operator
|
||||
* @lsmrule: audit rule
|
||||
@ -5583,9 +5618,10 @@ void security_audit_rule_free(void *lsmrule)
|
||||
* Return: Returns 1 if secid matches the rule, 0 if it does not, -ERRNO on
|
||||
* failure.
|
||||
*/
|
||||
int security_audit_rule_match(u32 secid, u32 field, u32 op, void *lsmrule)
|
||||
int security_audit_rule_match(struct lsm_prop *prop, u32 field, u32 op,
|
||||
void *lsmrule)
|
||||
{
|
||||
return call_int_hook(audit_rule_match, secid, field, op, lsmrule);
|
||||
return call_int_hook(audit_rule_match, prop, field, op, lsmrule);
|
||||
}
|
||||
#endif /* CONFIG_AUDIT */
|
||||
|
||||
|
@ -3503,15 +3503,16 @@ static int selinux_inode_listsecurity(struct inode *inode, char *buffer, size_t
|
||||
return len;
|
||||
}
|
||||
|
||||
static void selinux_inode_getsecid(struct inode *inode, u32 *secid)
|
||||
static void selinux_inode_getlsmprop(struct inode *inode, struct lsm_prop *prop)
|
||||
{
|
||||
struct inode_security_struct *isec = inode_security_novalidate(inode);
|
||||
*secid = isec->sid;
|
||||
|
||||
prop->selinux.secid = isec->sid;
|
||||
}
|
||||
|
||||
static int selinux_inode_copy_up(struct dentry *src, struct cred **new)
|
||||
{
|
||||
u32 sid;
|
||||
struct lsm_prop prop;
|
||||
struct task_security_struct *tsec;
|
||||
struct cred *new_creds = *new;
|
||||
|
||||
@ -3523,8 +3524,8 @@ static int selinux_inode_copy_up(struct dentry *src, struct cred **new)
|
||||
|
||||
tsec = selinux_cred(new_creds);
|
||||
/* Get label from overlay inode and set it in create_sid */
|
||||
selinux_inode_getsecid(d_inode(src), &sid);
|
||||
tsec->create_sid = sid;
|
||||
selinux_inode_getlsmprop(d_inode(src), &prop);
|
||||
tsec->create_sid = prop.selinux.secid;
|
||||
*new = new_creds;
|
||||
return 0;
|
||||
}
|
||||
@ -4034,6 +4035,11 @@ static void selinux_cred_getsecid(const struct cred *c, u32 *secid)
|
||||
*secid = cred_sid(c);
|
||||
}
|
||||
|
||||
static void selinux_cred_getlsmprop(const struct cred *c, struct lsm_prop *prop)
|
||||
{
|
||||
prop->selinux.secid = cred_sid(c);
|
||||
}
|
||||
|
||||
/*
|
||||
* set the security data for a kernel service
|
||||
* - all the creation contexts are set to unlabelled
|
||||
@ -4169,14 +4175,15 @@ static int selinux_task_getsid(struct task_struct *p)
|
||||
PROCESS__GETSESSION, NULL);
|
||||
}
|
||||
|
||||
static void selinux_current_getsecid_subj(u32 *secid)
|
||||
static void selinux_current_getlsmprop_subj(struct lsm_prop *prop)
|
||||
{
|
||||
*secid = current_sid();
|
||||
prop->selinux.secid = current_sid();
|
||||
}
|
||||
|
||||
static void selinux_task_getsecid_obj(struct task_struct *p, u32 *secid)
|
||||
static void selinux_task_getlsmprop_obj(struct task_struct *p,
|
||||
struct lsm_prop *prop)
|
||||
{
|
||||
*secid = task_sid_obj(p);
|
||||
prop->selinux.secid = task_sid_obj(p);
|
||||
}
|
||||
|
||||
static int selinux_task_setnice(struct task_struct *p, int nice)
|
||||
@ -6352,10 +6359,11 @@ static int selinux_ipc_permission(struct kern_ipc_perm *ipcp, short flag)
|
||||
return ipc_has_perm(ipcp, av);
|
||||
}
|
||||
|
||||
static void selinux_ipc_getsecid(struct kern_ipc_perm *ipcp, u32 *secid)
|
||||
static void selinux_ipc_getlsmprop(struct kern_ipc_perm *ipcp,
|
||||
struct lsm_prop *prop)
|
||||
{
|
||||
struct ipc_security_struct *isec = selinux_ipc(ipcp);
|
||||
*secid = isec->sid;
|
||||
prop->selinux.secid = isec->sid;
|
||||
}
|
||||
|
||||
static void selinux_d_instantiate(struct dentry *dentry, struct inode *inode)
|
||||
@ -6634,8 +6642,13 @@ static int selinux_ismaclabel(const char *name)
|
||||
|
||||
static int selinux_secid_to_secctx(u32 secid, char **secdata, u32 *seclen)
|
||||
{
|
||||
return security_sid_to_context(secid,
|
||||
secdata, seclen);
|
||||
return security_sid_to_context(secid, secdata, seclen);
|
||||
}
|
||||
|
||||
static int selinux_lsmprop_to_secctx(struct lsm_prop *prop, char **secdata,
|
||||
u32 *seclen)
|
||||
{
|
||||
return selinux_secid_to_secctx(prop->selinux.secid, secdata, seclen);
|
||||
}
|
||||
|
||||
static int selinux_secctx_to_secid(const char *secdata, u32 seclen, u32 *secid)
|
||||
@ -7188,7 +7201,7 @@ static struct security_hook_list selinux_hooks[] __ro_after_init = {
|
||||
LSM_HOOK_INIT(inode_getsecurity, selinux_inode_getsecurity),
|
||||
LSM_HOOK_INIT(inode_setsecurity, selinux_inode_setsecurity),
|
||||
LSM_HOOK_INIT(inode_listsecurity, selinux_inode_listsecurity),
|
||||
LSM_HOOK_INIT(inode_getsecid, selinux_inode_getsecid),
|
||||
LSM_HOOK_INIT(inode_getlsmprop, selinux_inode_getlsmprop),
|
||||
LSM_HOOK_INIT(inode_copy_up, selinux_inode_copy_up),
|
||||
LSM_HOOK_INIT(inode_copy_up_xattr, selinux_inode_copy_up_xattr),
|
||||
LSM_HOOK_INIT(path_notify, selinux_path_notify),
|
||||
@ -7214,6 +7227,7 @@ static struct security_hook_list selinux_hooks[] __ro_after_init = {
|
||||
LSM_HOOK_INIT(cred_prepare, selinux_cred_prepare),
|
||||
LSM_HOOK_INIT(cred_transfer, selinux_cred_transfer),
|
||||
LSM_HOOK_INIT(cred_getsecid, selinux_cred_getsecid),
|
||||
LSM_HOOK_INIT(cred_getlsmprop, selinux_cred_getlsmprop),
|
||||
LSM_HOOK_INIT(kernel_act_as, selinux_kernel_act_as),
|
||||
LSM_HOOK_INIT(kernel_create_files_as, selinux_kernel_create_files_as),
|
||||
LSM_HOOK_INIT(kernel_module_request, selinux_kernel_module_request),
|
||||
@ -7222,8 +7236,8 @@ static struct security_hook_list selinux_hooks[] __ro_after_init = {
|
||||
LSM_HOOK_INIT(task_setpgid, selinux_task_setpgid),
|
||||
LSM_HOOK_INIT(task_getpgid, selinux_task_getpgid),
|
||||
LSM_HOOK_INIT(task_getsid, selinux_task_getsid),
|
||||
LSM_HOOK_INIT(current_getsecid_subj, selinux_current_getsecid_subj),
|
||||
LSM_HOOK_INIT(task_getsecid_obj, selinux_task_getsecid_obj),
|
||||
LSM_HOOK_INIT(current_getlsmprop_subj, selinux_current_getlsmprop_subj),
|
||||
LSM_HOOK_INIT(task_getlsmprop_obj, selinux_task_getlsmprop_obj),
|
||||
LSM_HOOK_INIT(task_setnice, selinux_task_setnice),
|
||||
LSM_HOOK_INIT(task_setioprio, selinux_task_setioprio),
|
||||
LSM_HOOK_INIT(task_getioprio, selinux_task_getioprio),
|
||||
@ -7237,7 +7251,7 @@ static struct security_hook_list selinux_hooks[] __ro_after_init = {
|
||||
LSM_HOOK_INIT(userns_create, selinux_userns_create),
|
||||
|
||||
LSM_HOOK_INIT(ipc_permission, selinux_ipc_permission),
|
||||
LSM_HOOK_INIT(ipc_getsecid, selinux_ipc_getsecid),
|
||||
LSM_HOOK_INIT(ipc_getlsmprop, selinux_ipc_getlsmprop),
|
||||
|
||||
LSM_HOOK_INIT(msg_queue_associate, selinux_msg_queue_associate),
|
||||
LSM_HOOK_INIT(msg_queue_msgctl, selinux_msg_queue_msgctl),
|
||||
@ -7380,6 +7394,7 @@ static struct security_hook_list selinux_hooks[] __ro_after_init = {
|
||||
LSM_HOOK_INIT(inode_alloc_security, selinux_inode_alloc_security),
|
||||
LSM_HOOK_INIT(sem_alloc_security, selinux_sem_alloc_security),
|
||||
LSM_HOOK_INIT(secid_to_secctx, selinux_secid_to_secctx),
|
||||
LSM_HOOK_INIT(lsmprop_to_secctx, selinux_lsmprop_to_secctx),
|
||||
LSM_HOOK_INIT(inode_getsecctx, selinux_inode_getsecctx),
|
||||
LSM_HOOK_INIT(sk_alloc_security, selinux_sk_alloc_security),
|
||||
LSM_HOOK_INIT(tun_dev_alloc_security, selinux_tun_dev_alloc_security),
|
||||
|
@ -41,7 +41,7 @@ void selinux_audit_rule_free(void *rule);
|
||||
|
||||
/**
|
||||
* selinux_audit_rule_match - determine if a context ID matches a rule.
|
||||
* @sid: the context ID to check
|
||||
* @prop: includes the context ID to check
|
||||
* @field: the field this rule refers to
|
||||
* @op: the operator the rule uses
|
||||
* @rule: pointer to the audit rule to check against
|
||||
@ -49,7 +49,8 @@ void selinux_audit_rule_free(void *rule);
|
||||
* Returns 1 if the context id matches the rule, 0 if it does not, and
|
||||
* -errno on failure.
|
||||
*/
|
||||
int selinux_audit_rule_match(u32 sid, u32 field, u32 op, void *rule);
|
||||
int selinux_audit_rule_match(struct lsm_prop *prop, u32 field, u32 op,
|
||||
void *rule);
|
||||
|
||||
/**
|
||||
* selinux_audit_rule_known - check to see if rule contains selinux fields.
|
||||
|
@ -3641,7 +3641,7 @@ int selinux_audit_rule_known(struct audit_krule *rule)
|
||||
return 0;
|
||||
}
|
||||
|
||||
int selinux_audit_rule_match(u32 sid, u32 field, u32 op, void *vrule)
|
||||
int selinux_audit_rule_match(struct lsm_prop *prop, u32 field, u32 op, void *vrule)
|
||||
{
|
||||
struct selinux_state *state = &selinux_state;
|
||||
struct selinux_policy *policy;
|
||||
@ -3667,10 +3667,10 @@ int selinux_audit_rule_match(u32 sid, u32 field, u32 op, void *vrule)
|
||||
goto out;
|
||||
}
|
||||
|
||||
ctxt = sidtab_search(policy->sidtab, sid);
|
||||
ctxt = sidtab_search(policy->sidtab, prop->selinux.secid);
|
||||
if (unlikely(!ctxt)) {
|
||||
WARN_ONCE(1, "selinux_audit_rule_match: unrecognized SID %d\n",
|
||||
sid);
|
||||
prop->selinux.secid);
|
||||
match = -ENOENT;
|
||||
goto out;
|
||||
}
|
||||
|
@ -1649,15 +1649,13 @@ static int smack_inode_listsecurity(struct inode *inode, char *buffer,
|
||||
}
|
||||
|
||||
/**
|
||||
* smack_inode_getsecid - Extract inode's security id
|
||||
* smack_inode_getlsmprop - Extract inode's security id
|
||||
* @inode: inode to extract the info from
|
||||
* @secid: where result will be saved
|
||||
* @prop: where result will be saved
|
||||
*/
|
||||
static void smack_inode_getsecid(struct inode *inode, u32 *secid)
|
||||
static void smack_inode_getlsmprop(struct inode *inode, struct lsm_prop *prop)
|
||||
{
|
||||
struct smack_known *skp = smk_of_inode(inode);
|
||||
|
||||
*secid = skp->smk_secid;
|
||||
prop->smack.skp = smk_of_inode(inode);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -2148,6 +2146,21 @@ static void smack_cred_getsecid(const struct cred *cred, u32 *secid)
|
||||
rcu_read_unlock();
|
||||
}
|
||||
|
||||
/**
|
||||
* smack_cred_getlsmprop - get the Smack label for a creds structure
|
||||
* @cred: the object creds
|
||||
* @prop: where to put the data
|
||||
*
|
||||
* Sets the Smack part of the ref
|
||||
*/
|
||||
static void smack_cred_getlsmprop(const struct cred *cred,
|
||||
struct lsm_prop *prop)
|
||||
{
|
||||
rcu_read_lock();
|
||||
prop->smack.skp = smk_of_task(smack_cred(cred));
|
||||
rcu_read_unlock();
|
||||
}
|
||||
|
||||
/**
|
||||
* smack_kernel_act_as - Set the subjective context in a set of credentials
|
||||
* @new: points to the set of credentials to be modified.
|
||||
@ -2239,30 +2252,27 @@ static int smack_task_getsid(struct task_struct *p)
|
||||
}
|
||||
|
||||
/**
|
||||
* smack_current_getsecid_subj - get the subjective secid of the current task
|
||||
* @secid: where to put the result
|
||||
* smack_current_getlsmprop_subj - get the subjective secid of the current task
|
||||
* @prop: where to put the result
|
||||
*
|
||||
* Sets the secid to contain a u32 version of the task's subjective smack label.
|
||||
*/
|
||||
static void smack_current_getsecid_subj(u32 *secid)
|
||||
static void smack_current_getlsmprop_subj(struct lsm_prop *prop)
|
||||
{
|
||||
struct smack_known *skp = smk_of_current();
|
||||
|
||||
*secid = skp->smk_secid;
|
||||
prop->smack.skp = smk_of_current();
|
||||
}
|
||||
|
||||
/**
|
||||
* smack_task_getsecid_obj - get the objective secid of the task
|
||||
* smack_task_getlsmprop_obj - get the objective data of the task
|
||||
* @p: the task
|
||||
* @secid: where to put the result
|
||||
* @prop: where to put the result
|
||||
*
|
||||
* Sets the secid to contain a u32 version of the task's objective smack label.
|
||||
*/
|
||||
static void smack_task_getsecid_obj(struct task_struct *p, u32 *secid)
|
||||
static void smack_task_getlsmprop_obj(struct task_struct *p,
|
||||
struct lsm_prop *prop)
|
||||
{
|
||||
struct smack_known *skp = smk_of_task_struct_obj(p);
|
||||
|
||||
*secid = skp->smk_secid;
|
||||
prop->smack.skp = smk_of_task_struct_obj(p);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -3435,16 +3445,15 @@ static int smack_ipc_permission(struct kern_ipc_perm *ipp, short flag)
|
||||
}
|
||||
|
||||
/**
|
||||
* smack_ipc_getsecid - Extract smack security id
|
||||
* smack_ipc_getlsmprop - Extract smack security data
|
||||
* @ipp: the object permissions
|
||||
* @secid: where result will be saved
|
||||
* @prop: where result will be saved
|
||||
*/
|
||||
static void smack_ipc_getsecid(struct kern_ipc_perm *ipp, u32 *secid)
|
||||
static void smack_ipc_getlsmprop(struct kern_ipc_perm *ipp, struct lsm_prop *prop)
|
||||
{
|
||||
struct smack_known **blob = smack_ipc(ipp);
|
||||
struct smack_known *iskp = *blob;
|
||||
struct smack_known **iskpp = smack_ipc(ipp);
|
||||
|
||||
*secid = iskp->smk_secid;
|
||||
prop->smack.skp = *iskpp;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -4757,7 +4766,7 @@ static int smack_audit_rule_known(struct audit_krule *krule)
|
||||
|
||||
/**
|
||||
* smack_audit_rule_match - Audit given object ?
|
||||
* @secid: security id for identifying the object to test
|
||||
* @prop: security id for identifying the object to test
|
||||
* @field: audit rule flags given from user-space
|
||||
* @op: required testing operator
|
||||
* @vrule: smack internal rule presentation
|
||||
@ -4765,9 +4774,10 @@ static int smack_audit_rule_known(struct audit_krule *krule)
|
||||
* The core Audit hook. It's used to take the decision of
|
||||
* whether to audit or not to audit a given object.
|
||||
*/
|
||||
static int smack_audit_rule_match(u32 secid, u32 field, u32 op, void *vrule)
|
||||
static int smack_audit_rule_match(struct lsm_prop *prop, u32 field, u32 op,
|
||||
void *vrule)
|
||||
{
|
||||
struct smack_known *skp;
|
||||
struct smack_known *skp = prop->smack.skp;
|
||||
char *rule = vrule;
|
||||
|
||||
if (unlikely(!rule)) {
|
||||
@ -4778,8 +4788,6 @@ static int smack_audit_rule_match(u32 secid, u32 field, u32 op, void *vrule)
|
||||
if (field != AUDIT_SUBJ_USER && field != AUDIT_OBJ_USER)
|
||||
return 0;
|
||||
|
||||
skp = smack_from_secid(secid);
|
||||
|
||||
/*
|
||||
* No need to do string comparisons. If a match occurs,
|
||||
* both pointers will point to the same smack_known
|
||||
@ -4809,7 +4817,6 @@ static int smack_ismaclabel(const char *name)
|
||||
return (strcmp(name, XATTR_SMACK_SUFFIX) == 0);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* smack_secid_to_secctx - return the smack label for a secid
|
||||
* @secid: incoming integer
|
||||
@ -4828,6 +4835,25 @@ static int smack_secid_to_secctx(u32 secid, char **secdata, u32 *seclen)
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* smack_lsmprop_to_secctx - return the smack label
|
||||
* @prop: includes incoming Smack data
|
||||
* @secdata: destination
|
||||
* @seclen: how long it is
|
||||
*
|
||||
* Exists for audit code.
|
||||
*/
|
||||
static int smack_lsmprop_to_secctx(struct lsm_prop *prop, char **secdata,
|
||||
u32 *seclen)
|
||||
{
|
||||
struct smack_known *skp = prop->smack.skp;
|
||||
|
||||
if (secdata)
|
||||
*secdata = skp->smk_known;
|
||||
*seclen = strlen(skp->smk_known);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* smack_secctx_to_secid - return the secid for a smack label
|
||||
* @secdata: smack label
|
||||
@ -5078,7 +5104,7 @@ static struct security_hook_list smack_hooks[] __ro_after_init = {
|
||||
LSM_HOOK_INIT(inode_getsecurity, smack_inode_getsecurity),
|
||||
LSM_HOOK_INIT(inode_setsecurity, smack_inode_setsecurity),
|
||||
LSM_HOOK_INIT(inode_listsecurity, smack_inode_listsecurity),
|
||||
LSM_HOOK_INIT(inode_getsecid, smack_inode_getsecid),
|
||||
LSM_HOOK_INIT(inode_getlsmprop, smack_inode_getlsmprop),
|
||||
|
||||
LSM_HOOK_INIT(file_alloc_security, smack_file_alloc_security),
|
||||
LSM_HOOK_INIT(file_ioctl, smack_file_ioctl),
|
||||
@ -5098,13 +5124,14 @@ static struct security_hook_list smack_hooks[] __ro_after_init = {
|
||||
LSM_HOOK_INIT(cred_prepare, smack_cred_prepare),
|
||||
LSM_HOOK_INIT(cred_transfer, smack_cred_transfer),
|
||||
LSM_HOOK_INIT(cred_getsecid, smack_cred_getsecid),
|
||||
LSM_HOOK_INIT(cred_getlsmprop, smack_cred_getlsmprop),
|
||||
LSM_HOOK_INIT(kernel_act_as, smack_kernel_act_as),
|
||||
LSM_HOOK_INIT(kernel_create_files_as, smack_kernel_create_files_as),
|
||||
LSM_HOOK_INIT(task_setpgid, smack_task_setpgid),
|
||||
LSM_HOOK_INIT(task_getpgid, smack_task_getpgid),
|
||||
LSM_HOOK_INIT(task_getsid, smack_task_getsid),
|
||||
LSM_HOOK_INIT(current_getsecid_subj, smack_current_getsecid_subj),
|
||||
LSM_HOOK_INIT(task_getsecid_obj, smack_task_getsecid_obj),
|
||||
LSM_HOOK_INIT(current_getlsmprop_subj, smack_current_getlsmprop_subj),
|
||||
LSM_HOOK_INIT(task_getlsmprop_obj, smack_task_getlsmprop_obj),
|
||||
LSM_HOOK_INIT(task_setnice, smack_task_setnice),
|
||||
LSM_HOOK_INIT(task_setioprio, smack_task_setioprio),
|
||||
LSM_HOOK_INIT(task_getioprio, smack_task_getioprio),
|
||||
@ -5115,7 +5142,7 @@ static struct security_hook_list smack_hooks[] __ro_after_init = {
|
||||
LSM_HOOK_INIT(task_to_inode, smack_task_to_inode),
|
||||
|
||||
LSM_HOOK_INIT(ipc_permission, smack_ipc_permission),
|
||||
LSM_HOOK_INIT(ipc_getsecid, smack_ipc_getsecid),
|
||||
LSM_HOOK_INIT(ipc_getlsmprop, smack_ipc_getlsmprop),
|
||||
|
||||
LSM_HOOK_INIT(msg_msg_alloc_security, smack_msg_msg_alloc_security),
|
||||
|
||||
@ -5187,6 +5214,7 @@ static struct security_hook_list smack_hooks[] __ro_after_init = {
|
||||
|
||||
LSM_HOOK_INIT(ismaclabel, smack_ismaclabel),
|
||||
LSM_HOOK_INIT(secid_to_secctx, smack_secid_to_secctx),
|
||||
LSM_HOOK_INIT(lsmprop_to_secctx, smack_lsmprop_to_secctx),
|
||||
LSM_HOOK_INIT(secctx_to_secid, smack_secctx_to_secid),
|
||||
LSM_HOOK_INIT(inode_notifysecctx, smack_inode_notifysecctx),
|
||||
LSM_HOOK_INIT(inode_setsecctx, smack_inode_setsecctx),
|
||||
|
@ -182,11 +182,9 @@ static inline void smack_catset_bit(unsigned int cat, char *catsetp)
|
||||
*/
|
||||
static void smk_netlabel_audit_set(struct netlbl_audit *nap)
|
||||
{
|
||||
struct smack_known *skp = smk_of_current();
|
||||
|
||||
nap->loginuid = audit_get_loginuid(current);
|
||||
nap->sessionid = audit_get_sessionid(current);
|
||||
nap->secid = skp->smk_secid;
|
||||
nap->prop.smack.skp = smk_of_current();
|
||||
}
|
||||
|
||||
/*
|
||||
|
Loading…
Reference in New Issue
Block a user