From 0a164428fa59cc857eb2bedf6cdd1124e278e4b8 Mon Sep 17 00:00:00 2001 From: Alyssa Rosenzweig <alyssa@rosenzweig.io> Date: Thu, 25 Jan 2024 18:10:04 -0400 Subject: [PATCH] OpcodeDispatcher: eliminate select in RCR the nzcv clobber I actually came ofr Signed-off-by: Alyssa Rosenzweig <alyssa@rosenzweig.io> --- FEXCore/Source/Interface/Core/OpcodeDispatcher.cpp | 10 ++++------ 1 file changed, 4 insertions(+), 6 deletions(-) diff --git a/FEXCore/Source/Interface/Core/OpcodeDispatcher.cpp b/FEXCore/Source/Interface/Core/OpcodeDispatcher.cpp index d6c5bfc0a..3bf880506 100644 --- a/FEXCore/Source/Interface/Core/OpcodeDispatcher.cpp +++ b/FEXCore/Source/Interface/Core/OpcodeDispatcher.cpp @@ -2477,15 +2477,13 @@ void OpDispatchBuilder::RCROp(OpcodeArgs) { OrderedNode *SrcMasked = _And(OpSize, Src, _Constant(Size, Mask)); CalculateFlags_ShiftVariable(SrcMasked, [this, CF, Op, Size, OpSize, SrcMasked, Dest, &Res](){ - auto Zero = _Constant(Size, 0); auto One = _Constant(Size, 1); // Res |= (SrcMasked << (Size - Shift + 1)); - OrderedNode *SrcMaskedShl = _Sub(OpSize, _Constant(Size, Size + 1), SrcMasked); - auto TmpHigher = _Lshl(OpSize, Dest, SrcMaskedShl); - - auto CompareResult = _Select(FEXCore::IR::COND_UGT, SrcMasked, One, TmpHigher, Zero); - Res = _Or(OpSize, Res, CompareResult); + // Expressed as Res | ((SrcMasked << (Size - Shift)) << 1) to get correct + // behaviour for Shift without clobbering NZCV. + OrderedNode *SrcMaskedShl = _Sub(OpSize, _Constant(Size, Size), SrcMasked); + Res = _Orlshl(OpSize, Res, _Lshl(OpSize, Dest, SrcMaskedShl), 1); // Our new CF will be bit (Shift - 1) of the source. this is hoisted up to // avoid the need to copy the source.