d_path: Use struct path in struct avc_audit_data
audit_log_d_path() is a d_path() wrapper that is used by the audit code. To use a struct path in audit_log_d_path() I need to embed it into struct avc_audit_data. [akpm@linux-foundation.org: coding-style fixes] Signed-off-by: Jan Blunck <jblunck@suse.de> Acked-by: Christoph Hellwig <hch@infradead.org> Cc: Al Viro <viro@zeniv.linux.org.uk> Cc: "J. Bruce Fields" <bfields@fieldses.org> Cc: Neil Brown <neilb@suse.de> Cc: Stephen Smalley <sds@tycho.nsa.gov> Cc: James Morris <jmorris@namei.org> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
This commit is contained in:
parent
a03a8a709a
commit
44707fdf59
|
@ -534,8 +534,7 @@ extern void audit_log_n_untrustedstring(struct audit_buffer *ab,
|
||||||
const char *string);
|
const char *string);
|
||||||
extern void audit_log_d_path(struct audit_buffer *ab,
|
extern void audit_log_d_path(struct audit_buffer *ab,
|
||||||
const char *prefix,
|
const char *prefix,
|
||||||
struct dentry *dentry,
|
struct path *path);
|
||||||
struct vfsmount *vfsmnt);
|
|
||||||
extern void audit_log_lost(const char *message);
|
extern void audit_log_lost(const char *message);
|
||||||
/* Private API (for audit.c only) */
|
/* Private API (for audit.c only) */
|
||||||
extern int audit_filter_user(struct netlink_skb_parms *cb, int type);
|
extern int audit_filter_user(struct netlink_skb_parms *cb, int type);
|
||||||
|
@ -552,7 +551,7 @@ extern int audit_enabled;
|
||||||
#define audit_log_hex(a,b,l) do { ; } while (0)
|
#define audit_log_hex(a,b,l) do { ; } while (0)
|
||||||
#define audit_log_untrustedstring(a,s) do { ; } while (0)
|
#define audit_log_untrustedstring(a,s) do { ; } while (0)
|
||||||
#define audit_log_n_untrustedstring(a,n,s) do { ; } while (0)
|
#define audit_log_n_untrustedstring(a,n,s) do { ; } while (0)
|
||||||
#define audit_log_d_path(b,p,d,v) do { ; } while (0)
|
#define audit_log_d_path(b, p, d) do { ; } while (0)
|
||||||
#define audit_enabled 0
|
#define audit_enabled 0
|
||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -1312,26 +1312,26 @@ void audit_log_untrustedstring(struct audit_buffer *ab, const char *string)
|
||||||
|
|
||||||
/* This is a helper-function to print the escaped d_path */
|
/* This is a helper-function to print the escaped d_path */
|
||||||
void audit_log_d_path(struct audit_buffer *ab, const char *prefix,
|
void audit_log_d_path(struct audit_buffer *ab, const char *prefix,
|
||||||
struct dentry *dentry, struct vfsmount *vfsmnt)
|
struct path *path)
|
||||||
{
|
{
|
||||||
char *p, *path;
|
char *p, *pathname;
|
||||||
|
|
||||||
if (prefix)
|
if (prefix)
|
||||||
audit_log_format(ab, " %s", prefix);
|
audit_log_format(ab, " %s", prefix);
|
||||||
|
|
||||||
/* We will allow 11 spaces for ' (deleted)' to be appended */
|
/* We will allow 11 spaces for ' (deleted)' to be appended */
|
||||||
path = kmalloc(PATH_MAX+11, ab->gfp_mask);
|
pathname = kmalloc(PATH_MAX+11, ab->gfp_mask);
|
||||||
if (!path) {
|
if (!pathname) {
|
||||||
audit_log_format(ab, "<no memory>");
|
audit_log_format(ab, "<no memory>");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
p = d_path(dentry, vfsmnt, path, PATH_MAX+11);
|
p = d_path(path->dentry, path->mnt, pathname, PATH_MAX+11);
|
||||||
if (IS_ERR(p)) { /* Should never happen since we send PATH_MAX */
|
if (IS_ERR(p)) { /* Should never happen since we send PATH_MAX */
|
||||||
/* FIXME: can we save some information here? */
|
/* FIXME: can we save some information here? */
|
||||||
audit_log_format(ab, "<too long>");
|
audit_log_format(ab, "<too long>");
|
||||||
} else
|
} else
|
||||||
audit_log_untrustedstring(ab, p);
|
audit_log_untrustedstring(ab, p);
|
||||||
kfree(path);
|
kfree(pathname);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -208,8 +208,7 @@ struct audit_context {
|
||||||
int name_count;
|
int name_count;
|
||||||
struct audit_names names[AUDIT_NAMES];
|
struct audit_names names[AUDIT_NAMES];
|
||||||
char * filterkey; /* key for rule that triggered record */
|
char * filterkey; /* key for rule that triggered record */
|
||||||
struct dentry * pwd;
|
struct path pwd;
|
||||||
struct vfsmount * pwdmnt;
|
|
||||||
struct audit_context *previous; /* For nested syscalls */
|
struct audit_context *previous; /* For nested syscalls */
|
||||||
struct audit_aux_data *aux;
|
struct audit_aux_data *aux;
|
||||||
struct audit_aux_data *aux_pids;
|
struct audit_aux_data *aux_pids;
|
||||||
|
@ -786,12 +785,9 @@ static inline void audit_free_names(struct audit_context *context)
|
||||||
__putname(context->names[i].name);
|
__putname(context->names[i].name);
|
||||||
}
|
}
|
||||||
context->name_count = 0;
|
context->name_count = 0;
|
||||||
if (context->pwd)
|
path_put(&context->pwd);
|
||||||
dput(context->pwd);
|
context->pwd.dentry = NULL;
|
||||||
if (context->pwdmnt)
|
context->pwd.mnt = NULL;
|
||||||
mntput(context->pwdmnt);
|
|
||||||
context->pwd = NULL;
|
|
||||||
context->pwdmnt = NULL;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline void audit_free_aux(struct audit_context *context)
|
static inline void audit_free_aux(struct audit_context *context)
|
||||||
|
@ -930,8 +926,7 @@ static void audit_log_task_info(struct audit_buffer *ab, struct task_struct *tsk
|
||||||
if ((vma->vm_flags & VM_EXECUTABLE) &&
|
if ((vma->vm_flags & VM_EXECUTABLE) &&
|
||||||
vma->vm_file) {
|
vma->vm_file) {
|
||||||
audit_log_d_path(ab, "exe=",
|
audit_log_d_path(ab, "exe=",
|
||||||
vma->vm_file->f_path.dentry,
|
&vma->vm_file->f_path);
|
||||||
vma->vm_file->f_path.mnt);
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
vma = vma->vm_next;
|
vma = vma->vm_next;
|
||||||
|
@ -1341,10 +1336,10 @@ static void audit_log_exit(struct audit_context *context, struct task_struct *ts
|
||||||
context->target_sid, context->target_comm))
|
context->target_sid, context->target_comm))
|
||||||
call_panic = 1;
|
call_panic = 1;
|
||||||
|
|
||||||
if (context->pwd && context->pwdmnt) {
|
if (context->pwd.dentry && context->pwd.mnt) {
|
||||||
ab = audit_log_start(context, GFP_KERNEL, AUDIT_CWD);
|
ab = audit_log_start(context, GFP_KERNEL, AUDIT_CWD);
|
||||||
if (ab) {
|
if (ab) {
|
||||||
audit_log_d_path(ab, "cwd=", context->pwd, context->pwdmnt);
|
audit_log_d_path(ab, "cwd=", &context->pwd);
|
||||||
audit_log_end(ab);
|
audit_log_end(ab);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1367,8 +1362,7 @@ static void audit_log_exit(struct audit_context *context, struct task_struct *ts
|
||||||
case 0:
|
case 0:
|
||||||
/* name was specified as a relative path and the
|
/* name was specified as a relative path and the
|
||||||
* directory component is the cwd */
|
* directory component is the cwd */
|
||||||
audit_log_d_path(ab, " name=", context->pwd,
|
audit_log_d_path(ab, " name=", &context->pwd);
|
||||||
context->pwdmnt);
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
/* log the name's directory component */
|
/* log the name's directory component */
|
||||||
|
@ -1695,10 +1689,10 @@ void __audit_getname(const char *name)
|
||||||
context->names[context->name_count].ino = (unsigned long)-1;
|
context->names[context->name_count].ino = (unsigned long)-1;
|
||||||
context->names[context->name_count].osid = 0;
|
context->names[context->name_count].osid = 0;
|
||||||
++context->name_count;
|
++context->name_count;
|
||||||
if (!context->pwd) {
|
if (!context->pwd.dentry) {
|
||||||
read_lock(¤t->fs->lock);
|
read_lock(¤t->fs->lock);
|
||||||
context->pwd = dget(current->fs->pwd.dentry);
|
context->pwd = current->fs->pwd;
|
||||||
context->pwdmnt = mntget(current->fs->pwd.mnt);
|
path_get(¤t->fs->pwd);
|
||||||
read_unlock(¤t->fs->lock);
|
read_unlock(¤t->fs->lock);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -568,10 +568,11 @@ void avc_audit(u32 ssid, u32 tsid,
|
||||||
audit_log_format(ab, " capability=%d", a->u.cap);
|
audit_log_format(ab, " capability=%d", a->u.cap);
|
||||||
break;
|
break;
|
||||||
case AVC_AUDIT_DATA_FS:
|
case AVC_AUDIT_DATA_FS:
|
||||||
if (a->u.fs.dentry) {
|
if (a->u.fs.path.dentry) {
|
||||||
struct dentry *dentry = a->u.fs.dentry;
|
struct dentry *dentry = a->u.fs.path.dentry;
|
||||||
if (a->u.fs.mnt) {
|
if (a->u.fs.path.mnt) {
|
||||||
audit_log_d_path(ab, "path=", dentry, a->u.fs.mnt);
|
audit_log_d_path(ab, "path=",
|
||||||
|
&a->u.fs.path);
|
||||||
} else {
|
} else {
|
||||||
audit_log_format(ab, " name=");
|
audit_log_format(ab, " name=");
|
||||||
audit_log_untrustedstring(ab, dentry->d_name.name);
|
audit_log_untrustedstring(ab, dentry->d_name.name);
|
||||||
|
@ -626,8 +627,12 @@ void avc_audit(u32 ssid, u32 tsid,
|
||||||
case AF_UNIX:
|
case AF_UNIX:
|
||||||
u = unix_sk(sk);
|
u = unix_sk(sk);
|
||||||
if (u->dentry) {
|
if (u->dentry) {
|
||||||
|
struct path path = {
|
||||||
|
.dentry = u->dentry,
|
||||||
|
.mnt = u->mnt
|
||||||
|
};
|
||||||
audit_log_d_path(ab, "path=",
|
audit_log_d_path(ab, "path=",
|
||||||
u->dentry, u->mnt);
|
&path);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
if (!u->addr)
|
if (!u->addr)
|
||||||
|
|
|
@ -1356,8 +1356,8 @@ static inline int dentry_has_perm(struct task_struct *tsk,
|
||||||
struct inode *inode = dentry->d_inode;
|
struct inode *inode = dentry->d_inode;
|
||||||
struct avc_audit_data ad;
|
struct avc_audit_data ad;
|
||||||
AVC_AUDIT_DATA_INIT(&ad,FS);
|
AVC_AUDIT_DATA_INIT(&ad,FS);
|
||||||
ad.u.fs.mnt = mnt;
|
ad.u.fs.path.mnt = mnt;
|
||||||
ad.u.fs.dentry = dentry;
|
ad.u.fs.path.dentry = dentry;
|
||||||
return inode_has_perm(tsk, inode, av, &ad);
|
return inode_has_perm(tsk, inode, av, &ad);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1375,15 +1375,12 @@ static int file_has_perm(struct task_struct *tsk,
|
||||||
{
|
{
|
||||||
struct task_security_struct *tsec = tsk->security;
|
struct task_security_struct *tsec = tsk->security;
|
||||||
struct file_security_struct *fsec = file->f_security;
|
struct file_security_struct *fsec = file->f_security;
|
||||||
struct vfsmount *mnt = file->f_path.mnt;
|
struct inode *inode = file->f_path.dentry->d_inode;
|
||||||
struct dentry *dentry = file->f_path.dentry;
|
|
||||||
struct inode *inode = dentry->d_inode;
|
|
||||||
struct avc_audit_data ad;
|
struct avc_audit_data ad;
|
||||||
int rc;
|
int rc;
|
||||||
|
|
||||||
AVC_AUDIT_DATA_INIT(&ad, FS);
|
AVC_AUDIT_DATA_INIT(&ad, FS);
|
||||||
ad.u.fs.mnt = mnt;
|
ad.u.fs.path = file->f_path;
|
||||||
ad.u.fs.dentry = dentry;
|
|
||||||
|
|
||||||
if (tsec->sid != fsec->sid) {
|
if (tsec->sid != fsec->sid) {
|
||||||
rc = avc_has_perm(tsec->sid, fsec->sid,
|
rc = avc_has_perm(tsec->sid, fsec->sid,
|
||||||
|
@ -1418,7 +1415,7 @@ static int may_create(struct inode *dir,
|
||||||
sbsec = dir->i_sb->s_security;
|
sbsec = dir->i_sb->s_security;
|
||||||
|
|
||||||
AVC_AUDIT_DATA_INIT(&ad, FS);
|
AVC_AUDIT_DATA_INIT(&ad, FS);
|
||||||
ad.u.fs.dentry = dentry;
|
ad.u.fs.path.dentry = dentry;
|
||||||
|
|
||||||
rc = avc_has_perm(tsec->sid, dsec->sid, SECCLASS_DIR,
|
rc = avc_has_perm(tsec->sid, dsec->sid, SECCLASS_DIR,
|
||||||
DIR__ADD_NAME | DIR__SEARCH,
|
DIR__ADD_NAME | DIR__SEARCH,
|
||||||
|
@ -1476,7 +1473,7 @@ static int may_link(struct inode *dir,
|
||||||
isec = dentry->d_inode->i_security;
|
isec = dentry->d_inode->i_security;
|
||||||
|
|
||||||
AVC_AUDIT_DATA_INIT(&ad, FS);
|
AVC_AUDIT_DATA_INIT(&ad, FS);
|
||||||
ad.u.fs.dentry = dentry;
|
ad.u.fs.path.dentry = dentry;
|
||||||
|
|
||||||
av = DIR__SEARCH;
|
av = DIR__SEARCH;
|
||||||
av |= (kind ? DIR__REMOVE_NAME : DIR__ADD_NAME);
|
av |= (kind ? DIR__REMOVE_NAME : DIR__ADD_NAME);
|
||||||
|
@ -1523,7 +1520,7 @@ static inline int may_rename(struct inode *old_dir,
|
||||||
|
|
||||||
AVC_AUDIT_DATA_INIT(&ad, FS);
|
AVC_AUDIT_DATA_INIT(&ad, FS);
|
||||||
|
|
||||||
ad.u.fs.dentry = old_dentry;
|
ad.u.fs.path.dentry = old_dentry;
|
||||||
rc = avc_has_perm(tsec->sid, old_dsec->sid, SECCLASS_DIR,
|
rc = avc_has_perm(tsec->sid, old_dsec->sid, SECCLASS_DIR,
|
||||||
DIR__REMOVE_NAME | DIR__SEARCH, &ad);
|
DIR__REMOVE_NAME | DIR__SEARCH, &ad);
|
||||||
if (rc)
|
if (rc)
|
||||||
|
@ -1539,7 +1536,7 @@ static inline int may_rename(struct inode *old_dir,
|
||||||
return rc;
|
return rc;
|
||||||
}
|
}
|
||||||
|
|
||||||
ad.u.fs.dentry = new_dentry;
|
ad.u.fs.path.dentry = new_dentry;
|
||||||
av = DIR__ADD_NAME | DIR__SEARCH;
|
av = DIR__ADD_NAME | DIR__SEARCH;
|
||||||
if (new_dentry->d_inode)
|
if (new_dentry->d_inode)
|
||||||
av |= DIR__REMOVE_NAME;
|
av |= DIR__REMOVE_NAME;
|
||||||
|
@ -1918,8 +1915,7 @@ static int selinux_bprm_set_security(struct linux_binprm *bprm)
|
||||||
}
|
}
|
||||||
|
|
||||||
AVC_AUDIT_DATA_INIT(&ad, FS);
|
AVC_AUDIT_DATA_INIT(&ad, FS);
|
||||||
ad.u.fs.mnt = bprm->file->f_path.mnt;
|
ad.u.fs.path = bprm->file->f_path;
|
||||||
ad.u.fs.dentry = bprm->file->f_path.dentry;
|
|
||||||
|
|
||||||
if (bprm->file->f_path.mnt->mnt_flags & MNT_NOSUID)
|
if (bprm->file->f_path.mnt->mnt_flags & MNT_NOSUID)
|
||||||
newsid = tsec->sid;
|
newsid = tsec->sid;
|
||||||
|
@ -2315,7 +2311,7 @@ static int selinux_sb_kern_mount(struct super_block *sb, void *data)
|
||||||
return rc;
|
return rc;
|
||||||
|
|
||||||
AVC_AUDIT_DATA_INIT(&ad,FS);
|
AVC_AUDIT_DATA_INIT(&ad,FS);
|
||||||
ad.u.fs.dentry = sb->s_root;
|
ad.u.fs.path.dentry = sb->s_root;
|
||||||
return superblock_has_perm(current, sb, FILESYSTEM__MOUNT, &ad);
|
return superblock_has_perm(current, sb, FILESYSTEM__MOUNT, &ad);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2324,7 +2320,7 @@ static int selinux_sb_statfs(struct dentry *dentry)
|
||||||
struct avc_audit_data ad;
|
struct avc_audit_data ad;
|
||||||
|
|
||||||
AVC_AUDIT_DATA_INIT(&ad,FS);
|
AVC_AUDIT_DATA_INIT(&ad,FS);
|
||||||
ad.u.fs.dentry = dentry->d_sb->s_root;
|
ad.u.fs.path.dentry = dentry->d_sb->s_root;
|
||||||
return superblock_has_perm(current, dentry->d_sb, FILESYSTEM__GETATTR, &ad);
|
return superblock_has_perm(current, dentry->d_sb, FILESYSTEM__GETATTR, &ad);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2587,7 +2583,7 @@ static int selinux_inode_setxattr(struct dentry *dentry, char *name, void *value
|
||||||
return -EPERM;
|
return -EPERM;
|
||||||
|
|
||||||
AVC_AUDIT_DATA_INIT(&ad,FS);
|
AVC_AUDIT_DATA_INIT(&ad,FS);
|
||||||
ad.u.fs.dentry = dentry;
|
ad.u.fs.path.dentry = dentry;
|
||||||
|
|
||||||
rc = avc_has_perm(tsec->sid, isec->sid, isec->sclass,
|
rc = avc_has_perm(tsec->sid, isec->sid, isec->sclass,
|
||||||
FILE__RELABELFROM, &ad);
|
FILE__RELABELFROM, &ad);
|
||||||
|
|
|
@ -13,6 +13,7 @@
|
||||||
#include <linux/spinlock.h>
|
#include <linux/spinlock.h>
|
||||||
#include <linux/init.h>
|
#include <linux/init.h>
|
||||||
#include <linux/in6.h>
|
#include <linux/in6.h>
|
||||||
|
#include <linux/path.h>
|
||||||
#include <asm/system.h>
|
#include <asm/system.h>
|
||||||
#include "flask.h"
|
#include "flask.h"
|
||||||
#include "av_permissions.h"
|
#include "av_permissions.h"
|
||||||
|
@ -30,8 +31,6 @@ extern int selinux_enforcing;
|
||||||
struct avc_entry;
|
struct avc_entry;
|
||||||
|
|
||||||
struct task_struct;
|
struct task_struct;
|
||||||
struct vfsmount;
|
|
||||||
struct dentry;
|
|
||||||
struct inode;
|
struct inode;
|
||||||
struct sock;
|
struct sock;
|
||||||
struct sk_buff;
|
struct sk_buff;
|
||||||
|
@ -46,8 +45,7 @@ struct avc_audit_data {
|
||||||
struct task_struct *tsk;
|
struct task_struct *tsk;
|
||||||
union {
|
union {
|
||||||
struct {
|
struct {
|
||||||
struct vfsmount *mnt;
|
struct path path;
|
||||||
struct dentry *dentry;
|
|
||||||
struct inode *inode;
|
struct inode *inode;
|
||||||
} fs;
|
} fs;
|
||||||
struct {
|
struct {
|
||||||
|
|
Loading…
Reference in New Issue