diff -u --recursive --new-file linux-2.5.33-vfs2/drivers/block/floppy.c linux-2.5.33-vfs3/drivers/block/floppy.c --- linux-2.5.33-vfs2/drivers/block/floppy.c Tue Sep 3 21:08:16 2002 +++ linux-2.5.33-vfs3/drivers/block/floppy.c Sun Sep 8 23:01:12 2002 @@ -3786,7 +3786,7 @@ * Needed so that programs such as fdrawcmd still can work on write * protected disks */ if ((filp->f_mode & 2) || - (inode->i_sb && (permission(inode,2) == 0))) + (inode->i_sb && (permission(filp->f_cred, inode,2) == 0))) filp->private_data = (void*) 8; if (UFDCS->rawcmd == 1) diff -u --recursive --new-file linux-2.5.33-vfs2/fs/coda/dir.c linux-2.5.33-vfs3/fs/coda/dir.c --- linux-2.5.33-vfs2/fs/coda/dir.c Mon Jun 17 18:34:09 2002 +++ linux-2.5.33-vfs3/fs/coda/dir.c Sun Sep 8 23:01:12 2002 @@ -145,7 +145,7 @@ } -int coda_permission(struct inode *inode, int mask) +int coda_permission(struct vfs_cred *vfscred, struct inode *inode, int mask) { int error = 0; diff -u --recursive --new-file linux-2.5.33-vfs2/fs/coda/pioctl.c linux-2.5.33-vfs3/fs/coda/pioctl.c --- linux-2.5.33-vfs2/fs/coda/pioctl.c Wed May 22 18:24:07 2002 +++ linux-2.5.33-vfs3/fs/coda/pioctl.c Sun Sep 8 23:01:12 2002 @@ -25,7 +25,7 @@ #include /* pioctl ops */ -static int coda_ioctl_permission(struct inode *inode, int mask); +static int coda_ioctl_permission(struct vfs_cred *, struct inode *inode, int mask); static int coda_pioctl(struct inode * inode, struct file * filp, unsigned int cmd, unsigned long user_data); @@ -42,7 +42,7 @@ }; /* the coda pioctl inode ops */ -static int coda_ioctl_permission(struct inode *inode, int mask) +static int coda_ioctl_permission(struct vfs_cred *vfscred, struct inode *inode, int mask) { return 0; } diff -u --recursive --new-file linux-2.5.33-vfs2/fs/exec.c linux-2.5.33-vfs3/fs/exec.c --- linux-2.5.33-vfs2/fs/exec.c Sun Sep 8 20:17:35 2002 +++ linux-2.5.33-vfs3/fs/exec.c Sun Sep 8 23:01:12 2002 @@ -119,7 +119,7 @@ if (!S_ISREG(nd.dentry->d_inode->i_mode)) goto exit; - error = permission(nd.dentry->d_inode, MAY_READ | MAY_EXEC); + error = permission(nd.vfscred, nd.dentry->d_inode, MAY_READ | MAY_EXEC); if (error) goto exit; @@ -427,7 +427,7 @@ file = ERR_PTR(-EACCES); if (!(nd.mnt->mnt_flags & MNT_NOEXEC) && S_ISREG(inode->i_mode)) { - int err = permission(inode, MAY_EXEC); + int err = permission(nd.vfscred, inode, MAY_EXEC); if (!err && !(inode->i_mode & 0111)) err = -EACCES; file = ERR_PTR(err); @@ -655,7 +655,7 @@ de_thread(current); if (bprm->e_uid != current->euid || bprm->e_gid != current->egid || - permission(bprm->file->f_dentry->d_inode,MAY_READ)) + permission(NULL, bprm->file->f_dentry->d_inode,MAY_READ)) current->mm->dumpable = 0; /* An exec changes our domain. We are no longer part of the thread diff -u --recursive --new-file linux-2.5.33-vfs2/fs/intermezzo/dir.c linux-2.5.33-vfs3/fs/intermezzo/dir.c --- linux-2.5.33-vfs2/fs/intermezzo/dir.c Mon Jun 17 18:34:09 2002 +++ linux-2.5.33-vfs3/fs/intermezzo/dir.c Sun Sep 8 23:01:12 2002 @@ -69,7 +69,7 @@ /* * these are initialized in super.c */ -extern int presto_permission(struct inode *inode, int mask); +extern int presto_permission(struct vfs_cred *vfscred, struct inode *inode, int mask); int presto_ilookup_uid = 0; extern int presto_prep(struct dentry *, struct presto_cache **, @@ -781,7 +781,7 @@ * appropriate permission function. Thus we do not worry here about ACLs * or EAs. -SHP */ -int presto_permission(struct inode *inode, int mask) +int presto_permission(struct vfs_cred *vfscred, struct inode *inode, int mask) { unsigned short mode = inode->i_mode; struct presto_cache *cache; @@ -815,7 +815,7 @@ } } - rc = vfs_permission(inode, mask); + rc = vfs_permission(vfscred, inode, mask); EXIT; diff -u --recursive --new-file linux-2.5.33-vfs2/fs/intermezzo/file.c linux-2.5.33-vfs3/fs/intermezzo/file.c --- linux-2.5.33-vfs2/fs/intermezzo/file.c Sun Sep 8 20:05:44 2002 +++ linux-2.5.33-vfs3/fs/intermezzo/file.c Sun Sep 8 23:01:12 2002 @@ -45,7 +45,7 @@ /* * these are initialized in super.c */ -extern int presto_permission(struct inode *inode, int mask); +extern int presto_permission(struct vfs_cred *, struct inode *inode, int mask); extern int presto_opendir_upcall(int minor, struct dentry *de, int async); extern int presto_prep(struct dentry *, struct presto_cache **, diff -u --recursive --new-file linux-2.5.33-vfs2/fs/namei.c linux-2.5.33-vfs3/fs/namei.c --- linux-2.5.33-vfs2/fs/namei.c Sun Sep 8 20:17:35 2002 +++ linux-2.5.33-vfs3/fs/namei.c Sun Sep 8 23:01:12 2002 @@ -155,7 +155,7 @@ * for filesystem access without changing the "normal" uids which * are used for other things.. */ -int vfs_permission(struct inode * inode, int mask) +int vfs_permission(struct vfs_cred *vfscred, struct inode * inode, int mask) { umode_t mode = inode->i_mode; @@ -173,10 +173,13 @@ if (IS_IMMUTABLE(inode)) return -EACCES; } + /* FIXME: this hack *must* go before we do CLONE_CRED... */ + if (!vfscred) + vfscred = current->vfscred; - if (current->vfscred->uid == inode->i_uid) + if (vfscred->uid == inode->i_uid) mode >>= 6; - else if (in_group_p(inode->i_gid)) + else if (vfscred->gid == inode->i_gid && vfscred_match_group(vfscred, inode->i_gid)) mode >>= 3; /* @@ -203,7 +206,7 @@ return -EACCES; } -int permission(struct inode * inode,int mask) +int permission(struct vfs_cred *vfscred, struct inode * inode,int mask) { int retval; int submask; @@ -212,13 +215,13 @@ submask = mask & ~MAY_APPEND; if (inode->i_op && inode->i_op->permission) - retval = inode->i_op->permission(inode, submask); + retval = inode->i_op->permission(vfscred, inode, submask); else - retval = vfs_permission(inode, submask); + retval = vfs_permission(vfscred, inode, submask); if (retval) return retval; - return security_ops->inode_permission(inode, mask); + return security_ops->inode_permission(vfscred, inode, mask); } /* @@ -318,16 +321,16 @@ * short-cut DAC fails, then call permission() to do more * complete permission check. */ -static inline int exec_permission_lite(struct inode *inode) +static inline int exec_permission_lite(struct vfs_cred *vfscred, struct inode *inode) { umode_t mode = inode->i_mode; if ((inode->i_op && inode->i_op->permission)) return -EAGAIN; - if (current->vfscred->uid == inode->i_uid) + if (vfscred->uid == inode->i_uid) mode >>= 6; - else if (in_group_p(inode->i_gid)) + else if (vfscred->gid == inode->i_gid || vfscred_match_group(vfscred, inode->i_gid)) mode >>= 3; if (mode & MAY_EXEC) @@ -341,7 +344,7 @@ return -EACCES; ok: - return security_ops->inode_permission_lite(inode, MAY_EXEC); + return security_ops->inode_permission_lite(vfscred, inode, MAY_EXEC); } /* @@ -594,10 +597,10 @@ struct qstr this; unsigned int c; - err = exec_permission_lite(inode); + err = exec_permission_lite(nd->vfscred, inode); if (err == -EAGAIN) { unlock_nd(nd); - err = permission(inode, MAY_EXEC); + err = permission(nd->vfscred, inode, MAY_EXEC); lock_nd(nd); } if (err) @@ -895,7 +898,7 @@ int err; inode = base->d_inode; - err = permission(inode, MAY_EXEC); + err = permission(NULL, inode, MAY_EXEC); dentry = ERR_PTR(err); if (err) goto out; @@ -1009,12 +1012,12 @@ * 8. If we were asked to remove a non-directory and victim isn't one - EISDIR. * 9. We can't remove a root or mountpoint. */ -static inline int may_delete(struct inode *dir,struct dentry *victim, int isdir) +static inline int may_delete(struct vfs_cred *vfscred, struct inode *dir,struct dentry *victim, int isdir) { int error; if (!victim->d_inode || victim->d_parent->d_inode != dir) return -ENOENT; - error = permission(dir,MAY_WRITE | MAY_EXEC); + error = permission(vfscred, dir,MAY_WRITE | MAY_EXEC); if (error) return error; if (IS_APPEND(dir)) @@ -1042,12 +1045,12 @@ * 3. We should have write and exec permissions on dir * 4. We can't do it if dir is immutable (done in permission()) */ -static inline int may_create(struct inode *dir, struct dentry *child) { +static inline int may_create(struct vfs_cred *vfscred, struct inode *dir, struct dentry *child) { if (child->d_inode) return -EEXIST; if (IS_DEADDIR(dir)) return -ENOENT; - return permission(dir,MAY_WRITE | MAY_EXEC); + return permission(vfscred, dir,MAY_WRITE | MAY_EXEC); } /* @@ -1118,7 +1121,7 @@ int vfs_create(struct inode *dir, struct dentry *dentry, int mode) { - int error = may_create(dir, dentry); + int error = may_create(NULL, dir, dentry); if (error) return error; @@ -1154,7 +1157,7 @@ if (S_ISDIR(inode->i_mode) && (flag & FMODE_WRITE)) return -EISDIR; - error = permission(inode, acc_mode); + error = permission(nd->vfscred, inode, acc_mode); if (error) return error; @@ -1401,7 +1404,7 @@ int vfs_mknod(struct inode *dir, struct dentry *dentry, int mode, dev_t dev) { - int error = may_create(dir, dentry); + int error = may_create(NULL, dir, dentry); if (error) return error; @@ -1471,7 +1474,7 @@ int vfs_mkdir(struct inode *dir, struct dentry *dentry, int mode) { - int error = may_create(dir, dentry); + int error = may_create(NULL, dir, dentry); if (error) return error; @@ -1557,7 +1560,7 @@ int vfs_rmdir(struct inode *dir, struct dentry *dentry) { - int error = may_delete(dir, dentry, 1); + int error = may_delete(NULL, dir, dentry, 1); if (error) return error; @@ -1632,7 +1635,7 @@ int vfs_unlink(struct inode *dir, struct dentry *dentry) { - int error = may_delete(dir, dentry, 0); + int error = may_delete(NULL, dir, dentry, 0); if (error) return error; @@ -1703,7 +1706,7 @@ int vfs_symlink(struct inode *dir, struct dentry *dentry, const char *oldname) { - int error = may_create(dir, dentry); + int error = may_create(NULL, dir, dentry); if (error) return error; @@ -1765,7 +1768,7 @@ if (!inode) return -ENOENT; - error = may_create(dir, new_dentry); + error = may_create(NULL, dir, new_dentry); if (error) return error; @@ -1886,7 +1889,7 @@ * we'll need to flip '..'. */ if (new_dir != old_dir) { - error = permission(old_dentry->d_inode, MAY_WRITE); + error = permission(NULL, old_dentry->d_inode, MAY_WRITE); if (error) return error; } @@ -1959,14 +1962,14 @@ if (old_dentry->d_inode == new_dentry->d_inode) return 0; - error = may_delete(old_dir, old_dentry, is_dir); + error = may_delete(NULL, old_dir, old_dentry, is_dir); if (error) return error; if (!new_dentry->d_inode) - error = may_create(new_dir, new_dentry); + error = may_create(NULL, new_dir, new_dentry); else - error = may_delete(new_dir, new_dentry, is_dir); + error = may_delete(NULL, new_dir, new_dentry, is_dir); if (error) return error; diff -u --recursive --new-file linux-2.5.33-vfs2/fs/namespace.c linux-2.5.33-vfs3/fs/namespace.c --- linux-2.5.33-vfs2/fs/namespace.c Mon Jul 22 12:12:48 2002 +++ linux-2.5.33-vfs3/fs/namespace.c Sun Sep 8 23:01:12 2002 @@ -411,7 +411,7 @@ if (current->uid != nd->dentry->d_inode->i_uid) return -EPERM; } - if (permission(nd->dentry->d_inode, MAY_WRITE)) + if (permission(nd->vfscred, nd->dentry->d_inode, MAY_WRITE)) return -EPERM; return 0; #endif diff -u --recursive --new-file linux-2.5.33-vfs2/fs/nfs/dir.c linux-2.5.33-vfs3/fs/nfs/dir.c --- linux-2.5.33-vfs2/fs/nfs/dir.c Sun Sep 8 20:15:26 2002 +++ linux-2.5.33-vfs3/fs/nfs/dir.c Sun Sep 8 23:01:12 2002 @@ -1209,10 +1209,9 @@ } int -nfs_permission(struct inode *inode, int mask) +nfs_permission(struct vfs_cred *vfscred, struct inode *inode, int mask) { struct nfs_access_cache *cache = &NFS_I(inode)->cache_access; - struct vfs_cred *vfscred; struct rpc_cred *cred; int mode = inode->i_mode; int res; @@ -1241,9 +1240,7 @@ if (!NFS_PROTO(inode)->access) goto out_notsup; - vfscred = get_current_vfscred(); cred = rpcauth_lookupcred(vfscred, NFS_CLIENT(inode)->cl_auth, 0); - put_vfscred(vfscred); if (cache->cred == cred && time_before(jiffies, cache->jiffies + NFS_ATTRTIMEO(inode))) { if (!(res = cache->err)) { @@ -1266,7 +1263,7 @@ return res; out_notsup: nfs_revalidate_inode(NFS_SERVER(inode), inode); - res = vfs_permission(inode, mask); + res = vfs_permission(vfscred, inode, mask); unlock_kernel(); return res; add_cache: diff -u --recursive --new-file linux-2.5.33-vfs2/fs/open.c linux-2.5.33-vfs3/fs/open.c --- linux-2.5.33-vfs2/fs/open.c Sun Sep 8 20:17:35 2002 +++ linux-2.5.33-vfs3/fs/open.c Sun Sep 8 23:01:12 2002 @@ -116,7 +116,7 @@ if (!S_ISREG(inode->i_mode)) goto dput_and_out; - error = permission(inode,MAY_WRITE); + error = permission(nd.vfscred, inode,MAY_WRITE); if (error) goto dput_and_out; @@ -260,7 +260,7 @@ newattrs.ia_valid |= ATTR_ATIME_SET | ATTR_MTIME_SET; } else { if (current->vfscred->uid != inode->i_uid && - (error = permission(inode,MAY_WRITE)) != 0) + (error = permission(nd.vfscred, inode,MAY_WRITE)) != 0) goto dput_and_out; } down(&inode->i_sem); @@ -307,7 +307,7 @@ newattrs.ia_valid |= ATTR_ATIME_SET | ATTR_MTIME_SET; } else { if (current->vfscred->uid != inode->i_uid && - (error = permission(inode,MAY_WRITE)) != 0) + (error = permission(nd.vfscred, inode,MAY_WRITE)) != 0) goto dput_and_out; } down(&inode->i_sem); @@ -355,7 +355,7 @@ res = user_path_walk(filename, &nd); if (!res) { - res = permission(nd.dentry->d_inode, mode); + res = permission(nd.vfscred, nd.dentry->d_inode, mode); /* SuS v2 requires we report a read only fs too */ if(!res && (mode & S_IWOTH) && IS_RDONLY(nd.dentry->d_inode) && !special_file(nd.dentry->d_inode->i_mode)) @@ -379,7 +379,7 @@ if (error) goto out; - error = permission(nd.dentry->d_inode,MAY_EXEC); + error = permission(nd.vfscred, nd.dentry->d_inode,MAY_EXEC); if (error) goto dput_and_out; @@ -412,7 +412,7 @@ if (!S_ISDIR(inode->i_mode)) goto out_putf; - error = permission(inode, MAY_EXEC); + error = permission(NULL, inode, MAY_EXEC); if (!error) set_fs_pwd(current->fs, mnt, dentry); out_putf: @@ -430,7 +430,7 @@ if (error) goto out; - error = permission(nd.dentry->d_inode,MAY_EXEC); + error = permission(nd.vfscred, nd.dentry->d_inode,MAY_EXEC); if (error) goto dput_and_out; diff -u --recursive --new-file linux-2.5.33-vfs2/fs/proc/base.c linux-2.5.33-vfs3/fs/proc/base.c --- linux-2.5.33-vfs2/fs/proc/base.c Sun Sep 8 20:05:45 2002 +++ linux-2.5.33-vfs3/fs/proc/base.c Sun Sep 8 23:01:12 2002 @@ -291,9 +291,9 @@ goto exit; } -static int proc_permission(struct inode *inode, int mask) +static int proc_permission(struct vfs_cred *vfscred, struct inode *inode, int mask) { - if (vfs_permission(inode, mask) != 0) + if (vfs_permission(vfscred, inode, mask) != 0) return -EACCES; return proc_check_root(inode); } diff -u --recursive --new-file linux-2.5.33-vfs2/fs/smbfs/file.c linux-2.5.33-vfs3/fs/smbfs/file.c --- linux-2.5.33-vfs2/fs/smbfs/file.c Sun Sep 8 22:56:16 2002 +++ linux-2.5.33-vfs3/fs/smbfs/file.c Sun Sep 8 23:01:12 2002 @@ -363,7 +363,7 @@ * privileges, so we need our own check for this. */ static int -smb_file_permission(struct inode *inode, int mask) +smb_file_permission(struct vfs_cred *vfscred, struct inode *inode, int mask) { int mode = inode->i_mode; int error = 0; diff -u --recursive --new-file linux-2.5.33-vfs2/include/linux/coda_linux.h linux-2.5.33-vfs3/include/linux/coda_linux.h --- linux-2.5.33-vfs2/include/linux/coda_linux.h Wed May 22 14:30:46 2002 +++ linux-2.5.33-vfs3/include/linux/coda_linux.h Sun Sep 8 23:01:12 2002 @@ -38,7 +38,7 @@ int coda_open(struct inode *i, struct file *f); int coda_flush(struct file *f); int coda_release(struct inode *i, struct file *f); -int coda_permission(struct inode *inode, int mask); +int coda_permission(struct vfs_cred *, struct inode *inode, int mask); int coda_revalidate_inode(struct dentry *); int coda_getattr(struct vfsmount *, struct dentry *, struct kstat *); int coda_setattr(struct dentry *, struct iattr *); diff -u --recursive --new-file linux-2.5.33-vfs2/include/linux/fs.h linux-2.5.33-vfs3/include/linux/fs.h --- linux-2.5.33-vfs2/include/linux/fs.h Sun Sep 8 22:56:16 2002 +++ linux-2.5.33-vfs3/include/linux/fs.h Sun Sep 8 23:01:12 2002 @@ -786,7 +786,7 @@ int (*readlink) (struct dentry *, char *,int); int (*follow_link) (struct dentry *, struct nameidata *); void (*truncate) (struct inode *); - int (*permission) (struct inode *, int); + int (*permission) (struct vfs_cred *, struct inode *, int); int (*setattr) (struct dentry *, struct iattr *); int (*getattr) (struct vfsmount *mnt, struct dentry *, struct kstat *); int (*setxattr) (struct dentry *, const char *, void *, size_t, int); @@ -1150,8 +1150,8 @@ extern void sync_supers(void); extern int bmap(struct inode *, int); extern int notify_change(struct dentry *, struct iattr *); -extern int permission(struct inode *, int); -extern int vfs_permission(struct inode *, int); +extern int permission(struct vfs_cred *, struct inode *, int); +extern int vfs_permission(struct vfs_cred *, struct inode *, int); extern int get_write_access(struct inode *); extern int deny_write_access(struct file *); static inline void put_write_access(struct inode * inode) diff -u --recursive --new-file linux-2.5.33-vfs2/include/linux/nfs_fs.h linux-2.5.33-vfs3/include/linux/nfs_fs.h --- linux-2.5.33-vfs2/include/linux/nfs_fs.h Sun Sep 8 22:56:16 2002 +++ linux-2.5.33-vfs3/include/linux/nfs_fs.h Sun Sep 8 23:01:12 2002 @@ -257,7 +257,7 @@ struct nfs_fattr *); extern int __nfs_refresh_inode(struct inode *, struct nfs_fattr *); extern int nfs_getattr(struct vfsmount *, struct dentry *, struct kstat *); -extern int nfs_permission(struct inode *, int); +extern int nfs_permission(struct vfs_cred *, struct inode *, int); extern int nfs_open(struct inode *, struct file *); extern int nfs_release(struct inode *, struct file *); extern int __nfs_revalidate_inode(struct nfs_server *, struct inode *); diff -u --recursive --new-file linux-2.5.33-vfs2/include/linux/security.h linux-2.5.33-vfs3/include/linux/security.h --- linux-2.5.33-vfs2/include/linux/security.h Sat Jul 27 23:20:16 2002 +++ linux-2.5.33-vfs3/include/linux/security.h Sun Sep 8 23:01:12 2002 @@ -731,8 +731,8 @@ struct dentry *new_dentry); int (*inode_readlink) (struct dentry *dentry); int (*inode_follow_link) (struct dentry *dentry, struct nameidata *nd); - int (*inode_permission) (struct inode *inode, int mask); - int (*inode_permission_lite) (struct inode *inode, int mask); + int (*inode_permission) (struct vfs_cred *, struct inode *inode, int mask); + int (*inode_permission_lite) (struct vfs_cred *, struct inode *inode, int mask); int (*inode_setattr) (struct dentry *dentry, struct iattr *attr); int (*inode_getattr) (struct vfsmount *mnt, struct dentry *dentry); void (*inode_post_lookup) (struct inode *inode, struct dentry *d); diff -u --recursive --new-file linux-2.5.33-vfs2/net/unix/af_unix.c linux-2.5.33-vfs3/net/unix/af_unix.c --- linux-2.5.33-vfs2/net/unix/af_unix.c Sat Aug 24 13:27:51 2002 +++ linux-2.5.33-vfs3/net/unix/af_unix.c Sun Sep 8 23:01:12 2002 @@ -607,7 +607,7 @@ err = path_lookup(sunname->sun_path, LOOKUP_FOLLOW, &nd); if (err) goto fail; - err = permission(nd.dentry->d_inode,MAY_WRITE); + err = permission(nd.vfscred, nd.dentry->d_inode,MAY_WRITE); if (err) goto put_fail; diff -u --recursive --new-file linux-2.5.33-vfs2/security/capability.c linux-2.5.33-vfs3/security/capability.c --- linux-2.5.33-vfs2/security/capability.c Sun Sep 8 20:05:45 2002 +++ linux-2.5.33-vfs3/security/capability.c Sun Sep 8 23:01:12 2002 @@ -376,12 +376,12 @@ return 0; } -static int cap_inode_permission (struct inode *inode, int mask) +static int cap_inode_permission (struct vfs_cred *vfscred, struct inode *inode, int mask) { return 0; } -static int cap_inode_permission_lite (struct inode *inode, int mask) +static int cap_inode_permission_lite (struct vfs_cred *vfscred, struct inode *inode, int mask) { return 0; } diff -u --recursive --new-file linux-2.5.33-vfs2/security/dummy.c linux-2.5.33-vfs3/security/dummy.c --- linux-2.5.33-vfs2/security/dummy.c Sun Sep 8 20:05:45 2002 +++ linux-2.5.33-vfs3/security/dummy.c Sun Sep 8 23:01:12 2002 @@ -278,12 +278,12 @@ return 0; } -static int dummy_inode_permission (struct inode *inode, int mask) +static int dummy_inode_permission (struct vfs_cred *vfscred, struct inode *inode, int mask) { return 0; } -static int dummy_inode_permission_lite (struct inode *inode, int mask) +static int dummy_inode_permission_lite (struct vfs_cred *vfscred, struct inode *inode, int mask) { return 0; }