]> granicus.if.org Git - llvm/commitdiff
[ARM GlobalISel] Support pointer constants
authorDiana Picus <diana.picus@linaro.org>
Fri, 22 Dec 2017 11:09:18 +0000 (11:09 +0000)
committerDiana Picus <diana.picus@linaro.org>
Fri, 22 Dec 2017 11:09:18 +0000 (11:09 +0000)
Pointer constants are pretty rare, since we usually represent them as
integer constants and then cast to pointer. One notable exception is the
null pointer constant, which is represented directly as a G_CONSTANT 0
with pointer type. Mark it as legal and make sure it is selected like
any other integer constant.

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

lib/Target/ARM/ARMInstructionSelector.cpp
lib/Target/ARM/ARMLegalizerInfo.cpp
test/CodeGen/ARM/GlobalISel/arm-instruction-select.mir
test/CodeGen/ARM/GlobalISel/arm-legalizer.mir

index de2f79df49b016e0c1abf70acdde9ae2902e04c5..2e8e7a7d96779c41bd12da1fbd5c516039c20f85 100644 (file)
@@ -669,13 +669,22 @@ bool ARMInstructionSelector::select(MachineInstr &I,
     return true;
   }
 
+  using namespace TargetOpcode;
+  if (I.getOpcode() == G_CONSTANT) {
+    // Pointer constants should be treated the same as 32-bit integer constants.
+    // Change the type and let TableGen handle it.
+    unsigned ResultReg = I.getOperand(0).getReg();
+    LLT Ty = MRI.getType(ResultReg);
+    if (Ty.isPointer())
+      MRI.setType(ResultReg, LLT::scalar(32));
+  }
+
   if (selectImpl(I, CoverageInfo))
     return true;
 
   MachineInstrBuilder MIB{MF, I};
   bool isSExt = false;
 
-  using namespace TargetOpcode;
   switch (I.getOpcode()) {
   case G_SEXT:
     isSExt = true;
index 2dd1dff64e87856be1fe8bddc31e7a840848e491..d2095587a8be18a306e79af9c757a6834658a532 100644 (file)
@@ -139,6 +139,7 @@ ARMLegalizerInfo::ARMLegalizerInfo(const ARMSubtarget &ST) {
   setAction({G_BRCOND, s1}, Legal);
 
   setAction({G_CONSTANT, s32}, Legal);
+  setAction({G_CONSTANT, p0}, Legal);
   setLegalizeScalarToDifferentSizeStrategy(G_CONSTANT, 0, widen_1_8_16);
 
   setAction({G_ICMP, s1}, Legal);
index 53efa2cf0ffa58ba9fb69ab3b03584f4bff8152b..6ada5b627f0cca80b89135ef8fa847964551d1af 100644 (file)
@@ -47,6 +47,7 @@
   define void @test_gep() { ret void }
   define void @test_constant_imm() { ret void }
   define void @test_constant_cimm() { ret void }
+  define void @test_pointer_constant() { ret void }
 
   define void @test_select_s32() { ret void }
   define void @test_select_ptr() { ret void }
@@ -1106,6 +1107,23 @@ body:             |
     BX_RET 14, %noreg, implicit %r0
 ...
 ---
+name:            test_pointer_constant
+# CHECK-LABEL: name: test_pointer_constant
+legalized:       true
+regBankSelected: true
+selected:        false
+# CHECK: selected: true
+registers:
+  - { id: 0, class: gprb }
+body:             |
+  bb.0:
+    %0(p0) = G_CONSTANT i32 0
+    ; CHECK: %[[C:[0-9]+]]:gpr = MOVi 0, 14, %noreg, %noreg
+
+    %r0 = COPY %0(p0)
+    BX_RET 14, %noreg, implicit %r0
+...
+---
 name:            test_select_s32
 # CHECK-LABEL: name: test_select_s32
 legalized:       true
index e3e206cf76e9b2b2c0ad2f25772e245690a18e05..5725ee7d3c361aa453c13b4a890d2aeb51d8762f 100644 (file)
@@ -826,6 +826,7 @@ registers:
   - { id: 2, class: _ }
   - { id: 3, class: _ }
   - { id: 4, class: _ }
+  - { id: 5, class: _ }
 body:             |
   bb.0:
     liveins: %r0
@@ -856,6 +857,10 @@ body:             |
     ; CHECK: {{%[0-9]+}}:_(s1) = G_TRUNC [[EXT]](s32)
     ; CHECK-NOT: G_CONSTANT i1
 
+    %5(p0) = G_CONSTANT 0
+    G_STORE %5(p0), %4(p0) :: (store 4)
+    ; CHECK: {{%[0-9]+}}:_(p0) = G_CONSTANT 0
+
     %r0 = COPY %0(s32)
     BX_RET 14, %noreg, implicit %r0
 ...