Skip to content

Commit

Permalink
[PGO] Cleanup: Move large member functions out of line (NFC)
Browse files Browse the repository at this point in the history
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@256058 91177308-0d34-0410-b5e6-96231b3b80d8
  • Loading branch information
david-xl committed Dec 18, 2015
1 parent 21577c0 commit bde8257
Show file tree
Hide file tree
Showing 2 changed files with 99 additions and 92 deletions.
98 changes: 8 additions & 90 deletions include/llvm/ProfileData/InstrProf.h
Original file line number Diff line number Diff line change
Expand Up @@ -328,20 +328,20 @@ struct InstrProfRecord {
/// Reserve space for NumValueSites sites.
inline void reserveSites(uint32_t ValueKind, uint32_t NumValueSites);
/// Add ValueData for ValueKind at value Site.
inline void addValueData(uint32_t ValueKind, uint32_t Site,
InstrProfValueData *VData, uint32_t N,
ValueMapType *HashKeys);
void addValueData(uint32_t ValueKind, uint32_t Site,
InstrProfValueData *VData, uint32_t N,
ValueMapType *HashKeys);

/// Merge the counts in \p Other into this one.
/// Optionally scale merged counts by \p Weight.
inline instrprof_error merge(InstrProfRecord &Other, uint64_t Weight = 1);
instrprof_error merge(InstrProfRecord &Other, uint64_t Weight = 1);

/// Used by InstrProfWriter: update the value strings to commoned strings in
/// the writer instance.
inline void updateStrings(InstrProfStringTable *StrTab);
void updateStrings(InstrProfStringTable *StrTab);

/// Clear value data entries
inline void clearValueData() {
void clearValueData() {
for (uint32_t Kind = IPVK_First; Kind <= IPVK_Last; ++Kind)
getValueSitesForKind(Kind).clear();
}
Expand All @@ -368,41 +368,12 @@ struct InstrProfRecord {

// Map indirect call target name hash to name string.
uint64_t remapValue(uint64_t Value, uint32_t ValueKind,
ValueMapType *HashKeys) {
if (!HashKeys)
return Value;
switch (ValueKind) {
case IPVK_IndirectCallTarget: {
auto Result =
std::lower_bound(HashKeys->begin(), HashKeys->end(), Value,
[](const std::pair<uint64_t, const char *> &LHS,
uint64_t RHS) { return LHS.first < RHS; });
if (Result != HashKeys->end())
Value = (uint64_t)Result->second;
break;
}
}
return Value;
}
ValueMapType *HashKeys);

// Merge Value Profile data from Src record to this record for ValueKind.
// Scale merged value counts by \p Weight.
instrprof_error mergeValueProfData(uint32_t ValueKind, InstrProfRecord &Src,
uint64_t Weight) {
uint32_t ThisNumValueSites = getNumValueSites(ValueKind);
uint32_t OtherNumValueSites = Src.getNumValueSites(ValueKind);
if (ThisNumValueSites != OtherNumValueSites)
return instrprof_error::value_site_count_mismatch;
std::vector<InstrProfValueSiteRecord> &ThisSiteRecords =
getValueSitesForKind(ValueKind);
std::vector<InstrProfValueSiteRecord> &OtherSiteRecords =
Src.getValueSitesForKind(ValueKind);
instrprof_error Result = instrprof_error::success;
for (uint32_t I = 0; I < ThisNumValueSites; I++)
MergeResult(Result, ThisSiteRecords[I].mergeValueData(OtherSiteRecords[I],
Weight));
return Result;
}
uint64_t Weight);
};

uint32_t InstrProfRecord::getNumValueKinds() const {
Expand Down Expand Up @@ -456,69 +427,16 @@ void InstrProfRecord::getValueForSite(InstrProfValueData Dest[],
}
}

void InstrProfRecord::addValueData(uint32_t ValueKind, uint32_t Site,
InstrProfValueData *VData, uint32_t N,
ValueMapType *HashKeys) {
for (uint32_t I = 0; I < N; I++) {
VData[I].Value = remapValue(VData[I].Value, ValueKind, HashKeys);
}
std::vector<InstrProfValueSiteRecord> &ValueSites =
getValueSitesForKind(ValueKind);
if (N == 0)
ValueSites.push_back(InstrProfValueSiteRecord());
else
ValueSites.emplace_back(VData, VData + N);
}

void InstrProfRecord::reserveSites(uint32_t ValueKind, uint32_t NumValueSites) {
std::vector<InstrProfValueSiteRecord> &ValueSites =
getValueSitesForKind(ValueKind);
ValueSites.reserve(NumValueSites);
}

void InstrProfRecord::updateStrings(InstrProfStringTable *StrTab) {
if (!StrTab)
return;

Name = StrTab->insertString(Name);
for (auto &VSite : IndirectCallSites)
for (auto &VData : VSite.ValueData)
VData.Value = (uint64_t)StrTab->insertString((const char *)VData.Value);
}

