arm64/EE: PMADDW/PMSUBW Rd commit must refresh the pin mirror

recPMADDWLane committed Rd.UD[dd] with a raw Str, bypassing armStoreEERegPtr
— the only such bypass in the tree. With a pinned Rd the mirror stayed stale
after PMADDW/PMSUBW, so any subsequent pin-served read (branch compare,
address base, ALU source) used the pre-PMADDW value. Latent since the S3 pin
campaign; surfaced by the lazy-dirty test run (where the seam flush then
clobbered the correct memory with the stale mirror — 6 red tests).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
Brian Degenhardt
2026-07-07 08:15:51 -07:00
co-authored by Claude Fable 5
parent b7fb5e6174
commit 637701474a
+6 -2
View File
@@ -990,9 +990,13 @@ static void recPMADDWLane(int dd, int ss, bool isSub)
if (_Rd_)
{
// Rd.UD[dd] = the two low words just stored: LO in x9[31:0], HI
// inserted from x17[31:0].
// inserted from x17[31:0]. Through armStoreEERegPtr, NOT a raw Str:
// a raw store bypassed the pin mirror, leaving a pinned Rd's mirror
// stale after PMADDW/PMSUBW (latent under write-through — any
// pin-served read of Rd afterward saw the old value; fatal under
// lazy-dirty, where the seam flush then clobbered the result).
armAsm->Bfi(a64::x9, a64::x17, 32, 32);
armAsm->Str(a64::x9, armCpuRegMem(&cpuRegs.GPR.r[_Rd_].UD[dd]));
armStoreEERegPtr(a64::x9, &cpuRegs.GPR.r[_Rd_].UD[dd]);
}
}