Skip to content

Commit

Permalink
[MIPS] Remove an incorrect microMIPS instruction alias
Browse files Browse the repository at this point in the history
The microMIPS instruction set is compatible with the MIPS instruction
set at the assembly level but not in terms of encodings. `nop` in
microMIPS is a special case as it has the same encoding as `nop` for
MIPS.

Fix this error by reducing the usage of NOP in the MIPS backend such
that only that ISA correct variants are produced.

Differential Revision: https://reviews.llvm.org/D124716
  • Loading branch information
sdardis committed May 11, 2022
1 parent c2a7904 commit ba1c70c
Show file tree
Hide file tree
Showing 16 changed files with 169 additions and 140 deletions.
20 changes: 16 additions & 4 deletions llvm/lib/Target/Mips/MCTargetDesc/MipsTargetStreamer.cpp
Expand Up @@ -40,6 +40,10 @@ static bool isMicroMips(const MCSubtargetInfo *STI) {
return STI->getFeatureBits()[Mips::FeatureMicroMips];
}

static bool isMips32r6(const MCSubtargetInfo *STI) {
return STI->getFeatureBits()[Mips::FeatureMips32r6];
}

MipsTargetStreamer::MipsTargetStreamer(MCStreamer &S)
: MCTargetStreamer(S), GPReg(Mips::GP), ModuleDirectiveAllowed(true) {
GPRInfoSet = FPRInfoSet = FrameInfoSet = false;
Expand Down Expand Up @@ -279,10 +283,18 @@ void MipsTargetStreamer::emitDSLL(unsigned DstReg, unsigned SrcReg,

void MipsTargetStreamer::emitEmptyDelaySlot(bool hasShortDelaySlot, SMLoc IDLoc,
const MCSubtargetInfo *STI) {
if (hasShortDelaySlot)
emitRR(Mips::MOVE16_MM, Mips::ZERO, Mips::ZERO, IDLoc, STI);
else
emitRRI(Mips::SLL, Mips::ZERO, Mips::ZERO, 0, IDLoc, STI);
// The default case of `nop` is `sll $zero, $zero, 0`.
unsigned Opc = Mips::SLL;
if (isMicroMips(STI) && hasShortDelaySlot) {
Opc = isMips32r6(STI) ? Mips::MOVE16_MMR6 : Mips::MOVE16_MM;
emitRR(Opc, Mips::ZERO, Mips::ZERO, IDLoc, STI);
return;
}

if (isMicroMips(STI))
Opc = isMips32r6(STI) ? Mips::SLL_MMR6 : Mips::SLL_MM;

emitRRI(Opc, Mips::ZERO, Mips::ZERO, 0, IDLoc, STI);
}

void MipsTargetStreamer::emitNop(SMLoc IDLoc, const MCSubtargetInfo *STI) {
Expand Down
1 change: 0 additions & 1 deletion llvm/lib/Target/Mips/MicroMipsInstrInfo.td
Expand Up @@ -1325,7 +1325,6 @@ let EncodingPredicates = [InMicroMips] in {
II_DIVU, 0, 1, 1>, ISA_MIPS1_NOT_32R6_64R6;

def : MipsInstAlias<"wait", (WAIT_MM 0x0), 1>, ISA_MICROMIPS;
def : MipsInstAlias<"nop", (SLL ZERO, ZERO, 0), 1>, ISA_MICROMIPS;
def : MipsInstAlias<"nop", (SLL_MM ZERO, ZERO, 0), 1>, ISA_MICROMIPS;
def : MipsInstAlias<"nop", (MOVE16_MM ZERO, ZERO), 1>, ISA_MICROMIPS;
def : MipsInstAlias<"ei", (EI_MM ZERO), 1>, ISA_MICROMIPS;
Expand Down
11 changes: 5 additions & 6 deletions llvm/lib/Target/Mips/MipsBranchExpansion.cpp
Expand Up @@ -534,7 +534,7 @@ void MipsBranchExpansion::expandToLongBranch(MBBInfo &I) {
}
if (hasDelaySlot) {
if (STI->isTargetNaCl()) {
BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::NOP));
TII->insertNop(*BalTgtMBB, Pos, DL);
} else {
BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::ADDiu), Mips::SP)
.addReg(Mips::SP)
Expand Down Expand Up @@ -677,9 +677,8 @@ void MipsBranchExpansion::expandToLongBranch(MBBInfo &I) {
// nop
// $fallthrough:
//
MIBundleBuilder(*LongBrMBB, Pos)
.append(BuildMI(*MFp, DL, TII->get(Mips::J)).addMBB(TgtMBB))
.append(BuildMI(*MFp, DL, TII->get(Mips::NOP)));
BuildMI(*LongBrMBB, Pos, DL, TII->get(Mips::J)).addMBB(TgtMBB);
TII->insertNop(*LongBrMBB, Pos, DL)->bundleWithPred();
} else {
// At this point, offset where we need to branch does not fit into
// immediate field of the branch instruction and is not in the same
Expand Down Expand Up @@ -768,8 +767,8 @@ bool MipsBranchExpansion::handleSlot(Pred Predicate, Safe SafeInSlot) {
if (std::next(Iit) == FI->end() ||
std::next(Iit)->getOpcode() != Mips::NOP) {
Changed = true;
MIBundleBuilder(&*I).append(
BuildMI(*MFp, I->getDebugLoc(), TII->get(Mips::NOP)));
TII->insertNop(*(I->getParent()), std::next(I), I->getDebugLoc())
->bundleWithPred();
NumInsertedNops++;
}
}
Expand Down
2 changes: 1 addition & 1 deletion llvm/lib/Target/Mips/MipsDelaySlotFiller.cpp
Expand Up @@ -677,7 +677,7 @@ bool MipsDelaySlotFiller::runOnMachineBasicBlock(MachineBasicBlock &MBB) {
// Bundle the NOP to the instruction with the delay slot.
LLVM_DEBUG(dbgs() << DEBUG_TYPE << ": could not fill delay slot for ";
I->dump());
BuildMI(MBB, std::next(I), I->getDebugLoc(), TII->get(Mips::NOP));
TII->insertNop(MBB, std::next(I), I->getDebugLoc());
MIBundleBuilder(MBB, I, std::next(I, 2));
++FilledSlots;
Changed = true;
Expand Down
13 changes: 13 additions & 0 deletions llvm/lib/Target/Mips/MipsInstrInfo.cpp
Expand Up @@ -61,6 +61,19 @@ insertNoop(MachineBasicBlock &MBB, MachineBasicBlock::iterator MI) const
BuildMI(MBB, MI, DL, get(Mips::NOP));
}

MachineInstrBuilder MipsInstrInfo::insertNop(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MI,
DebugLoc DL) const {
assert(!Subtarget.inMips16Mode() &&
"insertNop does not support MIPS16e mode at this time");
const unsigned MMOpc =
Subtarget.hasMips32r6() ? Mips::SLL_MMR6 : Mips::SLL_MM;
const unsigned Opc = Subtarget.inMicroMipsMode() ? MMOpc : Mips::SLL;
return BuildMI(MBB, MI, DL, get(Opc), Mips::ZERO)
.addReg(Mips::ZERO)
.addImm(0);
}

MachineMemOperand *
MipsInstrInfo::GetMemOperand(MachineBasicBlock &MBB, int FI,
MachineMemOperand::Flags Flags) const {
Expand Down
6 changes: 6 additions & 0 deletions llvm/lib/Target/Mips/MipsInstrInfo.h
Expand Up @@ -113,6 +113,12 @@ class MipsInstrInfo : public MipsGenInstrInfo {
void insertNoop(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MI) const override;

/// Insert an ISA appropriate `nop`.
// FIXME: Add support for MIPS16e.
MachineInstrBuilder insertNop(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MI,
DebugLoc DL) const;

/// getRegisterInfo - TargetInstrInfo is a superset of MRegister info. As
/// such, whenever a client has an instance of instruction info, it should
/// always be able to get register info as well (through this method).
Expand Down
Expand Up @@ -72,11 +72,11 @@ body: |
; CHECK: $v0_64 = DADDiu $v0_64, 1
; CHECK: }
; CHECK: BNE killed renamable $at, $zero, %bb.2, implicit-def $at {
; CHECK: NOP
; CHECK: $zero = SLL $zero, 0
; CHECK: }
; CHECK: bb.1.return:
; CHECK: PseudoReturn64 undef $ra_64, implicit killed $v0_64 {
; CHECK: NOP
; CHECK: $zero = SLL $zero, 0
; CHECK: }
; CHECK: bb.2.err:
bb.0.entry:
Expand Down
6 changes: 3 additions & 3 deletions llvm/test/CodeGen/Mips/delay-slot-filler-bundled-insts.mir
Expand Up @@ -95,15 +95,15 @@ body: |
; CHECK: $sp_64 = DADDiu $sp_64, 16
; CHECK: }
; CHECK: BEQ64 renamable $a0_64, $zero_64, %bb.2, implicit-def $at {
; CHECK: NOP
; CHECK: $zero = SLL $zero, 0
; CHECK: }
; CHECK: bb.1.if.then:
; CHECK: successors: %bb.3(0x80000000)
; CHECK: JAL @func_a, csr_n64, implicit-def dead $ra, implicit $a0_64, implicit-def $sp, implicit-def $v0_64 {
; CHECK: NOP
; CHECK: $zero = SLL $zero, 0
; CHECK: }
; CHECK: J %bb.3, implicit-def dead $at {
; CHECK: NOP
; CHECK: $zero = SLL $zero, 0
; CHECK: }
; CHECK: bb.2.if.else:
; CHECK: successors: %bb.3(0x80000000)
Expand Down
10 changes: 5 additions & 5 deletions llvm/test/CodeGen/Mips/longbranch/branch-limits-fp-micromips.mir
Expand Up @@ -73,12 +73,12 @@ body: |
; MM: successors: %bb.2(0x50000000), %bb.1(0x30000000)
; MM: FCMP_D32_MM killed renamable $d6, killed renamable $d7, 2, implicit-def $fcc0
; MM: BC1F_MM $fcc0, %bb.2, implicit-def $at {
; MM: NOP
; MM: $zero = SLL_MM $zero, 0
; MM: }
; MM: bb.1.entry:
; MM: successors: %bb.3(0x80000000)
; MM: J %bb.3, implicit-def $at {
; MM: NOP
; MM: $zero = SLL_MM $zero, 0
; MM: }
; MM: bb.2.if.then:
; MM: INLINEASM &".space 310680", 1 /* sideeffect attdialect */, 12 /* clobber */, implicit-def dead early-clobber $at
Expand All @@ -92,7 +92,7 @@ body: |
; PIC: successors: %bb.3(0x50000000), %bb.1(0x30000000)
; PIC: FCMP_D32_MM killed renamable $d6, killed renamable $d7, 2, implicit-def $fcc0
; PIC: BC1F_MM $fcc0, %bb.3, implicit-def $at {
; PIC: NOP
; PIC: $zero = SLL_MM $zero, 0
; PIC: }
; PIC: bb.1.entry:
; PIC: successors: %bb.2(0x80000000)
Expand Down Expand Up @@ -173,7 +173,7 @@ body: |
; MM: successors: %bb.2(0x30000000), %bb.1(0x50000000)
; MM: FCMP_D32_MM killed renamable $d6, killed renamable $d7, 19, implicit-def $fcc0
; MM: BC1F_MM killed $fcc0, %bb.1, implicit-def dead $at {
; MM: NOP
; MM: $zero = SLL_MM $zero, 0
; MM: }
; MM: bb.1.return:
; MM: $v0 = LI16_MM 1
Expand All @@ -187,7 +187,7 @@ body: |
; PIC: successors: %bb.2(0x30000000), %bb.1(0x50000000)
; PIC: FCMP_D32_MM killed renamable $d6, killed renamable $d7, 19, implicit-def $fcc0
; PIC: BC1F_MM killed $fcc0, %bb.1, implicit-def dead $at {
; PIC: NOP
; PIC: $zero = SLL_MM $zero, 0
; PIC: }
; PIC: bb.1.return:
; PIC: $v0 = LI16_MM 1
Expand Down
12 changes: 6 additions & 6 deletions llvm/test/CodeGen/Mips/longbranch/branch-limits-fp-mips.mir
Expand Up @@ -72,12 +72,12 @@ body: |
; MIPS: successors: %bb.2(0x50000000), %bb.1(0x30000000)
; MIPS: FCMP_D32 killed renamable $d6, killed renamable $d7, 2, implicit-def $fcc0
; MIPS: BC1F $fcc0, %bb.2, implicit-def $at {
; MIPS: NOP
; MIPS: $zero = SLL $zero, 0
; MIPS: }
; MIPS: bb.1.entry:
; MIPS: successors: %bb.3(0x80000000)
; MIPS: J %bb.3, implicit-def $at {
; MIPS: NOP
; MIPS: $zero = SLL $zero, 0
; MIPS: }
; MIPS: bb.2.if.then:
; MIPS: INLINEASM &".space 310680", 1 /* sideeffect attdialect */, 12 /* clobber */, implicit-def dead early-clobber $at
Expand All @@ -93,7 +93,7 @@ body: |
; PIC: successors: %bb.3(0x50000000), %bb.1(0x30000000)
; PIC: FCMP_D32 killed renamable $d6, killed renamable $d7, 2, implicit-def $fcc0
; PIC: BC1F $fcc0, %bb.3, implicit-def $at {
; PIC: NOP
; PIC: $zero = SLL $zero, 0
; PIC: }
; PIC: bb.1.entry:
; PIC: successors: %bb.2(0x80000000)
Expand Down Expand Up @@ -176,12 +176,12 @@ body: |
; MIPS: successors: %bb.2(0x50000000), %bb.1(0x30000000)
; MIPS: FCMP_D32 killed renamable $d6, killed renamable $d7, 2, implicit-def $fcc0
; MIPS: BC1T $fcc0, %bb.2, implicit-def $at {
; MIPS: NOP
; MIPS: $zero = SLL $zero, 0
; MIPS: }
; MIPS: bb.1.entry:
; MIPS: successors: %bb.3(0x80000000)
; MIPS: J %bb.3, implicit-def $at {
; MIPS: NOP
; MIPS: $zero = SLL $zero, 0
; MIPS: }
; MIPS: bb.2.if.then:
; MIPS: INLINEASM &".space 310680", 1 /* sideeffect attdialect */, 12 /* clobber */, implicit-def dead early-clobber $at
Expand All @@ -197,7 +197,7 @@ body: |
; PIC: successors: %bb.3(0x50000000), %bb.1(0x30000000)
; PIC: FCMP_D32 killed renamable $d6, killed renamable $d7, 2, implicit-def $fcc0
; PIC: BC1T $fcc0, %bb.3, implicit-def $at {
; PIC: NOP
; PIC: $zero = SLL $zero, 0
; PIC: }
; PIC: bb.1.entry:
; PIC: successors: %bb.2(0x80000000)
Expand Down
8 changes: 4 additions & 4 deletions llvm/test/CodeGen/Mips/longbranch/branch-limits-fp-mipsr6.mir
Expand Up @@ -74,7 +74,7 @@ body: |
; R6: successors: %bb.2(0x50000000), %bb.1(0x30000000)
; R6: $f0 = CMP_EQ_D killed $d12_64, killed $d14_64
; R6: BC1NEZ $d0_64, %bb.2 {
; R6: NOP
; R6: $zero = SLL $zero, 0
; R6: }
; R6: bb.1.entry:
; R6: successors: %bb.3(0x80000000)
Expand All @@ -93,7 +93,7 @@ body: |
; PIC: successors: %bb.3(0x50000000), %bb.1(0x30000000)
; PIC: $f0 = CMP_EQ_D killed $d12_64, killed $d14_64
; PIC: BC1NEZ $d0_64, %bb.3 {
; PIC: NOP
; PIC: $zero = SLL $zero, 0
; PIC: }
; PIC: bb.1.entry:
; PIC: successors: %bb.2(0x80000000)
Expand Down Expand Up @@ -174,7 +174,7 @@ body: |
; R6: successors: %bb.2(0x50000000), %bb.1(0x30000000)
; R6: $f0 = CMP_EQ_D killed $d12_64, killed $d14_64
; R6: BC1EQZ $d0_64, %bb.2 {
; R6: NOP
; R6: $zero = SLL $zero, 0
; R6: }
; R6: bb.1.entry:
; R6: successors: %bb.3(0x80000000)
Expand All @@ -193,7 +193,7 @@ body: |
; PIC: successors: %bb.3(0x50000000), %bb.1(0x30000000)
; PIC: $f0 = CMP_EQ_D killed $d12_64, killed $d14_64
; PIC: BC1EQZ $d0_64, %bb.3 {
; PIC: NOP
; PIC: $zero = SLL $zero, 0
; PIC: }
; PIC: bb.1.entry:
; PIC: successors: %bb.2(0x80000000)
Expand Down

0 comments on commit ba1c70c

Please sign in to comment.