break;
}
+ EVT VT = N->getValueType(0);
+ SDValue Op = N->getOperand(1);
+ SDLoc dl(N);
+ if (VT == MVT::i64) {
+ Op = DAG.getNode(ISD::SCALAR_TO_VECTOR, dl, MVT::v1i64, Op);
+ VT = MVT::v1i64;
+ }
+
if (IsRightShift && ShiftAmount <= -1 && ShiftAmount >= -(int)ElemBits) {
- SDLoc dl(N);
- return DAG.getNode(Opcode, dl, N->getValueType(0), N->getOperand(1),
- DAG.getConstant(-ShiftAmount, dl, MVT::i32));
+ Op = DAG.getNode(Opcode, dl, VT, Op,
+ DAG.getConstant(-ShiftAmount, dl, MVT::i32));
+ if (N->getValueType(0) == MVT::i64)
+ Op = DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl, MVT::i64, Op,
+ DAG.getConstant(0, dl, MVT::i64));
+ return Op;
} else if (!IsRightShift && ShiftAmount >= 0 && ShiftAmount < ElemBits) {
- SDLoc dl(N);
- return DAG.getNode(Opcode, dl, N->getValueType(0), N->getOperand(1),
- DAG.getConstant(ShiftAmount, dl, MVT::i32));
+ Op = DAG.getNode(Opcode, dl, VT, Op,
+ DAG.getConstant(ShiftAmount, dl, MVT::i32));
+ if (N->getValueType(0) == MVT::i64)
+ Op = DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl, MVT::i64, Op,
+ DAG.getConstant(0, dl, MVT::i64));
+ return Op;
}
return SDValue();
define i64 @sqshl_scalar_constant(ptr %A) nounwind {
; CHECK-LABEL: sqshl_scalar_constant:
; CHECK: // %bb.0:
-; CHECK-NEXT: ldr x8, [x0]
-; CHECK-NEXT: fmov d0, x8
+; CHECK-NEXT: ldr d0, [x0]
; CHECK-NEXT: sqshl d0, d0, #1
; CHECK-NEXT: fmov x0, d0
; CHECK-NEXT: ret
define i64 @uqshl_scalar_constant(ptr %A) nounwind {
; CHECK-LABEL: uqshl_scalar_constant:
; CHECK: // %bb.0:
-; CHECK-NEXT: ldr x8, [x0]
-; CHECK-NEXT: fmov d0, x8
+; CHECK-NEXT: ldr d0, [x0]
; CHECK-NEXT: uqshl d0, d0, #1
; CHECK-NEXT: fmov x0, d0
; CHECK-NEXT: ret
define i64 @urshr_scalar(ptr %A) nounwind {
; CHECK-LABEL: urshr_scalar:
; CHECK: // %bb.0:
-; CHECK-NEXT: ldr x8, [x0]
-; CHECK-NEXT: fmov d0, x8
+; CHECK-NEXT: ldr d0, [x0]
; CHECK-NEXT: urshr d0, d0, #1
; CHECK-NEXT: fmov x0, d0
; CHECK-NEXT: ret
define i64 @srshr_scalar(ptr %A) nounwind {
; CHECK-LABEL: srshr_scalar:
; CHECK: // %bb.0:
-; CHECK-NEXT: ldr x8, [x0]
-; CHECK-NEXT: fmov d0, x8
+; CHECK-NEXT: ldr d0, [x0]
; CHECK-NEXT: srshr d0, d0, #1
; CHECK-NEXT: fmov x0, d0
; CHECK-NEXT: ret
define i64 @sqshlu_i64_constant(ptr %A) nounwind {
; CHECK-LABEL: sqshlu_i64_constant:
; CHECK: // %bb.0:
-; CHECK-NEXT: ldr x8, [x0]
-; CHECK-NEXT: fmov d0, x8
+; CHECK-NEXT: ldr d0, [x0]
; CHECK-NEXT: sqshlu d0, d0, #1
; CHECK-NEXT: fmov x0, d0
; CHECK-NEXT: ret
define i64 @ursra_scalar(ptr %A, ptr %B) nounwind {
; CHECK-LABEL: ursra_scalar:
; CHECK: // %bb.0:
-; CHECK-NEXT: ldr x8, [x0]
+; CHECK-NEXT: ldr d0, [x0]
; CHECK-NEXT: ldr x9, [x1]
-; CHECK-NEXT: fmov d1, x8
-; CHECK-NEXT: fmov d0, x9
-; CHECK-NEXT: ursra d0, d1, #1
-; CHECK-NEXT: fmov x0, d0
+; CHECK-NEXT: urshr d0, d0, #1
+; CHECK-NEXT: fmov x8, d0
+; CHECK-NEXT: add x0, x8, x9
; CHECK-NEXT: ret
%tmp1 = load i64, ptr %A
%tmp3 = call i64 @llvm.aarch64.neon.urshl.i64(i64 %tmp1, i64 -1)
define i64 @srsra_scalar(ptr %A, ptr %B) nounwind {
; CHECK-LABEL: srsra_scalar:
; CHECK: // %bb.0:
-; CHECK-NEXT: ldr x8, [x0]
+; CHECK-NEXT: ldr d0, [x0]
; CHECK-NEXT: ldr x9, [x1]
-; CHECK-NEXT: fmov d1, x8
-; CHECK-NEXT: fmov d0, x9
-; CHECK-NEXT: srsra d0, d1, #1
-; CHECK-NEXT: fmov x0, d0
+; CHECK-NEXT: srshr d0, d0, #1
+; CHECK-NEXT: fmov x8, d0
+; CHECK-NEXT: add x0, x8, x9
; CHECK-NEXT: ret
%tmp1 = load i64, ptr %A
%tmp3 = call i64 @llvm.aarch64.neon.srshl.i64(i64 %tmp1, i64 -1)