LLVM 20.0.0git
UpdateCompilerUsed.cpp
Go to the documentation of this file.
1//==-LTOInternalize.cpp - LLVM Link Time Optimizer Internalization Utility -==//
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 a helper to run the internalization part of LTO.
10//
11//===----------------------------------------------------------------------===//
12
17#include "llvm/IR/Mangler.h"
18#include "llvm/IR/Module.h"
21
22using namespace llvm;
23
24namespace {
25
26// Helper class that collects AsmUsed and user supplied libcalls.
27class PreserveLibCallsAndAsmUsed {
28public:
29 PreserveLibCallsAndAsmUsed(const StringSet<> &AsmUndefinedRefs,
30 const TargetMachine &TM,
31 std::vector<GlobalValue *> &LLVMUsed)
32 : AsmUndefinedRefs(AsmUndefinedRefs), TM(TM), LLVMUsed(LLVMUsed) {}
33
34 void findInModule(Module &TheModule) {
35 initializeLibCalls(TheModule);
36 for (Function &F : TheModule)
37 findLibCallsAndAsm(F);
38 for (GlobalVariable &GV : TheModule.globals())
39 findLibCallsAndAsm(GV);
40 for (GlobalAlias &GA : TheModule.aliases())
41 findLibCallsAndAsm(GA);
42 }
43
44private:
45 // Inputs
46 const StringSet<> &AsmUndefinedRefs;
47 const TargetMachine &TM;
48
49 // Temps
51 StringSet<> Libcalls;
52
53 // Output
54 std::vector<GlobalValue *> &LLVMUsed;
55
56 // Collect names of runtime library functions. User-defined functions with the
57 // same names are added to llvm.compiler.used to prevent them from being
58 // deleted by optimizations.
59 void initializeLibCalls(const Module &TheModule) {
60 TargetLibraryInfoImpl TLII(Triple(TM.getTargetTriple()));
61 TargetLibraryInfo TLI(TLII);
62
63 // TargetLibraryInfo has info on C runtime library calls on the current
64 // target.
65 for (unsigned I = 0, E = static_cast<unsigned>(LibFunc::NumLibFuncs);
66 I != E; ++I) {
67 LibFunc F = static_cast<LibFunc>(I);
68 if (TLI.has(F))
69 Libcalls.insert(TLI.getName(F));
70 }
71
73
74 for (const Function &F : TheModule) {
76 TM.getSubtargetImpl(F)->getTargetLowering();
77
78 if (Lowering && TLSet.insert(Lowering).second)
79 // TargetLowering has info on library calls that CodeGen expects to be
80 // available, both from the C runtime and compiler-rt.
81 for (unsigned I = 0, E = static_cast<unsigned>(RTLIB::UNKNOWN_LIBCALL);
82 I != E; ++I)
83 if (const char *Name =
84 Lowering->getLibcallName(static_cast<RTLIB::Libcall>(I)))
85 Libcalls.insert(Name);
86 }
87 }
88
89 void findLibCallsAndAsm(GlobalValue &GV) {
90 // There are no restrictions to apply to declarations.
91 if (GV.isDeclaration())
92 return;
93
94 // There is nothing more restrictive than private linkage.
95 if (GV.hasPrivateLinkage())
96 return;
97
98 // Conservatively append user-supplied runtime library functions (supplied
99 // either directly, or via a function alias) to llvm.compiler.used. These
100 // could be internalized and deleted by optimizations like -globalopt,
101 // causing problems when later optimizations add new library calls (e.g.,
102 // llvm.memset => memset and printf => puts).
103 // Leave it to the linker to remove any dead code (e.g. with -dead_strip).
104 GlobalValue *FuncAliasee = nullptr;
105 if (isa<GlobalAlias>(GV)) {
106 auto *A = cast<GlobalAlias>(&GV);
107 FuncAliasee = dyn_cast<Function>(A->getAliasee());
108 }
109 if ((isa<Function>(GV) || FuncAliasee) && Libcalls.count(GV.getName())) {
110 LLVMUsed.push_back(&GV);
111 return;
112 }
113
114 SmallString<64> Buffer;
115 TM.getNameWithPrefix(Buffer, &GV, Mangler);
116 if (AsmUndefinedRefs.count(Buffer))
117 LLVMUsed.push_back(&GV);
118 }
119};
120
121} // namespace anonymous
122
124 const StringSet<> &AsmUndefinedRefs) {
125 std::vector<GlobalValue *> UsedValues;
126 PreserveLibCallsAndAsmUsed(AsmUndefinedRefs, TM, UsedValues)
127 .findInModule(TheModule);
128
129 if (UsedValues.empty())
130 return;
131
132 appendToCompilerUsed(TheModule, UsedValues);
133}
static GCRegistry::Add< ErlangGC > A("erlang", "erlang-compatible garbage collector")
std::string Name
#define F(x, y, z)
Definition: MD5.cpp:55
#define I(x, y, z)
Definition: MD5.cpp:58
Module.h This file contains the declarations for the Module class.
const char LLVMTargetMachineRef TM
pre isel intrinsic Pre ISel Intrinsic Lowering
static void initializeLibCalls(TargetLibraryInfoImpl &TLI, const Triple &T, ArrayRef< StringLiteral > StandardNames)
Initialize the set of available library functions based on the specified target triple.
This file describes how to lower LLVM code to machine code.
bool isDeclaration() const
Return true if the primary definition of this global value is outside of the current translation unit...
Definition: Globals.cpp:290
bool hasPrivateLinkage() const
Definition: GlobalValue.h:527
A Module instance is used to store all the information related to an LLVM module.
Definition: Module.h:65
std::pair< iterator, bool > insert(PtrType Ptr)
Inserts Ptr if and only if there is no element in the container equal to Ptr.
Definition: SmallPtrSet.h:368
SmallPtrSet - This class implements a set which is optimized for holding SmallSize or less elements.
Definition: SmallPtrSet.h:503
SmallString - A SmallString is just a SmallVector with methods and accessors that make it work better...
Definition: SmallString.h:26
size_type count(StringRef Key) const
count - Return 1 if the element is in the map, 0 otherwise.
Definition: StringMap.h:276
StringSet - A wrapper for StringMap that provides set-like functionality.
Definition: StringSet.h:23
std::pair< typename Base::iterator, bool > insert(StringRef key)
Definition: StringSet.h:38
Implementation of the target library information.
Provides information about what library functions are available for the current target.
This class defines information used to lower LLVM code to legal SelectionDAG operators that the targe...
Primary interface to the complete machine description for the target machine.
Definition: TargetMachine.h:77
Triple - Helper class for working with autoconf configuration names.
Definition: Triple.h:44
StringRef getName() const
Return a constant reference to the value's name.
Definition: Value.cpp:309
Libcall
RTLIB::Libcall enum - This enum defines all of the runtime library calls the backend can emit.
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:18
void updateCompilerUsed(Module &TheModule, const TargetMachine &TM, const StringSet<> &AsmUndefinedRefs)
Find all globals in TheModule that are referenced in AsmUndefinedRefs, as well as the user-supplied f...
void appendToCompilerUsed(Module &M, ArrayRef< GlobalValue * > Values)
Adds global values to the llvm.compiler.used list.