gfs2: fix scheduling while atomic bug in glocks
Before this patch, in the unlikely event that gfs2_glock_dq encountered
a withdraw, it would do a wait_on_bit to wait for its journal to be
recovered, but it never released the glock's spin_lock, which caused a
scheduling-while-atomic error.
This patch unlocks the lockref spin_lock before waiting for recovery.
Fixes: 601ef0d52e
("gfs2: Force withdraw to replay journals and wait for it to finish")
Cc: stable@vger.kernel.org # v5.7+
Reported-by: Alexander Aring <aahringo@redhat.com>
Signed-off-by: Bob Peterson <rpeterso@redhat.com>
Signed-off-by: Andreas Gruenbacher <agruenba@redhat.com>
This commit is contained in:
parent
4194dec4b4
commit
20265d9a67
|
@ -1466,9 +1466,11 @@ void gfs2_glock_dq(struct gfs2_holder *gh)
|
||||||
glock_blocked_by_withdraw(gl) &&
|
glock_blocked_by_withdraw(gl) &&
|
||||||
gh->gh_gl != sdp->sd_jinode_gl) {
|
gh->gh_gl != sdp->sd_jinode_gl) {
|
||||||
sdp->sd_glock_dqs_held++;
|
sdp->sd_glock_dqs_held++;
|
||||||
|
spin_unlock(&gl->gl_lockref.lock);
|
||||||
might_sleep();
|
might_sleep();
|
||||||
wait_on_bit(&sdp->sd_flags, SDF_WITHDRAW_RECOVERY,
|
wait_on_bit(&sdp->sd_flags, SDF_WITHDRAW_RECOVERY,
|
||||||
TASK_UNINTERRUPTIBLE);
|
TASK_UNINTERRUPTIBLE);
|
||||||
|
spin_lock(&gl->gl_lockref.lock);
|
||||||
}
|
}
|
||||||
if (gh->gh_flags & GL_NOCACHE)
|
if (gh->gh_flags & GL_NOCACHE)
|
||||||
handle_callback(gl, LM_ST_UNLOCKED, 0, false);
|
handle_callback(gl, LM_ST_UNLOCKED, 0, false);
|
||||||
|
|
Loading…
Reference in New Issue