return SDValue();
}
-static SDValue ReassociateBinops(SDNode *N, SelectionDAG &DAG) {
- assert(N->getNumOperands() == 2 && "Invalid node for binop reassociation");
- SDValue N0 = N->getOperand(0);
- SDValue N1 = N->getOperand(1);
- EVT VT = N->getValueType(0);
- SDLoc DL(N);
- unsigned Opcode = N->getOpcode();
-
- // Canonicalize chains of this operation to LHS to allow the following fold.
- if (N0.getOpcode() != Opcode && N1.getOpcode() == Opcode)
- return DAG.getNode(Opcode, DL, VT, N1, N0);
-
- // Convert a chain of 3 dependent operations into 2 independent operations
- // and 1 dependent operation:
- // (op N0: (op N00: (op z, w), N01: y), N1: x) ->
- // (op N00: (op z, w), (op N1: x, N01: y))
- if (N0.getOpcode() == Opcode && N0.hasOneUse() && N1.getOpcode() != Opcode) {
- SDValue N00 = N0.getOperand(0);
- if (N00.getOpcode() == Opcode) {
- SDValue N01 = N0.getOperand(1);
- SDValue NewOp = DAG.getNode(Opcode, DL, VT, N1, N01);
- return DAG.getNode(Opcode, DL, VT, N00, NewOp);
- }
- }
- return SDValue();
-}
-
SDValue DAGCombiner::visitFADD(SDNode *N) {
SDValue N0 = N->getOperand(0);
SDValue N1 = N->getOperand(1);
N0.getOperand(0), DAG.getConstantFP(4.0, DL, VT));
}
}
-
- if (SDValue Reassociated = ReassociateBinops(N, DAG))
- return Reassociated;
-
} // enable-unsafe-fp-math
// FADD -> FMA combines:
ret float %t2
}
-; Verify that the first two adds are independent; the destination registers
-; are used as source registers for the third add.
-
-define float @reassociate_adds1(float %a, float %b, float %c, float %d) {
-; CHECK-LABEL: reassociate_adds1:
-; CHECK: # BB#0:
-; CHECK-NEXT: vaddss %xmm1, %xmm0, %xmm0
-; CHECK-NEXT: vaddss %xmm2, %xmm3, %xmm1
-; CHECK-NEXT: vaddss %xmm1, %xmm0, %xmm0
-; CHECK-NEXT: retq
- %add0 = fadd float %a, %b
- %add1 = fadd float %add0, %c
- %add2 = fadd float %add1, %d
- ret float %add2
-}
-
-define float @reassociate_adds2(float %a, float %b, float %c, float %d) {
-; CHECK-LABEL: reassociate_adds2:
-; CHECK: # BB#0:
-; CHECK-NEXT: vaddss %xmm1, %xmm0, %xmm0
-; CHECK-NEXT: vaddss %xmm2, %xmm3, %xmm1
-; CHECK-NEXT: vaddss %xmm1, %xmm0, %xmm0
-; CHECK-NEXT: retq
- %add0 = fadd float %a, %b
- %add1 = fadd float %c, %add0
- %add2 = fadd float %add1, %d
- ret float %add2
-}
-
-define float @reassociate_adds3(float %a, float %b, float %c, float %d) {
-; CHECK-LABEL: reassociate_adds3:
-; CHECK: # BB#0:
-; CHECK-NEXT: vaddss %xmm1, %xmm0, %xmm0
-; CHECK-NEXT: vaddss %xmm2, %xmm3, %xmm1
-; CHECK-NEXT: vaddss %xmm1, %xmm0, %xmm0
-; CHECK-NEXT: retq
- %add0 = fadd float %a, %b
- %add1 = fadd float %add0, %c
- %add2 = fadd float %d, %add1
- ret float %add2
-}
-