1 //===-- MipsExpandPseudoInsts.cpp - Expand pseudo instructions ------------===//
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //===----------------------------------------------------------------------===//
9 // This file contains a pass that expands pseudo instructions into target
10 // instructions to allow proper scheduling, if-conversion, and other late
11 // optimizations. This pass should be run after register allocation but before
12 // the post-regalloc scheduling pass.
14 // This is currently only used for expanding atomic pseudos after register
15 // allocation. We do this to avoid the fast register allocator introducing
16 // spills between ll and sc. These stores cause some MIPS implementations to
17 // abort the atomic RMW sequence.
19 //===----------------------------------------------------------------------===//
22 #include "MipsInstrInfo.h"
23 #include "MipsSubtarget.h"
24 #include "llvm/CodeGen/LivePhysRegs.h"
25 #include "llvm/CodeGen/MachineFunctionPass.h"
26 #include "llvm/CodeGen/MachineInstrBuilder.h"
30 #define DEBUG_TYPE "mips-pseudo"
33 class MipsExpandPseudo
: public MachineFunctionPass
{
36 MipsExpandPseudo() : MachineFunctionPass(ID
) {}
38 const MipsInstrInfo
*TII
;
39 const MipsSubtarget
*STI
;
41 bool runOnMachineFunction(MachineFunction
&Fn
) override
;
43 MachineFunctionProperties
getRequiredProperties() const override
{
44 return MachineFunctionProperties().set(
45 MachineFunctionProperties::Property::NoVRegs
);
48 StringRef
getPassName() const override
{
49 return "Mips pseudo instruction expansion pass";
53 bool expandAtomicCmpSwap(MachineBasicBlock
&MBB
,
54 MachineBasicBlock::iterator MBBI
,
55 MachineBasicBlock::iterator
&NextMBBI
);
56 bool expandAtomicCmpSwapSubword(MachineBasicBlock
&MBB
,
57 MachineBasicBlock::iterator MBBI
,
58 MachineBasicBlock::iterator
&NextMBBI
);
60 bool expandAtomicBinOp(MachineBasicBlock
&BB
,
61 MachineBasicBlock::iterator I
,
62 MachineBasicBlock::iterator
&NMBBI
, unsigned Size
);
63 bool expandAtomicBinOpSubword(MachineBasicBlock
&BB
,
64 MachineBasicBlock::iterator I
,
65 MachineBasicBlock::iterator
&NMBBI
);
67 bool expandMI(MachineBasicBlock
&MBB
, MachineBasicBlock::iterator MBBI
,
68 MachineBasicBlock::iterator
&NMBB
);
69 bool expandMBB(MachineBasicBlock
&MBB
);
71 char MipsExpandPseudo::ID
= 0;
74 bool MipsExpandPseudo::expandAtomicCmpSwapSubword(
75 MachineBasicBlock
&BB
, MachineBasicBlock::iterator I
,
76 MachineBasicBlock::iterator
&NMBBI
) {
78 MachineFunction
*MF
= BB
.getParent();
80 const bool ArePtrs64bit
= STI
->getABI().ArePtrs64bit();
81 DebugLoc DL
= I
->getDebugLoc();
84 unsigned ZERO
= Mips::ZERO
;
85 unsigned BNE
= Mips::BNE
;
86 unsigned BEQ
= Mips::BEQ
;
88 I
->getOpcode() == Mips::ATOMIC_CMP_SWAP_I8_POSTRA
? Mips::SEB
: Mips::SEH
;
90 if (STI
->inMicroMipsMode()) {
91 LL
= STI
->hasMips32r6() ? Mips::LL_MMR6
: Mips::LL_MM
;
92 SC
= STI
->hasMips32r6() ? Mips::SC_MMR6
: Mips::SC_MM
;
93 BNE
= STI
->hasMips32r6() ? Mips::BNEC_MMR6
: Mips::BNE_MM
;
94 BEQ
= STI
->hasMips32r6() ? Mips::BEQC_MMR6
: Mips::BEQ_MM
;
96 LL
= STI
->hasMips32r6() ? (ArePtrs64bit
? Mips::LL64_R6
: Mips::LL_R6
)
97 : (ArePtrs64bit
? Mips::LL64
: Mips::LL
);
98 SC
= STI
->hasMips32r6() ? (ArePtrs64bit
? Mips::SC64_R6
: Mips::SC_R6
)
99 : (ArePtrs64bit
? Mips::SC64
: Mips::SC
);
102 Register Dest
= I
->getOperand(0).getReg();
103 Register Ptr
= I
->getOperand(1).getReg();
104 Register Mask
= I
->getOperand(2).getReg();
105 Register ShiftCmpVal
= I
->getOperand(3).getReg();
106 Register Mask2
= I
->getOperand(4).getReg();
107 Register ShiftNewVal
= I
->getOperand(5).getReg();
108 Register ShiftAmnt
= I
->getOperand(6).getReg();
109 Register Scratch
= I
->getOperand(7).getReg();
110 Register Scratch2
= I
->getOperand(8).getReg();
112 // insert new blocks after the current block
113 const BasicBlock
*LLVM_BB
= BB
.getBasicBlock();
114 MachineBasicBlock
*loop1MBB
= MF
->CreateMachineBasicBlock(LLVM_BB
);
115 MachineBasicBlock
*loop2MBB
= MF
->CreateMachineBasicBlock(LLVM_BB
);
116 MachineBasicBlock
*sinkMBB
= MF
->CreateMachineBasicBlock(LLVM_BB
);
117 MachineBasicBlock
*exitMBB
= MF
->CreateMachineBasicBlock(LLVM_BB
);
118 MachineFunction::iterator It
= ++BB
.getIterator();
119 MF
->insert(It
, loop1MBB
);
120 MF
->insert(It
, loop2MBB
);
121 MF
->insert(It
, sinkMBB
);
122 MF
->insert(It
, exitMBB
);
124 // Transfer the remainder of BB and its successor edges to exitMBB.
125 exitMBB
->splice(exitMBB
->begin(), &BB
,
126 std::next(MachineBasicBlock::iterator(I
)), BB
.end());
127 exitMBB
->transferSuccessorsAndUpdatePHIs(&BB
);
131 // fallthrough --> loop1MBB
132 BB
.addSuccessor(loop1MBB
, BranchProbability::getOne());
133 loop1MBB
->addSuccessor(sinkMBB
);
134 loop1MBB
->addSuccessor(loop2MBB
);
135 loop1MBB
->normalizeSuccProbs();
136 loop2MBB
->addSuccessor(loop1MBB
);
137 loop2MBB
->addSuccessor(sinkMBB
);
138 loop2MBB
->normalizeSuccProbs();
139 sinkMBB
->addSuccessor(exitMBB
, BranchProbability::getOne());
143 // and Mask', dest, Mask
144 // bne Mask', ShiftCmpVal, exitMBB
145 BuildMI(loop1MBB
, DL
, TII
->get(LL
), Scratch
).addReg(Ptr
).addImm(0);
146 BuildMI(loop1MBB
, DL
, TII
->get(Mips::AND
), Scratch2
)
149 BuildMI(loop1MBB
, DL
, TII
->get(BNE
))
150 .addReg(Scratch2
).addReg(ShiftCmpVal
).addMBB(sinkMBB
);
153 // and dest, dest, mask2
154 // or dest, dest, ShiftNewVal
155 // sc dest, dest, 0(ptr)
156 // beq dest, $0, loop1MBB
157 BuildMI(loop2MBB
, DL
, TII
->get(Mips::AND
), Scratch
)
158 .addReg(Scratch
, RegState::Kill
)
160 BuildMI(loop2MBB
, DL
, TII
->get(Mips::OR
), Scratch
)
161 .addReg(Scratch
, RegState::Kill
)
162 .addReg(ShiftNewVal
);
163 BuildMI(loop2MBB
, DL
, TII
->get(SC
), Scratch
)
164 .addReg(Scratch
, RegState::Kill
)
167 BuildMI(loop2MBB
, DL
, TII
->get(BEQ
))
168 .addReg(Scratch
, RegState::Kill
)
173 // srl srlres, Mask', shiftamt
174 // sign_extend dest,srlres
175 BuildMI(sinkMBB
, DL
, TII
->get(Mips::SRLV
), Dest
)
178 if (STI
->hasMips32r2()) {
179 BuildMI(sinkMBB
, DL
, TII
->get(SEOp
), Dest
).addReg(Dest
);
181 const unsigned ShiftImm
=
182 I
->getOpcode() == Mips::ATOMIC_CMP_SWAP_I16_POSTRA
? 16 : 24;
183 BuildMI(sinkMBB
, DL
, TII
->get(Mips::SLL
), Dest
)
184 .addReg(Dest
, RegState::Kill
)
186 BuildMI(sinkMBB
, DL
, TII
->get(Mips::SRA
), Dest
)
187 .addReg(Dest
, RegState::Kill
)
191 LivePhysRegs LiveRegs
;
192 computeAndAddLiveIns(LiveRegs
, *loop1MBB
);
193 computeAndAddLiveIns(LiveRegs
, *loop2MBB
);
194 computeAndAddLiveIns(LiveRegs
, *sinkMBB
);
195 computeAndAddLiveIns(LiveRegs
, *exitMBB
);
198 I
->eraseFromParent();
202 bool MipsExpandPseudo::expandAtomicCmpSwap(MachineBasicBlock
&BB
,
203 MachineBasicBlock::iterator I
,
204 MachineBasicBlock::iterator
&NMBBI
) {
206 const unsigned Size
=
207 I
->getOpcode() == Mips::ATOMIC_CMP_SWAP_I32_POSTRA
? 4 : 8;
208 MachineFunction
*MF
= BB
.getParent();
210 const bool ArePtrs64bit
= STI
->getABI().ArePtrs64bit();
211 DebugLoc DL
= I
->getDebugLoc();
213 unsigned LL
, SC
, ZERO
, BNE
, BEQ
, MOVE
;
216 if (STI
->inMicroMipsMode()) {
217 LL
= STI
->hasMips32r6() ? Mips::LL_MMR6
: Mips::LL_MM
;
218 SC
= STI
->hasMips32r6() ? Mips::SC_MMR6
: Mips::SC_MM
;
219 BNE
= STI
->hasMips32r6() ? Mips::BNEC_MMR6
: Mips::BNE_MM
;
220 BEQ
= STI
->hasMips32r6() ? Mips::BEQC_MMR6
: Mips::BEQ_MM
;
222 LL
= STI
->hasMips32r6()
223 ? (ArePtrs64bit
? Mips::LL64_R6
: Mips::LL_R6
)
224 : (ArePtrs64bit
? Mips::LL64
: Mips::LL
);
225 SC
= STI
->hasMips32r6()
226 ? (ArePtrs64bit
? Mips::SC64_R6
: Mips::SC_R6
)
227 : (ArePtrs64bit
? Mips::SC64
: Mips::SC
);
235 LL
= STI
->hasMips64r6() ? Mips::LLD_R6
: Mips::LLD
;
236 SC
= STI
->hasMips64r6() ? Mips::SCD_R6
: Mips::SCD
;
237 ZERO
= Mips::ZERO_64
;
243 Register Dest
= I
->getOperand(0).getReg();
244 Register Ptr
= I
->getOperand(1).getReg();
245 Register OldVal
= I
->getOperand(2).getReg();
246 Register NewVal
= I
->getOperand(3).getReg();
247 Register Scratch
= I
->getOperand(4).getReg();
249 // insert new blocks after the current block
250 const BasicBlock
*LLVM_BB
= BB
.getBasicBlock();
251 MachineBasicBlock
*loop1MBB
= MF
->CreateMachineBasicBlock(LLVM_BB
);
252 MachineBasicBlock
*loop2MBB
= MF
->CreateMachineBasicBlock(LLVM_BB
);
253 MachineBasicBlock
*exitMBB
= MF
->CreateMachineBasicBlock(LLVM_BB
);
254 MachineFunction::iterator It
= ++BB
.getIterator();
255 MF
->insert(It
, loop1MBB
);
256 MF
->insert(It
, loop2MBB
);
257 MF
->insert(It
, exitMBB
);
259 // Transfer the remainder of BB and its successor edges to exitMBB.
260 exitMBB
->splice(exitMBB
->begin(), &BB
,
261 std::next(MachineBasicBlock::iterator(I
)), BB
.end());
262 exitMBB
->transferSuccessorsAndUpdatePHIs(&BB
);
266 // fallthrough --> loop1MBB
267 BB
.addSuccessor(loop1MBB
, BranchProbability::getOne());
268 loop1MBB
->addSuccessor(exitMBB
);
269 loop1MBB
->addSuccessor(loop2MBB
);
270 loop1MBB
->normalizeSuccProbs();
271 loop2MBB
->addSuccessor(loop1MBB
);
272 loop2MBB
->addSuccessor(exitMBB
);
273 loop2MBB
->normalizeSuccProbs();
277 // bne dest, oldval, exitMBB
278 BuildMI(loop1MBB
, DL
, TII
->get(LL
), Dest
).addReg(Ptr
).addImm(0);
279 BuildMI(loop1MBB
, DL
, TII
->get(BNE
))
280 .addReg(Dest
, RegState::Kill
).addReg(OldVal
).addMBB(exitMBB
);
283 // move scratch, NewVal
284 // sc Scratch, Scratch, 0(ptr)
285 // beq Scratch, $0, loop1MBB
286 BuildMI(loop2MBB
, DL
, TII
->get(MOVE
), Scratch
).addReg(NewVal
).addReg(ZERO
);
287 BuildMI(loop2MBB
, DL
, TII
->get(SC
), Scratch
)
288 .addReg(Scratch
).addReg(Ptr
).addImm(0);
289 BuildMI(loop2MBB
, DL
, TII
->get(BEQ
))
290 .addReg(Scratch
, RegState::Kill
).addReg(ZERO
).addMBB(loop1MBB
);
292 LivePhysRegs LiveRegs
;
293 computeAndAddLiveIns(LiveRegs
, *loop1MBB
);
294 computeAndAddLiveIns(LiveRegs
, *loop2MBB
);
295 computeAndAddLiveIns(LiveRegs
, *exitMBB
);
298 I
->eraseFromParent();
302 bool MipsExpandPseudo::expandAtomicBinOpSubword(
303 MachineBasicBlock
&BB
, MachineBasicBlock::iterator I
,
304 MachineBasicBlock::iterator
&NMBBI
) {
306 MachineFunction
*MF
= BB
.getParent();
308 const bool ArePtrs64bit
= STI
->getABI().ArePtrs64bit();
309 DebugLoc DL
= I
->getDebugLoc();
312 unsigned BEQ
= Mips::BEQ
;
313 unsigned SEOp
= Mips::SEH
;
315 if (STI
->inMicroMipsMode()) {
316 LL
= STI
->hasMips32r6() ? Mips::LL_MMR6
: Mips::LL_MM
;
317 SC
= STI
->hasMips32r6() ? Mips::SC_MMR6
: Mips::SC_MM
;
318 BEQ
= STI
->hasMips32r6() ? Mips::BEQC_MMR6
: Mips::BEQ_MM
;
320 LL
= STI
->hasMips32r6() ? (ArePtrs64bit
? Mips::LL64_R6
: Mips::LL_R6
)
321 : (ArePtrs64bit
? Mips::LL64
: Mips::LL
);
322 SC
= STI
->hasMips32r6() ? (ArePtrs64bit
? Mips::SC64_R6
: Mips::SC_R6
)
323 : (ArePtrs64bit
? Mips::SC64
: Mips::SC
);
330 switch (I
->getOpcode()) {
331 case Mips::ATOMIC_LOAD_NAND_I8_POSTRA
:
334 case Mips::ATOMIC_LOAD_NAND_I16_POSTRA
:
337 case Mips::ATOMIC_SWAP_I8_POSTRA
:
340 case Mips::ATOMIC_SWAP_I16_POSTRA
:
343 case Mips::ATOMIC_LOAD_ADD_I8_POSTRA
:
346 case Mips::ATOMIC_LOAD_ADD_I16_POSTRA
:
349 case Mips::ATOMIC_LOAD_SUB_I8_POSTRA
:
352 case Mips::ATOMIC_LOAD_SUB_I16_POSTRA
:
355 case Mips::ATOMIC_LOAD_AND_I8_POSTRA
:
358 case Mips::ATOMIC_LOAD_AND_I16_POSTRA
:
361 case Mips::ATOMIC_LOAD_OR_I8_POSTRA
:
364 case Mips::ATOMIC_LOAD_OR_I16_POSTRA
:
367 case Mips::ATOMIC_LOAD_XOR_I8_POSTRA
:
370 case Mips::ATOMIC_LOAD_XOR_I16_POSTRA
:
374 llvm_unreachable("Unknown subword atomic pseudo for expansion!");
377 Register Dest
= I
->getOperand(0).getReg();
378 Register Ptr
= I
->getOperand(1).getReg();
379 Register Incr
= I
->getOperand(2).getReg();
380 Register Mask
= I
->getOperand(3).getReg();
381 Register Mask2
= I
->getOperand(4).getReg();
382 Register ShiftAmnt
= I
->getOperand(5).getReg();
383 Register OldVal
= I
->getOperand(6).getReg();
384 Register BinOpRes
= I
->getOperand(7).getReg();
385 Register StoreVal
= I
->getOperand(8).getReg();
387 const BasicBlock
*LLVM_BB
= BB
.getBasicBlock();
388 MachineBasicBlock
*loopMBB
= MF
->CreateMachineBasicBlock(LLVM_BB
);
389 MachineBasicBlock
*sinkMBB
= MF
->CreateMachineBasicBlock(LLVM_BB
);
390 MachineBasicBlock
*exitMBB
= MF
->CreateMachineBasicBlock(LLVM_BB
);
391 MachineFunction::iterator It
= ++BB
.getIterator();
392 MF
->insert(It
, loopMBB
);
393 MF
->insert(It
, sinkMBB
);
394 MF
->insert(It
, exitMBB
);
396 exitMBB
->splice(exitMBB
->begin(), &BB
, std::next(I
), BB
.end());
397 exitMBB
->transferSuccessorsAndUpdatePHIs(&BB
);
399 BB
.addSuccessor(loopMBB
, BranchProbability::getOne());
400 loopMBB
->addSuccessor(sinkMBB
);
401 loopMBB
->addSuccessor(loopMBB
);
402 loopMBB
->normalizeSuccProbs();
404 BuildMI(loopMBB
, DL
, TII
->get(LL
), OldVal
).addReg(Ptr
).addImm(0);
406 // and andres, oldval, incr2
407 // nor binopres, $0, andres
408 // and newval, binopres, mask
409 BuildMI(loopMBB
, DL
, TII
->get(Mips::AND
), BinOpRes
)
412 BuildMI(loopMBB
, DL
, TII
->get(Mips::NOR
), BinOpRes
)
415 BuildMI(loopMBB
, DL
, TII
->get(Mips::AND
), BinOpRes
)
418 } else if (!IsSwap
) {
419 // <binop> binopres, oldval, incr2
420 // and newval, binopres, mask
421 BuildMI(loopMBB
, DL
, TII
->get(Opcode
), BinOpRes
)
424 BuildMI(loopMBB
, DL
, TII
->get(Mips::AND
), BinOpRes
)
427 } else { // atomic.swap
428 // and newval, incr2, mask
429 BuildMI(loopMBB
, DL
, TII
->get(Mips::AND
), BinOpRes
)
434 // and StoreVal, OlddVal, Mask2
435 // or StoreVal, StoreVal, BinOpRes
436 // StoreVal<tied1> = sc StoreVal, 0(Ptr)
437 // beq StoreVal, zero, loopMBB
438 BuildMI(loopMBB
, DL
, TII
->get(Mips::AND
), StoreVal
)
439 .addReg(OldVal
).addReg(Mask2
);
440 BuildMI(loopMBB
, DL
, TII
->get(Mips::OR
), StoreVal
)
441 .addReg(StoreVal
).addReg(BinOpRes
);
442 BuildMI(loopMBB
, DL
, TII
->get(SC
), StoreVal
)
443 .addReg(StoreVal
).addReg(Ptr
).addImm(0);
444 BuildMI(loopMBB
, DL
, TII
->get(BEQ
))
445 .addReg(StoreVal
).addReg(Mips::ZERO
).addMBB(loopMBB
);
448 // and maskedoldval1,oldval,mask
449 // srl srlres,maskedoldval1,shiftamt
450 // sign_extend dest,srlres
452 sinkMBB
->addSuccessor(exitMBB
, BranchProbability::getOne());
454 BuildMI(sinkMBB
, DL
, TII
->get(Mips::AND
), Dest
)
455 .addReg(OldVal
).addReg(Mask
);
456 BuildMI(sinkMBB
, DL
, TII
->get(Mips::SRLV
), Dest
)
457 .addReg(Dest
).addReg(ShiftAmnt
);
459 if (STI
->hasMips32r2()) {
460 BuildMI(sinkMBB
, DL
, TII
->get(SEOp
), Dest
).addReg(Dest
);
462 const unsigned ShiftImm
= SEOp
== Mips::SEH
? 16 : 24;
463 BuildMI(sinkMBB
, DL
, TII
->get(Mips::SLL
), Dest
)
464 .addReg(Dest
, RegState::Kill
)
466 BuildMI(sinkMBB
, DL
, TII
->get(Mips::SRA
), Dest
)
467 .addReg(Dest
, RegState::Kill
)
471 LivePhysRegs LiveRegs
;
472 computeAndAddLiveIns(LiveRegs
, *loopMBB
);
473 computeAndAddLiveIns(LiveRegs
, *sinkMBB
);
474 computeAndAddLiveIns(LiveRegs
, *exitMBB
);
477 I
->eraseFromParent();
482 bool MipsExpandPseudo::expandAtomicBinOp(MachineBasicBlock
&BB
,
483 MachineBasicBlock::iterator I
,
484 MachineBasicBlock::iterator
&NMBBI
,
486 MachineFunction
*MF
= BB
.getParent();
488 const bool ArePtrs64bit
= STI
->getABI().ArePtrs64bit();
489 DebugLoc DL
= I
->getDebugLoc();
491 unsigned LL
, SC
, ZERO
, BEQ
;
494 if (STI
->inMicroMipsMode()) {
495 LL
= STI
->hasMips32r6() ? Mips::LL_MMR6
: Mips::LL_MM
;
496 SC
= STI
->hasMips32r6() ? Mips::SC_MMR6
: Mips::SC_MM
;
497 BEQ
= STI
->hasMips32r6() ? Mips::BEQC_MMR6
: Mips::BEQ_MM
;
499 LL
= STI
->hasMips32r6()
500 ? (ArePtrs64bit
? Mips::LL64_R6
: Mips::LL_R6
)
501 : (ArePtrs64bit
? Mips::LL64
: Mips::LL
);
502 SC
= STI
->hasMips32r6()
503 ? (ArePtrs64bit
? Mips::SC64_R6
: Mips::SC_R6
)
504 : (ArePtrs64bit
? Mips::SC64
: Mips::SC
);
510 LL
= STI
->hasMips64r6() ? Mips::LLD_R6
: Mips::LLD
;
511 SC
= STI
->hasMips64r6() ? Mips::SCD_R6
: Mips::SCD
;
512 ZERO
= Mips::ZERO_64
;
516 Register OldVal
= I
->getOperand(0).getReg();
517 Register Ptr
= I
->getOperand(1).getReg();
518 Register Incr
= I
->getOperand(2).getReg();
519 Register Scratch
= I
->getOperand(3).getReg();
526 switch (I
->getOpcode()) {
527 case Mips::ATOMIC_LOAD_ADD_I32_POSTRA
:
530 case Mips::ATOMIC_LOAD_SUB_I32_POSTRA
:
533 case Mips::ATOMIC_LOAD_AND_I32_POSTRA
:
536 case Mips::ATOMIC_LOAD_OR_I32_POSTRA
:
539 case Mips::ATOMIC_LOAD_XOR_I32_POSTRA
:
542 case Mips::ATOMIC_LOAD_NAND_I32_POSTRA
:
547 case Mips::ATOMIC_SWAP_I32_POSTRA
:
550 case Mips::ATOMIC_LOAD_ADD_I64_POSTRA
:
551 Opcode
= Mips::DADDu
;
553 case Mips::ATOMIC_LOAD_SUB_I64_POSTRA
:
554 Opcode
= Mips::DSUBu
;
556 case Mips::ATOMIC_LOAD_AND_I64_POSTRA
:
557 Opcode
= Mips::AND64
;
559 case Mips::ATOMIC_LOAD_OR_I64_POSTRA
:
562 case Mips::ATOMIC_LOAD_XOR_I64_POSTRA
:
563 Opcode
= Mips::XOR64
;
565 case Mips::ATOMIC_LOAD_NAND_I64_POSTRA
:
570 case Mips::ATOMIC_SWAP_I64_POSTRA
:
574 llvm_unreachable("Unknown pseudo atomic!");
577 const BasicBlock
*LLVM_BB
= BB
.getBasicBlock();
578 MachineBasicBlock
*loopMBB
= MF
->CreateMachineBasicBlock(LLVM_BB
);
579 MachineBasicBlock
*exitMBB
= MF
->CreateMachineBasicBlock(LLVM_BB
);
580 MachineFunction::iterator It
= ++BB
.getIterator();
581 MF
->insert(It
, loopMBB
);
582 MF
->insert(It
, exitMBB
);
584 exitMBB
->splice(exitMBB
->begin(), &BB
, std::next(I
), BB
.end());
585 exitMBB
->transferSuccessorsAndUpdatePHIs(&BB
);
587 BB
.addSuccessor(loopMBB
, BranchProbability::getOne());
588 loopMBB
->addSuccessor(exitMBB
);
589 loopMBB
->addSuccessor(loopMBB
);
590 loopMBB
->normalizeSuccProbs();
592 BuildMI(loopMBB
, DL
, TII
->get(LL
), OldVal
).addReg(Ptr
).addImm(0);
593 assert((OldVal
!= Ptr
) && "Clobbered the wrong ptr reg!");
594 assert((OldVal
!= Incr
) && "Clobbered the wrong reg!");
596 BuildMI(loopMBB
, DL
, TII
->get(Opcode
), Scratch
).addReg(OldVal
).addReg(Incr
);
599 "Unknown nand instruction for atomic pseudo expansion");
600 BuildMI(loopMBB
, DL
, TII
->get(AND
), Scratch
).addReg(OldVal
).addReg(Incr
);
601 BuildMI(loopMBB
, DL
, TII
->get(NOR
), Scratch
).addReg(ZERO
).addReg(Scratch
);
603 assert(OR
&& "Unknown instruction for atomic pseudo expansion!");
604 BuildMI(loopMBB
, DL
, TII
->get(OR
), Scratch
).addReg(Incr
).addReg(ZERO
);
607 BuildMI(loopMBB
, DL
, TII
->get(SC
), Scratch
).addReg(Scratch
).addReg(Ptr
).addImm(0);
608 BuildMI(loopMBB
, DL
, TII
->get(BEQ
)).addReg(Scratch
).addReg(ZERO
).addMBB(loopMBB
);
611 I
->eraseFromParent();
613 LivePhysRegs LiveRegs
;
614 computeAndAddLiveIns(LiveRegs
, *loopMBB
);
615 computeAndAddLiveIns(LiveRegs
, *exitMBB
);
620 bool MipsExpandPseudo::expandMI(MachineBasicBlock
&MBB
,
621 MachineBasicBlock::iterator MBBI
,
622 MachineBasicBlock::iterator
&NMBB
) {
624 bool Modified
= false;
626 switch (MBBI
->getOpcode()) {
627 case Mips::ATOMIC_CMP_SWAP_I32_POSTRA
:
628 case Mips::ATOMIC_CMP_SWAP_I64_POSTRA
:
629 return expandAtomicCmpSwap(MBB
, MBBI
, NMBB
);
630 case Mips::ATOMIC_CMP_SWAP_I8_POSTRA
:
631 case Mips::ATOMIC_CMP_SWAP_I16_POSTRA
:
632 return expandAtomicCmpSwapSubword(MBB
, MBBI
, NMBB
);
633 case Mips::ATOMIC_SWAP_I8_POSTRA
:
634 case Mips::ATOMIC_SWAP_I16_POSTRA
:
635 case Mips::ATOMIC_LOAD_NAND_I8_POSTRA
:
636 case Mips::ATOMIC_LOAD_NAND_I16_POSTRA
:
637 case Mips::ATOMIC_LOAD_ADD_I8_POSTRA
:
638 case Mips::ATOMIC_LOAD_ADD_I16_POSTRA
:
639 case Mips::ATOMIC_LOAD_SUB_I8_POSTRA
:
640 case Mips::ATOMIC_LOAD_SUB_I16_POSTRA
:
641 case Mips::ATOMIC_LOAD_AND_I8_POSTRA
:
642 case Mips::ATOMIC_LOAD_AND_I16_POSTRA
:
643 case Mips::ATOMIC_LOAD_OR_I8_POSTRA
:
644 case Mips::ATOMIC_LOAD_OR_I16_POSTRA
:
645 case Mips::ATOMIC_LOAD_XOR_I8_POSTRA
:
646 case Mips::ATOMIC_LOAD_XOR_I16_POSTRA
:
647 return expandAtomicBinOpSubword(MBB
, MBBI
, NMBB
);
648 case Mips::ATOMIC_LOAD_ADD_I32_POSTRA
:
649 case Mips::ATOMIC_LOAD_SUB_I32_POSTRA
:
650 case Mips::ATOMIC_LOAD_AND_I32_POSTRA
:
651 case Mips::ATOMIC_LOAD_OR_I32_POSTRA
:
652 case Mips::ATOMIC_LOAD_XOR_I32_POSTRA
:
653 case Mips::ATOMIC_LOAD_NAND_I32_POSTRA
:
654 case Mips::ATOMIC_SWAP_I32_POSTRA
:
655 return expandAtomicBinOp(MBB
, MBBI
, NMBB
, 4);
656 case Mips::ATOMIC_LOAD_ADD_I64_POSTRA
:
657 case Mips::ATOMIC_LOAD_SUB_I64_POSTRA
:
658 case Mips::ATOMIC_LOAD_AND_I64_POSTRA
:
659 case Mips::ATOMIC_LOAD_OR_I64_POSTRA
:
660 case Mips::ATOMIC_LOAD_XOR_I64_POSTRA
:
661 case Mips::ATOMIC_LOAD_NAND_I64_POSTRA
:
662 case Mips::ATOMIC_SWAP_I64_POSTRA
:
663 return expandAtomicBinOp(MBB
, MBBI
, NMBB
, 8);
669 bool MipsExpandPseudo::expandMBB(MachineBasicBlock
&MBB
) {
670 bool Modified
= false;
672 MachineBasicBlock::iterator MBBI
= MBB
.begin(), E
= MBB
.end();
674 MachineBasicBlock::iterator NMBBI
= std::next(MBBI
);
675 Modified
|= expandMI(MBB
, MBBI
, NMBBI
);
682 bool MipsExpandPseudo::runOnMachineFunction(MachineFunction
&MF
) {
683 STI
= &static_cast<const MipsSubtarget
&>(MF
.getSubtarget());
684 TII
= STI
->getInstrInfo();
686 bool Modified
= false;
687 for (MachineFunction::iterator MFI
= MF
.begin(), E
= MF
.end(); MFI
!= E
;
689 Modified
|= expandMBB(*MFI
);
697 /// createMipsExpandPseudoPass - returns an instance of the pseudo instruction
699 FunctionPass
*llvm::createMipsExpandPseudoPass() {
700 return new MipsExpandPseudo();