summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--llvm/include/llvm/CodeGen/MachineOutliner.h7
-rw-r--r--llvm/lib/CodeGen/MachineOutliner.cpp11
-rw-r--r--llvm/lib/Target/AArch64/AArch64InstrInfo.cpp46
3 files changed, 39 insertions, 25 deletions
diff --git a/llvm/include/llvm/CodeGen/MachineOutliner.h b/llvm/include/llvm/CodeGen/MachineOutliner.h
index eaa741353ab..2bd39b2392d 100644
--- a/llvm/include/llvm/CodeGen/MachineOutliner.h
+++ b/llvm/include/llvm/CodeGen/MachineOutliner.h
@@ -82,6 +82,9 @@ public:
/// been used across the sequence.
LiveRegUnits UsedInSequence;
+ /// Target-specific flags for this Candidate's MBB.
+ unsigned Flags = 0x0;
+
/// Return the number of instructions in this Candidate.
unsigned getLength() const { return Len; }
@@ -120,9 +123,9 @@ public:
Candidate(unsigned StartIdx, unsigned Len,
MachineBasicBlock::iterator &FirstInst,
MachineBasicBlock::iterator &LastInst, MachineBasicBlock *MBB,
- unsigned FunctionIdx)
+ unsigned FunctionIdx, unsigned Flags)
: StartIdx(StartIdx), Len(Len), FirstInst(FirstInst), LastInst(LastInst),
- MBB(MBB), FunctionIdx(FunctionIdx) {}
+ MBB(MBB), FunctionIdx(FunctionIdx), Flags(Flags) {}
Candidate() {}
/// Used to ensure that \p Candidates are outlined in an order that
diff --git a/llvm/lib/CodeGen/MachineOutliner.cpp b/llvm/lib/CodeGen/MachineOutliner.cpp
index 6b9faddd9b2..49d0893afd7 100644
--- a/llvm/lib/CodeGen/MachineOutliner.cpp
+++ b/llvm/lib/CodeGen/MachineOutliner.cpp
@@ -625,6 +625,9 @@ struct InstructionMapper {
/// Inverse of \p InstructionIntegerMap.
DenseMap<unsigned, MachineInstr *> IntegerInstructionMap;
+ /// Correspondence between \p MachineBasicBlocks and target-defined flags.
+ DenseMap<MachineBasicBlock *, unsigned> MBBFlagsMap;
+
/// The vector of unsigned integers that the module is mapped to.
std::vector<unsigned> UnsignedVec;
@@ -748,6 +751,9 @@ struct InstructionMapper {
if (!TII.isMBBSafeToOutlineFrom(MBB, Flags))
return;
+ // Store info for the MBB for later outlining.
+ MBBFlagsMap[&MBB] = Flags;
+
MachineBasicBlock::iterator It = MBB.begin();
// The number of instructions in this block that will be considered for
@@ -1106,10 +1112,11 @@ unsigned MachineOutliner::findCandidates(
MachineBasicBlock::iterator StartIt = Mapper.InstrList[StartIdx];
MachineBasicBlock::iterator EndIt = Mapper.InstrList[EndIdx];
+ MachineBasicBlock *MBB = StartIt->getParent();
CandidatesForRepeatedSeq.emplace_back(StartIdx, StringLen, StartIt,
- EndIt, StartIt->getParent(),
- FunctionList.size());
+ EndIt, MBB, FunctionList.size(),
+ Mapper.MBBFlagsMap[MBB]);
}
}
diff --git a/llvm/lib/Target/AArch64/AArch64InstrInfo.cpp b/llvm/lib/Target/AArch64/AArch64InstrInfo.cpp
index 176514dd361..219dd4ddf5a 100644
--- a/llvm/lib/Target/AArch64/AArch64InstrInfo.cpp
+++ b/llvm/lib/Target/AArch64/AArch64InstrInfo.cpp
@@ -5128,12 +5128,12 @@ AArch64InstrInfo::findRegisterToSaveLRTo(const outliner::Candidate &C) const {
outliner::OutlinedFunction
AArch64InstrInfo::getOutliningCandidateInfo(
std::vector<outliner::Candidate> &RepeatedSequenceLocs) const {
- unsigned SequenceSize = std::accumulate(
- RepeatedSequenceLocs[0].front(),
- std::next(RepeatedSequenceLocs[0].back()),
- 0, [this](unsigned Sum, const MachineInstr &MI) {
- return Sum + getInstSizeInBytes(MI);
- });
+ outliner::Candidate &FirstCand = RepeatedSequenceLocs[0];
+ unsigned SequenceSize =
+ std::accumulate(FirstCand.front(), std::next(FirstCand.back()), 0,
+ [this](unsigned Sum, const MachineInstr &MI) {
+ return Sum + getInstSizeInBytes(MI);
+ });
// Compute liveness information for each candidate.
const TargetRegisterInfo &TRI = getRegisterInfo();
@@ -5240,21 +5240,25 @@ AArch64InstrInfo::getOutliningCandidateInfo(
}
}
- // Check if the range contains a call. These require a save + restore of the
- // link register.
- if (std::any_of(RepeatedSequenceLocs[0].front(),
- RepeatedSequenceLocs[0].back(),
- [](const MachineInstr &MI) { return MI.isCall(); }))
- NumBytesToCreateFrame += 8; // Save + restore the link register.
-
- // Handle the last instruction separately. If this is a tail call, then the
- // last instruction is a call. We don't want to save + restore in this case.
- // However, it could be possible that the last instruction is a call without
- // it being valid to tail call this sequence. We should consider this as well.
- else if (FrameID != MachineOutlinerThunk &&
- FrameID != MachineOutlinerTailCall &&
- RepeatedSequenceLocs[0].back()->isCall())
- NumBytesToCreateFrame += 8;
+ // If the MBB containing the first candidate has calls, then it's possible
+ // that we have calls in the candidate. If there are no calls, then there's
+ // no way that any candidate could have any calls.
+ if (FirstCand.Flags & MachineOutlinerMBBFlags::HasCalls) {
+ // Check if the range contains a call. These require a save + restore of the
+ // link register.
+ if (std::any_of(FirstCand.front(), FirstCand.back(),
+ [](const MachineInstr &MI) { return MI.isCall(); }))
+ NumBytesToCreateFrame += 8; // Save + restore the link register.
+
+ // Handle the last instruction separately. If this is a tail call, then the
+ // last instruction is a call. We don't want to save + restore in this case.
+ // However, it could be possible that the last instruction is a call without
+ // it being valid to tail call this sequence. We should consider this as
+ // well.
+ else if (FrameID != MachineOutlinerThunk &&
+ FrameID != MachineOutlinerTailCall && FirstCand.back()->isCall())
+ NumBytesToCreateFrame += 8;
+ }
return outliner::OutlinedFunction(RepeatedSequenceLocs, SequenceSize,
NumBytesToCreateFrame, FrameID);
OpenPOWER on IntegriCloud