[DAG] TransformFPLoadStorePair - replace getABITypeAlign with allowsMemoryAccess (PR45116)

One of the cases identified in PR45116 - we don't need to limit load combines (in this case for fp->int load/store copies) to ABI alignment, we can use allowsMemoryAccess - which tests using getABITypeAlign, but also checks if a target permits (fast) misaligned memory loads by checking allowsMisalignedMemoryAccesses as a fallback.

Differential Revision: https://reviews.llvm.org/D108318
This commit is contained in:
Simon Pilgrim 2021-08-24 13:11:27 +01:00
parent e431b280c9
commit 6de0b55188
3 changed files with 25 additions and 26 deletions

View File

@ -16800,27 +16800,26 @@ SDValue DAGCombiner::TransformFPLoadStorePair(SDNode *N) {
if (VTSize.isScalable())
return SDValue();
bool FastLD = false, FastST = false;
EVT IntVT = EVT::getIntegerVT(*DAG.getContext(), VTSize.getFixedSize());
if (!TLI.isOperationLegal(ISD::LOAD, IntVT) ||
!TLI.isOperationLegal(ISD::STORE, IntVT) ||
!TLI.isDesirableToTransformToIntegerOp(ISD::LOAD, VT) ||
!TLI.isDesirableToTransformToIntegerOp(ISD::STORE, VT))
return SDValue();
Align LDAlign = LD->getAlign();
Align STAlign = ST->getAlign();
Type *IntVTTy = IntVT.getTypeForEVT(*DAG.getContext());
Align ABIAlign = DAG.getDataLayout().getABITypeAlign(IntVTTy);
if (LDAlign < ABIAlign || STAlign < ABIAlign)
!TLI.isDesirableToTransformToIntegerOp(ISD::STORE, VT) ||
!TLI.allowsMemoryAccess(*DAG.getContext(), DAG.getDataLayout(), IntVT,
*LD->getMemOperand(), &FastLD) ||
!TLI.allowsMemoryAccess(*DAG.getContext(), DAG.getDataLayout(), IntVT,
*ST->getMemOperand(), &FastST) ||
!FastLD || !FastST)
return SDValue();
SDValue NewLD =
DAG.getLoad(IntVT, SDLoc(Value), LD->getChain(), LD->getBasePtr(),
LD->getPointerInfo(), LDAlign);
LD->getPointerInfo(), LD->getAlign());
SDValue NewST =
DAG.getStore(ST->getChain(), SDLoc(N), NewLD, ST->getBasePtr(),
ST->getPointerInfo(), STAlign);
ST->getPointerInfo(), ST->getAlign());
AddToWorklist(NewLD.getNode());
AddToWorklist(NewST.getNode());

View File

@ -19,16 +19,16 @@ define i32 @foo() {
; CHECK-NEXT: .cfi_def_cfa_offset 16
; CHECK-NEXT: lis 3, s@ha
; CHECK-NEXT: la 3, s@l(3)
; CHECK-NEXT: lfs 0, 1(3)
; CHECK-NEXT: lis 3, u@ha
; CHECK-NEXT: la 3, u@l(3)
; CHECK-NEXT: lfd 1, 1(3)
; CHECK-NEXT: lis 3, t@ha
; CHECK-NEXT: la 3, t@l(3)
; CHECK-NEXT: stfs 0, 1(3)
; CHECK-NEXT: lis 4, u@ha
; CHECK-NEXT: lwz 3, 1(3)
; CHECK-NEXT: la 4, u@l(4)
; CHECK-NEXT: lfd 0, 1(4)
; CHECK-NEXT: lis 4, t@ha
; CHECK-NEXT: la 4, t@l(4)
; CHECK-NEXT: stw 3, 1(4)
; CHECK-NEXT: lis 3, v@ha
; CHECK-NEXT: la 3, v@l(3)
; CHECK-NEXT: stfd 1, 1(3)
; CHECK-NEXT: stfd 0, 1(3)
; CHECK-NEXT: lwz 3, 12(1)
; CHECK-NEXT: addi 1, 1, 16
; CHECK-NEXT: blr

View File

@ -66,14 +66,14 @@ entry:
define void @foo4(float* %p, float* %r) nounwind {
; CHECK-LABEL: foo4:
; CHECK: # %bb.0: # %entry
; CHECK-NEXT: lfs 0, 0(3)
; CHECK-NEXT: stfs 0, 0(4)
; CHECK-NEXT: lwz 3, 0(3)
; CHECK-NEXT: stw 3, 0(4)
; CHECK-NEXT: blr
;
; CHECK-VSX-LABEL: foo4:
; CHECK-VSX: # %bb.0: # %entry
; CHECK-VSX-NEXT: lfs 0, 0(3)
; CHECK-VSX-NEXT: stfs 0, 0(4)
; CHECK-VSX-NEXT: lwz 3, 0(3)
; CHECK-VSX-NEXT: stw 3, 0(4)
; CHECK-VSX-NEXT: blr
entry:
%v = load float, float* %p, align 1
@ -86,14 +86,14 @@ entry:
define void @foo5(double* %p, double* %r) nounwind {
; CHECK-LABEL: foo5:
; CHECK: # %bb.0: # %entry
; CHECK-NEXT: lfd 0, 0(3)
; CHECK-NEXT: stfd 0, 0(4)
; CHECK-NEXT: ld 3, 0(3)
; CHECK-NEXT: std 3, 0(4)
; CHECK-NEXT: blr
;
; CHECK-VSX-LABEL: foo5:
; CHECK-VSX: # %bb.0: # %entry
; CHECK-VSX-NEXT: lfd 0, 0(3)
; CHECK-VSX-NEXT: stfd 0, 0(4)
; CHECK-VSX-NEXT: ld 3, 0(3)
; CHECK-VSX-NEXT: std 3, 0(4)
; CHECK-VSX-NEXT: blr
entry:
%v = load double, double* %p, align 1