[llvm] 16f777f - [NFC] Add debug and stat counters to assume queries and assume builder
via llvm-commits
llvm-commits at lists.llvm.org
Tue Jul 14 12:49:35 PDT 2020
Author: Tyker
Date: 2020-07-14T21:49:14+02:00
New Revision: 16f777f4217cfcdcf6ddce8eb1e3525a65563c43
URL: https://github.com/llvm/llvm-project/commit/16f777f4217cfcdcf6ddce8eb1e3525a65563c43
DIFF: https://github.com/llvm/llvm-project/commit/16f777f4217cfcdcf6ddce8eb1e3525a65563c43.diff
LOG: [NFC] Add debug and stat counters to assume queries and assume builder
Summary:
Add debug counter and stats counter to assume queries and assume builder
here is the collected stats on a build of check-llvm + check-clang.
"assume-builder.NumAssumeBuilt": 2720879,
"assume-builder.NumAssumesMerged": 761396,
"assume-builder.NumAssumesRemoved": 1576212,
"assume-builder.NumBundlesInAssumes": 6518809,
"assume-queries.NumAssumeQueries": 85566380,
"assume-queries.NumUsefullAssumeQueries": 2727360,
the NumUsefullAssumeQueries stat is actually pessimistic because in a few places queries
ask to keep providing information to try to get better information. and this isn't counted
as a usefull query evem tho it can be usefull
Reviewers: jdoerfert
Reviewed By: jdoerfert
Subscribers: hiraditya, llvm-commits
Tags: #llvm
Differential Revision: https://reviews.llvm.org/D83506
Added:
llvm/test/Analysis/ValueTracking/assume-queries-counter.ll
llvm/test/Transforms/Util/assume-builder-counter.ll
Modified:
llvm/lib/Analysis/AssumeBundleQueries.cpp
llvm/lib/Transforms/Utils/AssumeBundleBuilder.cpp
Removed:
################################################################################
diff --git a/llvm/lib/Analysis/AssumeBundleQueries.cpp b/llvm/lib/Analysis/AssumeBundleQueries.cpp
index af81216f6526..05fe05a0bd85 100644
--- a/llvm/lib/Analysis/AssumeBundleQueries.cpp
+++ b/llvm/lib/Analysis/AssumeBundleQueries.cpp
@@ -6,17 +6,29 @@
//
//===----------------------------------------------------------------------===//
+#define DEBUG_TYPE "assume-queries"
+
#include "llvm/Analysis/AssumeBundleQueries.h"
+#include "llvm/ADT/Statistic.h"
#include "llvm/Analysis/AssumptionCache.h"
#include "llvm/Analysis/ValueTracking.h"
#include "llvm/IR/Function.h"
#include "llvm/IR/InstIterator.h"
#include "llvm/IR/IntrinsicInst.h"
#include "llvm/IR/PatternMatch.h"
+#include "llvm/Support/DebugCounter.h"
using namespace llvm;
using namespace llvm::PatternMatch;
+STATISTIC(NumAssumeQueries, "Number of Queries into an assume assume bundles");
+STATISTIC(
+ NumUsefullAssumeQueries,
+ "Number of Queries into an assume assume bundles that were satisfied");
+
+DEBUG_COUNTER(AssumeQueryCounter, "assume-queries-counter",
+ "Controls which assumes gets created");
+
static bool bundleHasArgument(const CallBase::BundleOpInfo &BOI, unsigned Idx) {
return BOI.End - BOI.Begin > Idx;
}
@@ -158,6 +170,9 @@ llvm::getKnowledgeForValue(const Value *V,
function_ref<bool(RetainedKnowledge, Instruction *,
const CallBase::BundleOpInfo *)>
Filter) {
+ NumAssumeQueries++;
+ if (!DebugCounter::shouldExecute(AssumeQueryCounter))
+ return RetainedKnowledge::none();
if (AC) {
for (AssumptionCache::ResultElem &Elem : AC->assumptionsFor(V)) {
IntrinsicInst *II = cast_or_null<IntrinsicInst>(Elem.Assume);
@@ -166,20 +181,24 @@ llvm::getKnowledgeForValue(const Value *V,
if (RetainedKnowledge RK = getKnowledgeFromBundle(
*II, II->bundle_op_info_begin()[Elem.Index]))
if (is_contained(AttrKinds, RK.AttrKind) &&
- Filter(RK, II, &II->bundle_op_info_begin()[Elem.Index]))
+ Filter(RK, II, &II->bundle_op_info_begin()[Elem.Index])) {
+ NumUsefullAssumeQueries++;
return RK;
+ }
}
return RetainedKnowledge::none();
}
- for (auto &U : V->uses()) {
+ for (const auto &U : V->uses()) {
CallInst::BundleOpInfo* Bundle = getBundleFromUse(&U);
if (!Bundle)
continue;
if (RetainedKnowledge RK =
getKnowledgeFromBundle(*cast<CallInst>(U.getUser()), *Bundle))
if (is_contained(AttrKinds, RK.AttrKind) &&
- Filter(RK, cast<Instruction>(U.getUser()), Bundle))
+ Filter(RK, cast<Instruction>(U.getUser()), Bundle)) {
+ NumUsefullAssumeQueries++;
return RK;
+ }
}
return RetainedKnowledge::none();
}
diff --git a/llvm/lib/Transforms/Utils/AssumeBundleBuilder.cpp b/llvm/lib/Transforms/Utils/AssumeBundleBuilder.cpp
index f2208edd5b19..7ff73fcdada7 100644
--- a/llvm/lib/Transforms/Utils/AssumeBundleBuilder.cpp
+++ b/llvm/lib/Transforms/Utils/AssumeBundleBuilder.cpp
@@ -6,9 +6,12 @@
//
//===----------------------------------------------------------------------===//
+#define DEBUG_TYPE "assume-builder"
+
#include "llvm/Transforms/Utils/AssumeBundleBuilder.h"
#include "llvm/ADT/DepthFirstIterator.h"
#include "llvm/ADT/MapVector.h"
+#include "llvm/ADT/Statistic.h"
#include "llvm/Analysis/AssumeBundleQueries.h"
#include "llvm/Analysis/AssumptionCache.h"
#include "llvm/Analysis/ValueTracking.h"
@@ -19,6 +22,7 @@
#include "llvm/IR/Module.h"
#include "llvm/InitializePasses.h"
#include "llvm/Support/CommandLine.h"
+#include "llvm/Support/DebugCounter.h"
#include "llvm/Transforms/Utils/Local.h"
using namespace llvm;
@@ -33,6 +37,16 @@ cl::opt<bool> EnableKnowledgeRetention(
cl::desc(
"enable preservation of attributes throughout code transformation"));
+STATISTIC(NumAssumeBuilt, "Number of assume built by the assume builder");
+STATISTIC(NumBundlesInAssumes, "Total number of Bundles in the assume built");
+STATISTIC(NumAssumesMerged,
+ "Number of assume merged by the assume simplify pass");
+STATISTIC(NumAssumesRemoved,
+ "Number of assume removed by the assume simplify pass");
+
+DEBUG_COUNTER(BuildAssumeCounter, "assume-builder-counter",
+ "Controls which assumes gets created");
+
namespace {
bool isUsefullToPreserve(Attribute::AttrKind Kind) {
@@ -204,6 +218,8 @@ struct AssumeBuilderState {
IntrinsicInst *build() {
if (AssumedKnowledgeMap.empty())
return nullptr;
+ if (!DebugCounter::shouldExecute(BuildAssumeCounter))
+ return nullptr;
Function *FnAssume = Intrinsic::getDeclaration(M, Intrinsic::assume);
LLVMContext &C = M->getContext();
SmallVector<OperandBundleDef, 8> OpBundle;
@@ -220,7 +236,9 @@ struct AssumeBuilderState {
OpBundle.push_back(OperandBundleDefT<Value *>(
std::string(Attribute::getNameFromAttrKind(MapElem.first.second)),
Args));
+ NumBundlesInAssumes++;
}
+ NumAssumeBuilt++;
return cast<IntrinsicInst>(CallInst::Create(
FnAssume, ArrayRef<Value *>({ConstantInt::getTrue(C)}), OpBundle));
}
@@ -328,6 +346,10 @@ struct AssumeSimplify {
(!ForceCleanup && !isAssumeWithEmptyBundle(*Assume)))
continue;
MadeChange = true;
+ if (ForceCleanup)
+ NumAssumesMerged++;
+ else
+ NumAssumesRemoved++;
Assume->eraseFromParent();
}
CleanupToDo.clear();
diff --git a/llvm/test/Analysis/ValueTracking/assume-queries-counter.ll b/llvm/test/Analysis/ValueTracking/assume-queries-counter.ll
new file mode 100644
index 000000000000..476b0ef04d34
--- /dev/null
+++ b/llvm/test/Analysis/ValueTracking/assume-queries-counter.ll
@@ -0,0 +1,110 @@
+; NOTE: Assertions have been autogenerated by utils/update_test_checks.py
+; RUN: opt < %s -instcombine --debug-counter=assume-queries-counter-skip=0,assume-queries-counter-count=1 -S | FileCheck %s --check-prefixes=SAME,COUNTER1
+; RUN: opt < %s -instcombine --debug-counter=assume-queries-counter-skip=1,assume-queries-counter-count=2 -S | FileCheck %s --check-prefixes=SAME,COUNTER2
+; RUN: opt < %s -instcombine --debug-counter=assume-queries-counter-skip=2,assume-queries-counter-count=1 -S | FileCheck %s --check-prefixes=SAME,COUNTER3
+
+declare i1 @get_val()
+declare void @llvm.assume(i1)
+
+define dso_local i1 @test1(i32* readonly %0) {
+; COUNTER1-LABEL: @test1(
+; COUNTER1-NEXT: call void @llvm.assume(i1 true) [ "nonnull"(i32* [[TMP0:%.*]]) ]
+; COUNTER1-NEXT: ret i1 false
+;
+; COUNTER2-LABEL: @test1(
+; COUNTER2-NEXT: call void @llvm.assume(i1 true) [ "nonnull"(i32* [[TMP0:%.*]]) ]
+; COUNTER2-NEXT: [[TMP2:%.*]] = icmp eq i32* [[TMP0]], null
+; COUNTER2-NEXT: ret i1 [[TMP2]]
+;
+; COUNTER3-LABEL: @test1(
+; COUNTER3-NEXT: call void @llvm.assume(i1 true) [ "nonnull"(i32* [[TMP0:%.*]]) ]
+; COUNTER3-NEXT: [[TMP2:%.*]] = icmp eq i32* [[TMP0]], null
+; COUNTER3-NEXT: ret i1 [[TMP2]]
+;
+ call void @llvm.assume(i1 true) ["nonnull"(i32* %0)]
+ %2 = icmp eq i32* %0, null
+ ret i1 %2
+}
+
+define dso_local i1 @test2(i32* readonly %0) {
+; COUNTER1-LABEL: @test2(
+; COUNTER1-NEXT: [[TMP2:%.*]] = icmp eq i32* [[TMP0:%.*]], null
+; COUNTER1-NEXT: call void @llvm.assume(i1 true) [ "nonnull"(i32* [[TMP0]]) ]
+; COUNTER1-NEXT: ret i1 [[TMP2]]
+;
+; COUNTER2-LABEL: @test2(
+; COUNTER2-NEXT: call void @llvm.assume(i1 true) [ "nonnull"(i32* [[TMP0:%.*]]) ]
+; COUNTER2-NEXT: ret i1 false
+;
+; COUNTER3-LABEL: @test2(
+; COUNTER3-NEXT: [[TMP2:%.*]] = icmp eq i32* [[TMP0:%.*]], null
+; COUNTER3-NEXT: call void @llvm.assume(i1 true) [ "nonnull"(i32* [[TMP0]]) ]
+; COUNTER3-NEXT: ret i1 [[TMP2]]
+;
+ %2 = icmp eq i32* %0, null
+ call void @llvm.assume(i1 true) ["nonnull"(i32* %0)]
+ ret i1 %2
+}
+
+define dso_local i32 @test4(i32* readonly %0, i1 %cond) {
+; COUNTER1-LABEL: @test4(
+; COUNTER1-NEXT: call void @llvm.assume(i1 true) [ "dereferenceable"(i32* [[TMP0:%.*]], i32 4) ]
+; COUNTER1-NEXT: br i1 [[COND:%.*]], label [[A:%.*]], label [[B:%.*]]
+; COUNTER1: B:
+; COUNTER1-NEXT: br label [[A]]
+; COUNTER1: A:
+; COUNTER1-NEXT: [[TMP2:%.*]] = icmp eq i32* [[TMP0]], null
+; COUNTER1-NEXT: br i1 [[TMP2]], label [[TMP5:%.*]], label [[TMP3:%.*]]
+; COUNTER1: 3:
+; COUNTER1-NEXT: [[TMP4:%.*]] = load i32, i32* [[TMP0]], align 4
+; COUNTER1-NEXT: br label [[TMP5]]
+; COUNTER1: 5:
+; COUNTER1-NEXT: [[TMP6:%.*]] = phi i32 [ [[TMP4]], [[TMP3]] ], [ 0, [[A]] ]
+; COUNTER1-NEXT: ret i32 [[TMP6]]
+;
+; COUNTER2-LABEL: @test4(
+; COUNTER2-NEXT: call void @llvm.assume(i1 true) [ "dereferenceable"(i32* [[TMP0:%.*]], i32 4) ]
+; COUNTER2-NEXT: br i1 [[COND:%.*]], label [[A:%.*]], label [[B:%.*]]
+; COUNTER2: B:
+; COUNTER2-NEXT: br label [[A]]
+; COUNTER2: A:
+; COUNTER2-NEXT: br i1 false, label [[TMP4:%.*]], label [[TMP2:%.*]]
+; COUNTER2: 2:
+; COUNTER2-NEXT: [[TMP3:%.*]] = load i32, i32* [[TMP0]], align 4
+; COUNTER2-NEXT: br label [[TMP4]]
+; COUNTER2: 4:
+; COUNTER2-NEXT: [[TMP5:%.*]] = phi i32 [ [[TMP3]], [[TMP2]] ], [ 0, [[A]] ]
+; COUNTER2-NEXT: ret i32 [[TMP5]]
+;
+; COUNTER3-LABEL: @test4(
+; COUNTER3-NEXT: call void @llvm.assume(i1 true) [ "dereferenceable"(i32* [[TMP0:%.*]], i32 4) ]
+; COUNTER3-NEXT: br i1 [[COND:%.*]], label [[A:%.*]], label [[B:%.*]]
+; COUNTER3: B:
+; COUNTER3-NEXT: br label [[A]]
+; COUNTER3: A:
+; COUNTER3-NEXT: br i1 false, label [[TMP4:%.*]], label [[TMP2:%.*]]
+; COUNTER3: 2:
+; COUNTER3-NEXT: [[TMP3:%.*]] = load i32, i32* [[TMP0]], align 4
+; COUNTER3-NEXT: br label [[TMP4]]
+; COUNTER3: 4:
+; COUNTER3-NEXT: [[TMP5:%.*]] = phi i32 [ [[TMP3]], [[TMP2]] ], [ 0, [[A]] ]
+; COUNTER3-NEXT: ret i32 [[TMP5]]
+;
+ call void @llvm.assume(i1 true) ["dereferenceable"(i32* %0, i32 4)]
+ br i1 %cond, label %A, label %B
+
+B:
+ br label %A
+
+A:
+ %2 = icmp eq i32* %0, null
+ br i1 %2, label %5, label %3
+
+3: ; preds = %1
+ %4 = load i32, i32* %0, align 4
+ br label %5
+
+5: ; preds = %1, %3
+ %6 = phi i32 [ %4, %3 ], [ 0, %A ]
+ ret i32 %6
+}
diff --git a/llvm/test/Transforms/Util/assume-builder-counter.ll b/llvm/test/Transforms/Util/assume-builder-counter.ll
new file mode 100644
index 000000000000..380b88314032
--- /dev/null
+++ b/llvm/test/Transforms/Util/assume-builder-counter.ll
@@ -0,0 +1,79 @@
+; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --function-signature
+; RUN: opt -passes='assume-builder,verify' --enable-knowledge-retention --debug-counter=assume-builder-counter-skip=5,assume-builder-counter-count=1 -S %s | FileCheck %s --check-prefixes=COUNTER1
+; RUN: opt -passes='assume-builder,verify' --enable-knowledge-retention --debug-counter=assume-builder-counter-skip=1,assume-builder-counter-count=3 -S %s | FileCheck %s --check-prefixes=COUNTER2
+; RUN: opt -passes='assume-builder,verify' --enable-knowledge-retention --debug-counter=assume-builder-counter-skip=2,assume-builder-counter-count=200 -S %s | FileCheck %s --check-prefixes=COUNTER3
+
+target datalayout = "e-m:e-p270:32:32-p271:32:32-p272:64:64-i64:64-f80:128-n8:16:32:64-S128"
+
+declare void @func(i32*, i32*)
+declare void @func_cold(i32*) cold willreturn nounwind
+declare void @func_strbool(i32*) "no-jump-tables"
+declare void @func_many(i32*) "no-jump-tables" nounwind "less-precise-fpmad" willreturn norecurse
+declare void @func_argattr(i32* align 8, i32* nonnull) nounwind
+declare void @may_throw()
+
+define void @test(i32* %P, i32* %P1, i32* %P2, i32* %P3) {
+; COUNTER1-LABEL: define {{[^@]+}}@test
+; COUNTER1-SAME: (i32* [[P:%.*]], i32* [[P1:%.*]], i32* [[P2:%.*]], i32* [[P3:%.*]])
+; COUNTER1-NEXT: call void @func(i32* nonnull dereferenceable(16) [[P]], i32* null)
+; COUNTER1-NEXT: call void @func(i32* dereferenceable(12) [[P1]], i32* nonnull [[P]])
+; COUNTER1-NEXT: call void @func_cold(i32* dereferenceable(12) [[P1]]) #5
+; COUNTER1-NEXT: call void @func_cold(i32* dereferenceable(12) [[P1]])
+; COUNTER1-NEXT: call void @func(i32* [[P1]], i32* [[P]])
+; COUNTER1-NEXT: call void @func_strbool(i32* [[P1]])
+; COUNTER1-NEXT: call void @func(i32* dereferenceable(32) [[P]], i32* dereferenceable(8) [[P]])
+; COUNTER1-NEXT: call void @llvm.assume(i1 true) [ "align"(i32* [[P1]], i64 8) ]
+; COUNTER1-NEXT: call void @func_many(i32* align 8 [[P1]])
+; COUNTER1-NEXT: call void @func_argattr(i32* [[P2]], i32* [[P3]])
+; COUNTER1-NEXT: call void @func(i32* nonnull [[P1]], i32* nonnull [[P]])
+; COUNTER1-NEXT: ret void
+;
+; COUNTER2-LABEL: define {{[^@]+}}@test
+; COUNTER2-SAME: (i32* [[P:%.*]], i32* [[P1:%.*]], i32* [[P2:%.*]], i32* [[P3:%.*]])
+; COUNTER2-NEXT: call void @func(i32* nonnull dereferenceable(16) [[P]], i32* null)
+; COUNTER2-NEXT: call void @llvm.assume(i1 true) [ "dereferenceable"(i32* [[P1]], i64 12), "nonnull"(i32* [[P]]) ]
+; COUNTER2-NEXT: call void @func(i32* dereferenceable(12) [[P1]], i32* nonnull [[P]])
+; COUNTER2-NEXT: call void @llvm.assume(i1 true) [ "cold"() ]
+; COUNTER2-NEXT: call void @func_cold(i32* dereferenceable(12) [[P1]]) #5
+; COUNTER2-NEXT: call void @llvm.assume(i1 true) [ "cold"() ]
+; COUNTER2-NEXT: call void @func_cold(i32* dereferenceable(12) [[P1]])
+; COUNTER2-NEXT: call void @func(i32* [[P1]], i32* [[P]])
+; COUNTER2-NEXT: call void @func_strbool(i32* [[P1]])
+; COUNTER2-NEXT: call void @func(i32* dereferenceable(32) [[P]], i32* dereferenceable(8) [[P]])
+; COUNTER2-NEXT: call void @func_many(i32* align 8 [[P1]])
+; COUNTER2-NEXT: call void @func_argattr(i32* [[P2]], i32* [[P3]])
+; COUNTER2-NEXT: call void @func(i32* nonnull [[P1]], i32* nonnull [[P]])
+; COUNTER2-NEXT: ret void
+;
+; COUNTER3-LABEL: define {{[^@]+}}@test
+; COUNTER3-SAME: (i32* [[P:%.*]], i32* [[P1:%.*]], i32* [[P2:%.*]], i32* [[P3:%.*]])
+; COUNTER3-NEXT: call void @func(i32* nonnull dereferenceable(16) [[P]], i32* null)
+; COUNTER3-NEXT: call void @func(i32* dereferenceable(12) [[P1]], i32* nonnull [[P]])
+; COUNTER3-NEXT: call void @llvm.assume(i1 true) [ "dereferenceable"(i32* [[P1]], i64 12), "cold"() ]
+; COUNTER3-NEXT: call void @func_cold(i32* dereferenceable(12) [[P1]]) #5
+; COUNTER3-NEXT: call void @llvm.assume(i1 true) [ "cold"() ]
+; COUNTER3-NEXT: call void @func_cold(i32* dereferenceable(12) [[P1]])
+; COUNTER3-NEXT: call void @func(i32* [[P1]], i32* [[P]])
+; COUNTER3-NEXT: call void @func_strbool(i32* [[P1]])
+; COUNTER3-NEXT: call void @llvm.assume(i1 true) [ "dereferenceable"(i32* [[P]], i64 32) ]
+; COUNTER3-NEXT: call void @func(i32* dereferenceable(32) [[P]], i32* dereferenceable(8) [[P]])
+; COUNTER3-NEXT: call void @llvm.assume(i1 true) [ "align"(i32* [[P1]], i64 8) ]
+; COUNTER3-NEXT: call void @func_many(i32* align 8 [[P1]])
+; COUNTER3-NEXT: call void @llvm.assume(i1 true) [ "align"(i32* [[P2]], i64 8), "nonnull"(i32* [[P3]]) ]
+; COUNTER3-NEXT: call void @func_argattr(i32* [[P2]], i32* [[P3]])
+; COUNTER3-NEXT: call void @llvm.assume(i1 true) [ "nonnull"(i32* [[P1]]), "nonnull"(i32* [[P]]) ]
+; COUNTER3-NEXT: call void @func(i32* nonnull [[P1]], i32* nonnull [[P]])
+; COUNTER3-NEXT: ret void
+;
+ call void @func(i32* nonnull dereferenceable(16) %P, i32* null)
+ call void @func(i32* dereferenceable(12) %P1, i32* nonnull %P)
+ call void @func_cold(i32* dereferenceable(12) %P1) cold
+ call void @func_cold(i32* dereferenceable(12) %P1)
+ call void @func(i32* %P1, i32* %P)
+ call void @func_strbool(i32* %P1)
+ call void @func(i32* dereferenceable(32) %P, i32* dereferenceable(8) %P)
+ call void @func_many(i32* align 8 %P1)
+ call void @func_argattr(i32* %P2, i32* %P3)
+ call void @func(i32* nonnull %P1, i32* nonnull %P)
+ ret void
+}
More information about the llvm-commits
mailing list