[llvm] r202394 - [XCore] Add dag combines for instructions that ignore some input bits.

Richard Osborne richard at xmos.com
Thu Feb 27 05:20:12 PST 2014


Author: friedgold
Date: Thu Feb 27 07:20:11 2014
New Revision: 202394

URL: http://llvm.org/viewvc/llvm-project?rev=202394&view=rev
Log:
[XCore] Add dag combines for instructions that ignore some input bits.

These instructions ignore the high bits of one of their input operands -
try and use this to simplify the code.

Modified:
    llvm/trunk/lib/Target/XCore/XCoreISelLowering.cpp
    llvm/trunk/test/CodeGen/XCore/resources_combine.ll

Modified: llvm/trunk/lib/Target/XCore/XCoreISelLowering.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/XCore/XCoreISelLowering.cpp?rev=202394&r1=202393&r2=202394&view=diff
==============================================================================
--- llvm/trunk/lib/Target/XCore/XCoreISelLowering.cpp (original)
+++ llvm/trunk/lib/Target/XCore/XCoreISelLowering.cpp Thu Feb 27 07:20:11 2014
@@ -180,6 +180,8 @@ XCoreTargetLowering::XCoreTargetLowering
   // We have target-specific dag combine patterns for the following nodes:
   setTargetDAGCombine(ISD::STORE);
   setTargetDAGCombine(ISD::ADD);
+  setTargetDAGCombine(ISD::INTRINSIC_VOID);
+  setTargetDAGCombine(ISD::INTRINSIC_W_CHAIN);
 
   setMinFunctionAlignment(1);
   setPrefFunctionAlignment(2);
@@ -1566,6 +1568,46 @@ SDValue XCoreTargetLowering::PerformDAGC
   SDLoc dl(N);
   switch (N->getOpcode()) {
   default: break;
+  case ISD::INTRINSIC_VOID:
+    switch (cast<ConstantSDNode>(N->getOperand(1))->getZExtValue()) {
+    case Intrinsic::xcore_outt:
+    case Intrinsic::xcore_outct:
+    case Intrinsic::xcore_chkct: {
+      SDValue OutVal = N->getOperand(3);
+      // These instructions ignore the high bits.
+      if (OutVal.hasOneUse()) {
+        unsigned BitWidth = OutVal.getValueSizeInBits();
+        APInt DemandedMask = APInt::getLowBitsSet(BitWidth, 8);
+        APInt KnownZero, KnownOne;
+        TargetLowering::TargetLoweringOpt TLO(DAG, !DCI.isBeforeLegalize(),
+                                              !DCI.isBeforeLegalizeOps());
+        const TargetLowering &TLI = DAG.getTargetLoweringInfo();
+        if (TLO.ShrinkDemandedConstant(OutVal, DemandedMask) ||
+            TLI.SimplifyDemandedBits(OutVal, DemandedMask, KnownZero, KnownOne,
+                                     TLO))
+          DCI.CommitTargetLoweringOpt(TLO);
+      }
+      break;
+    }
+    case Intrinsic::xcore_setpt: {
+      SDValue Time = N->getOperand(3);
+      // This instruction ignores the high bits.
+      if (Time.hasOneUse()) {
+        unsigned BitWidth = Time.getValueSizeInBits();
+        APInt DemandedMask = APInt::getLowBitsSet(BitWidth, 16);
+        APInt KnownZero, KnownOne;
+        TargetLowering::TargetLoweringOpt TLO(DAG, !DCI.isBeforeLegalize(),
+                                              !DCI.isBeforeLegalizeOps());
+        const TargetLowering &TLI = DAG.getTargetLoweringInfo();
+        if (TLO.ShrinkDemandedConstant(Time, DemandedMask) ||
+            TLI.SimplifyDemandedBits(Time, DemandedMask, KnownZero, KnownOne,
+                                     TLO))
+          DCI.CommitTargetLoweringOpt(TLO);
+      }
+      break;
+    }
+    }
+    break;
   case XCoreISD::LADD: {
     SDValue N0 = N->getOperand(0);
     SDValue N1 = N->getOperand(1);

Modified: llvm/trunk/test/CodeGen/XCore/resources_combine.ll
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/CodeGen/XCore/resources_combine.ll?rev=202394&r1=202393&r2=202394&view=diff
==============================================================================
--- llvm/trunk/test/CodeGen/XCore/resources_combine.ll (original)
+++ llvm/trunk/test/CodeGen/XCore/resources_combine.ll Thu Feb 27 07:20:11 2014
@@ -5,6 +5,10 @@ declare i32 @llvm.xcore.inct.p1i8(i8 add
 declare i32 @llvm.xcore.testct.p1i8(i8 addrspace(1)* %r)
 declare i32 @llvm.xcore.testwct.p1i8(i8 addrspace(1)* %r)
 declare i32 @llvm.xcore.getts.p1i8(i8 addrspace(1)* %r)
+declare void @llvm.xcore.outt.p1i8(i8 addrspace(1)* %r, i32 %value)
+declare void @llvm.xcore.outct.p1i8(i8 addrspace(1)* %r, i32 %value)
+declare void @llvm.xcore.chkct.p1i8(i8 addrspace(1)* %r, i32 %value)
+declare void @llvm.xcore.setpt.p1i8(i8 addrspace(1)* %r, i32 %value)
 
 define i32 @int(i8 addrspace(1)* %r) nounwind {
 ; CHECK-LABEL: int:
@@ -50,3 +54,40 @@ define i32 @getts(i8 addrspace(1)* %r) n
 	%trunc = and i32 %result, 65535
 	ret i32 %result
 }
+
+define void @outt(i8 addrspace(1)* %r, i32 %value) nounwind {
+; CHECK-LABEL: outt:
+; CHECK-NOT: zext
+; CHECK: outt res[r0], r1
+; CHECK-NEXT: retsp 0
+	%trunc = and i32 %value, 255
+	call void @llvm.xcore.outt.p1i8(i8 addrspace(1)* %r, i32 %trunc)
+	ret void
+}
+
+define void @outct(i8 addrspace(1)* %r, i32 %value) nounwind {
+; CHECK-LABEL: outct:
+; CHECK-NOT: zext
+; CHECK: outct res[r0], r1
+	%trunc = and i32 %value, 255
+	call void @llvm.xcore.outct.p1i8(i8 addrspace(1)* %r, i32 %trunc)
+	ret void
+}
+
+define void @chkct(i8 addrspace(1)* %r, i32 %value) nounwind {
+; CHECK-LABEL: chkct:
+; CHECK-NOT: zext
+; CHECK: chkct res[r0], r1
+	%trunc = and i32 %value, 255
+	call void @llvm.xcore.chkct.p1i8(i8 addrspace(1)* %r, i32 %trunc)
+	ret void
+}
+
+define void @setpt(i8 addrspace(1)* %r, i32 %value) nounwind {
+; CHECK-LABEL: setpt:
+; CHECK-NOT: zext
+; CHECK: setpt res[r0], r1
+	%trunc = and i32 %value, 65535
+	call void @llvm.xcore.setpt.p1i8(i8 addrspace(1)* %r, i32 %trunc)
+	ret void
+}





More information about the llvm-commits mailing list