Skip to content

Commit

Permalink
when creating new inodes, use file_mode/dir_mode exclusively on mount…
Browse files Browse the repository at this point in the history
… without unix extensions

When CIFS creates a new inode on a mount without unix extensions, it
temporarily assigns the mode that was passed to it in the create/mkdir
call. Eventually, when the inode is revalidated, it changes to have the
file_mode or dir_mode for the mount. This is confusing to users who
expect that the mode shouldn't change this way. It's also problematic
since only the mode is treated this way, not the uid or gid. Suppose you
have a CIFS mount that's mounted with:

uid=0,gid=0,file_mode=0666,dir_mode=0777

...if an unprivileged user comes along and does this on the mount:

mkdir -m 0700 foo
touch foo/bar

...there is a period of time where the touch will fail, since the dir
will initially be owned by root and have mode 0700. If the user waits
long enough, then "foo" will be revalidated and will get the correct
dir_mode permissions.

This patch changes cifs_mkdir and cifs_create to not overwrite the
mode found by the initial cifs_get_inode_info call after the inode is
created on the server. Legacy behavior can be reenabled with the
new "dynperm" mount option.

Signed-off-by: Jeff Layton <jlayton@redhat.com>
Signed-off-by: Steve French <sfrench@us.ibm.com>
  • Loading branch information
Jeff Layton authored and Steve French committed May 23, 2008
1 parent 4468eb3 commit b0fd30d
Show file tree
Hide file tree
Showing 2 changed files with 8 additions and 3 deletions.
4 changes: 3 additions & 1 deletion fs/cifs/dir.c
Original file line number Diff line number Diff line change
Expand Up @@ -260,7 +260,9 @@ cifs_create(struct inode *inode, struct dentry *direntry, int mode,
buf, inode->i_sb, xid,
&fileHandle);
if (newinode) {
newinode->i_mode = mode;
if (cifs_sb->mnt_cifs_flags &
CIFS_MOUNT_DYNPERM)
newinode->i_mode = mode;
if ((oplock & CIFS_CREATE_ACTION) &&
(cifs_sb->mnt_cifs_flags &
CIFS_MOUNT_SET_UID)) {
Expand Down
7 changes: 5 additions & 2 deletions fs/cifs/inode.c
Original file line number Diff line number Diff line change
Expand Up @@ -1015,8 +1015,11 @@ int cifs_mkdir(struct inode *inode, struct dentry *direntry, int mode)
CIFS_MOUNT_MAP_SPECIAL_CHR);
}
if (direntry->d_inode) {
direntry->d_inode->i_mode = mode;
direntry->d_inode->i_mode |= S_IFDIR;
if (cifs_sb->mnt_cifs_flags &
CIFS_MOUNT_DYNPERM)
direntry->d_inode->i_mode =
(mode | S_IFDIR);

if (cifs_sb->mnt_cifs_flags &
CIFS_MOUNT_SET_UID) {
direntry->d_inode->i_uid =
Expand Down

0 comments on commit b0fd30d

Please sign in to comment.