diff options
author | phk <phk@FreeBSD.org> | 2002-09-05 20:28:24 +0000 |
---|---|---|
committer | phk <phk@FreeBSD.org> | 2002-09-05 20:28:24 +0000 |
commit | 80704cd6a8a2a0695b39f547e7db36b0cb9f7d6f (patch) | |
tree | e1db70630b4c787321650b25c78a37e763a3af71 /sys | |
parent | eadbc1f97fdb7cef5ffff5800d10c332dac6b4fd (diff) | |
download | FreeBSD-src-80704cd6a8a2a0695b39f547e7db36b0cb9f7d6f.zip FreeBSD-src-80704cd6a8a2a0695b39f547e7db36b0cb9f7d6f.tar.gz |
Fix credentials check: do not leak ENOATTR until we know if they're
supposed to know.
Sponsored by: DARPA & NAI Labs.
Diffstat (limited to 'sys')
-rw-r--r-- | sys/ufs/ufs/ufs_extattr.c | 27 |
1 files changed, 15 insertions, 12 deletions
diff --git a/sys/ufs/ufs/ufs_extattr.c b/sys/ufs/ufs/ufs_extattr.c index 49ab022..27e5812 100644 --- a/sys/ufs/ufs/ufs_extattr.c +++ b/sys/ufs/ufs/ufs_extattr.c @@ -79,7 +79,7 @@ SYSCTL_INT(_debug, OID_AUTO, ufs_extattr_sync, CTLFLAG_RW, &ufs_extattr_sync, static int ufs_extattr_valid_attrname(int attrnamespace, const char *attrname); static int ufs_extattr_credcheck(struct vnode *vp, - struct ufs_extattr_list_entry *uele, struct ucred *cred, + int attrnamespace, struct ucred *cred, struct thread *td, int access); static int ufs_extattr_enable_with_open(struct ufsmount *ump, struct vnode *vp, int attrnamespace, const char *attrname, @@ -793,7 +793,7 @@ ufs_extattrctl(struct mount *mp, int cmd, struct vnode *filename_vp, * permissions. */ static int -ufs_extattr_credcheck(struct vnode *vp, struct ufs_extattr_list_entry *uele, +ufs_extattr_credcheck(struct vnode *vp, int attrnamespace, struct ucred *cred, struct thread *td, int access) { @@ -810,7 +810,7 @@ ufs_extattr_credcheck(struct vnode *vp, struct ufs_extattr_list_entry *uele, * XXX What capability should apply here? * Probably CAP_SYS_SETFFLAG. */ - switch (uele->uele_attrnamespace) { + switch (attrnamespace) { case EXTATTR_NAMESPACE_SYSTEM: /* Potentially should be: return (EPERM); */ return (suser_cred(cred, 0)); @@ -880,13 +880,14 @@ ufs_extattr_get(struct vnode *vp, int attrnamespace, const char *name, return (EINVAL); } + error = ufs_extattr_credcheck(vp, attrnamespace, cred, td, IREAD); + if (error) + return (error); + attribute = ufs_extattr_find_attr(ump, attrnamespace, name); if (!attribute) return (ENOATTR); - if ((error = ufs_extattr_credcheck(vp, attribute, cred, td, IREAD))) - return (error); - /* * Allow only offsets of zero to encourage the read/replace * extended attribute semantic. Otherwise we can't guarantee @@ -1058,13 +1059,14 @@ ufs_extattr_set(struct vnode *vp, int attrnamespace, const char *name, if (!ufs_extattr_valid_attrname(attrnamespace, name)) return (EINVAL); + error = ufs_extattr_credcheck(vp, attrnamespace, cred, td, IWRITE); + if (error) + return (error); + attribute = ufs_extattr_find_attr(ump, attrnamespace, name); if (!attribute) return (ENOATTR); - if ((error = ufs_extattr_credcheck(vp, attribute, cred, td, IWRITE))) - return (error); - /* * Early rejection of invalid offsets/length. * Reject: any offset but 0 (replace) @@ -1169,13 +1171,14 @@ ufs_extattr_rm(struct vnode *vp, int attrnamespace, const char *name, if (!ufs_extattr_valid_attrname(attrnamespace, name)) return (EINVAL); + error = ufs_extattr_credcheck(vp, attrnamespace, cred, td, IWRITE); + if (error) + return (error); + attribute = ufs_extattr_find_attr(ump, attrnamespace, name); if (!attribute) return (ENOATTR); - if ((error = ufs_extattr_credcheck(vp, attribute, cred, td, IWRITE))) - return (error); - /* * Find base offset of header in file based on file header size, and * data header size + maximum data size, indexed by inode number. |