instrprof_error InstrProfRecord::merge(InstrProfRecord &Other,
uint64_t Weight) {
// If the number of counters doesn't match we either have bad data
// or a hash collision.
if (Counts.size() != Other.Counts.size())
return instrprof_error::count_mismatch;

instrprof_error Result = instrprof_error::success;

for (size_t I = 0, E = Other.Counts.size(); I < E; ++I) {
bool Overflowed;
uint64_t OtherCount = Other.Counts[I];
if (Weight > 1) {
OtherCount = SaturatingMultiply(OtherCount, Weight, &Overflowed);
if (Overflowed)
Result = instrprof_error::counter_overflow;
}
Counts[I] = SaturatingAdd(Counts[I], OtherCount, &Overflowed);
if (Overflowed)
Result = instrprof_error::counter_overflow;
}

for (uint32_t Kind = IPVK_First; Kind <= IPVK_Last; ++Kind)
MergeResult(Result, mergeValueProfData(Kind, Other, Weight));

return Result;
}

inline support::endianness getHostEndianness() {
return sys::IsLittleEndianHost ? support::little : support::big;
}


// Include definitions for value profile data
#define INSTR_PROF_VALUE_PROF_DATA
#include "llvm/ProfileData/InstrProfData.inc"
Expand Down
93 changes: 91 additions & 2 deletions lib/ProfileData/InstrProf.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -162,11 +162,100 @@ GlobalVariable *createPGOFuncNameVar(Function &F, StringRef FuncName) {
return createPGOFuncNameVar(*F.getParent(), F.getLinkage(), FuncName);
}

// Merge Value Profile data from Src record to this record for ValueKind.
// Scale merged value counts by \p Weight.
instrprof_error InstrProfRecord::mergeValueProfData(uint32_t ValueKind,
InstrProfRecord &Src,
uint64_t Weight) {
uint32_t ThisNumValueSites = getNumValueSites(ValueKind);
uint32_t OtherNumValueSites = Src.getNumValueSites(ValueKind);
if (ThisNumValueSites != OtherNumValueSites)
return instrprof_error::value_site_count_mismatch;
std::vector<InstrProfValueSiteRecord> &ThisSiteRecords =
getValueSitesForKind(ValueKind);
std::vector<InstrProfValueSiteRecord> &OtherSiteRecords =
Src.getValueSitesForKind(ValueKind);
instrprof_error Result = instrprof_error::success;
for (uint32_t I = 0; I < ThisNumValueSites; I++)
MergeResult(Result,
ThisSiteRecords[I].mergeValueData(OtherSiteRecords[I], Weight));
return Result;
}

instrprof_error InstrProfRecord::merge(InstrProfRecord &Other,
uint64_t Weight) {
// If the number of counters doesn't match we either have bad data
// or a hash collision.
if (Counts.size() != Other.Counts.size())
return instrprof_error::count_mismatch;

instrprof_error Result = instrprof_error::success;

for (size_t I = 0, E = Other.Counts.size(); I < E; ++I) {
bool Overflowed;
uint64_t OtherCount = Other.Counts[I];
if (Weight > 1) {
OtherCount = SaturatingMultiply(OtherCount, Weight, &Overflowed);
if (Overflowed)
Result = instrprof_error::counter_overflow;
}
Counts[I] = SaturatingAdd(Counts[I], OtherCount, &Overflowed);
if (Overflowed)
Result = instrprof_error::counter_overflow;
}

for (uint32_t Kind = IPVK_First; Kind <= IPVK_Last; ++Kind)
MergeResult(Result, mergeValueProfData(Kind, Other, Weight));

return Result;
}
// Map indirect call target name hash to name string.
uint64_t InstrProfRecord::remapValue(uint64_t Value, uint32_t ValueKind,
ValueMapType *HashKeys) {
if (!HashKeys)
return Value;
switch (ValueKind) {
case IPVK_IndirectCallTarget: {
auto Result =
std::lower_bound(HashKeys->begin(), HashKeys->end(), Value,
[](const std::pair<uint64_t, const char *> &LHS,
uint64_t RHS) { return LHS.first < RHS; });
if (Result != HashKeys->end())
Value = (uint64_t)Result->second;
break;
}
}
return Value;
}

void InstrProfRecord::updateStrings(InstrProfStringTable *StrTab) {
if (!StrTab)
return;

Name = StrTab->insertString(Name);
for (auto &VSite : IndirectCallSites)
for (auto &VData : VSite.ValueData)
VData.Value = (uint64_t)StrTab->insertString((const char *)VData.Value);
}

void InstrProfRecord::addValueData(uint32_t ValueKind, uint32_t Site,
InstrProfValueData *VData, uint32_t N,
ValueMapType *HashKeys) {
for (uint32_t I = 0; I < N; I++) {
VData[I].Value = remapValue(VData[I].Value, ValueKind, HashKeys);
}
std::vector<InstrProfValueSiteRecord> &ValueSites =
getValueSitesForKind(ValueKind);
if (N == 0)
ValueSites.push_back(InstrProfValueSiteRecord());
else
ValueSites.emplace_back(VData, VData + N);
}

#define INSTR_PROF_COMMON_API_IMPL
#include "llvm/ProfileData/InstrProfData.inc"


/*!
/*!
* \brief ValueProfRecordClosure Interface implementation for InstrProfRecord
* class. These C wrappers are used as adaptors so that C++ code can be
* invoked as callbacks.
Expand Down

0 comments on commit bde8257

Please sign in to comment.