[llvm] [M68k] Introduce more MOVI cases (PR #98377)

Min-Yih Hsu via llvm-commits llvm-commits at lists.llvm.org
Wed Aug 28 20:47:07 PDT 2024


================
@@ -360,18 +360,66 @@ bool M68kInstrInfo::ExpandMOVI(MachineInstrBuilder &MIB, MVT MVTSize) const {
   if (AR16->contains(Reg) || AR32->contains(Reg))
     IsAddressReg = true;
 
+  // We need to assign to the full register to make IV happy
+  Register SReg =
+      MVTSize == MVT::i32
+          ? Reg
+          : Register(RI.getMatchingMegaReg(Reg, IsAddressReg ? AR32 : DR32));
+  assert(SReg && "No viable MEGA register available");
+
   LLVM_DEBUG(dbgs() << "Expand " << *MIB.getInstr() << " to ");
 
+  // Sign extention doesn't matter if we only use the bottom 8 bits
   if (MVTSize == MVT::i8 || (!IsAddressReg && Imm >= -128 && Imm <= 127)) {
     LLVM_DEBUG(dbgs() << "MOVEQ\n");
 
-    // We need to assign to the full register to make IV happy
-    Register SReg =
-        MVTSize == MVT::i32 ? Reg : Register(RI.getMatchingMegaReg(Reg, DR32));
-    assert(SReg && "No viable MEGA register available");
-
     MIB->setDesc(get(M68k::MOVQ));
     MIB->getOperand(0).setReg(SReg);
+
+    // Counter the effects of sign-extension with a bitwise not.
+    // This is only faster and smaller for 32 bit values.
+  } else if (DR32->contains(Reg) && std::abs(Imm) <= 255) {
+    LLVM_DEBUG(dbgs() << "MOVEQ and NOT\n");
+
+    MachineBasicBlock &MBB = *MIB->getParent();
+    DebugLoc DL = MIB->getDebugLoc();
+
+    unsigned SubReg = RI.getSubReg(Reg, M68k::MxSubRegIndex8Lo);
+    assert(SubReg && "No viable SUB register available");
+
+    BuildMI(MBB, MIB.getInstr(), DL, get(M68k::MOVQ), SReg).addImm(~Imm & 0xFF);
+    BuildMI(MBB, MIB.getInstr(), DL, get(M68k::NOT8d), SubReg).addReg(SubReg);
+
+    MIB->removeFromParent();
+
+    // Special case for setting address register to NULL (0)
+  } else if (IsAddressReg && Imm == 0) {
+    LLVM_DEBUG(dbgs() << "SUBA\n");
+
+    MachineBasicBlock &MBB = *MIB->getParent();
+    DebugLoc DL = MIB->getDebugLoc();
+
+    BuildMI(MBB, MIB.getInstr(), DL, get(M68k::SUB32ar), SReg)
+        .addReg(SReg, RegState::Undef)
+        .addReg(SReg, RegState::Undef);
+
+    MIB->removeFromParent();
+
+    // movea.w implicitly sign extends to the full register width,
+    // so exploit that if the immediate fits in the correct range.
+    //
+    // TODO: use lea imm.w, %an for further constants when 16-bit
+    // absolute addressing is implemented.
+  } else if (AR32->contains(Reg) && Imm >= -32768 && Imm <= 32767) {
----------------
mshockwave wrote:

ditto, `llvm::isUInt<16>(Imm)`?

https://github.com/llvm/llvm-project/pull/98377


More information about the llvm-commits mailing list