mirror of
https://github.com/RPCS3/llvm-mirror.git
synced 2024-11-22 18:54:02 +01:00
[Profile] refactor meta data copying/swapping code
Differential Revision: http://reviews.llvm.org/D23619 llvm-svn: 279523
This commit is contained in:
parent
a7c0951c9e
commit
df1f2a779a
@ -198,6 +198,16 @@ public:
|
||||
void setMetadata(unsigned KindID, MDNode *Node);
|
||||
void setMetadata(StringRef Kind, MDNode *Node);
|
||||
|
||||
/// Copy metadata from \p SrcInst to this instruction. \p WL, if not empty,
|
||||
/// specifies the list of meta data that needs to be copied. If \p WL is
|
||||
/// empty, all meta data will be copied.
|
||||
void copyMetadata(const Instruction &SrcInst, ArrayRef<unsigned> WL = {});
|
||||
|
||||
/// If the instruction has "branch_weights" MD_prof metadata and the MDNode
|
||||
/// has three operands (including name string), swap the order of the
|
||||
/// metadata.
|
||||
void swapProfMetadata();
|
||||
|
||||
/// Drop all unknown metadata except for debug locations.
|
||||
/// @{
|
||||
/// Passes are required to drop metadata they don't understand. This is a
|
||||
|
@ -11,6 +11,7 @@
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "llvm/ADT/DenseSet.h"
|
||||
#include "llvm/IR/Instruction.h"
|
||||
#include "llvm/IR/CallSite.h"
|
||||
#include "llvm/IR/Constants.h"
|
||||
@ -632,6 +633,47 @@ Instruction *Instruction::cloneImpl() const {
|
||||
llvm_unreachable("Subclass of Instruction failed to implement cloneImpl");
|
||||
}
|
||||
|
||||
void Instruction::swapProfMetadata() {
|
||||
MDNode *ProfileData = getMetadata(LLVMContext::MD_prof);
|
||||
if (!ProfileData || ProfileData->getNumOperands() != 3 ||
|
||||
!isa<MDString>(ProfileData->getOperand(0)))
|
||||
return;
|
||||
|
||||
MDString *MDName = cast<MDString>(ProfileData->getOperand(0));
|
||||
if (MDName->getString() != "branch_weights")
|
||||
return;
|
||||
|
||||
// The first operand is the name. Fetch them backwards and build a new one.
|
||||
Metadata *Ops[] = {ProfileData->getOperand(0), ProfileData->getOperand(2),
|
||||
ProfileData->getOperand(1)};
|
||||
setMetadata(LLVMContext::MD_prof,
|
||||
MDNode::get(ProfileData->getContext(), Ops));
|
||||
}
|
||||
|
||||
/// Copy meta data from \p SrcInst to this instruction. If WL is empty, all
|
||||
/// data will be copied, otherwise only ones specified in WL will be copied.
|
||||
void Instruction::copyMetadata(const Instruction &SrcInst,
|
||||
ArrayRef<unsigned> WL) {
|
||||
if (!SrcInst.hasMetadata())
|
||||
return;
|
||||
|
||||
DenseSet<unsigned> WLS;
|
||||
for (unsigned M : WL)
|
||||
WLS.insert(M);
|
||||
|
||||
// Otherwise, enumerate and copy over metadata from the old instruction to the
|
||||
// new one.
|
||||
SmallVector<std::pair<unsigned, MDNode *>, 4> TheMDs;
|
||||
SrcInst.getAllMetadataOtherThanDebugLoc(TheMDs);
|
||||
for (const auto &MD : TheMDs) {
|
||||
if (WL.empty() || WLS.count(MD.first))
|
||||
setMetadata(MD.first, MD.second);
|
||||
}
|
||||
if (WL.empty() || WLS.count(LLVMContext::MD_dbg))
|
||||
setDebugLoc(SrcInst.getDebugLoc());
|
||||
return;
|
||||
}
|
||||
|
||||
Instruction *Instruction::clone() const {
|
||||
Instruction *New = nullptr;
|
||||
switch (getOpcode()) {
|
||||
@ -646,16 +688,6 @@ Instruction *Instruction::clone() const {
|
||||
}
|
||||
|
||||
New->SubclassOptionalData = SubclassOptionalData;
|
||||
if (!hasMetadata())
|
||||
return New;
|
||||
|
||||
// Otherwise, enumerate and copy over metadata from the old instruction to the
|
||||
// new one.
|
||||
SmallVector<std::pair<unsigned, MDNode *>, 4> TheMDs;
|
||||
getAllMetadataOtherThanDebugLoc(TheMDs);
|
||||
for (const auto &MD : TheMDs)
|
||||
New->setMetadata(MD.first, MD.second);
|
||||
|
||||
New->setDebugLoc(getDebugLoc());
|
||||
New->copyMetadata(*this);
|
||||
return New;
|
||||
}
|
||||
|
@ -1209,15 +1209,7 @@ void BranchInst::swapSuccessors() {
|
||||
|
||||
// Update profile metadata if present and it matches our structural
|
||||
// expectations.
|
||||
MDNode *ProfileData = getMetadata(LLVMContext::MD_prof);
|
||||
if (!ProfileData || ProfileData->getNumOperands() != 3)
|
||||
return;
|
||||
|
||||
// The first operand is the name. Fetch them backwards and build a new one.
|
||||
Metadata *Ops[] = {ProfileData->getOperand(0), ProfileData->getOperand(2),
|
||||
ProfileData->getOperand(1)};
|
||||
setMetadata(LLVMContext::MD_prof,
|
||||
MDNode::get(ProfileData->getContext(), Ops));
|
||||
swapProfMetadata();
|
||||
}
|
||||
|
||||
BasicBlock *BranchInst::getSuccessorV(unsigned idx) const {
|
||||
|
@ -742,42 +742,6 @@ static Loop *CloneLoop(Loop *L, Loop *PL, ValueToValueMapTy &VM,
|
||||
return &New;
|
||||
}
|
||||
|
||||
static void copyMetadata(Instruction *DstInst, const Instruction *SrcInst,
|
||||
bool Swapped) {
|
||||
if (!SrcInst || !SrcInst->hasMetadata())
|
||||
return;
|
||||
|
||||
SmallVector<std::pair<unsigned, MDNode *>, 4> MDs;
|
||||
SrcInst->getAllMetadata(MDs);
|
||||
for (auto &MD : MDs) {
|
||||
switch (MD.first) {
|
||||
default:
|
||||
break;
|
||||
case LLVMContext::MD_prof:
|
||||
if (Swapped && MD.second->getNumOperands() == 3 &&
|
||||
isa<MDString>(MD.second->getOperand(0))) {
|
||||
MDString *MDName = cast<MDString>(MD.second->getOperand(0));
|
||||
if (MDName->getString() == "branch_weights") {
|
||||
auto *ValT = cast_or_null<ConstantAsMetadata>(
|
||||
MD.second->getOperand(1))->getValue();
|
||||
auto *ValF = cast_or_null<ConstantAsMetadata>(
|
||||
MD.second->getOperand(2))->getValue();
|
||||
assert(ValT && ValF && "Invalid Operands of branch_weights");
|
||||
auto NewMD =
|
||||
MDBuilder(DstInst->getParent()->getContext())
|
||||
.createBranchWeights(cast<ConstantInt>(ValF)->getZExtValue(),
|
||||
cast<ConstantInt>(ValT)->getZExtValue());
|
||||
MD.second = NewMD;
|
||||
}
|
||||
}
|
||||
LLVM_FALLTHROUGH;
|
||||
case LLVMContext::MD_make_implicit:
|
||||
case LLVMContext::MD_dbg:
|
||||
DstInst->setMetadata(MD.first, MD.second);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Emit a conditional branch on two values if LIC == Val, branch to TrueDst,
|
||||
/// otherwise branch to FalseDest. Insert the code immediately before InsertPt.
|
||||
void LoopUnswitch::EmitPreheaderBranchOnCondition(Value *LIC, Constant *Val,
|
||||
@ -800,7 +764,14 @@ void LoopUnswitch::EmitPreheaderBranchOnCondition(Value *LIC, Constant *Val,
|
||||
|
||||
// Insert the new branch.
|
||||
BranchInst *BI = BranchInst::Create(TrueDest, FalseDest, BranchVal, InsertPt);
|
||||
copyMetadata(BI, TI, Swapped);
|
||||
if (TI) {
|
||||
// FIXME: check why white list is needed here:
|
||||
ArrayRef<unsigned> WL = {LLVMContext::MD_dbg, LLVMContext::MD_prof,
|
||||
LLVMContext::MD_make_implicit};
|
||||
BI->copyMetadata(*TI, WL);
|
||||
if (Swapped)
|
||||
BI->swapProfMetadata();
|
||||
}
|
||||
|
||||
// If either edge is critical, split it. This helps preserve LoopSimplify
|
||||
// form for enclosing loops.
|
||||
|
Loading…
Reference in New Issue
Block a user