diff options
| author | Alan Cox <alc@FreeBSD.org> | 2026-08-07 21:51:04 +0000 |
|---|---|---|
| committer | Alan Cox <alc@FreeBSD.org> | 2026-08-14 20:57:35 +0000 |
| commit | 6fa9c2b1d2824034268646e0744e5e010155ffaf (patch) | |
| tree | b39943ae752499de8d20013550fc5127456e2253 | |
| parent | 7753a59fdf196fcbd8bb5706ad44bfc590bce0a9 (diff) | |
arm64: close a race in SVE register management
While testing an unrelated pmap change, D58708, that dramatically
reduces the number of TLBI instructions performed, and likely the
timing of unrelated events, I started seeing "Storing an invalid VFP
state" panics in vfp_save_state_common(). However, the origin of this
panic is elsewhere, in the else branch of sve_restore_state().
Specifically, my pmap change seems to have increased the likelihood that
the thread executing the else branch would be preempted by another
thread between the critical_exit() inside the else branch's call to
vfp_restore_state_common() and its own call to critical_enter(). Prior
to expanding the scope of the else branch's critical section, the MPASS
added by this change would fire, catching the problem at its source,
rather than later in vfp_save_state_common().
Assisted-by: Claude Code (Opus 5)
Reviewed by: kib, markj
MFC after: 1 week
Differential Revision: https://reviews.freebsd.org/D58723
| -rw-r--r-- | sys/arm64/arm64/vfp.c | 6 |
1 files changed, 4 insertions, 2 deletions
diff --git a/sys/arm64/arm64/vfp.c b/sys/arm64/arm64/vfp.c index d4c0eacf690c..11faa4cc21cd 100644 --- a/sys/arm64/arm64/vfp.c +++ b/sys/arm64/arm64/vfp.c @@ -797,15 +797,17 @@ sve_restore_state(struct thread *td) critical_exit(); } else { + critical_enter(); + vfp_restore_state_common(td, curpcb->pcb_fpflags); /* Enable SVE if it wasn't previously enabled */ if ((curpcb->pcb_fpflags & PCB_FP_SVEVALID) == 0) { - critical_enter(); + MPASS(PCPU_GET(fpcurthread) == td); sve_enable(); curpcb->pcb_fpflags |= PCB_FP_SVEVALID; - critical_exit(); } + critical_exit(); } return (true); |
