aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBrian Behlendorf <[email protected]>2020-05-14 20:45:16 -0700
committerGitHub <[email protected]>2020-05-14 20:45:16 -0700
commit2ade659eb4f836931f10b69477657a054d743894 (patch)
tree33701c974d5c1ce7815ab424771d6ee1111d158d
parenteeb8fae9c7dc9a116f061ee8b266f0a51fd6c8ad (diff)
Fix abd_enter/exit_critical wrappers
Commit fc551d7 introduced the wrappers abd_enter_critical() and abd_exit_critical() to mark critical sections. On Linux these are implemented with the local_irq_save() and local_irq_restore() macros which set the 'flags' argument when saving. By wrapping them with a function the local variable is no longer set by the macro and is no longer properly restored. Convert abd_enter_critical() and abd_exit_critical() to macros to resolve this issue and ensure the flags are properly restored. Reviewed-by: Matthew Ahrens <[email protected]> Reviewed-by: Brian Atkinson <[email protected]> Signed-off-by: Brian Behlendorf <[email protected]> Closes #10332
-rw-r--r--include/sys/abd_impl.h15
-rw-r--r--module/os/freebsd/zfs/abd_os.c12
-rw-r--r--module/os/linux/zfs/abd_os.c12
-rw-r--r--module/zfs/abd.c4
4 files changed, 15 insertions, 28 deletions
diff --git a/include/sys/abd_impl.h b/include/sys/abd_impl.h
index 6027678af..5aee772b1 100644
--- a/include/sys/abd_impl.h
+++ b/include/sys/abd_impl.h
@@ -98,8 +98,6 @@ void abd_update_scatter_stats(abd_t *, abd_stats_op_t);
void abd_update_linear_stats(abd_t *, abd_stats_op_t);
void abd_verify_scatter(abd_t *);
void abd_free_linear_page(abd_t *);
-void abd_enter_critical(unsigned long);
-void abd_exit_critical(unsigned long);
/* OS specific abd_iter functions */
void abd_iter_init(struct abd_iter *, abd_t *);
boolean_t abd_iter_at_end(struct abd_iter *);
@@ -119,6 +117,19 @@ void abd_iter_unmap(struct abd_iter *);
#define ABD_SCATTER(abd) (abd->abd_u.abd_scatter)
#define ABD_LINEAR_BUF(abd) (abd->abd_u.abd_linear.abd_buf)
+#if defined(_KERNEL)
+#if defined(__FreeBSD__)
+#define abd_enter_critical(flags) critical_enter()
+#define abd_exit_critical(flags) critical_exit()
+#else
+#define abd_enter_critical(flags) local_irq_save(flags)
+#define abd_exit_critical(flags) local_irq_restore(flags)
+#endif
+#else /* !_KERNEL */
+#define abd_enter_critical(flags) ((void)0)
+#define abd_exit_critical(flags) ((void)0)
+#endif
+
#ifdef __cplusplus
}
#endif
diff --git a/module/os/freebsd/zfs/abd_os.c b/module/os/freebsd/zfs/abd_os.c
index f438841cd..6b967bc07 100644
--- a/module/os/freebsd/zfs/abd_os.c
+++ b/module/os/freebsd/zfs/abd_os.c
@@ -419,15 +419,3 @@ abd_iter_unmap(struct abd_iter *aiter)
aiter->iter_mapaddr = NULL;
aiter->iter_mapsize = 0;
}
-
-void
-abd_enter_critical(unsigned long flags)
-{
- critical_enter();
-}
-
-void
-abd_exit_critical(unsigned long flags)
-{
- critical_exit();
-}
diff --git a/module/os/linux/zfs/abd_os.c b/module/os/linux/zfs/abd_os.c
index 57e415ef3..a8e8f404d 100644
--- a/module/os/linux/zfs/abd_os.c
+++ b/module/os/linux/zfs/abd_os.c
@@ -803,18 +803,6 @@ abd_iter_unmap(struct abd_iter *aiter)
aiter->iter_mapsize = 0;
}
-void
-abd_enter_critical(unsigned long flags)
-{
- local_irq_save(flags);
-}
-
-void
-abd_exit_critical(unsigned long flags)
-{
- local_irq_restore(flags);
-}
-
#if defined(_KERNEL)
/*
* bio_nr_pages for ABD.
diff --git a/module/zfs/abd.c b/module/zfs/abd.c
index 2e4554da7..abb5d5f2e 100644
--- a/module/zfs/abd.c
+++ b/module/zfs/abd.c
@@ -703,7 +703,7 @@ abd_raidz_gen_iterate(abd_t **cabds, abd_t *dabd,
struct abd_iter caiters[3];
struct abd_iter daiter = {0};
void *caddrs[3];
- unsigned long flags = 0;
+ unsigned long flags __maybe_unused = 0;
ASSERT3U(parity, <=, 3);
@@ -800,7 +800,7 @@ abd_raidz_rec_iterate(abd_t **cabds, abd_t **tabds,
struct abd_iter citers[3];
struct abd_iter xiters[3];
void *caddrs[3], *xaddrs[3];
- unsigned long flags = 0;
+ unsigned long flags __maybe_unused = 0;
ASSERT3U(parity, <=, 3);