@@ -711,7 +711,7 @@ bool DataAggregator::doInterBranch(BinaryFunction *FromFunc,
711711}
712712
713713bool DataAggregator::doBranch (uint64_t From, uint64_t To, uint64_t Count,
714- uint64_t Mispreds, bool IsPreagg ) {
714+ uint64_t Mispreds) {
715715 // Returns whether \p Offset in \p Func contains a return instruction.
716716 auto checkReturn = [&](const BinaryFunction &Func, const uint64_t Offset) {
717717 auto isReturn = [&](auto MI) { return MI && BC->MIB ->isReturn (*MI); };
@@ -772,7 +772,8 @@ bool DataAggregator::doBranch(uint64_t From, uint64_t To, uint64_t Count,
772772 return false ;
773773
774774 // Record call to continuation trace.
775- if (IsPreagg && FromFunc != ToFunc && (IsReturn || IsCallCont)) {
775+ if (NeedsConvertRetProfileToCallCont && FromFunc != ToFunc &&
776+ (IsReturn || IsCallCont)) {
776777 LBREntry First{ToOrig - 1 , ToOrig - 1 , false };
777778 LBREntry Second{ToOrig, ToOrig, false };
778779 return doTrace (First, Second, Count);
@@ -1216,20 +1217,24 @@ ErrorOr<Location> DataAggregator::parseLocationOrOffset() {
12161217 return Location (true , BuildID.get (), Offset.get ());
12171218}
12181219
1219- ErrorOr<DataAggregator::AggregatedLBREntry>
1220- DataAggregator::parseAggregatedLBREntry () {
1220+ std::error_code DataAggregator::parseAggregatedLBREntry () {
12211221 while (checkAndConsumeFS ()) {
12221222 }
12231223
12241224 ErrorOr<StringRef> TypeOrErr = parseString (FieldSeparator);
12251225 if (std::error_code EC = TypeOrErr.getError ())
12261226 return EC;
1227+ // Pre-aggregated profile with branches and fallthroughs needs to convert
1228+ // return profile into call to continuation fall-through.
12271229 auto Type = AggregatedLBREntry::BRANCH;
12281230 if (TypeOrErr.get () == " B" ) {
1231+ NeedsConvertRetProfileToCallCont = true ;
12291232 Type = AggregatedLBREntry::BRANCH;
12301233 } else if (TypeOrErr.get () == " F" ) {
1234+ NeedsConvertRetProfileToCallCont = true ;
12311235 Type = AggregatedLBREntry::FT;
12321236 } else if (TypeOrErr.get () == " f" ) {
1237+ NeedsConvertRetProfileToCallCont = true ;
12331238 Type = AggregatedLBREntry::FT_EXTERNAL_ORIGIN;
12341239 } else {
12351240 reportError (" expected B, F or f" );
@@ -1250,10 +1255,11 @@ DataAggregator::parseAggregatedLBREntry() {
12501255
12511256 while (checkAndConsumeFS ()) {
12521257 }
1253- ErrorOr<int64_t > Frequency =
1258+ ErrorOr<int64_t > FrequencyOrErr =
12541259 parseNumberField (FieldSeparator, Type != AggregatedLBREntry::BRANCH);
1255- if (std::error_code EC = Frequency .getError ())
1260+ if (std::error_code EC = FrequencyOrErr .getError ())
12561261 return EC;
1262+ uint64_t Frequency = static_cast <uint64_t >(FrequencyOrErr.get ());
12571263
12581264 uint64_t Mispreds = 0 ;
12591265 if (Type == AggregatedLBREntry::BRANCH) {
@@ -1270,9 +1276,16 @@ DataAggregator::parseAggregatedLBREntry() {
12701276 return make_error_code (llvm::errc::io_error);
12711277 }
12721278
1273- return AggregatedLBREntry{From.get (), To.get (),
1274- static_cast <uint64_t >(Frequency.get ()), Mispreds,
1275- Type};
1279+ BinaryFunction *FromFunc = getBinaryFunctionContainingAddress (From->Offset );
1280+ BinaryFunction *ToFunc = getBinaryFunctionContainingAddress (To->Offset );
1281+
1282+ for (BinaryFunction *BF : {FromFunc, ToFunc})
1283+ if (BF)
1284+ BF->setHasProfileAvailable ();
1285+
1286+ AggregatedLBRs.emplace_back (From.get (), To.get (), Frequency, Mispreds, Type);
1287+
1288+ return std::error_code ();
12761289}
12771290
12781291bool DataAggregator::ignoreKernelInterrupt (LBREntry &LBR) const {
@@ -1585,8 +1598,7 @@ void DataAggregator::processBranchEvents() {
15851598 for (const auto &AggrLBR : BranchLBRs) {
15861599 const Trace &Loc = AggrLBR.first ;
15871600 const TakenBranchInfo &Info = AggrLBR.second ;
1588- doBranch (Loc.From , Loc.To , Info.TakenCount , Info.MispredCount ,
1589- /* IsPreagg*/ false );
1601+ doBranch (Loc.From , Loc.To , Info.TakenCount , Info.MispredCount );
15901602 }
15911603}
15921604
@@ -1722,18 +1734,10 @@ std::error_code DataAggregator::parsePreAggregatedLBRSamples() {
17221734 outs () << " PERF2BOLT: parsing pre-aggregated profile...\n " ;
17231735 NamedRegionTimer T (" parseAggregated" , " Parsing aggregated branch events" ,
17241736 TimerGroupName, TimerGroupDesc, opts::TimeAggregator);
1725- while (hasData ()) {
1726- ErrorOr<AggregatedLBREntry> AggrEntry = parseAggregatedLBREntry ();
1727- if (std::error_code EC = AggrEntry.getError ())
1737+ while (hasData ())
1738+ if (std::error_code EC = parseAggregatedLBREntry ())
17281739 return EC;
17291740
1730- for (const uint64_t Addr : {AggrEntry->From .Offset , AggrEntry->To .Offset })
1731- if (BinaryFunction *BF = getBinaryFunctionContainingAddress (Addr))
1732- BF->setHasProfileAvailable ();
1733-
1734- AggregatedLBRs.emplace_back (std::move (AggrEntry.get ()));
1735- }
1736-
17371741 return std::error_code ();
17381742}
17391743
@@ -1747,7 +1751,7 @@ void DataAggregator::processPreAggregated() {
17471751 switch (AggrEntry.EntryType ) {
17481752 case AggregatedLBREntry::BRANCH:
17491753 doBranch (AggrEntry.From .Offset , AggrEntry.To .Offset , AggrEntry.Count ,
1750- AggrEntry.Mispreds , /* IsPreagg */ true );
1754+ AggrEntry.Mispreds );
17511755 break ;
17521756 case AggregatedLBREntry::FT:
17531757 case AggregatedLBREntry::FT_EXTERNAL_ORIGIN: {
0 commit comments