[llvm] [LoopIdiomRecognize] Enable clmul optimization for CRC loops (PR #203405)
Sean Clarke via llvm-commits
llvm-commits at lists.llvm.org
Fri Jun 26 12:00:30 PDT 2026
================
@@ -1549,7 +1551,128 @@ bool LoopIdiomRecognize::avoidLIRForMultiBlockLoop(bool IsMemset,
return false;
}
-bool LoopIdiomRecognize::optimizeCRCLoop(const PolynomialInfo &Info) {
+bool LoopIdiomRecognize::optimizeCRCLoopToClmul(const PolynomialInfo &Info) {
+ Type *CRCTy = Info.LHS->getType();
+ LLVMContext &Ctx = CRCTy->getContext();
+ unsigned CRCBW = CRCTy->getIntegerBitWidth();
+ // The TripCount determines how many bits of data are processed, regardless of
+ // whether the actual data bit width matches (if auxiliary data is even used
+ // at all).
+ unsigned EffectiveDataBW = Info.TripCount;
+ // The width used for clmul operations should be a power of 2, and should be
+ // at least CRCBW + DataBW.
+ unsigned ClmulBW = 2 * std::max(CRCBW, EffectiveDataBW);
+ Type *ClmulTy = IntegerType::get(Ctx, ClmulBW);
+
+ // For big-endian CRC loops where the auxiliary data is XORed with the CRC
+ // inside the loop, the bits won't be aligned properly if the bit widths don't
+ // match, and thus the CRC computation is incorrect, but HashRecognize will
+ // still detect the loop. Since this optimization always produces a correct
+ // CRC computation, bail in this edge case.
----------------
xarkenz wrote:
I figured out how to get rid of this bailout and replace it with additional logic so that this specific case is transformed properly. As for the asymmetry, I think it stems from an underlying asymmetry in the HashRecognize detection, specifically where it allows both sides of the XOR between CRC and data to be `CastOrSelf`, regardless of ByteOrderSwapped.
https://github.com/llvm/llvm-project/pull/203405
More information about the llvm-commits
mailing list