[CIFS] Allow reset of file to ATTR_NORMAL when archive bit not set

When a file had a dos attribute of 0x1 (readonly - but dos attribute
of archive was not set) - doing chmod 0777 or equivalent would
try to set a dos attribute of 0 (which some servers ignore)
rather than ATTR_NORMAL (0x20) which most servers accept.
Does not affect servers which support the CIFS Unix Extensions.

Acked-by: Prasad Potluri <pvp@us.ibm.com>
Acked-by: Shirish Pargaonkar <shirishp@us.ibm.com>
Signed-off-by: Steve French <sfrench@us.ibm.com>
This commit is contained in:
Steve French 2007-03-23 00:45:08 +00:00
parent 38e2aff670
commit 066fcb06d3
2 changed files with 16 additions and 4 deletions

View File

@ -6,7 +6,10 @@ on smp system corrupts sequence number. Do not reread unnecessarily partial page
(which we are about to overwrite anyway) when writing out file opened rw.
When DOS attribute of file on non-Unix server's file changes on the server side
from read-only back to read-write, reflect this change in default file mode
(we had been leaving a file's mode read-only until the inode were reloaded)
(we had been leaving a file's mode read-only until the inode were reloaded).
Allow setting of attribute back to ATTR_NORMAL (removing readonly dos attribute
when archive dos attribute not set and we are changing mode back to writeable
on server which does not support the Unix Extensions).
Version 1.47
------------

View File

@ -1196,6 +1196,7 @@ int cifs_setattr(struct dentry *direntry, struct iattr *attrs)
struct cifsFileInfo *open_file = NULL;
FILE_BASIC_INFO time_buf;
int set_time = FALSE;
int set_dosattr = FALSE;
__u64 mode = 0xFFFFFFFFFFFFFFFFULL;
__u64 uid = 0xFFFFFFFFFFFFFFFFULL;
__u64 gid = 0xFFFFFFFFFFFFFFFFULL;
@ -1332,15 +1333,23 @@ int cifs_setattr(struct dentry *direntry, struct iattr *attrs)
else if (attrs->ia_valid & ATTR_MODE) {
rc = 0;
if ((mode & S_IWUGO) == 0) /* not writeable */ {
if ((cifsInode->cifsAttrs & ATTR_READONLY) == 0)
if ((cifsInode->cifsAttrs & ATTR_READONLY) == 0) {
set_dosattr = TRUE;
time_buf.Attributes =
cpu_to_le32(cifsInode->cifsAttrs |
ATTR_READONLY);
}
} else if ((mode & S_IWUGO) == S_IWUGO) {
if (cifsInode->cifsAttrs & ATTR_READONLY)
if (cifsInode->cifsAttrs & ATTR_READONLY) {
set_dosattr = TRUE;
time_buf.Attributes =
cpu_to_le32(cifsInode->cifsAttrs &
(~ATTR_READONLY));
/* Windows ignores set to zero */
if(time_buf.Attributes == 0)
time_buf.Attributes |=
cpu_to_le32(ATTR_NORMAL);
}
}
/* BB to be implemented -
via Windows security descriptors or streams */
@ -1378,7 +1387,7 @@ int cifs_setattr(struct dentry *direntry, struct iattr *attrs)
} else
time_buf.ChangeTime = 0;
if (set_time || time_buf.Attributes) {
if (set_time || set_dosattr) {
time_buf.CreationTime = 0; /* do not change */
/* In the future we should experiment - try setting timestamps
via Handle (SetFileInfo) instead of by path */