diff options
-rw-r--r-- | fs/cifs/file.c | 10 | ||||
-rw-r--r-- | fs/locks.c | 3 | ||||
-rw-r--r-- | include/linux/fs.h | 5 |
3 files changed, 16 insertions, 2 deletions
diff --git a/fs/cifs/file.c b/fs/cifs/file.c index 460d87b7cda0..fae765dac934 100644 --- a/fs/cifs/file.c +++ b/fs/cifs/file.c | |||
@@ -835,13 +835,21 @@ cifs_posix_lock_set(struct file *file, struct file_lock *flock) | |||
835 | if ((flock->fl_flags & FL_POSIX) == 0) | 835 | if ((flock->fl_flags & FL_POSIX) == 0) |
836 | return rc; | 836 | return rc; |
837 | 837 | ||
838 | try_again: | ||
838 | mutex_lock(&cinode->lock_mutex); | 839 | mutex_lock(&cinode->lock_mutex); |
839 | if (!cinode->can_cache_brlcks) { | 840 | if (!cinode->can_cache_brlcks) { |
840 | mutex_unlock(&cinode->lock_mutex); | 841 | mutex_unlock(&cinode->lock_mutex); |
841 | return rc; | 842 | return rc; |
842 | } | 843 | } |
843 | rc = posix_lock_file_wait(file, flock); | 844 | |
845 | rc = posix_lock_file(file, flock, NULL); | ||
844 | mutex_unlock(&cinode->lock_mutex); | 846 | mutex_unlock(&cinode->lock_mutex); |
847 | if (rc == FILE_LOCK_DEFERRED) { | ||
848 | rc = wait_event_interruptible(flock->fl_wait, !flock->fl_next); | ||
849 | if (!rc) | ||
850 | goto try_again; | ||
851 | locks_delete_block(flock); | ||
852 | } | ||
845 | return rc; | 853 | return rc; |
846 | } | 854 | } |
847 | 855 | ||
diff --git a/fs/locks.c b/fs/locks.c index 637694bf3a03..0d68f1f81799 100644 --- a/fs/locks.c +++ b/fs/locks.c | |||
@@ -510,12 +510,13 @@ static void __locks_delete_block(struct file_lock *waiter) | |||
510 | 510 | ||
511 | /* | 511 | /* |
512 | */ | 512 | */ |
513 | static void locks_delete_block(struct file_lock *waiter) | 513 | void locks_delete_block(struct file_lock *waiter) |
514 | { | 514 | { |
515 | lock_flocks(); | 515 | lock_flocks(); |
516 | __locks_delete_block(waiter); | 516 | __locks_delete_block(waiter); |
517 | unlock_flocks(); | 517 | unlock_flocks(); |
518 | } | 518 | } |
519 | EXPORT_SYMBOL(locks_delete_block); | ||
519 | 520 | ||
520 | /* Insert waiter into blocker's block list. | 521 | /* Insert waiter into blocker's block list. |
521 | * We use a circular list so that processes can be easily woken up in | 522 | * We use a circular list so that processes can be easily woken up in |
diff --git a/include/linux/fs.h b/include/linux/fs.h index 135693e79f2b..528611843ba0 100644 --- a/include/linux/fs.h +++ b/include/linux/fs.h | |||
@@ -1215,6 +1215,7 @@ extern int vfs_setlease(struct file *, long, struct file_lock **); | |||
1215 | extern int lease_modify(struct file_lock **, int); | 1215 | extern int lease_modify(struct file_lock **, int); |
1216 | extern int lock_may_read(struct inode *, loff_t start, unsigned long count); | 1216 | extern int lock_may_read(struct inode *, loff_t start, unsigned long count); |
1217 | extern int lock_may_write(struct inode *, loff_t start, unsigned long count); | 1217 | extern int lock_may_write(struct inode *, loff_t start, unsigned long count); |
1218 | extern void locks_delete_block(struct file_lock *waiter); | ||
1218 | extern void lock_flocks(void); | 1219 | extern void lock_flocks(void); |
1219 | extern void unlock_flocks(void); | 1220 | extern void unlock_flocks(void); |
1220 | #else /* !CONFIG_FILE_LOCKING */ | 1221 | #else /* !CONFIG_FILE_LOCKING */ |
@@ -1359,6 +1360,10 @@ static inline int lock_may_write(struct inode *inode, loff_t start, | |||
1359 | return 1; | 1360 | return 1; |
1360 | } | 1361 | } |
1361 | 1362 | ||
1363 | static inline void locks_delete_block(struct file_lock *waiter) | ||
1364 | { | ||
1365 | } | ||
1366 | |||
1362 | static inline void lock_flocks(void) | 1367 | static inline void lock_flocks(void) |
1363 | { | 1368 | { |
1364 | } | 1369 | } |