|
13 | 13 | #include "bolt/Passes/BinaryPasses.h" |
14 | 14 | #include "bolt/Core/FunctionLayout.h" |
15 | 15 | #include "bolt/Core/ParallelUtilities.h" |
| 16 | +#include "bolt/Passes/ProfileStats.h" |
16 | 17 | #include "bolt/Passes/ReorderAlgorithm.h" |
17 | 18 | #include "bolt/Passes/ReorderFunctions.h" |
18 | 19 | #include "llvm/Support/CommandLine.h" |
@@ -1280,96 +1281,7 @@ Error AssignSections::runOnFunctions(BinaryContext &BC) { |
1280 | 1281 | } |
1281 | 1282 |
|
1282 | 1283 | Error PrintProfileStats::runOnFunctions(BinaryContext &BC) { |
1283 | | - double FlowImbalanceMean = 0.0; |
1284 | | - size_t NumBlocksConsidered = 0; |
1285 | | - double WorstBias = 0.0; |
1286 | | - const BinaryFunction *WorstBiasFunc = nullptr; |
1287 | | - |
1288 | | - // For each function CFG, we fill an IncomingMap with the sum of the frequency |
1289 | | - // of incoming edges for each BB. Likewise for each OutgoingMap and the sum |
1290 | | - // of the frequency of outgoing edges. |
1291 | | - using FlowMapTy = std::unordered_map<const BinaryBasicBlock *, uint64_t>; |
1292 | | - std::unordered_map<const BinaryFunction *, FlowMapTy> TotalIncomingMaps; |
1293 | | - std::unordered_map<const BinaryFunction *, FlowMapTy> TotalOutgoingMaps; |
1294 | | - |
1295 | | - // Compute mean |
1296 | | - for (const auto &BFI : BC.getBinaryFunctions()) { |
1297 | | - const BinaryFunction &Function = BFI.second; |
1298 | | - if (Function.empty() || !Function.isSimple()) |
1299 | | - continue; |
1300 | | - FlowMapTy &IncomingMap = TotalIncomingMaps[&Function]; |
1301 | | - FlowMapTy &OutgoingMap = TotalOutgoingMaps[&Function]; |
1302 | | - for (const BinaryBasicBlock &BB : Function) { |
1303 | | - uint64_t TotalOutgoing = 0ULL; |
1304 | | - auto SuccBIIter = BB.branch_info_begin(); |
1305 | | - for (BinaryBasicBlock *Succ : BB.successors()) { |
1306 | | - uint64_t Count = SuccBIIter->Count; |
1307 | | - if (Count == BinaryBasicBlock::COUNT_NO_PROFILE || Count == 0) { |
1308 | | - ++SuccBIIter; |
1309 | | - continue; |
1310 | | - } |
1311 | | - TotalOutgoing += Count; |
1312 | | - IncomingMap[Succ] += Count; |
1313 | | - ++SuccBIIter; |
1314 | | - } |
1315 | | - OutgoingMap[&BB] = TotalOutgoing; |
1316 | | - } |
1317 | | - |
1318 | | - size_t NumBlocks = 0; |
1319 | | - double Mean = 0.0; |
1320 | | - for (const BinaryBasicBlock &BB : Function) { |
1321 | | - // Do not compute score for low frequency blocks, entry or exit blocks |
1322 | | - if (IncomingMap[&BB] < 100 || OutgoingMap[&BB] == 0 || BB.isEntryPoint()) |
1323 | | - continue; |
1324 | | - ++NumBlocks; |
1325 | | - const double Difference = (double)OutgoingMap[&BB] - IncomingMap[&BB]; |
1326 | | - Mean += fabs(Difference / IncomingMap[&BB]); |
1327 | | - } |
1328 | | - |
1329 | | - FlowImbalanceMean += Mean; |
1330 | | - NumBlocksConsidered += NumBlocks; |
1331 | | - if (!NumBlocks) |
1332 | | - continue; |
1333 | | - double FuncMean = Mean / NumBlocks; |
1334 | | - if (FuncMean > WorstBias) { |
1335 | | - WorstBias = FuncMean; |
1336 | | - WorstBiasFunc = &Function; |
1337 | | - } |
1338 | | - } |
1339 | | - if (NumBlocksConsidered > 0) |
1340 | | - FlowImbalanceMean /= NumBlocksConsidered; |
1341 | | - |
1342 | | - // Compute standard deviation |
1343 | | - NumBlocksConsidered = 0; |
1344 | | - double FlowImbalanceVar = 0.0; |
1345 | | - for (const auto &BFI : BC.getBinaryFunctions()) { |
1346 | | - const BinaryFunction &Function = BFI.second; |
1347 | | - if (Function.empty() || !Function.isSimple()) |
1348 | | - continue; |
1349 | | - FlowMapTy &IncomingMap = TotalIncomingMaps[&Function]; |
1350 | | - FlowMapTy &OutgoingMap = TotalOutgoingMaps[&Function]; |
1351 | | - for (const BinaryBasicBlock &BB : Function) { |
1352 | | - if (IncomingMap[&BB] < 100 || OutgoingMap[&BB] == 0) |
1353 | | - continue; |
1354 | | - ++NumBlocksConsidered; |
1355 | | - const double Difference = (double)OutgoingMap[&BB] - IncomingMap[&BB]; |
1356 | | - FlowImbalanceVar += |
1357 | | - pow(fabs(Difference / IncomingMap[&BB]) - FlowImbalanceMean, 2); |
1358 | | - } |
1359 | | - } |
1360 | | - if (NumBlocksConsidered) { |
1361 | | - FlowImbalanceVar /= NumBlocksConsidered; |
1362 | | - FlowImbalanceVar = sqrt(FlowImbalanceVar); |
1363 | | - } |
1364 | | - |
1365 | | - // Report to user |
1366 | | - BC.outs() << format("BOLT-INFO: Profile bias score: %.4lf%% StDev: %.4lf%%\n", |
1367 | | - (100.0 * FlowImbalanceMean), (100.0 * FlowImbalanceVar)); |
1368 | | - if (WorstBiasFunc && opts::Verbosity >= 1) { |
1369 | | - BC.outs() << "Worst average bias observed in " |
1370 | | - << WorstBiasFunc->getPrintName() << "\n"; |
1371 | | - LLVM_DEBUG(WorstBiasFunc->dump()); |
1372 | | - } |
| 1284 | + ProfileStats::printAll(BC.outs(), BC); |
1373 | 1285 | return Error::success(); |
1374 | 1286 | } |
1375 | 1287 |
|
|
0 commit comments