summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorSteve French <sfrench@us.ibm.com>2006-03-03 09:53:36 +0000
committerSteve French <sfrench@us.ibm.com>2006-03-03 09:53:36 +0000
commit083d3a2cff514c5301f3a043642940d4d5371b22 (patch)
tree9dd82892244234401b54fe4133d3c2947b8a3b90
parenta4e85b5f620f59bd9308e29f833648f792d422f7 (diff)
downloadlinux-083d3a2cff514c5301f3a043642940d4d5371b22.tar.bz2
[CIFS] Workaround various server bugs found in testing at connectathon
- slow down negprot 1ms during mount when RFC1001 over port 139 to give buggy servers time to clear sess_init - remap some plausible but incorrect SMB return codes to the right ones in truncate and hardlink paths Signed-off-by: Steve French <sfrench@us.ibm.com>
-rw-r--r--fs/cifs/CHANGES3
-rw-r--r--fs/cifs/cifsfs.h2
-rw-r--r--fs/cifs/connect.c8
-rw-r--r--fs/cifs/inode.c4
-rw-r--r--fs/cifs/link.c2
5 files changed, 14 insertions, 5 deletions
diff --git a/fs/cifs/CHANGES b/fs/cifs/CHANGES
index 25d7df4a00c3..6238da96cc77 100644
--- a/fs/cifs/CHANGES
+++ b/fs/cifs/CHANGES
@@ -8,7 +8,8 @@ max smb buffer size when CIFSMaxBufSize over 64K. Fix oops in
cifs_user_read and cifs_readpages (when EAGAIN on send of smb
on socket is returned over and over). Add POSIX (advisory) byte range
locking support (requires server with newest CIFS UNIX Extensions
-to the protocol implemented).
+to the protocol implemented). Slow down negprot slightly in port 139
+RFC1001 case to give session_init time on buggy servers.
Version 1.40
------------
diff --git a/fs/cifs/cifsfs.h b/fs/cifs/cifsfs.h
index 4cf10f23cda9..b4dcdc2052a0 100644
--- a/fs/cifs/cifsfs.h
+++ b/fs/cifs/cifsfs.h
@@ -99,5 +99,5 @@ extern ssize_t cifs_getxattr(struct dentry *, const char *, void *, size_t);
extern ssize_t cifs_listxattr(struct dentry *, char *, size_t);
extern int cifs_ioctl (struct inode * inode, struct file * filep,
unsigned int command, unsigned long arg);
-#define CIFS_VERSION "1.41"
+#define CIFS_VERSION "1.42"
#endif /* _CIFSFS_H */
diff --git a/fs/cifs/connect.c b/fs/cifs/connect.c
index b8f1baabd343..3651deca4f24 100644
--- a/fs/cifs/connect.c
+++ b/fs/cifs/connect.c
@@ -1476,6 +1476,14 @@ ipv4_connect(struct sockaddr_in *psin_server, struct socket **csocket,
rc = smb_send(*csocket, smb_buf, 0x44,
(struct sockaddr *)psin_server);
kfree(ses_init_buf);
+ msleep(1); /* RFC1001 layer in at least one server
+ requires very short break before negprot
+ presumably because not expecting negprot
+ to follow so fast. This is a simple
+ solution that works without
+ complicating the code and causes no
+ significant slowing down on mount
+ for everyone else */
}
/* else the negprot may still work without this
even though malloc failed */
diff --git a/fs/cifs/inode.c b/fs/cifs/inode.c
index 0a46a9395ec4..b21038b99fc2 100644
--- a/fs/cifs/inode.c
+++ b/fs/cifs/inode.c
@@ -1166,7 +1166,7 @@ int cifs_setattr(struct dentry *direntry, struct iattr *attrs)
nfid, npid, FALSE);
atomic_dec(&open_file->wrtPending);
cFYI(1,("SetFSize for attrs rc = %d", rc));
- if((rc == -EINVAL) ||(rc == -EOPNOTSUPP)) {
+ if((rc == -EINVAL) || (rc == -EOPNOTSUPP)) {
int bytes_written;
rc = CIFSSMBWrite(xid, pTcon,
nfid, 0, attrs->ia_size,
@@ -1188,7 +1188,7 @@ int cifs_setattr(struct dentry *direntry, struct iattr *attrs)
cifs_sb->mnt_cifs_flags &
CIFS_MOUNT_MAP_SPECIAL_CHR);
cFYI(1, ("SetEOF by path (setattrs) rc = %d", rc));
- if(rc == -EINVAL) {
+ if((rc == -EINVAL) || (rc == -EOPNOTSUPP)) {
__u16 netfid;
int oplock = FALSE;
diff --git a/fs/cifs/link.c b/fs/cifs/link.c
index 0f99aae33162..ce86ec69fe01 100644
--- a/fs/cifs/link.c
+++ b/fs/cifs/link.c
@@ -67,7 +67,7 @@ cifs_hardlink(struct dentry *old_file, struct inode *inode,
cifs_sb_target->local_nls,
cifs_sb_target->mnt_cifs_flags &
CIFS_MOUNT_MAP_SPECIAL_CHR);
- if(rc == -EIO)
+ if((rc == -EIO) || (rc == -EINVAL))
rc = -EOPNOTSUPP;
}