FunctionPropertiesAnalysis.cpp 3.1 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788
  1. //===- FunctionPropertiesAnalysis.cpp - Function Properties Analysis ------===//
  2. //
  3. // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
  4. // See https://llvm.org/LICENSE.txt for license information.
  5. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  6. //
  7. //===----------------------------------------------------------------------===//
  8. //
  9. // This file defines the FunctionPropertiesInfo and FunctionPropertiesAnalysis
  10. // classes used to extract function properties.
  11. //
  12. //===----------------------------------------------------------------------===//
  13. #include "llvm/Analysis/FunctionPropertiesAnalysis.h"
  14. #include "llvm/IR/Instructions.h"
  15. using namespace llvm;
  16. FunctionPropertiesInfo
  17. FunctionPropertiesInfo::getFunctionPropertiesInfo(const Function &F,
  18. const LoopInfo &LI) {
  19. FunctionPropertiesInfo FPI;
  20. FPI.Uses = ((!F.hasLocalLinkage()) ? 1 : 0) + F.getNumUses();
  21. for (const auto &BB : F) {
  22. ++FPI.BasicBlockCount;
  23. if (const auto *BI = dyn_cast<BranchInst>(BB.getTerminator())) {
  24. if (BI->isConditional())
  25. FPI.BlocksReachedFromConditionalInstruction += BI->getNumSuccessors();
  26. } else if (const auto *SI = dyn_cast<SwitchInst>(BB.getTerminator())) {
  27. FPI.BlocksReachedFromConditionalInstruction +=
  28. (SI->getNumCases() + (nullptr != SI->getDefaultDest()));
  29. }
  30. for (const auto &I : BB) {
  31. if (auto *CS = dyn_cast<CallBase>(&I)) {
  32. const auto *Callee = CS->getCalledFunction();
  33. if (Callee && !Callee->isIntrinsic() && !Callee->isDeclaration())
  34. ++FPI.DirectCallsToDefinedFunctions;
  35. }
  36. if (I.getOpcode() == Instruction::Load) {
  37. ++FPI.LoadInstCount;
  38. } else if (I.getOpcode() == Instruction::Store) {
  39. ++FPI.StoreInstCount;
  40. }
  41. }
  42. // Loop Depth of the Basic Block
  43. int64_t LoopDepth;
  44. LoopDepth = LI.getLoopDepth(&BB);
  45. if (FPI.MaxLoopDepth < LoopDepth)
  46. FPI.MaxLoopDepth = LoopDepth;
  47. }
  48. FPI.TopLevelLoopCount += llvm::size(LI);
  49. return FPI;
  50. }
  51. void FunctionPropertiesInfo::print(raw_ostream &OS) const {
  52. OS << "BasicBlockCount: " << BasicBlockCount << "\n"
  53. << "BlocksReachedFromConditionalInstruction: "
  54. << BlocksReachedFromConditionalInstruction << "\n"
  55. << "Uses: " << Uses << "\n"
  56. << "DirectCallsToDefinedFunctions: " << DirectCallsToDefinedFunctions
  57. << "\n"
  58. << "LoadInstCount: " << LoadInstCount << "\n"
  59. << "StoreInstCount: " << StoreInstCount << "\n"
  60. << "MaxLoopDepth: " << MaxLoopDepth << "\n"
  61. << "TopLevelLoopCount: " << TopLevelLoopCount << "\n\n";
  62. }
  63. AnalysisKey FunctionPropertiesAnalysis::Key;
  64. FunctionPropertiesInfo
  65. FunctionPropertiesAnalysis::run(Function &F, FunctionAnalysisManager &FAM) {
  66. return FunctionPropertiesInfo::getFunctionPropertiesInfo(
  67. F, FAM.getResult<LoopAnalysis>(F));
  68. }
  69. PreservedAnalyses
  70. FunctionPropertiesPrinterPass::run(Function &F, FunctionAnalysisManager &AM) {
  71. OS << "Printing analysis results of CFA for function "
  72. << "'" << F.getName() << "':"
  73. << "\n";
  74. AM.getResult<FunctionPropertiesAnalysis>(F).print(OS);
  75. return PreservedAnalyses::all();
  76. }