fsfreeze: wait in killable state in __sb_start_write
PATCH 1/4 fsfreeze: wait in killable state in __sb_start_write
Added a new enum to decide if we want to sleep in uninterruptible or killable state or we want simply to return immediately.
Signed-off-by Marco Stornelli <[email protected]>
Reviewed-by Jan Kara <[email protected]>
--- fs/super.c | 24 ++++++++++++++++++------ include/linux/fs.h | 21 ++++++++++++++------- 2 files changed, 32 insertions(+), 13 deletions(-)
fs/super.c +18 -6
@@ -1190,14 +1190,25 @@ static void acquire_freeze_lock(struct super_block *sb, int level, bool trylock,* This is an internal function, please use sb_start_{write,pagefault,intwrite} * instead. */ -int __sb_start_write (struct super_block *sb,int level,bool wait) +int __sb_start_write (struct super_block *sb,int level,int wait) { +int ret =0 ; retry:if (unlikely (sb->s_writers.frozen >= level)) { -if (!wait) -return 0 ; -wait_event (sb->s_writers.wait_unfrozen, - sb->s_writers.frozen < level); +switch (wait) { +case FREEZE_NOWAIT : +return ret; +case FREEZE_WAIT : +wait_event (sb->s_writers.wait_unfrozen, + sb->s_writers.frozen < level); +break ; +case FREEZE_WAIT_KILLABLE : + ret =wait_event_killable (sb->s_writers.wait_unfrozen, + sb->s_writers.frozen < level); +if (ret) +return -EINTR ; +break ; + } }#ifdef CONFIG_LOCKDEP
@@ -1213,7 +1224,8 @@ retry:__sb_end_write (sb, level); goto retry; } -return 1 ; + ret =1 ; +return ret; }EXPORT_SYMBOL (__sb_start_write);
include/linux/fs.h +14 -7
@@ -1220,6 +1220,13 @@ enum {#define SB_FREEZE_LEVELS (SB_FREEZE_COMPLETE - 1) +/* Possible waiting modes */ +enum { +FREEZE_NOWAIT =0 ,/* no blocking call */ +FREEZE_WAIT =1 ,/* wait in uninterruptible state */ +FREEZE_WAIT_KILLABLE =2 ,/* wait in killable state */ +}; +struct sb_writers {/* Counters for counting writers at each level */ struct percpu_counter counter[SB_FREEZE_LEVELS ];
@@ -1335,7 +1342,7 @@ extern struct timespec current_fs_time(struct super_block *sb);*/ void __sb_end_write (struct super_block *sb,int level); -int __sb_start_write (struct super_block *sb,int level,bool wait); +int __sb_start_write (struct super_block *sb,int level,int wait);/** * sb_end_write - drop write access to a superblock
@@ -1394,12 +1401,12 @@ static inline void sb_end_intwrite(struct super_block *sb)*/ static inline void sb_start_write (struct super_block *sb) { -__sb_start_write (sb,SB_FREEZE_WRITE , true); +__sb_start_write (sb,SB_FREEZE_WRITE ,FREEZE_WAIT ); }static inline int sb_start_write_trylock (struct super_block *sb) { -return __sb_start_write (sb,SB_FREEZE_WRITE , false); +return __sb_start_write (sb,SB_FREEZE_WRITE ,FREEZE_NOWAIT ); }/**
@@ -1423,7 +1430,7 @@ static inline int sb_start_write_trylock(struct super_block *sb)*/ static inline void sb_start_pagefault (struct super_block *sb) { -__sb_start_write (sb,SB_FREEZE_PAGEFAULT , true); +__sb_start_write (sb,SB_FREEZE_PAGEFAULT ,FREEZE_WAIT ); }/*
@@ -1441,7 +1448,7 @@ static inline void sb_start_pagefault(struct super_block *sb)*/ static inline void sb_start_intwrite (struct super_block *sb) { -__sb_start_write (sb,SB_FREEZE_FS , true); +__sb_start_write (sb,SB_FREEZE_FS ,FREEZE_WAIT ); }
@@ -2224,14 +2231,14 @@ static inline void file_start_write(struct file *file) {if (!S_ISREG (file_inode (file)->i_mode))return ; -__sb_start_write (file_inode (file)->i_sb,SB_FREEZE_WRITE , true); +__sb_start_write (file_inode (file)->i_sb,SB_FREEZE_WRITE ,FREEZE_WAIT ); }static inline bool file_start_write_trylock (struct file *file) {if (!S_ISREG (file_inode (file)->i_mode))return true; -return __sb_start_write (file_inode (file)->i_sb,SB_FREEZE_WRITE , false); +return __sb_start_write (file_inode (file)->i_sb,SB_FREEZE_WRITE ,FREEZE_NOWAIT ); }static inline void file_end_write (struct file *file)
Signature · 1 line
1.7.3.4