Commit fc94cdb9 authored by Steve French's avatar Steve French

[CIFS] Fix new POSIX Locking for setting lock_type correctly on unlock

Signed-off-by: default avatarSteve French <sfrench@us.ibm.com>
parent d9ec5ad2
Version 1.43
------------
POSIX locking to servers which support CIFS POSIX Extensions
(disabled by default controlled by proc/fs/cifs/Experimental)
Version 1.42 Version 1.42
------------ ------------
Fix slow oplock break when mounted to different servers at the same time and Fix slow oplock break when mounted to different servers at the same time and
......
...@@ -99,5 +99,5 @@ extern ssize_t cifs_getxattr(struct dentry *, const char *, void *, size_t); ...@@ -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 ssize_t cifs_listxattr(struct dentry *, char *, size_t);
extern int cifs_ioctl (struct inode * inode, struct file * filep, extern int cifs_ioctl (struct inode * inode, struct file * filep,
unsigned int command, unsigned long arg); unsigned int command, unsigned long arg);
#define CIFS_VERSION "1.42" #define CIFS_VERSION "1.43"
#endif /* _CIFSFS_H */ #endif /* _CIFSFS_H */
...@@ -267,7 +267,7 @@ extern int CIFSSMBLock(const int xid, struct cifsTconInfo *tcon, ...@@ -267,7 +267,7 @@ extern int CIFSSMBLock(const int xid, struct cifsTconInfo *tcon,
const int waitFlag); const int waitFlag);
extern int CIFSSMBPosixLock(const int xid, struct cifsTconInfo *tcon, extern int CIFSSMBPosixLock(const int xid, struct cifsTconInfo *tcon,
const __u16 smb_file_id, const int get_flag, const __u16 smb_file_id, const int get_flag,
const __u64 len, const __u64 offset, const __u64 len, struct file_lock *,
const __u16 lock_type, const int waitFlag); const __u16 lock_type, const int waitFlag);
extern int CIFSSMBTDis(const int xid, struct cifsTconInfo *tcon); extern int CIFSSMBTDis(const int xid, struct cifsTconInfo *tcon);
extern int CIFSSMBLogoff(const int xid, struct cifsSesInfo *ses); extern int CIFSSMBLogoff(const int xid, struct cifsSesInfo *ses);
......
...@@ -1355,7 +1355,8 @@ CIFSSMBLock(const int xid, struct cifsTconInfo *tcon, ...@@ -1355,7 +1355,8 @@ CIFSSMBLock(const int xid, struct cifsTconInfo *tcon,
int int
CIFSSMBPosixLock(const int xid, struct cifsTconInfo *tcon, CIFSSMBPosixLock(const int xid, struct cifsTconInfo *tcon,
const __u16 smb_file_id, const int get_flag, const __u64 len, const __u16 smb_file_id, const int get_flag, const __u64 len,
const __u64 lkoffset, const __u16 lock_type, const int waitFlag) struct file_lock *pLockData, const __u16 lock_type,
const int waitFlag)
{ {
struct smb_com_transaction2_sfi_req *pSMB = NULL; struct smb_com_transaction2_sfi_req *pSMB = NULL;
struct smb_com_transaction2_sfi_rsp *pSMBr = NULL; struct smb_com_transaction2_sfi_rsp *pSMBr = NULL;
...@@ -1366,6 +1367,10 @@ CIFSSMBPosixLock(const int xid, struct cifsTconInfo *tcon, ...@@ -1366,6 +1367,10 @@ CIFSSMBPosixLock(const int xid, struct cifsTconInfo *tcon,
__u16 params, param_offset, offset, byte_count, count; __u16 params, param_offset, offset, byte_count, count;
cFYI(1, ("Posix Lock")); cFYI(1, ("Posix Lock"));
if(pLockData == NULL)
return EINVAL;
rc = small_smb_init(SMB_COM_TRANSACTION2, 15, tcon, (void **) &pSMB); rc = small_smb_init(SMB_COM_TRANSACTION2, 15, tcon, (void **) &pSMB);
if (rc) if (rc)
...@@ -1406,7 +1411,7 @@ CIFSSMBPosixLock(const int xid, struct cifsTconInfo *tcon, ...@@ -1406,7 +1411,7 @@ CIFSSMBPosixLock(const int xid, struct cifsTconInfo *tcon,
if(waitFlag) if(waitFlag)
parm_data->lock_flags = 1; parm_data->lock_flags = 1;
parm_data->pid = cpu_to_le32(current->tgid); parm_data->pid = cpu_to_le32(current->tgid);
parm_data->start = lkoffset; parm_data->start = cpu_to_le64(pLockData->fl_start);
parm_data->length = len; /* normalize negative numbers */ parm_data->length = len; /* normalize negative numbers */
pSMB->DataOffset = cpu_to_le16(offset); pSMB->DataOffset = cpu_to_le16(offset);
...@@ -1419,8 +1424,33 @@ CIFSSMBPosixLock(const int xid, struct cifsTconInfo *tcon, ...@@ -1419,8 +1424,33 @@ CIFSSMBPosixLock(const int xid, struct cifsTconInfo *tcon,
(struct smb_hdr *) pSMBr, &bytes_returned, 0); (struct smb_hdr *) pSMBr, &bytes_returned, 0);
if (rc) { if (rc) {
cFYI(1, ("Send error in Posix Lock = %d", rc)); cFYI(1, ("Send error in Posix Lock = %d", rc));
} else if (get_flag) {
/* lock structure can be returned on get */
__u16 data_offset;
__u16 data_count;
rc = validate_t2((struct smb_t2_rsp *)pSMBr);
if (rc || (pSMBr->ByteCount < sizeof(struct cifs_posix_lock))) {
rc = -EIO; /* bad smb */
goto plk_err_exit;
}
if(pLockData == NULL) {
rc = -EINVAL;
goto plk_err_exit;
}
data_offset = le16_to_cpu(pSMBr->t2.DataOffset);
data_count = le16_to_cpu(pSMBr->t2.DataCount);
if(data_count < sizeof(struct cifs_posix_lock)) {
rc = -EIO;
goto plk_err_exit;
}
parm_data = (struct cifs_posix_lock *)
((char *)&pSMBr->hdr.Protocol + data_offset);
if(parm_data->lock_type == cpu_to_le16(CIFS_UNLCK))
pLockData->fl_type = F_UNLCK;
} }
plk_err_exit:
if (pSMB) if (pSMB)
cifs_small_buf_release(pSMB); cifs_small_buf_release(pSMB);
......
...@@ -656,7 +656,7 @@ int cifs_lock(struct file *file, int cmd, struct file_lock *pfLock) ...@@ -656,7 +656,7 @@ int cifs_lock(struct file *file, int cmd, struct file_lock *pfLock)
else else
posix_lock_type = CIFS_WRLCK; posix_lock_type = CIFS_WRLCK;
rc = CIFSSMBPosixLock(xid, pTcon, netfid, 1 /* get */, rc = CIFSSMBPosixLock(xid, pTcon, netfid, 1 /* get */,
length, pfLock->fl_start, length, pfLock,
posix_lock_type, wait_flag); posix_lock_type, wait_flag);
FreeXid(xid); FreeXid(xid);
return rc; return rc;
...@@ -704,7 +704,7 @@ int cifs_lock(struct file *file, int cmd, struct file_lock *pfLock) ...@@ -704,7 +704,7 @@ int cifs_lock(struct file *file, int cmd, struct file_lock *pfLock)
return -EOPNOTSUPP; return -EOPNOTSUPP;
} }
rc = CIFSSMBPosixLock(xid, pTcon, netfid, 0 /* set */, rc = CIFSSMBPosixLock(xid, pTcon, netfid, 0 /* set */,
length, pfLock->fl_start, length, pfLock,
posix_lock_type, wait_flag); posix_lock_type, wait_flag);
} else } else
rc = CIFSSMBLock(xid, pTcon, netfid, length, pfLock->fl_start, rc = CIFSSMBLock(xid, pTcon, netfid, length, pfLock->fl_start,
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment