forked from OSchip/llvm-project
[AVR] Fix rotate instructions
This patch fixes some issues with the RORB pseudo instruction. - A minor issue in which the instructions were said to use the SREG, which is not true. - An issue with the BLD instruction, which did not have an output operand. - A major issue in which invalid instructions were generated. The fix also reduce RORB from 4 to 3 instructions, so it's also a small optimization. These issues were flagged by the machine verifier. Differential Revision: https://reviews.llvm.org/D96957
This commit is contained in:
parent
6aa9e746eb
commit
41f905b211
|
@ -1345,42 +1345,20 @@ bool AVRExpandPseudo::expand<AVR::RORBRd>(Block &MBB, BlockIt MBBI) {
|
|||
// to explicitly add the carry bit.
|
||||
|
||||
MachineInstr &MI = *MBBI;
|
||||
unsigned OpShiftOut, OpLoad, OpShiftIn, OpAdd;
|
||||
Register DstReg = MI.getOperand(0).getReg();
|
||||
bool DstIsDead = MI.getOperand(0).isDead();
|
||||
OpShiftOut = AVR::LSRRd;
|
||||
OpLoad = AVR::LDIRdK;
|
||||
OpShiftIn = AVR::RORRd;
|
||||
OpAdd = AVR::ORRdRr;
|
||||
|
||||
// lsr r16
|
||||
// ldi r0, 0
|
||||
// ror r0
|
||||
// or r16, r17
|
||||
// bst r16, 0
|
||||
// ror r16
|
||||
// bld r16, 7
|
||||
|
||||
// Shift out
|
||||
buildMI(MBB, MBBI, OpShiftOut)
|
||||
.addReg(DstReg, RegState::Define | getDeadRegState(DstIsDead))
|
||||
.addReg(DstReg);
|
||||
// Move the lowest bit from DstReg into the T bit
|
||||
buildMI(MBB, MBBI, AVR::BST).addReg(DstReg).addImm(0);
|
||||
|
||||
// Put 0 in temporary register
|
||||
buildMI(MBB, MBBI, OpLoad)
|
||||
.addReg(SCRATCH_REGISTER, RegState::Define | getDeadRegState(true))
|
||||
.addImm(0x00);
|
||||
// Rotate to the right
|
||||
buildMI(MBB, MBBI, AVR::RORRd, DstReg).addReg(DstReg);
|
||||
|
||||
// Shift in
|
||||
buildMI(MBB, MBBI, OpShiftIn)
|
||||
.addReg(SCRATCH_REGISTER, RegState::Define | getDeadRegState(true))
|
||||
.addReg(SCRATCH_REGISTER);
|
||||
|
||||
// Add the results together using an or-instruction
|
||||
auto MIB = buildMI(MBB, MBBI, OpAdd)
|
||||
.addReg(DstReg, RegState::Define | getDeadRegState(DstIsDead))
|
||||
.addReg(DstReg)
|
||||
.addReg(SCRATCH_REGISTER);
|
||||
|
||||
// SREG is always implicitly killed
|
||||
MIB->getOperand(2).setIsKill();
|
||||
// Move the T bit into the highest bit of DstReg.
|
||||
buildMI(MBB, MBBI, AVR::BLD, DstReg).addReg(DstReg).addImm(7);
|
||||
|
||||
MI.eraseFromParent();
|
||||
return true;
|
||||
|
|
|
@ -1735,20 +1735,19 @@ Defs = [SREG] in
|
|||
"asrw\t$rd",
|
||||
[(set i16:$rd, (AVRasr i16:$src)), (implicit SREG)]>;
|
||||
|
||||
def ROLBRd : Pseudo<(outs GPR8:$rd),
|
||||
(ins GPR8:$src),
|
||||
"rolb\t$rd",
|
||||
[(set i8:$rd, (AVRrol i8:$src)), (implicit SREG)]>;
|
||||
|
||||
def RORBRd : Pseudo<(outs GPR8:$rd),
|
||||
(ins GPR8:$src),
|
||||
"rorb\t$rd",
|
||||
[(set i8:$rd, (AVRror i8:$src)), (implicit SREG)]>;
|
||||
|
||||
// Bit rotate operations.
|
||||
let Uses = [SREG] in
|
||||
{
|
||||
// 8-bit ROL is an alias of ADC Rd, Rd
|
||||
|
||||
def ROLBRd : Pseudo<(outs GPR8:$rd),
|
||||
(ins GPR8:$src),
|
||||
"rolb\t$rd",
|
||||
[(set i8:$rd, (AVRrol i8:$src)), (implicit SREG)]>;
|
||||
|
||||
def RORBRd : Pseudo<(outs GPR8:$rd),
|
||||
(ins GPR8:$src),
|
||||
"rorb\t$rd",
|
||||
[(set i8:$rd, (AVRror i8:$src)), (implicit SREG)]>;
|
||||
|
||||
def ROLWRd : Pseudo<(outs DREGS:$rd),
|
||||
(ins DREGS:$src),
|
||||
|
@ -1804,10 +1803,11 @@ def BST : FRdB<0b01,
|
|||
"bst\t$rd, $b",
|
||||
[]>;
|
||||
|
||||
let Uses = [SREG] in
|
||||
let Constraints = "$src = $rd",
|
||||
Uses = [SREG] in
|
||||
def BLD : FRdB<0b00,
|
||||
(outs),
|
||||
(ins GPR8:$rd, i8imm:$b),
|
||||
(outs GPR8:$rd),
|
||||
(ins GPR8:$src, i8imm:$b),
|
||||
"bld\t$rd, $b",
|
||||
[]>;
|
||||
|
||||
|
|
|
@ -37,10 +37,9 @@ define i8 @ror8(i8 %val, i8 %amt) {
|
|||
; CHECK-NEXT: brmi .LBB1_2
|
||||
|
||||
; CHECK-NEXT: .LBB1_1:
|
||||
; CHECK-NEXT: lsr r24
|
||||
; CHECK-NEXT: ldi r0, 0
|
||||
; CHECK-NEXT: ror r0
|
||||
; CHECK-NEXT: or r24, r0
|
||||
; CHECK-NEXT: bst r24, 0
|
||||
; CHECK-NEXT: ror r24
|
||||
; CHECK-NEXT: bld r24, 7
|
||||
; CHECK-NEXT: dec r22
|
||||
; CHECK-NEXT: brpl .LBB1_1
|
||||
|
||||
|
|
Loading…
Reference in New Issue