Linux 4.12 compat: PF_FSTRANS was removed

Change SPL_FSTRANS to optionally contains PF_FSTRANS. Also, add
__spl_pf_fstrans_check for the checks specifically for PF_FSTRANS.

Reviewed-by: Brian Behlendorf <behlendorf1@llnl.gov>
Signed-off-by: Chunwei Chen <david.chen@osnexus.com>
Closes #614
This commit is contained in:
Chunwei Chen 2017-05-09 10:36:54 -07:00 committed by Brian Behlendorf
parent 3665037f30
commit 8f87971e1f
2 changed files with 39 additions and 10 deletions

View File

@ -46,6 +46,8 @@ extern void strfree(char *str);
#define KM_PUBLIC_MASK (KM_SLEEP | KM_NOSLEEP | KM_PUSHPAGE) #define KM_PUBLIC_MASK (KM_SLEEP | KM_NOSLEEP | KM_PUSHPAGE)
static int spl_fstrans_check(void);
/* /*
* Convert a KM_* flags mask to its Linux GFP_* counterpart. The conversion * Convert a KM_* flags mask to its Linux GFP_* counterpart. The conversion
* function is context aware which means that KM_SLEEP allocations can be * function is context aware which means that KM_SLEEP allocations can be
@ -60,7 +62,7 @@ kmem_flags_convert(int flags)
lflags |= GFP_ATOMIC | __GFP_NORETRY; lflags |= GFP_ATOMIC | __GFP_NORETRY;
} else { } else {
lflags |= GFP_KERNEL; lflags |= GFP_KERNEL;
if ((current->flags & PF_FSTRANS)) if (spl_fstrans_check())
lflags &= ~(__GFP_IO|__GFP_FS); lflags &= ~(__GFP_IO|__GFP_FS);
} }
@ -78,17 +80,34 @@ typedef struct {
unsigned int saved_flags; unsigned int saved_flags;
} fstrans_cookie_t; } fstrans_cookie_t;
/*
* Introduced in Linux 3.9, however this cannot be solely relied on before
* Linux 3.18 as it doesn't turn off __GFP_FS as it should.
*/
#ifdef PF_MEMALLOC_NOIO #ifdef PF_MEMALLOC_NOIO
#define SPL_FSTRANS (PF_FSTRANS|PF_MEMALLOC_NOIO) #define __SPL_PF_MEMALLOC_NOIO (PF_MEMALLOC_NOIO)
#else #else
#define SPL_FSTRANS (PF_FSTRANS) #define __SPL_PF_MEMALLOC_NOIO (0)
#endif #endif
/*
* PF_FSTRANS is removed from Linux 4.12
*/
#ifdef PF_FSTRANS
#define __SPL_PF_FSTRANS (PF_FSTRANS)
#else
#define __SPL_PF_FSTRANS (0)
#endif
#define SPL_FSTRANS (__SPL_PF_FSTRANS|__SPL_PF_MEMALLOC_NOIO)
static inline fstrans_cookie_t static inline fstrans_cookie_t
spl_fstrans_mark(void) spl_fstrans_mark(void)
{ {
fstrans_cookie_t cookie; fstrans_cookie_t cookie;
BUILD_BUG_ON(SPL_FSTRANS == 0);
cookie.fstrans_thread = current; cookie.fstrans_thread = current;
cookie.saved_flags = current->flags & SPL_FSTRANS; cookie.saved_flags = current->flags & SPL_FSTRANS;
current->flags |= SPL_FSTRANS; current->flags |= SPL_FSTRANS;
@ -109,7 +128,17 @@ spl_fstrans_unmark(fstrans_cookie_t cookie)
static inline int static inline int
spl_fstrans_check(void) spl_fstrans_check(void)
{ {
return (current->flags & PF_FSTRANS); return (current->flags & SPL_FSTRANS);
}
/*
* specifically used to check PF_FSTRANS flag, cannot be relied on for
* checking spl_fstrans_mark().
*/
static inline int
__spl_pf_fstrans_check(void)
{
return (current->flags & __SPL_PF_FSTRANS);
} }
#ifdef HAVE_ATOMIC64_T #ifdef HAVE_ATOMIC64_T

View File

@ -558,13 +558,13 @@ int vn_fsync(vnode_t *vp, int flags, void *x3, void *x4)
* May enter XFS which generates a warning when PF_FSTRANS is set. * May enter XFS which generates a warning when PF_FSTRANS is set.
* To avoid this the flag is cleared over vfs_sync() and then reset. * To avoid this the flag is cleared over vfs_sync() and then reset.
*/ */
fstrans = spl_fstrans_check(); fstrans = __spl_pf_fstrans_check();
if (fstrans) if (fstrans)
current->flags &= ~(PF_FSTRANS); current->flags &= ~(__SPL_PF_FSTRANS);
error = -spl_filp_fsync(vp->v_file, datasync); error = -spl_filp_fsync(vp->v_file, datasync);
if (fstrans) if (fstrans)
current->flags |= PF_FSTRANS; current->flags |= __SPL_PF_FSTRANS;
return (error); return (error);
} /* vn_fsync() */ } /* vn_fsync() */
@ -590,9 +590,9 @@ int vn_space(vnode_t *vp, int cmd, struct flock *bfp, int flag,
* May enter XFS which generates a warning when PF_FSTRANS is set. * May enter XFS which generates a warning when PF_FSTRANS is set.
* To avoid this the flag is cleared over vfs_sync() and then reset. * To avoid this the flag is cleared over vfs_sync() and then reset.
*/ */
fstrans = spl_fstrans_check(); fstrans = __spl_pf_fstrans_check();
if (fstrans) if (fstrans)
current->flags &= ~(PF_FSTRANS); current->flags &= ~(__SPL_PF_FSTRANS);
/* /*
* When supported by the underlying file system preferentially * When supported by the underlying file system preferentially
@ -603,7 +603,7 @@ int vn_space(vnode_t *vp, int cmd, struct flock *bfp, int flag,
bfp->l_start, bfp->l_len); bfp->l_start, bfp->l_len);
if (fstrans) if (fstrans)
current->flags |= PF_FSTRANS; current->flags |= __SPL_PF_FSTRANS;
if (error == 0) if (error == 0)
return (0); return (0);