[llvm] [IR][TLI] Cache getLibFunc() result on Function (NFC) (PR #72867)

Nikita Popov via llvm-commits llvm-commits at lists.llvm.org
Tue Nov 21 01:08:24 PST 2023


https://github.com/nikic updated https://github.com/llvm/llvm-project/pull/72867

>From ca1de086971bcb7094f5066f867957af36455a4f Mon Sep 17 00:00:00 2001
From: Nikita Popov <npopov at redhat.com>
Date: Mon, 20 Nov 2023 12:08:39 +0100
Subject: [PATCH 1/2] [IR][TLI] Cache getLibFunc() result on Function (NFC)

Cache the result of the TLI libfunc lookup in the Function object.
This only caches the actual lookup of the LibFunc in the TLI map,
but not the prototype validation, as that might differ between
different TLI instances.

This uses the existing mechanism for invalidating the intrinsic
ID when the function name changes. The libfunc wil be invalidated
in that case as well.
---
 llvm/include/llvm/IR/Function.h         |  9 +++++++++
 llvm/lib/Analysis/TargetLibraryInfo.cpp | 11 +++++++++--
 llvm/lib/IR/Function.cpp                |  1 +
 3 files changed, 19 insertions(+), 2 deletions(-)

diff --git a/llvm/include/llvm/IR/Function.h b/llvm/include/llvm/IR/Function.h
index 955a4fca6f86f7e..0089fd7d5d8788d 100644
--- a/llvm/include/llvm/IR/Function.h
+++ b/llvm/include/llvm/IR/Function.h
@@ -48,9 +48,11 @@ class AssemblyAnnotationWriter;
 class Constant;
 struct DenormalMode;
 class DISubprogram;
+enum LibFunc : unsigned;
 class LLVMContext;
 class Module;
 class raw_ostream;
+class TargetLibraryInfoImpl;
 class Type;
 class User;
 class BranchProbabilityInfo;
@@ -120,6 +122,13 @@ class LLVM_EXTERNAL_VISIBILITY Function : public GlobalObject,
   void setIsNewDbgInfoFormat(bool NewVal);
 
 private:
+  friend class TargetLibraryInfoImpl;
+
+  /// Cache for TLI::getLibFunc() result without prototype validation.
+  /// -1 if uninitialized. NotLibFunc if definitely not lib func.
+  /// Otherwise may be libfunc if prototype validation passes.
+  mutable LibFunc LibFuncCache = LibFunc(-1);
+
   void CheckLazyArguments() const {
     if (hasLazyArguments())
       BuildLazyArguments();
diff --git a/llvm/lib/Analysis/TargetLibraryInfo.cpp b/llvm/lib/Analysis/TargetLibraryInfo.cpp
index 7b38583e9bc75f0..1037368169bbaad 100644
--- a/llvm/lib/Analysis/TargetLibraryInfo.cpp
+++ b/llvm/lib/Analysis/TargetLibraryInfo.cpp
@@ -1138,8 +1138,15 @@ bool TargetLibraryInfoImpl::getLibFunc(const Function &FDecl,
   const Module *M = FDecl.getParent();
   assert(M && "Expecting FDecl to be connected to a Module.");
 
-  return getLibFunc(FDecl.getName(), F) &&
-         isValidProtoForLibFunc(*FDecl.getFunctionType(), F, *M);
+  if (FDecl.LibFuncCache == LibFunc(-1))
+    if (!getLibFunc(FDecl.getName(), FDecl.LibFuncCache))
+      FDecl.LibFuncCache = NotLibFunc;
+
+  if (FDecl.LibFuncCache == NotLibFunc)
+    return false;
+
+  F = FDecl.LibFuncCache;
+  return isValidProtoForLibFunc(*FDecl.getFunctionType(), F, *M);
 }
 
 void TargetLibraryInfoImpl::disableAllFunctions() {
diff --git a/llvm/lib/IR/Function.cpp b/llvm/lib/IR/Function.cpp
index 49e0c1c5883c265..bff36b02c20246f 100644
--- a/llvm/lib/IR/Function.cpp
+++ b/llvm/lib/IR/Function.cpp
@@ -913,6 +913,7 @@ Intrinsic::ID Function::lookupIntrinsicID(StringRef Name) {
 }
 
 void Function::recalculateIntrinsicID() {
+  LibFuncCache = LibFunc(-1);
   StringRef Name = getName();
   if (!Name.startswith("llvm.")) {
     HasLLVMReservedName = false;

>From f7dd251b2afbafdff5bb69491931fc68284523eb Mon Sep 17 00:00:00 2001
From: Nikita Popov <npopov at redhat.com>
Date: Tue, 21 Nov 2023 10:07:59 +0100
Subject: [PATCH 2/2] Add UnknownLibFunc alias for LibFunc(-1)

---
 llvm/include/llvm/IR/Function.h         | 6 ++++--
 llvm/lib/Analysis/TargetLibraryInfo.cpp | 2 +-
 llvm/lib/IR/Function.cpp                | 2 +-
 3 files changed, 6 insertions(+), 4 deletions(-)

diff --git a/llvm/include/llvm/IR/Function.h b/llvm/include/llvm/IR/Function.h
index 0089fd7d5d8788d..aa36a2dd12a7e87 100644
--- a/llvm/include/llvm/IR/Function.h
+++ b/llvm/include/llvm/IR/Function.h
@@ -124,10 +124,12 @@ class LLVM_EXTERNAL_VISIBILITY Function : public GlobalObject,
 private:
   friend class TargetLibraryInfoImpl;
 
+  static constexpr LibFunc UnknownLibFunc = LibFunc(-1);
+
   /// Cache for TLI::getLibFunc() result without prototype validation.
-  /// -1 if uninitialized. NotLibFunc if definitely not lib func.
+  /// UnknownLibFunc if uninitialized. NotLibFunc if definitely not lib func.
   /// Otherwise may be libfunc if prototype validation passes.
-  mutable LibFunc LibFuncCache = LibFunc(-1);
+  mutable LibFunc LibFuncCache = UnknownLibFunc;
 
   void CheckLazyArguments() const {
     if (hasLazyArguments())
diff --git a/llvm/lib/Analysis/TargetLibraryInfo.cpp b/llvm/lib/Analysis/TargetLibraryInfo.cpp
index 1037368169bbaad..20959cf6948f656 100644
--- a/llvm/lib/Analysis/TargetLibraryInfo.cpp
+++ b/llvm/lib/Analysis/TargetLibraryInfo.cpp
@@ -1138,7 +1138,7 @@ bool TargetLibraryInfoImpl::getLibFunc(const Function &FDecl,
   const Module *M = FDecl.getParent();
   assert(M && "Expecting FDecl to be connected to a Module.");
 
-  if (FDecl.LibFuncCache == LibFunc(-1))
+  if (FDecl.LibFuncCache == Function::UnknownLibFunc)
     if (!getLibFunc(FDecl.getName(), FDecl.LibFuncCache))
       FDecl.LibFuncCache = NotLibFunc;
 
diff --git a/llvm/lib/IR/Function.cpp b/llvm/lib/IR/Function.cpp
index bff36b02c20246f..64b48897485e32f 100644
--- a/llvm/lib/IR/Function.cpp
+++ b/llvm/lib/IR/Function.cpp
@@ -913,7 +913,7 @@ Intrinsic::ID Function::lookupIntrinsicID(StringRef Name) {
 }
 
 void Function::recalculateIntrinsicID() {
-  LibFuncCache = LibFunc(-1);
+  LibFuncCache = UnknownLibFunc;
   StringRef Name = getName();
   if (!Name.startswith("llvm.")) {
     HasLLVMReservedName = false;



More information about the llvm-commits mailing list