OSDN Git Service

GlobalISel: extend add widening to SUB, MUL, OR, AND and XOR.
authorTim Northover <tnorthover@apple.com>
Thu, 4 Aug 2016 21:39:49 +0000 (21:39 +0000)
committerTim Northover <tnorthover@apple.com>
Thu, 4 Aug 2016 21:39:49 +0000 (21:39 +0000)
These are the operations that are trivially identical. Division is omitted for
now because you need to use the correct sign/zero extension.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@277775 91177308-0d34-0410-b5e6-96231b3b80d8

lib/CodeGen/GlobalISel/MachineLegalizeHelper.cpp
lib/Target/AArch64/AArch64MachineLegalizer.cpp
test/CodeGen/AArch64/GlobalISel/legalize-and.mir [new file with mode: 0644]
test/CodeGen/AArch64/GlobalISel/legalize-mul.mir [new file with mode: 0644]
test/CodeGen/AArch64/GlobalISel/legalize-or.mir [new file with mode: 0644]
test/CodeGen/AArch64/GlobalISel/legalize-sub.mir [new file with mode: 0644]
test/CodeGen/AArch64/GlobalISel/legalize-xor.mir [new file with mode: 0644]

index 31092a5..01d87d1 100644 (file)
@@ -100,7 +100,12 @@ MachineLegalizeHelper::widenScalar(MachineInstr &MI, LLT WideTy) {
   switch (MI.getOpcode()) {
   default:
     return UnableToLegalize;
-  case TargetOpcode::G_ADD: {
+  case TargetOpcode::G_ADD:
+  case TargetOpcode::G_AND:
+  case TargetOpcode::G_MUL:
+  case TargetOpcode::G_OR:
+  case TargetOpcode::G_XOR:
+  case TargetOpcode::G_SUB: {
     // Perform operation at larger width (any extension is fine here, high bits
     // don't affect the result) and then truncate the result back to the
     // original type.
@@ -114,7 +119,8 @@ MachineLegalizeHelper::widenScalar(MachineInstr &MI, LLT WideTy) {
     MIRBuilder.buildAnyExtend(WideTy, Src2Ext, MI.getOperand(2).getReg());
 
     unsigned DstExt = MRI.createGenericVirtualRegister(WideSize);
-    MIRBuilder.buildAdd(WideTy, DstExt, Src1Ext, Src2Ext);
+    MIRBuilder.buildInstr(MI.getOpcode(), WideTy)
+      .addDef(DstExt).addUse(Src1Ext).addUse(Src2Ext);
 
     MIRBuilder.buildTrunc(MI.getType(), MI.getOperand(0).getReg(), DstExt);
     MI.eraseFromParent();
index c547f7b..02be3bf 100644 (file)
@@ -34,7 +34,7 @@ AArch64MachineLegalizer::AArch64MachineLegalizer() {
   const LLT v4s32 = LLT::vector(4, 32);
   const LLT v2s64 = LLT::vector(2, 64);
 
-  for (auto BinOp : {G_ADD, G_SUB, G_AND, G_OR, G_XOR}) {
+  for (auto BinOp : {G_ADD, G_SUB, G_MUL, G_AND, G_OR, G_XOR}) {
     for (auto Ty : {s32, s64, v2s32, v4s32, v2s64})
       setAction(BinOp, Ty, Legal);
 
diff --git a/test/CodeGen/AArch64/GlobalISel/legalize-and.mir b/test/CodeGen/AArch64/GlobalISel/legalize-and.mir
new file mode 100644 (file)
index 0000000..2896401
--- /dev/null
@@ -0,0 +1,32 @@
+# RUN: llc -O0 -run-pass=legalize-mir -global-isel %s -o - 2>&1 | FileCheck %s
+
+--- |
+  target datalayout = "e-m:o-i64:64-i128:128-n32:64-S128"
+  target triple = "aarch64-apple-ios"
+  define void @test_scalar_and_small() {
+  entry:
+    ret void
+  }
+...
+
+---
+name:            test_scalar_and_small
+isSSA:           true
+registers:
+  - { id: 0, class: _ }
+  - { id: 1, class: _ }
+  - { id: 2, class: _ }
+body: |
+  bb.0.entry:
+    liveins: %x0, %x1, %x2, %x3
+    ; CHECK-LABEL: name: test_scalar_and_small
+    ; CHECK-DAG: [[LHS:%.*]](32) = G_ANYEXTEND s32 %0
+    ; CHECK-DAG: [[RHS:%.*]](32) = G_ANYEXTEND s32 %1
+    ; CHECK: [[RES:%.*]](32) = G_AND s32 [[LHS]], [[RHS]]
+    ; CHECK: %2(8) = G_TRUNC s8 [[RES]]
+
+    %0(8) = G_TRUNC s8 %x0
+    %1(8) = G_TRUNC s8 %x1
+    %2(8) = G_AND s8 %0, %1
+    %x0 = G_ANYEXTEND s64 %2
+...
diff --git a/test/CodeGen/AArch64/GlobalISel/legalize-mul.mir b/test/CodeGen/AArch64/GlobalISel/legalize-mul.mir
new file mode 100644 (file)
index 0000000..d559353
--- /dev/null
@@ -0,0 +1,32 @@
+# RUN: llc -O0 -run-pass=legalize-mir -global-isel %s -o - 2>&1 | FileCheck %s
+
+--- |
+  target datalayout = "e-m:o-i64:64-i128:128-n32:64-S128"
+  target triple = "aarch64-apple-ios"
+  define void @test_scalar_mul_small() {
+  entry:
+    ret void
+  }
+...
+
+---
+name:            test_scalar_mul_small
+isSSA:           true
+registers:
+  - { id: 0, class: _ }
+  - { id: 1, class: _ }
+  - { id: 2, class: _ }
+body: |
+  bb.0.entry:
+    liveins: %x0, %x1, %x2, %x3
+    ; CHECK-LABEL: name: test_scalar_mul_small
+    ; CHECK-DAG: [[LHS:%.*]](32) = G_ANYEXTEND s32 %0
+    ; CHECK-DAG: [[RHS:%.*]](32) = G_ANYEXTEND s32 %1
+    ; CHECK: [[RES:%.*]](32) = G_MUL s32 [[LHS]], [[RHS]]
+    ; CHECK: %2(8) = G_TRUNC s8 [[RES]]
+
+    %0(8) = G_TRUNC s8 %x0
+    %1(8) = G_TRUNC s8 %x1
+    %2(8) = G_MUL s8 %0, %1
+    %x0 = G_ANYEXTEND s64 %2
+...
diff --git a/test/CodeGen/AArch64/GlobalISel/legalize-or.mir b/test/CodeGen/AArch64/GlobalISel/legalize-or.mir
new file mode 100644 (file)
index 0000000..e777d44
--- /dev/null
@@ -0,0 +1,32 @@
+# RUN: llc -O0 -run-pass=legalize-mir -global-isel %s -o - 2>&1 | FileCheck %s
+
+--- |
+  target datalayout = "e-m:o-i64:64-i128:128-n32:64-S128"
+  target triple = "aarch64-apple-ios"
+  define void @test_scalar_or_small() {
+  entry:
+    ret void
+  }
+...
+
+---
+name:            test_scalar_or_small
+isSSA:           true
+registers:
+  - { id: 0, class: _ }
+  - { id: 1, class: _ }
+  - { id: 2, class: _ }
+body: |
+  bb.0.entry:
+    liveins: %x0, %x1, %x2, %x3
+    ; CHECK-LABEL: name: test_scalar_or_small
+    ; CHECK-DAG: [[LHS:%.*]](32) = G_ANYEXTEND s32 %0
+    ; CHECK-DAG: [[RHS:%.*]](32) = G_ANYEXTEND s32 %1
+    ; CHECK: [[RES:%.*]](32) = G_OR s32 [[LHS]], [[RHS]]
+    ; CHECK: %2(8) = G_TRUNC s8 [[RES]]
+
+    %0(8) = G_TRUNC s8 %x0
+    %1(8) = G_TRUNC s8 %x1
+    %2(8) = G_OR s8 %0, %1
+    %x0 = G_ANYEXTEND s64 %2
+...
diff --git a/test/CodeGen/AArch64/GlobalISel/legalize-sub.mir b/test/CodeGen/AArch64/GlobalISel/legalize-sub.mir
new file mode 100644 (file)
index 0000000..b99b9f0
--- /dev/null
@@ -0,0 +1,32 @@
+# RUN: llc -O0 -run-pass=legalize-mir -global-isel %s -o - 2>&1 | FileCheck %s
+
+--- |
+  target datalayout = "e-m:o-i64:64-i128:128-n32:64-S128"
+  target triple = "aarch64-apple-ios"
+  define void @test_scalar_sub_small() {
+  entry:
+    ret void
+  }
+...
+
+---
+name:            test_scalar_sub_small
+isSSA:           true
+registers:
+  - { id: 0, class: _ }
+  - { id: 1, class: _ }
+  - { id: 2, class: _ }
+body: |
+  bb.0.entry:
+    liveins: %x0, %x1, %x2, %x3
+    ; CHECK-LABEL: name: test_scalar_sub_small
+    ; CHECK-DAG: [[LHS:%.*]](32) = G_ANYEXTEND s32 %0
+    ; CHECK-DAG: [[RHS:%.*]](32) = G_ANYEXTEND s32 %1
+    ; CHECK: [[RES:%.*]](32) = G_SUB s32 [[LHS]], [[RHS]]
+    ; CHECK: %2(8) = G_TRUNC s8 [[RES]]
+
+    %0(8) = G_TRUNC s8 %x0
+    %1(8) = G_TRUNC s8 %x1
+    %2(8) = G_SUB s8 %0, %1
+    %x0 = G_ANYEXTEND s64 %2
+...
diff --git a/test/CodeGen/AArch64/GlobalISel/legalize-xor.mir b/test/CodeGen/AArch64/GlobalISel/legalize-xor.mir
new file mode 100644 (file)
index 0000000..8c9c31a
--- /dev/null
@@ -0,0 +1,32 @@
+# RUN: llc -O0 -run-pass=legalize-mir -global-isel %s -o - 2>&1 | FileCheck %s
+
+--- |
+  target datalayout = "e-m:o-i64:64-i128:128-n32:64-S128"
+  target triple = "aarch64-apple-ios"
+  define void @test_scalar_xor_small() {
+  entry:
+    ret void
+  }
+...
+
+---
+name:            test_scalar_xor_small
+isSSA:           true
+registers:
+  - { id: 0, class: _ }
+  - { id: 1, class: _ }
+  - { id: 2, class: _ }
+body: |
+  bb.0.entry:
+    liveins: %x0, %x1, %x2, %x3
+    ; CHECK-LABEL: name: test_scalar_xor_small
+    ; CHECK-DAG: [[LHS:%.*]](32) = G_ANYEXTEND s32 %0
+    ; CHECK-DAG: [[RHS:%.*]](32) = G_ANYEXTEND s32 %1
+    ; CHECK: [[RES:%.*]](32) = G_XOR s32 [[LHS]], [[RHS]]
+    ; CHECK: %2(8) = G_TRUNC s8 [[RES]]
+
+    %0(8) = G_TRUNC s8 %x0
+    %1(8) = G_TRUNC s8 %x1
+    %2(8) = G_XOR s8 %0, %1
+    %x0 = G_ANYEXTEND s64 %2
+...