diff --git a/llvm/lib/Target/ARM/ARMExpandPseudoInsts.cpp b/llvm/lib/Target/ARM/ARMExpandPseudoInsts.cpp --- a/llvm/lib/Target/ARM/ARMExpandPseudoInsts.cpp +++ b/llvm/lib/Target/ARM/ARMExpandPseudoInsts.cpp @@ -1333,7 +1333,7 @@ const LivePhysRegs &LiveRegs, SmallVectorImpl &ScratchRegs) { if (STI->hasV8_1MMainlineOps()) CMSESaveClearFPRegsV81(MBB, MBBI, DL, LiveRegs); - else + else if (STI->hasV8MMainlineOps()) CMSESaveClearFPRegsV8(MBB, MBBI, DL, LiveRegs, ScratchRegs); } @@ -1341,8 +1341,6 @@ void ARMExpandPseudo::CMSESaveClearFPRegsV8( MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI, DebugLoc &DL, const LivePhysRegs &LiveRegs, SmallVectorImpl &ScratchRegs) { - if (!STI->hasFPRegs()) - return; // Store an available register for FPSCR clearing assert(!ScratchRegs.empty()); @@ -1396,7 +1394,11 @@ bool passesFPReg = (!NonclearedFPRegs.empty() || !ClearedFPRegs.empty()); - // Lazy store all fp registers to the stack + if (passesFPReg) + assert(STI->hasFPRegs() && "Subtarget needs fpregs"); + + // Lazy store all fp registers to the stack. + // This executes as NOP in the absence of floating-point support. MachineInstrBuilder VLSTM = BuildMI(MBB, MBBI, DL, TII->get(ARM::VLSTM)) .addReg(ARM::SP) .add(predOps(ARMCC::AL)); @@ -1524,15 +1526,13 @@ SmallVectorImpl &AvailableRegs) { if (STI->hasV8_1MMainlineOps()) CMSERestoreFPRegsV81(MBB, MBBI, DL, AvailableRegs); - else + else if (STI->hasV8MMainlineOps()) CMSERestoreFPRegsV8(MBB, MBBI, DL, AvailableRegs); } void ARMExpandPseudo::CMSERestoreFPRegsV8( MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI, DebugLoc &DL, SmallVectorImpl &AvailableRegs) { - if (!STI->hasFPRegs()) - return; // Use AvailableRegs to store the fp regs std::vector> ClearedFPRegs; @@ -1574,6 +1574,11 @@ } } + bool returnsFPReg = (!NonclearedFPRegs.empty() || !ClearedFPRegs.empty()); + + if (returnsFPReg) + assert(STI->hasFPRegs() && "Subtarget needs fpregs"); + // Push FP regs that cannot be restored via normal registers on the stack for (unsigned Reg : NonclearedFPRegs) { if (ARM::DPR_VFP2RegClass.contains(Reg)) @@ -1588,7 +1593,8 @@ .add(predOps(ARMCC::AL)); } - // Lazy load fp regs from stack + // Lazy load fp regs from stack. + // This executes as NOP in the absence of floating-point support. BuildMI(MBB, MBBI, DL, TII->get(ARM::VLLDM)) .addReg(ARM::SP) .add(predOps(ARMCC::AL)); diff --git a/llvm/test/CodeGen/ARM/cmse-clear.ll b/llvm/test/CodeGen/ARM/cmse-clear.ll --- a/llvm/test/CodeGen/ARM/cmse-clear.ll +++ b/llvm/test/CodeGen/ARM/cmse-clear.ll @@ -166,7 +166,8 @@ ; CHECK-8M-SOFT-NEXT: movs r0, #10 ; CHECK-8M-SOFT-NEXT: push.w {r4, r5, r6, r7, r8, r9, r10, r11} ; CHECK-8M-SOFT-NEXT: bic r1, r1, #1 -; CHECK-8M-SOFT-NEXT: msr apsr_nzcvqg, r1 +; CHECK-8M-SOFT-NEXT: sub sp, #136 +; CHECK-8M-SOFT-NEXT: vlstm sp ; CHECK-8M-SOFT-NEXT: mov r2, r1 ; CHECK-8M-SOFT-NEXT: mov r3, r1 ; CHECK-8M-SOFT-NEXT: mov r4, r1 @@ -178,7 +179,10 @@ ; CHECK-8M-SOFT-NEXT: mov r10, r1 ; CHECK-8M-SOFT-NEXT: mov r11, r1 ; CHECK-8M-SOFT-NEXT: mov r12, r1 +; CHECK-8M-SOFT-NEXT: msr apsr_nzcvqg, r1 ; CHECK-8M-SOFT-NEXT: blxns r1 +; CHECK-8M-SOFT-NEXT: vlldm sp +; CHECK-8M-SOFT-NEXT: add sp, #136 ; CHECK-8M-SOFT-NEXT: pop.w {r4, r5, r6, r7, r8, r9, r10, r11} ; CHECK-8M-SOFT-NEXT: pop {r7, pc} ; @@ -291,7 +295,8 @@ ; CHECK-8M-SOFT-NEXT: movs r0, #10 ; CHECK-8M-SOFT-NEXT: push.w {r4, r5, r6, r7, r8, r9, r10, r11} ; CHECK-8M-SOFT-NEXT: bic r1, r1, #1 -; CHECK-8M-SOFT-NEXT: msr apsr_nzcvqg, r1 +; CHECK-8M-SOFT-NEXT: sub sp, #136 +; CHECK-8M-SOFT-NEXT: vlstm sp ; CHECK-8M-SOFT-NEXT: mov r2, r1 ; CHECK-8M-SOFT-NEXT: mov r3, r1 ; CHECK-8M-SOFT-NEXT: mov r4, r1 @@ -303,7 +308,10 @@ ; CHECK-8M-SOFT-NEXT: mov r10, r1 ; CHECK-8M-SOFT-NEXT: mov r11, r1 ; CHECK-8M-SOFT-NEXT: mov r12, r1 +; CHECK-8M-SOFT-NEXT: msr apsr_nzcvqg, r1 ; CHECK-8M-SOFT-NEXT: blxns r1 +; CHECK-8M-SOFT-NEXT: vlldm sp +; CHECK-8M-SOFT-NEXT: add sp, #136 ; CHECK-8M-SOFT-NEXT: pop.w {r4, r5, r6, r7, r8, r9, r10, r11} ; CHECK-8M-SOFT-NEXT: pop {r7, pc} ; @@ -423,7 +431,8 @@ ; CHECK-8M-SOFT-NEXT: mov r2, r12 ; CHECK-8M-SOFT-NEXT: push.w {r4, r5, r6, r7, r8, r9, r10, r11} ; CHECK-8M-SOFT-NEXT: bic r4, r4, #1 -; CHECK-8M-SOFT-NEXT: msr apsr_nzcvqg, r4 +; CHECK-8M-SOFT-NEXT: sub sp, #136 +; CHECK-8M-SOFT-NEXT: vlstm sp ; CHECK-8M-SOFT-NEXT: mov r5, r4 ; CHECK-8M-SOFT-NEXT: mov r6, r4 ; CHECK-8M-SOFT-NEXT: mov r7, r4 @@ -432,7 +441,10 @@ ; CHECK-8M-SOFT-NEXT: mov r10, r4 ; CHECK-8M-SOFT-NEXT: mov r11, r4 ; CHECK-8M-SOFT-NEXT: mov r12, r4 +; CHECK-8M-SOFT-NEXT: msr apsr_nzcvqg, r4 ; CHECK-8M-SOFT-NEXT: blxns r4 +; CHECK-8M-SOFT-NEXT: vlldm sp +; CHECK-8M-SOFT-NEXT: add sp, #136 ; CHECK-8M-SOFT-NEXT: pop.w {r4, r5, r6, r7, r8, r9, r10, r11} ; CHECK-8M-SOFT-NEXT: mov r0, r4 ; CHECK-8M-SOFT-NEXT: pop {r4, pc} @@ -554,7 +566,8 @@ ; CHECK-8M-SOFT-NEXT: push {r7, lr} ; CHECK-8M-SOFT-NEXT: push.w {r4, r5, r6, r7, r8, r9, r10, r11} ; CHECK-8M-SOFT-NEXT: bic r1, r1, #1 -; CHECK-8M-SOFT-NEXT: msr apsr_nzcvqg, r1 +; CHECK-8M-SOFT-NEXT: sub sp, #136 +; CHECK-8M-SOFT-NEXT: vlstm sp ; CHECK-8M-SOFT-NEXT: mov r0, r1 ; CHECK-8M-SOFT-NEXT: mov r2, r1 ; CHECK-8M-SOFT-NEXT: mov r3, r1 @@ -567,7 +580,10 @@ ; CHECK-8M-SOFT-NEXT: mov r10, r1 ; CHECK-8M-SOFT-NEXT: mov r11, r1 ; CHECK-8M-SOFT-NEXT: mov r12, r1 +; CHECK-8M-SOFT-NEXT: msr apsr_nzcvqg, r1 ; CHECK-8M-SOFT-NEXT: blxns r1 +; CHECK-8M-SOFT-NEXT: vlldm sp +; CHECK-8M-SOFT-NEXT: add sp, #136 ; CHECK-8M-SOFT-NEXT: pop.w {r4, r5, r6, r7, r8, r9, r10, r11} ; CHECK-8M-SOFT-NEXT: pop {r7, pc} ; diff --git a/llvm/test/CodeGen/ARM/cmse.ll b/llvm/test/CodeGen/ARM/cmse.ll --- a/llvm/test/CodeGen/ARM/cmse.ll +++ b/llvm/test/CodeGen/ARM/cmse.ll @@ -61,7 +61,8 @@ ; CHECK-8M-NEXT: push {r7, lr} ; CHECK-8M-NEXT: push.w {r4, r5, r6, r7, r8, r9, r10, r11} ; CHECK-8M-NEXT: bic r0, r0, #1 -; CHECK-8M-NEXT: msr apsr_nzcvq, r0 +; CHECK-8M-NEXT: sub sp, #136 +; CHECK-8M-NEXT: vlstm sp ; CHECK-8M-NEXT: mov r1, r0 ; CHECK-8M-NEXT: mov r2, r0 ; CHECK-8M-NEXT: mov r3, r0 @@ -74,7 +75,10 @@ ; CHECK-8M-NEXT: mov r10, r0 ; CHECK-8M-NEXT: mov r11, r0 ; CHECK-8M-NEXT: mov r12, r0 +; CHECK-8M-NEXT: msr apsr_nzcvq, r0 ; CHECK-8M-NEXT: blxns r0 +; CHECK-8M-NEXT: vlldm sp +; CHECK-8M-NEXT: add sp, #136 ; CHECK-8M-NEXT: pop.w {r4, r5, r6, r7, r8, r9, r10, r11} ; CHECK-8M-NEXT: pop.w {r7, lr} ; CHECK-8M-NEXT: mov r0, lr @@ -152,7 +156,8 @@ ; CHECK-8M-NEXT: push {r7, lr} ; CHECK-8M-NEXT: push.w {r4, r5, r6, r7, r8, r9, r10, r11} ; CHECK-8M-NEXT: bic r0, r0, #1 -; CHECK-8M-NEXT: msr apsr_nzcvq, r0 +; CHECK-8M-NEXT: sub sp, #136 +; CHECK-8M-NEXT: vlstm sp ; CHECK-8M-NEXT: mov r1, r0 ; CHECK-8M-NEXT: mov r2, r0 ; CHECK-8M-NEXT: mov r3, r0 @@ -165,7 +170,10 @@ ; CHECK-8M-NEXT: mov r10, r0 ; CHECK-8M-NEXT: mov r11, r0 ; CHECK-8M-NEXT: mov r12, r0 +; CHECK-8M-NEXT: msr apsr_nzcvq, r0 ; CHECK-8M-NEXT: blxns r0 +; CHECK-8M-NEXT: vlldm sp +; CHECK-8M-NEXT: add sp, #136 ; CHECK-8M-NEXT: pop.w {r4, r5, r6, r7, r8, r9, r10, r11} ; CHECK-8M-NEXT: pop {r7, pc} ;