aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorPavel Shilovsky <piastryyy@gmail.com>2010-11-02 05:00:42 -0400
committerSteve French <sfrench@us.ibm.com>2010-11-02 14:40:54 -0400
commite66673e39ac9d4749bd9676dd1caf928095409f5 (patch)
treef16191d689910a4f939992d8836e575195633116
parentce2f6fb8bd8c1e85f288033020dfc31c9fc2be94 (diff)
CIFS: Add cifs_set_oplock_level
Simplify many places when we need to set oplock level on an inode. Signed-off-by: Pavel Shilovsky <piastryyy@gmail.com> Reviewed-by: Jeff Layton <jlayton@redhat.com> Signed-off-by: Steve French <sfrench@us.ibm.com>
-rw-r--r--fs/cifs/cifsproto.h1
-rw-r--r--fs/cifs/file.c38
-rw-r--r--fs/cifs/misc.c23
3 files changed, 30 insertions, 32 deletions
diff --git a/fs/cifs/cifsproto.h b/fs/cifs/cifsproto.h
index edb6d90efdf2..7f050f4fc3d9 100644
--- a/fs/cifs/cifsproto.h
+++ b/fs/cifs/cifsproto.h
@@ -104,6 +104,7 @@ extern struct timespec cifs_NTtimeToUnix(__le64 utc_nanoseconds_since_1601);
104extern u64 cifs_UnixTimeToNT(struct timespec); 104extern u64 cifs_UnixTimeToNT(struct timespec);
105extern struct timespec cnvrtDosUnixTm(__le16 le_date, __le16 le_time, 105extern struct timespec cnvrtDosUnixTm(__le16 le_date, __le16 le_time,
106 int offset); 106 int offset);
107extern void cifs_set_oplock_level(struct inode *inode, __u32 oplock);
107 108
108extern struct cifsFileInfo *cifs_new_fileinfo(__u16 fileHandle, 109extern struct cifsFileInfo *cifs_new_fileinfo(__u16 fileHandle,
109 struct file *file, struct tcon_link *tlink, 110 struct file *file, struct tcon_link *tlink,
diff --git a/fs/cifs/file.c b/fs/cifs/file.c
index 5d06eb3078de..a566f155df49 100644
--- a/fs/cifs/file.c
+++ b/fs/cifs/file.c
@@ -146,12 +146,7 @@ client_can_cache:
146 rc = cifs_get_inode_info(&inode, full_path, buf, inode->i_sb, 146 rc = cifs_get_inode_info(&inode, full_path, buf, inode->i_sb,
147 xid, NULL); 147 xid, NULL);
148 148
149 if ((oplock & 0xF) == OPLOCK_EXCLUSIVE) { 149 cifs_set_oplock_level(inode, oplock);
150 pCifsInode->clientCanCacheAll = true;
151 pCifsInode->clientCanCacheRead = true;
152 cFYI(1, "Exclusive Oplock granted on inode %p", inode);
153 } else if ((oplock & 0xF) == OPLOCK_READ)
154 pCifsInode->clientCanCacheRead = true;
155 150
156 return rc; 151 return rc;
157} 152}
@@ -253,12 +248,7 @@ cifs_new_fileinfo(__u16 fileHandle, struct file *file,
253 list_add_tail(&pCifsFile->flist, &pCifsInode->openFileList); 248 list_add_tail(&pCifsFile->flist, &pCifsInode->openFileList);
254 spin_unlock(&cifs_file_list_lock); 249 spin_unlock(&cifs_file_list_lock);
255 250
256 if ((oplock & 0xF) == OPLOCK_EXCLUSIVE) { 251 cifs_set_oplock_level(inode, oplock);
257 pCifsInode->clientCanCacheAll = true;
258 pCifsInode->clientCanCacheRead = true;
259 cFYI(1, "Exclusive Oplock inode %p", inode);
260 } else if ((oplock & 0xF) == OPLOCK_READ)
261 pCifsInode->clientCanCacheRead = true;
262 252
263 file->private_data = pCifsFile; 253 file->private_data = pCifsFile;
264 return pCifsFile; 254 return pCifsFile;
@@ -271,8 +261,10 @@ cifs_new_fileinfo(__u16 fileHandle, struct file *file,
271 */ 261 */
272void cifsFileInfo_put(struct cifsFileInfo *cifs_file) 262void cifsFileInfo_put(struct cifsFileInfo *cifs_file)
273{ 263{
264 struct inode *inode = cifs_file->dentry->d_inode;
274 struct cifsTconInfo *tcon = tlink_tcon(cifs_file->tlink); 265 struct cifsTconInfo *tcon = tlink_tcon(cifs_file->tlink);
275 struct cifsInodeInfo *cifsi = CIFS_I(cifs_file->dentry->d_inode); 266 struct cifsInodeInfo *cifsi = CIFS_I(inode);
267 struct cifs_sb_info *cifs_sb = CIFS_SB(inode->i_sb);
276 struct cifsLockInfo *li, *tmp; 268 struct cifsLockInfo *li, *tmp;
277 269
278 spin_lock(&cifs_file_list_lock); 270 spin_lock(&cifs_file_list_lock);
@@ -288,8 +280,7 @@ void cifsFileInfo_put(struct cifsFileInfo *cifs_file)
288 if (list_empty(&cifsi->openFileList)) { 280 if (list_empty(&cifsi->openFileList)) {
289 cFYI(1, "closing last open instance for inode %p", 281 cFYI(1, "closing last open instance for inode %p",
290 cifs_file->dentry->d_inode); 282 cifs_file->dentry->d_inode);
291 cifsi->clientCanCacheRead = false; 283 cifs_set_oplock_level(inode, 0);
292 cifsi->clientCanCacheAll = false;
293 } 284 }
294 spin_unlock(&cifs_file_list_lock); 285 spin_unlock(&cifs_file_list_lock);
295 286
@@ -607,8 +598,6 @@ reopen_success:
607 rc = filemap_write_and_wait(inode->i_mapping); 598 rc = filemap_write_and_wait(inode->i_mapping);
608 mapping_set_error(inode->i_mapping, rc); 599 mapping_set_error(inode->i_mapping, rc);
609 600
610 pCifsInode->clientCanCacheAll = false;
611 pCifsInode->clientCanCacheRead = false;
612 if (tcon->unix_ext) 601 if (tcon->unix_ext)
613 rc = cifs_get_inode_info_unix(&inode, 602 rc = cifs_get_inode_info_unix(&inode,
614 full_path, inode->i_sb, xid); 603 full_path, inode->i_sb, xid);
@@ -622,18 +611,9 @@ reopen_success:
622 invalidate the current end of file on the server 611 invalidate the current end of file on the server
623 we can not go to the server to get the new inod 612 we can not go to the server to get the new inod
624 info */ 613 info */
625 if ((oplock & 0xF) == OPLOCK_EXCLUSIVE) { 614
626 pCifsInode->clientCanCacheAll = true; 615 cifs_set_oplock_level(inode, oplock);
627 pCifsInode->clientCanCacheRead = true; 616
628 cFYI(1, "Exclusive Oplock granted on inode %p",
629 pCifsFile->dentry->d_inode);
630 } else if ((oplock & 0xF) == OPLOCK_READ) {
631 pCifsInode->clientCanCacheRead = true;
632 pCifsInode->clientCanCacheAll = false;
633 } else {
634 pCifsInode->clientCanCacheRead = false;
635 pCifsInode->clientCanCacheAll = false;
636 }
637 cifs_relock_file(pCifsFile); 617 cifs_relock_file(pCifsFile);
638 618
639reopen_error_exit: 619reopen_error_exit:
diff --git a/fs/cifs/misc.c b/fs/cifs/misc.c
index c4e296fe3518..d3b9ddebc17e 100644
--- a/fs/cifs/misc.c
+++ b/fs/cifs/misc.c
@@ -569,10 +569,9 @@ is_valid_oplock_break(struct smb_hdr *buf, struct TCP_Server_Info *srv)
569 569
570 cFYI(1, "file id match, oplock break"); 570 cFYI(1, "file id match, oplock break");
571 pCifsInode = CIFS_I(netfile->dentry->d_inode); 571 pCifsInode = CIFS_I(netfile->dentry->d_inode);
572 pCifsInode->clientCanCacheAll = false;
573 if (pSMB->OplockLevel == 0)
574 pCifsInode->clientCanCacheRead = false;
575 572
573 cifs_set_oplock_level(netfile->dentry->d_inode,
574 pSMB->OplockLevel);
576 /* 575 /*
577 * cifs_oplock_break_put() can't be called 576 * cifs_oplock_break_put() can't be called
578 * from here. Get reference after queueing 577 * from here. Get reference after queueing
@@ -722,3 +721,21 @@ cifs_autodisable_serverino(struct cifs_sb_info *cifs_sb)
722 cifs_sb_master_tcon(cifs_sb)->treeName); 721 cifs_sb_master_tcon(cifs_sb)->treeName);
723 } 722 }
724} 723}
724
725void cifs_set_oplock_level(struct inode *inode, __u32 oplock)
726{
727 struct cifsInodeInfo *cinode = CIFS_I(inode);
728
729 if ((oplock & 0xF) == OPLOCK_EXCLUSIVE) {
730 cinode->clientCanCacheAll = true;
731 cinode->clientCanCacheRead = true;
732 cFYI(1, "Exclusive Oplock granted on inode %p", inode);
733 } else if ((oplock & 0xF) == OPLOCK_READ) {
734 cinode->clientCanCacheAll = false;
735 cinode->clientCanCacheRead = true;
736 cFYI(1, "Level II Oplock granted on inode %p", inode);
737 } else {
738 cinode->clientCanCacheAll = false;
739 cinode->clientCanCacheRead = false;
740 }
741}