LLVM 24.0.0git
LowerTypeTests.cpp
Go to the documentation of this file.
1//===- LowerTypeTests.cpp - type metadata lowering pass -------------------===//
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 pass lowers type metadata and calls to the llvm.type.test intrinsic.
10// It also ensures that globals are properly laid out for the
11// llvm.icall.branch.funnel intrinsic.
12// See http://llvm.org/docs/TypeMetadata.html for more information.
13//
14//===----------------------------------------------------------------------===//
15
17#include "IPOOptions.h"
18#include "llvm/ADT/APInt.h"
19#include "llvm/ADT/ArrayRef.h"
20#include "llvm/ADT/DenseMap.h"
23#include "llvm/ADT/MapVector.h"
25#include "llvm/ADT/STLExtras.h"
26#include "llvm/ADT/SetVector.h"
28#include "llvm/ADT/Statistic.h"
29#include "llvm/ADT/StringRef.h"
40#include "llvm/IR/Attributes.h"
41#include "llvm/IR/BasicBlock.h"
42#include "llvm/IR/Constant.h"
43#include "llvm/IR/Constants.h"
44#include "llvm/IR/DIBuilder.h"
45#include "llvm/IR/DataLayout.h"
47#include "llvm/IR/Function.h"
48#include "llvm/IR/GlobalAlias.h"
50#include "llvm/IR/GlobalValue.h"
52#include "llvm/IR/IRBuilder.h"
53#include "llvm/IR/InlineAsm.h"
54#include "llvm/IR/Instruction.h"
57#include "llvm/IR/Intrinsics.h"
58#include "llvm/IR/LLVMContext.h"
59#include "llvm/IR/MDBuilder.h"
60#include "llvm/IR/Metadata.h"
61#include "llvm/IR/Module.h"
64#include "llvm/IR/Operator.h"
65#include "llvm/IR/PassManager.h"
68#include "llvm/IR/Type.h"
69#include "llvm/IR/Use.h"
70#include "llvm/IR/User.h"
71#include "llvm/IR/Value.h"
75#include "llvm/Support/Debug.h"
76#include "llvm/Support/Error.h"
86#include "llvm/Transforms/IPO.h"
89#include <algorithm>
90#include <cassert>
91#include <cstdint>
92#include <set>
93#include <string>
94#include <system_error>
95#include <utility>
96#include <vector>
97
98using namespace llvm;
99using namespace lowertypetests;
100
101#define DEBUG_TYPE "lowertypetests"
102
103STATISTIC(ByteArraySizeBits, "Byte array size in bits");
104STATISTIC(ByteArraySizeBytes, "Byte array size in bytes");
105STATISTIC(NumByteArraysCreated, "Number of byte arrays created");
106STATISTIC(NumTypeTestCallsLowered, "Number of type test calls lowered");
107STATISTIC(NumTypeIdDisjointSets, "Number of disjoint sets of type identifiers");
108
110 if (Offset < ByteOffset)
111 return false;
112
113 if ((Offset - ByteOffset) % (uint64_t(1) << AlignLog2) != 0)
114 return false;
115
116 uint64_t BitOffset = (Offset - ByteOffset) >> AlignLog2;
117 if (BitOffset >= BitSize)
118 return false;
119
120 return Bits.count(BitSize - 1 - BitOffset);
121}
122
124 OS << "offset " << ByteOffset << " size " << BitSize << " align "
125 << (1 << AlignLog2);
126
127 if (isAllOnes()) {
128 OS << " all-ones\n";
129 return;
130 }
131
132 OS << " { ";
133 for (uint64_t B : Bits)
134 OS << B << ' ';
135 OS << "}\n";
136}
137
139 if (Min > Max)
140 Min = 0;
141
142 // Normalize each offset against the minimum observed offset, and compute
143 // the bitwise OR of each of the offsets. The number of trailing zeros
144 // in the mask gives us the log2 of the alignment of all offsets, which
145 // allows us to compress the bitset by only storing one bit per aligned
146 // address.
147 uint64_t Mask = 0;
148 for (uint64_t &Offset : Offsets) {
149 Offset -= Min;
150 Mask |= Offset;
151 }
152
153 BitSetInfo BSI;
154 BSI.ByteOffset = Min;
155
156 BSI.AlignLog2 = 0;
157 if (Mask != 0)
158 BSI.AlignLog2 = llvm::countr_zero(Mask);
159
160 // Build the compressed bitset while normalizing the offsets against the
161 // computed alignment.
162 BSI.BitSize = ((Max - Min) >> BSI.AlignLog2) + 1;
163 for (uint64_t Offset : Offsets) {
164 Offset >>= BSI.AlignLog2;
165 // We invert the order of bits when adding them to the bitset. This is
166 // because the offset that we test against is computed by subtracting the
167 // address that we are testing from the global's address, which means that
168 // the offset increases as the tested address decreases.
169 BSI.Bits.insert(BSI.BitSize - 1 - Offset);
170 }
171
172 return BSI;
173}
174
175void GlobalLayoutBuilder::addFragment(const std::set<uint64_t> &F) {
176 assert(Fragments.front().empty() && "Cannot add fragments after build()");
177
178 // Create a new fragment to hold the layout for F.
179 Fragments.emplace_back();
180 std::vector<uint64_t> &Fragment = Fragments.back();
181 uint64_t FragmentIndex = Fragments.size() - 1;
182
183 std::vector<std::vector<uint64_t>> SubFragments;
184 for (auto ObjIndex : F) {
185 uint64_t OldFragmentIndex = FragmentMap[ObjIndex];
186 if (OldFragmentIndex == 0) {
187 // We haven't seen this object index before, so just add it to the current
188 // fragment.
189 SubFragments.push_back({ObjIndex});
190 } else if (!Fragments[OldFragmentIndex].empty()) {
191 // This index belongs to an existing fragment. Copy the elements of the
192 // old fragment into this one and clear the old fragment. We don't update
193 // the fragment map just yet, this ensures that any further references to
194 // indices from the old fragment in this fragment do not insert any more
195 // indices.
196 SubFragments.push_back(std::move(Fragments[OldFragmentIndex]));
197 }
198 }
199
200 if (Less) {
201 llvm::stable_sort(SubFragments, [&](const std::vector<uint64_t> &A,
202 const std::vector<uint64_t> &B) {
203 return Less(A.back(), B.back());
204 });
205 }
206
207 for (auto &SF : SubFragments)
208 llvm::append_range(Fragment, std::move(SF));
209
210 // Update the fragment map to point our object indices to this fragment.
211 for (uint64_t ObjIndex : Fragment)
212 FragmentMap[ObjIndex] = FragmentIndex;
213}
214
215const std::vector<uint64_t> &GlobalLayoutBuilder::build() {
216 if (Less) {
217 // If multiple root fragments remain (e.g. disjoint signatures with no
218 // generalized type), order them so the one containing the hottest function
219 // is placed last.
220 llvm::erase_if(Fragments,
221 [](const std::vector<uint64_t> &F) { return F.empty(); });
222 llvm::stable_sort(Fragments, [&](const std::vector<uint64_t> &FA,
223 const std::vector<uint64_t> &FB) {
224 return Less(FA.back(), FB.back());
225 });
226 }
227
228 std::vector<uint64_t> Layout;
229 Layout.reserve(FragmentMap.size());
230 for (auto &&F : Fragments)
231 llvm::append_range(Layout, F);
232 Fragments.clear();
233 Fragments.push_back(std::move(Layout));
234 return Fragments.front();
235}
236
237void ByteArrayBuilder::allocate(const std::set<uint64_t> &Bits,
238 uint64_t BitSize, uint64_t &AllocByteOffset,
239 uint8_t &AllocMask) {
240 // Find the smallest current allocation.
241 unsigned Bit = 0;
242 for (unsigned I = 1; I != BitsPerByte; ++I)
243 if (BitAllocs[I] < BitAllocs[Bit])
244 Bit = I;
245
246 AllocByteOffset = BitAllocs[Bit];
247
248 // Add our size to it.
249 unsigned ReqSize = AllocByteOffset + BitSize;
250 BitAllocs[Bit] = ReqSize;
251 if (Bytes.size() < ReqSize)
252 Bytes.resize(ReqSize);
253
254 // Set our bits.
255 AllocMask = 1 << Bit;
256 for (uint64_t B : Bits)
257 Bytes[AllocByteOffset + B] |= AllocMask;
258}
259
261 if (F->isDeclarationForLinker())
262 return false;
264 F->getParent()->getModuleFlag("CFI Canonical Jump Tables"));
265 if (!CI || !CI->isZero())
266 return true;
267 return F->hasFnAttribute("cfi-canonical-jump-table");
268}
269
271 if (MDNode *MD = GO.getMetadata(LLVMContext::MD_associated))
272 if (auto *AssocVM = dyn_cast_or_null<ValueAsMetadata>(MD->getOperand(0)))
273 if (auto *AssocGO = dyn_cast<GlobalObject>(AssocVM->getValue()))
274 if (AssocGO->hasMetadata(LLVMContext::MD_type))
275 return true;
276 return GO.hasMetadata(LLVMContext::MD_type);
277}
278
280 SetVector<GlobalValue *> CfiFunctions;
281 for (auto &F : M)
282 if ((!F.hasLocalLinkage() || F.hasAddressTaken()) && hasTypeMetadata(F))
283 CfiFunctions.insert(&F);
284 for (auto &A : M.aliases())
285 if (auto *F = dyn_cast<Function>(A.getAliasee()))
286 if (hasTypeMetadata(*F))
287 CfiFunctions.insert(&A);
288 return CfiFunctions;
289}
290
291/// Extracts a numeric type identifier from an MDNode containing type metadata.
293 // This check excludes vtables for classes inside anonymous namespaces.
294 auto TM = dyn_cast<ValueAsMetadata>(MD.getOperand(1));
295 if (!TM)
296 return nullptr;
297 auto C = dyn_cast_or_null<ConstantInt>(TM->getValue());
298 if (!C)
299 return nullptr;
300 // We are looking for i64 constants.
301 if (C->getBitWidth() != 64)
302 return nullptr;
303
304 return C;
305}
306
308 SetVector<uint64_t> TypeIds;
310 for (const GlobalObject &GO : M.global_objects()) {
311 Types.clear();
312 GO.getMetadata(LLVMContext::MD_type, Types);
313 for (MDNode *Type : Types)
314 if (ConstantInt *TypeId = extractNumericTypeId(*Type))
315 TypeIds.insert(TypeId->getZExtValue());
316 }
317
318 if (NamedMDNode *CfiFunctionsMD = M.getNamedMetadata("cfi.functions")) {
319 for (auto *Func : CfiFunctionsMD->operands()) {
320 assert(Func->getNumOperands() >= 3);
321 assert(isa<ConstantAsMetadata>(Func->getOperand(2)));
322 for (unsigned I = 3; I < Func->getNumOperands(); ++I)
323 if (ConstantInt *TypeId =
324 extractNumericTypeId(*cast<MDNode>(Func->getOperand(I))))
325 TypeIds.insert(TypeId->getZExtValue());
326 }
327 }
328 return TypeIds;
329}
330
331namespace {
332
333/// The type of CFI jumptable needed for a function.
334enum class CfiFunctionLinkage : uint8_t {
335 Definition = 0,
336 Declaration = 1,
337 WeakDeclaration = 2,
338};
339
340/// The hotness of a CFI jumptable function entry.
341class CfiFunctionHotness {
342 enum class Kind : uint8_t {
343 Unknown = 0, // It's higher rank than Cold, but convenient to store as zero.
344 Cold = 1,
345 Other = 2,
346 Hot = 3,
347 };
348
349 Kind Type = Kind::Unknown;
350
351 CfiFunctionHotness(Kind Type) : Type(Type) {}
352
353public:
354 CfiFunctionHotness() = default;
355
356 // Computes the execution weight for F across its entry count and basic block
357 // counts. Placing the hottest function (i.e. the function with the highest
358 // weight) as the last jump table entry makes it more likely to benefit from
359 // the SHT_LLVM_CFI_JUMP_TABLE last-entry optimization and locks the jump
360 // table into the target's section, which is likely hot.
361 // The most important goal is to put functions which end up in .hot at the
362 // end of jumptable, to keep jump table in the same section.
363 static CfiFunctionHotness
364 fromFunction(Function &F, ProfileSummaryInfo &PSI,
365 function_ref<const BlockFrequencyInfo &(Function &)> BFIGetter) {
366 if (F.isDeclaration())
367 return Kind::Unknown;
368
369 // We want to mimic CodeGenPrepare::_run to match section assignments.
370 const BlockFrequencyInfo &BFI = BFIGetter(F);
371 if (F.hasFnAttribute(Attribute::Hot) ||
372 PSI.isFunctionHotInCallGraph(&F, BFI)) {
373 return Kind::Hot;
374 }
375
376 if (PSI.isFunctionColdInCallGraph(&F, BFI) ||
377 F.hasFnAttribute(Attribute::Cold)) {
378 return Kind::Cold;
379 }
380
382 ? Kind::Unknown
383 : Kind::Other;
384 }
385
386 static CfiFunctionHotness fromUint6(uint8_t V) {
387 return CfiFunctionHotness(static_cast<Kind>(V & 0x3));
388 }
389
390 uint8_t asUint6() const { return static_cast<uint8_t>(Type) & 0x3; }
391
392 bool operator==(const CfiFunctionHotness &Other) const {
393 return Type == Other.Type;
394 }
395
396 bool operator<(const CfiFunctionHotness &Other) const {
397 auto Rank = [](Kind K) -> int {
398 return (K == Kind::Cold) ? -1 : static_cast<int>(K);
399 };
400 return Rank(Type) < Rank(Other.Type);
401 }
402};
403
404} // namespace
405
406static CfiFunctionLinkage decodeCfiFunctionLinkage(uint8_t Encoded) {
407 return static_cast<CfiFunctionLinkage>(Encoded & 0x3);
408}
409
410static CfiFunctionHotness decodeCfiFunctionHotness(uint8_t Encoded) {
411 return CfiFunctionHotness::fromUint6(Encoded >> 2);
412}
413
414static uint8_t encodeCfiFunctionLinkage(CfiFunctionLinkage Linkage,
415 CfiFunctionHotness Hotness) {
416 uint8_t Encoded =
417 (Hotness.asUint6() << 2) | (static_cast<uint8_t>(Linkage) & 0x3);
419 assert(decodeCfiFunctionHotness(Encoded) == Hotness);
420 return Encoded;
421}
422
424 Module &DestM, ArrayRef<GlobalValue *> CfiFunctions,
426 function_ref<const BlockFrequencyInfo &(Function &)> BFIGetter) {
427 const IPOOptions &Opts = getIPOOptions(DestM);
428 auto &Ctx = DestM.getContext();
429 SmallVector<MDNode *, 8> CfiFunctionMDs;
430 for (auto *V : CfiFunctions) {
431 Function &F = *cast<Function>(V->getAliaseeObject());
433 F.getMetadata(LLVMContext::MD_type, Types);
434
436 Elts.push_back(MDString::get(Ctx, V->getName()));
437 CfiFunctionLinkage Linkage = CfiFunctionLinkage::Declaration;
439 Linkage = CfiFunctionLinkage::Definition;
440 else if (F.hasExternalWeakLinkage())
441 Linkage = CfiFunctionLinkage::WeakDeclaration;
442
443 CfiFunctionHotness Hotness =
444 Opts.reorder_cfi_jump_tables_profiles
445 ? CfiFunctionHotness::fromFunction(F, PSI, BFIGetter)
446 : CfiFunctionHotness();
447
448 uint8_t EncodedLinkage = encodeCfiFunctionLinkage(Linkage, Hotness);
449
451 llvm::ConstantInt::get(Type::getInt8Ty(Ctx), EncodedLinkage)));
452 GlobalValue::GUID GUID = V->getGUID();
454 llvm::ConstantInt::get(Type::getInt64Ty(Ctx), GUID)));
455 append_range(Elts, Types);
456 CfiFunctionMDs.push_back(MDTuple::get(Ctx, Elts));
457 }
458
459 if (!CfiFunctionMDs.empty()) {
460 NamedMDNode *NMD = DestM.getOrInsertNamedMetadata("cfi.functions");
461 for (auto *MD : CfiFunctionMDs)
462 NMD->addOperand(MD);
463 }
464}
465
466static void createCfiAliasesMetadata(Module &DestM, const Module &SrcM) {
467 auto &Ctx = DestM.getContext();
469 for (const auto &A : SrcM.aliases()) {
470 if (!isa<Function>(A.getAliasee()))
471 continue;
472
473 const auto *F = cast<Function>(A.getAliasee());
474 FunctionAliases[F].push_back(&A);
475 }
476
477 if (!FunctionAliases.empty()) {
478 NamedMDNode *NMD = DestM.getOrInsertNamedMetadata("aliases");
479 for (auto &Alias : FunctionAliases) {
481 Elts.push_back(MDString::get(Ctx, Alias.first->getName()));
482 for (auto *A : Alias.second)
483 Elts.push_back(MDString::get(Ctx, A->getName()));
484 NMD->addOperand(MDTuple::get(Ctx, Elts));
485 }
486 }
487}
488
489static void createCfiSymversMetadata(Module &DestM, const Module &SrcM) {
490 auto &Ctx = DestM.getContext();
493 SrcM, [&](StringRef Name, StringRef Alias) {
494 const Function *F = SrcM.getFunction(Name);
495 if (!F || F->use_empty())
496 return;
497
498 Symvers.push_back(MDTuple::get(
499 Ctx, {MDString::get(Ctx, Name), MDString::get(Ctx, Alias)}));
500 });
501
502 if (!Symvers.empty()) {
503 NamedMDNode *NMD = DestM.getOrInsertNamedMetadata("symvers");
504 for (auto *MD : Symvers)
505 NMD->addOperand(MD);
506 }
507}
508
510 Module &DestM, const Module &SrcM, ArrayRef<GlobalValue *> CfiFunctions,
512 function_ref<const BlockFrequencyInfo &(Function &)> BFIGetter) {
513 createCfiFunctionsMetadata(DestM, CfiFunctions, PSI, BFIGetter);
514 createCfiAliasesMetadata(DestM, SrcM);
515 createCfiSymversMetadata(DestM, SrcM);
516}
517
518namespace {
519
520struct ByteArrayInfo {
521 std::set<uint64_t> Bits;
522 uint64_t BitSize;
523 GlobalVariable *ByteArray;
524 GlobalVariable *MaskGlobal;
525 uint8_t *MaskPtr = nullptr;
526};
527
528/// A POD-like structure that we use to store a global reference together with
529/// its metadata types. In this pass we frequently need to query the set of
530/// metadata types referenced by a global, which at the IR level is an expensive
531/// operation involving a map lookup; this data structure helps to reduce the
532/// number of times we need to do this lookup.
533class GlobalTypeMember final : TrailingObjects<GlobalTypeMember, MDNode *> {
534 friend TrailingObjects;
535
536 GlobalObject *GO;
537 size_t NTypes;
538
539 // For functions: true if the jump table is canonical. This essentially means
540 // whether the canonical address (i.e. the symbol table entry) of the function
541 // is provided by the local jump table. This is normally the same as whether
542 // the function is defined locally, but if canonical jump tables are disabled
543 // by the user then the jump table never provides a canonical definition.
544 bool IsJumpTableCanonical;
545
546 // For functions: true if this function is either defined or used in a thinlto
547 // module and its jumptable entry needs to be exported to thinlto backends.
548 bool IsExported;
549
550public:
551 static GlobalTypeMember *create(BumpPtrAllocator &Alloc, GlobalObject *GO,
552 bool IsJumpTableCanonical, bool IsExported,
553 ArrayRef<MDNode *> Types) {
554 auto *GTM = static_cast<GlobalTypeMember *>(Alloc.Allocate(
555 totalSizeToAlloc<MDNode *>(Types.size()), alignof(GlobalTypeMember)));
556 GTM->GO = GO;
557 GTM->NTypes = Types.size();
558 GTM->IsJumpTableCanonical = IsJumpTableCanonical;
559 GTM->IsExported = IsExported;
560 llvm::copy(Types, GTM->getTrailingObjects());
561 return GTM;
562 }
563
564 GlobalObject *getGlobal() const {
565 return GO;
566 }
567
568 bool isJumpTableCanonical() const {
569 return IsJumpTableCanonical;
570 }
571
572 bool isExported() const {
573 return IsExported;
574 }
575
576 ArrayRef<MDNode *> types() const { return getTrailingObjects(NTypes); }
577};
578
579struct ICallBranchFunnel final
580 : TrailingObjects<ICallBranchFunnel, GlobalTypeMember *> {
581 static ICallBranchFunnel *create(BumpPtrAllocator &Alloc, CallInst *CI,
583 unsigned UniqueId) {
584 auto *Call = static_cast<ICallBranchFunnel *>(
585 Alloc.Allocate(totalSizeToAlloc<GlobalTypeMember *>(Targets.size()),
586 alignof(ICallBranchFunnel)));
587 Call->CI = CI;
588 Call->UniqueId = UniqueId;
589 Call->NTargets = Targets.size();
590 llvm::copy(Targets, Call->getTrailingObjects());
591 return Call;
592 }
593
594 CallInst *CI;
595 ArrayRef<GlobalTypeMember *> targets() const {
596 return getTrailingObjects(NTargets);
597 }
598
599 unsigned UniqueId;
600
601private:
602 size_t NTargets;
603};
604
605struct ScopedSaveAliaseesAndUsed {
606 Module &M;
608 std::vector<std::pair<GlobalAlias *, Function *>> FunctionAliases;
609 std::vector<std::pair<GlobalIFunc *, Function *>> ResolverIFuncs;
610
611 // This function only removes functions from llvm.used and llvm.compiler.used.
612 // We cannot remove global variables because they need to follow RAUW, as
613 // they may be deleted by buildBitSetsFromGlobalVariables.
614 void collectAndEraseUsedFunctions(Module &M,
615 SmallVectorImpl<GlobalValue *> &Vec,
616 bool CompilerUsed) {
617 auto *GV = collectUsedGlobalVariables(M, Vec, CompilerUsed);
618 if (!GV)
619 return;
620 // There's no API to only remove certain array elements from
621 // llvm.used/llvm.compiler.used, so we remove all of them and add back only
622 // the non-functions.
623 GV->eraseFromParent();
624 auto NonFuncBegin =
625 std::stable_partition(Vec.begin(), Vec.end(), [](GlobalValue *GV) {
626 return isa<Function>(GV);
627 });
628 if (CompilerUsed)
629 appendToCompilerUsed(M, {NonFuncBegin, Vec.end()});
630 else
631 appendToUsed(M, {NonFuncBegin, Vec.end()});
632 Vec.resize(NonFuncBegin - Vec.begin());
633 }
634
635 ScopedSaveAliaseesAndUsed(Module &M) : M(M) {
636 // The users of this class want to replace all function references except
637 // for aliases and llvm.used/llvm.compiler.used with references to a jump
638 // table. We avoid replacing aliases in order to avoid introducing a double
639 // indirection (or an alias pointing to a declaration in ThinLTO mode), and
640 // we avoid replacing llvm.used/llvm.compiler.used because these global
641 // variables describe properties of the global, not the jump table (besides,
642 // offseted references to the jump table in llvm.used are invalid).
643 // Unfortunately, LLVM doesn't have a "RAUW except for these (possibly
644 // indirect) users", so what we do is save the list of globals referenced by
645 // llvm.used/llvm.compiler.used and aliases, erase the used lists, let RAUW
646 // replace the aliasees and then set them back to their original values at
647 // the end.
648 collectAndEraseUsedFunctions(M, Used, false);
649 collectAndEraseUsedFunctions(M, CompilerUsed, true);
650
651 for (auto &GA : M.aliases()) {
652 // FIXME: This should look past all aliases not just interposable ones,
653 // see discussion on D65118.
654 if (auto *F = dyn_cast<Function>(GA.getAliasee()->stripPointerCasts()))
655 FunctionAliases.push_back({&GA, F});
656 }
657
658 for (auto &GI : M.ifuncs())
659 if (auto *F = dyn_cast<Function>(GI.getResolver()->stripPointerCasts()))
660 ResolverIFuncs.push_back({&GI, F});
661 }
662
663 ~ScopedSaveAliaseesAndUsed() {
664 appendToUsed(M, Used);
665 appendToCompilerUsed(M, CompilerUsed);
666
667 for (auto P : FunctionAliases)
668 P.first->setAliasee(P.second);
669
670 for (auto P : ResolverIFuncs) {
671 // This does not preserve pointer casts that may have been stripped by the
672 // constructor, but the resolver's type is different from that of the
673 // ifunc anyway.
674 P.first->setResolver(P.second);
675 }
676 }
677};
678
679class LowerTypeTestsModule {
680 const IPOOptions &Opts;
681 Module &M;
682
683 ModuleSummaryIndex *ExportSummary;
684 const ModuleSummaryIndex *ImportSummary;
685
686 Triple::ArchType Arch;
688 Triple::ObjectFormatType ObjectFormat;
689
690 // Determines which kind of Thumb jump table we generate. If arch is
691 // either 'arm' or 'thumb' we need to find this out, because
692 // selectJumpTableArmEncoding may decide to use Thumb in either case.
693 bool CanUseArmJumpTable = false, CanUseThumbBWJumpTable = false;
694
695 // Cache variable used by hasBranchTargetEnforcement().
696 int HasBranchTargetEnforcement = -1;
697
698 // Map from function to hotness passed via cfi.functions metadata.
699 DenseMap<const Function *, CfiFunctionHotness> FunctionSummaryHotness;
700
701 IntegerType *Int1Ty = Type::getInt1Ty(M.getContext());
702 IntegerType *Int8Ty = Type::getInt8Ty(M.getContext());
703 PointerType *PtrTy = PointerType::getUnqual(M.getContext());
704 ArrayType *Int8Arr0Ty = ArrayType::get(Type::getInt8Ty(M.getContext()), 0);
705 IntegerType *Int32Ty = Type::getInt32Ty(M.getContext());
706 IntegerType *Int64Ty = Type::getInt64Ty(M.getContext());
707 IntegerType *IntPtrTy = M.getDataLayout().getIntPtrType(M.getContext(), 0);
708
709 // Indirect function call index assignment counter for WebAssembly
710 uint64_t IndirectIndex = 1;
711
712 // Mapping from type identifiers to the call sites that test them, as well as
713 // whether the type identifier needs to be exported to ThinLTO backends as
714 // part of the regular LTO phase of the ThinLTO pipeline (see exportTypeId).
715 struct TypeIdUserInfo {
716 std::vector<CallInst *> CallSites;
717 bool IsExported = false;
718 };
719 DenseMap<Metadata *, TypeIdUserInfo> TypeIdUsers;
720
721 /// This structure describes how to lower type tests for a particular type
722 /// identifier. It is either built directly from the global analysis (during
723 /// regular LTO or the regular LTO phase of ThinLTO), or indirectly using type
724 /// identifier summaries and external symbol references (in ThinLTO backends).
725 struct TypeIdLowering {
727
728 /// All except Unsat: the address of the last element within the combined
729 /// global.
730 Constant *OffsetedGlobal;
731
732 /// ByteArray, Inline, AllOnes: log2 of the required global alignment
733 /// relative to the start address.
734 Constant *AlignLog2;
735
736 /// ByteArray, Inline, AllOnes: one less than the size of the memory region
737 /// covering members of this type identifier as a multiple of 2^AlignLog2.
738 Constant *SizeM1;
739
740 /// ByteArray: the byte array to test the address against.
741 Constant *TheByteArray;
742
743 /// ByteArray: the bit mask to apply to bytes loaded from the byte array.
744 Constant *BitMask;
745
746 /// Inline: the bit mask to test the address against.
747 Constant *InlineBits;
748 };
749
750 std::vector<ByteArrayInfo> ByteArrayInfos;
751
752 Function *WeakInitializerFn = nullptr;
753
754 GlobalVariable *GlobalAnnotation;
755 DenseSet<Value *> FunctionAnnotations;
756
757 // Cross-DSO CFI emits jumptable entries for exported functions as well as
758 // address taken functions in case they are address taken in other modules.
759 bool CrossDsoCfi = M.getModuleFlag("Cross-DSO CFI") != nullptr;
760
761 bool shouldExportConstantsAsAbsoluteSymbols();
762 uint8_t *exportTypeId(StringRef TypeId, const TypeIdLowering &TIL);
763 TypeIdLowering importTypeId(StringRef TypeId);
764 void importTypeTest(CallInst *CI);
765 void importFunction(Function *F, bool isJumpTableCanonical);
766
767 ByteArrayInfo *createByteArray(const BitSetInfo &BSI);
768 void allocateByteArrays();
769 Value *createBitSetTest(IRBuilder<> &B, const TypeIdLowering &TIL,
770 Value *BitOffset);
771 void lowerTypeTestCalls(
772 ArrayRef<Metadata *> TypeIds, Constant *CombinedGlobalAddr,
773 const DenseMap<GlobalTypeMember *, uint64_t> &GlobalLayout);
774 Value *lowerTypeTestCall(Metadata *TypeId, CallInst *CI,
775 const TypeIdLowering &TIL);
776
777 void buildBitSetsFromGlobalVariables(ArrayRef<Metadata *> TypeIds,
780 selectJumpTableArmEncoding(ArrayRef<GlobalTypeMember *> Functions);
781 bool hasBranchTargetEnforcement();
782 unsigned getJumpTableEntrySize(Triple::ArchType JumpTableArch);
783 InlineAsm *createJumpTableEntryAsm(Triple::ArchType JumpTableArch);
784 void verifyTypeMDNode(GlobalObject *GO, MDNode *Type);
785 void buildBitSetsFromFunctions(ArrayRef<Metadata *> TypeIds,
787 void buildBitSetsFromFunctionsNative(ArrayRef<Metadata *> TypeIds,
789 void buildBitSetsFromFunctionsWASM(ArrayRef<Metadata *> TypeIds,
791 void
792 buildBitSetsFromDisjointSet(ArrayRef<Metadata *> TypeIds,
794 ArrayRef<ICallBranchFunnel *> ICallBranchFunnels);
795
796 void replaceWeakDeclarationWithJumpTablePtr(Function *F, Constant *JT,
797 bool IsJumpTableCanonical);
798 void moveInitializerToModuleConstructor(GlobalVariable *GV);
799 void findGlobalVariableUsersOf(Constant *C,
800 SmallSetVector<GlobalVariable *, 8> &Out);
801
802 void createJumpTable(Function *F, ArrayRef<GlobalTypeMember *> Functions,
803 Triple::ArchType JumpTableArch);
804
805 /// replaceCfiUses - Go through the uses list for this definition and make
806 /// each use point to "New" instead of "Old" when the use is outside the
807 /// block. 'Old's use list is expected to have at least one element. Unlike
808 /// replaceAllUsesWith this function skips blockaddr and direct call uses.
809 void replaceCfiUses(Function *Old, Value *New, bool IsJumpTableCanonical);
810
811 /// replaceDirectCalls - Go through the uses list for this definition and
812 /// replace each use, which is a direct function call.
813 void replaceDirectCalls(Value *Old, Value *New);
814
815 bool isFunctionAnnotation(Value *V) const {
816 return FunctionAnnotations.contains(V);
817 }
818
819 void maybeReplaceComdat(Function *F, StringRef OriginalName);
820
821public:
822 LowerTypeTestsModule(Module &M, ModuleAnalysisManager &AM,
823 ModuleSummaryIndex *ExportSummary,
824 const ModuleSummaryIndex *ImportSummary);
825
826 bool lower();
827
828 // Lower the module using the action and summary passed as command line
829 // arguments. For testing purposes only.
830 static bool runForTesting(Module &M, ModuleAnalysisManager &AM);
831};
832} // end anonymous namespace
833
834/// Build a bit set for list of offsets.
836 // Compute the byte offset of each address associated with this type
837 // identifier.
838 return BitSetBuilder(Offsets).build();
839}
840
841/// Build a test that bit BitOffset mod sizeof(Bits)*8 is set in
842/// Bits. This pattern matches to the bt instruction on x86.
844 Value *BitOffset) {
845 auto BitsType = cast<IntegerType>(Bits->getType());
846 unsigned BitWidth = BitsType->getBitWidth();
847
848 BitOffset = B.CreateZExtOrTrunc(BitOffset, BitsType);
849 Value *BitIndex =
850 B.CreateAnd(BitOffset, ConstantInt::get(BitsType, BitWidth - 1));
851 Value *BitMask = B.CreateShl(ConstantInt::get(BitsType, 1), BitIndex);
852 Value *MaskedBits = B.CreateAnd(Bits, BitMask);
853 return B.CreateICmpNE(MaskedBits, ConstantInt::get(BitsType, 0));
854}
855
856ByteArrayInfo *LowerTypeTestsModule::createByteArray(const BitSetInfo &BSI) {
857 // Create globals to stand in for byte arrays and masks. These never actually
858 // get initialized, we RAUW and erase them later in allocateByteArrays() once
859 // we know the offset and mask to use.
860 auto ByteArrayGlobal = new GlobalVariable(
861 M, Int8Ty, /*isConstant=*/true, GlobalValue::PrivateLinkage, nullptr);
862 auto MaskGlobal = new GlobalVariable(M, Int8Ty, /*isConstant=*/true,
864
865 ByteArrayInfos.emplace_back();
866 ByteArrayInfo *BAI = &ByteArrayInfos.back();
867
868 BAI->Bits = BSI.Bits;
869 BAI->BitSize = BSI.BitSize;
870 BAI->ByteArray = ByteArrayGlobal;
871 BAI->MaskGlobal = MaskGlobal;
872 return BAI;
873}
874
875void LowerTypeTestsModule::allocateByteArrays() {
876 llvm::stable_sort(ByteArrayInfos,
877 [](const ByteArrayInfo &BAI1, const ByteArrayInfo &BAI2) {
878 return BAI1.BitSize > BAI2.BitSize;
879 });
880
881 std::vector<uint64_t> ByteArrayOffsets(ByteArrayInfos.size());
882
884 for (unsigned I = 0; I != ByteArrayInfos.size(); ++I) {
885 ByteArrayInfo *BAI = &ByteArrayInfos[I];
886
887 uint8_t Mask;
888 BAB.allocate(BAI->Bits, BAI->BitSize, ByteArrayOffsets[I], Mask);
889
890 BAI->MaskGlobal->replaceAllUsesWith(
891 ConstantExpr::getIntToPtr(ConstantInt::get(Int8Ty, Mask), PtrTy));
892 BAI->MaskGlobal->eraseFromParent();
893 if (BAI->MaskPtr)
894 *BAI->MaskPtr = Mask;
895 }
896
897 Constant *ByteArrayConst = ConstantDataArray::get(M.getContext(), BAB.Bytes);
898 auto ByteArray =
899 new GlobalVariable(M, ByteArrayConst->getType(), /*isConstant=*/true,
900 GlobalValue::PrivateLinkage, ByteArrayConst);
901
902 for (unsigned I = 0; I != ByteArrayInfos.size(); ++I) {
903 ByteArrayInfo *BAI = &ByteArrayInfos[I];
905 ByteArray, ConstantInt::get(IntPtrTy, ByteArrayOffsets[I]));
906
907 // Create an alias instead of RAUW'ing the gep directly. On x86 this ensures
908 // that the pc-relative displacement is folded into the lea instead of the
909 // test instruction getting another displacement.
910 GlobalAlias *Alias = GlobalAlias::create(
911 Int8Ty, 0, GlobalValue::PrivateLinkage, "bits", GEP, &M);
912 BAI->ByteArray->replaceAllUsesWith(Alias);
913 BAI->ByteArray->eraseFromParent();
914 }
915
916 ByteArraySizeBits = BAB.BitAllocs[0] + BAB.BitAllocs[1] + BAB.BitAllocs[2] +
917 BAB.BitAllocs[3] + BAB.BitAllocs[4] + BAB.BitAllocs[5] +
918 BAB.BitAllocs[6] + BAB.BitAllocs[7];
919 ByteArraySizeBytes = BAB.Bytes.size();
920}
921
922/// Build a test that bit BitOffset is set in the type identifier that was
923/// lowered to TIL, which must be either an Inline or a ByteArray.
924Value *LowerTypeTestsModule::createBitSetTest(IRBuilder<> &B,
925 const TypeIdLowering &TIL,
926 Value *BitOffset) {
927 if (TIL.TheKind == TypeTestResolution::Inline) {
928 // If the bit set is sufficiently small, we can avoid a load by bit testing
929 // a constant.
930 return createMaskedBitTest(B, TIL.InlineBits, BitOffset);
931 } else {
932 Constant *ByteArray = TIL.TheByteArray;
933 if (Opts.lowertypetests_avoid_reuse && !ImportSummary) {
934 // Each use of the byte array uses a different alias. This makes the
935 // backend less likely to reuse previously computed byte array addresses,
936 // improving the security of the CFI mechanism based on this pass.
937 // This won't work when importing because TheByteArray is external.
939 "bits_use", ByteArray, &M);
940 }
941
942 Value *ByteAddr = B.CreateGEP(Int8Ty, ByteArray, BitOffset);
943 Value *Byte = B.CreateLoad(Int8Ty, ByteAddr);
944
945 Value *ByteAndMask =
946 B.CreateAnd(Byte, ConstantExpr::getPtrToInt(TIL.BitMask, Int8Ty));
947 return B.CreateICmpNE(ByteAndMask, ConstantInt::get(Int8Ty, 0));
948 }
949}
950
951static bool isKnownTypeIdMember(Metadata *TypeId, const DataLayout &DL,
952 Value *V, uint64_t COffset) {
953 if (auto GV = dyn_cast<GlobalObject>(V)) {
955 GV->getMetadata(LLVMContext::MD_type, Types);
956 for (MDNode *Type : Types) {
957 if (Type->getOperand(1) != TypeId)
958 continue;
961 cast<ConstantAsMetadata>(Type->getOperand(0))->getValue())
962 ->getZExtValue();
963 if (COffset == Offset)
964 return true;
965 }
966 return false;
967 }
968
969 if (auto GEP = dyn_cast<GEPOperator>(V)) {
970 APInt APOffset(DL.getIndexSizeInBits(0), 0);
971 bool Result = GEP->accumulateConstantOffset(DL, APOffset);
972 if (!Result)
973 return false;
974 COffset += APOffset.getZExtValue();
975 return isKnownTypeIdMember(TypeId, DL, GEP->getPointerOperand(), COffset);
976 }
977
978 if (auto Op = dyn_cast<Operator>(V)) {
979 if (Op->getOpcode() == Instruction::BitCast)
980 return isKnownTypeIdMember(TypeId, DL, Op->getOperand(0), COffset);
981
982 if (Op->getOpcode() == Instruction::Select)
983 return isKnownTypeIdMember(TypeId, DL, Op->getOperand(1), COffset) &&
984 isKnownTypeIdMember(TypeId, DL, Op->getOperand(2), COffset);
985 }
986
987 return false;
988}
989
990/// Lower a llvm.type.test call to its implementation. Returns the value to
991/// replace the call with.
992Value *LowerTypeTestsModule::lowerTypeTestCall(Metadata *TypeId, CallInst *CI,
993 const TypeIdLowering &TIL) {
994 // Delay lowering if the resolution is currently unknown.
995 if (TIL.TheKind == TypeTestResolution::Unknown)
996 return nullptr;
997 if (TIL.TheKind == TypeTestResolution::Unsat)
998 return ConstantInt::getFalse(M.getContext());
999
1000 Value *Ptr = CI->getArgOperand(0);
1001 const DataLayout &DL = M.getDataLayout();
1002 if (isKnownTypeIdMember(TypeId, DL, Ptr, 0))
1003 return ConstantInt::getTrue(M.getContext());
1004
1005 BasicBlock *InitialBB = CI->getParent();
1006
1007 IRBuilder<> B(CI);
1008
1009 Value *PtrAsInt = B.CreatePtrToInt(Ptr, IntPtrTy);
1010
1011 Constant *OffsetedGlobalAsInt =
1012 ConstantExpr::getPtrToInt(TIL.OffsetedGlobal, IntPtrTy);
1013 if (TIL.TheKind == TypeTestResolution::Single)
1014 return B.CreateICmpEQ(PtrAsInt, OffsetedGlobalAsInt);
1015
1016 // Here we compute `last element - address`. The reason why we do this instead
1017 // of computing `address - first element` is that it leads to a slightly
1018 // shorter instruction sequence on x86. Because it doesn't matter how we do
1019 // the subtraction on other architectures, we do so unconditionally.
1020 Value *PtrOffset = B.CreateSub(OffsetedGlobalAsInt, PtrAsInt);
1021
1022 // We need to check that the offset both falls within our range and is
1023 // suitably aligned. We can check both properties at the same time by
1024 // performing a right rotate by log2(alignment) followed by an integer
1025 // comparison against the bitset size. The rotate will move the lower
1026 // order bits that need to be zero into the higher order bits of the
1027 // result, causing the comparison to fail if they are nonzero. The rotate
1028 // also conveniently gives us a bit offset to use during the load from
1029 // the bitset.
1030 Value *BitOffset = B.CreateIntrinsic(IntPtrTy, Intrinsic::fshr,
1031 {PtrOffset, PtrOffset, TIL.AlignLog2});
1032
1033 Value *OffsetInRange = B.CreateICmpULE(BitOffset, TIL.SizeM1);
1034
1035 // If the bit set is all ones, testing against it is unnecessary.
1036 if (TIL.TheKind == TypeTestResolution::AllOnes)
1037 return OffsetInRange;
1038
1039 // See if the intrinsic is used in the following common pattern:
1040 // br(llvm.type.test(...), thenbb, elsebb)
1041 // where nothing happens between the type test and the br.
1042 // If so, create slightly simpler IR.
1043 if (CI->hasOneUse())
1044 if (auto *Br = dyn_cast<CondBrInst>(*CI->user_begin()))
1045 if (CI->getNextNode() == Br) {
1046 BasicBlock *Then = InitialBB->splitBasicBlock(CI->getIterator());
1047 BasicBlock *Else = Br->getSuccessor(1);
1048 CondBrInst *NewBr = CondBrInst::Create(OffsetInRange, Then, Else);
1049 NewBr->setMetadata(LLVMContext::MD_prof,
1050 Br->getMetadata(LLVMContext::MD_prof));
1051 ReplaceInstWithInst(InitialBB->getTerminator(), NewBr);
1052
1053 // Update phis in Else resulting from InitialBB being split
1054 for (auto &Phi : Else->phis())
1055 Phi.addIncoming(Phi.getIncomingValueForBlock(Then), InitialBB);
1056
1057 IRBuilder<> ThenB(CI);
1058 return createBitSetTest(ThenB, TIL, BitOffset);
1059 }
1060
1061 MDBuilder MDB(M.getContext());
1062 IRBuilder<> ThenB(SplitBlockAndInsertIfThen(OffsetInRange, CI, false,
1063 MDB.createLikelyBranchWeights()));
1064
1065 // Now that we know that the offset is in range and aligned, load the
1066 // appropriate bit from the bitset.
1067 Value *Bit = createBitSetTest(ThenB, TIL, BitOffset);
1068
1069 // The value we want is 0 if we came directly from the initial block
1070 // (having failed the range or alignment checks), or the loaded bit if
1071 // we came from the block in which we loaded it.
1072 B.SetInsertPoint(CI);
1073 PHINode *P = B.CreatePHI(Int1Ty, 2);
1074 P->addIncoming(ConstantInt::get(Int1Ty, 0), InitialBB);
1075 P->addIncoming(Bit, ThenB.GetInsertBlock());
1076 return P;
1077}
1078
1079/// Given a disjoint set of type identifiers and globals, lay out the globals,
1080/// build the bit sets and lower the llvm.type.test calls.
1081void LowerTypeTestsModule::buildBitSetsFromGlobalVariables(
1083 // Build a new global with the combined contents of the referenced globals.
1084 // This global is a struct whose even-indexed elements contain the original
1085 // contents of the referenced globals and whose odd-indexed elements contain
1086 // any padding required to align the next element to the next power of 2 plus
1087 // any additional padding required to meet its alignment requirements.
1088 std::vector<Constant *> GlobalInits;
1089 const DataLayout &DL = M.getDataLayout();
1090 DenseMap<GlobalTypeMember *, uint64_t> GlobalLayout;
1091 Align MaxAlign;
1092 uint64_t CurOffset = 0;
1093 uint64_t DesiredPadding = 0;
1094 for (GlobalTypeMember *G : Globals) {
1095 auto *GV = cast<GlobalVariable>(G->getGlobal());
1097 DL.getValueOrABITypeAlignment(GV->getAlign(), GV->getValueType());
1098 MaxAlign = std::max(MaxAlign, Alignment);
1099 uint64_t GVOffset = alignTo(CurOffset + DesiredPadding, Alignment);
1100 GlobalLayout[G] = GVOffset;
1101 if (GVOffset != 0) {
1102 uint64_t Padding = GVOffset - CurOffset;
1103 GlobalInits.push_back(
1104 ConstantAggregateZero::get(ArrayType::get(Int8Ty, Padding)));
1105 }
1106
1107 GlobalInits.push_back(GV->getInitializer());
1108 uint64_t InitSize = GV->getGlobalSize(DL);
1109 CurOffset = GVOffset + InitSize;
1110
1111 // Compute the amount of padding that we'd like for the next element.
1112 DesiredPadding = NextPowerOf2(InitSize - 1) - InitSize;
1113
1114 // Experiments of different caps with Chromium on both x64 and ARM64
1115 // have shown that the 32-byte cap generates the smallest binary on
1116 // both platforms while different caps yield similar performance.
1117 // (see https://lists.llvm.org/pipermail/llvm-dev/2018-July/124694.html)
1118 if (DesiredPadding > 32)
1119 DesiredPadding = alignTo(InitSize, 32) - InitSize;
1120 }
1121
1122 Constant *NewInit = ConstantStruct::getAnon(M.getContext(), GlobalInits);
1123 auto *CombinedGlobal =
1124 new GlobalVariable(M, NewInit->getType(), /*isConstant=*/true,
1126 CombinedGlobal->setAlignment(MaxAlign);
1127
1128 StructType *NewTy = cast<StructType>(NewInit->getType());
1129 lowerTypeTestCalls(TypeIds, CombinedGlobal, GlobalLayout);
1130
1131 // Build aliases pointing to offsets into the combined global for each
1132 // global from which we built the combined global, and replace references
1133 // to the original globals with references to the aliases.
1134 for (unsigned I = 0; I != Globals.size(); ++I) {
1135 GlobalVariable *GV = cast<GlobalVariable>(Globals[I]->getGlobal());
1136
1137 // Multiply by 2 to account for padding elements.
1138 Constant *CombinedGlobalIdxs[] = {ConstantInt::get(Int32Ty, 0),
1139 ConstantInt::get(Int32Ty, I * 2)};
1140 Constant *CombinedGlobalElemPtr = ConstantExpr::getGetElementPtr(
1141 DL, NewInit->getType(), CombinedGlobal, CombinedGlobalIdxs,
1143 assert(GV->getType()->getAddressSpace() == 0);
1144 GlobalAlias *GAlias =
1145 GlobalAlias::create(NewTy->getElementType(I * 2), 0, GV->getLinkage(),
1146 "", CombinedGlobalElemPtr, &M);
1147 GAlias->setVisibility(GV->getVisibility());
1148 GAlias->takeName(GV);
1149 GV->replaceAllUsesWith(GAlias);
1150 GV->eraseFromParent();
1151 }
1152}
1153
1154bool LowerTypeTestsModule::shouldExportConstantsAsAbsoluteSymbols() {
1155 return (Arch == Triple::x86 || Arch == Triple::x86_64) &&
1156 ObjectFormat == Triple::ELF;
1157}
1158
1159/// Export the given type identifier so that ThinLTO backends may import it.
1160/// Type identifiers are exported by adding coarse-grained information about how
1161/// to test the type identifier to the summary, and creating symbols in the
1162/// object file (aliases and absolute symbols) containing fine-grained
1163/// information about the type identifier.
1164///
1165/// Returns a pointer to the location in which to store the bitmask, if
1166/// applicable.
1167uint8_t *LowerTypeTestsModule::exportTypeId(StringRef TypeId,
1168 const TypeIdLowering &TIL) {
1169 TypeTestResolution &TTRes =
1170 ExportSummary->getOrInsertTypeIdSummary(TypeId).TTRes;
1171 TTRes.TheKind = TIL.TheKind;
1172
1173 auto ExportGlobal = [&](StringRef Name, Constant *C) {
1174 GlobalAlias *GA =
1176 "__typeid_" + TypeId + "_" + Name, C, &M);
1178 };
1179
1180 auto ExportConstant = [&](StringRef Name, uint64_t &Storage, Constant *C) {
1181 if (shouldExportConstantsAsAbsoluteSymbols())
1182 ExportGlobal(Name, ConstantExpr::getIntToPtr(C, PtrTy));
1183 else
1184 Storage = cast<ConstantInt>(C)->getZExtValue();
1185 };
1186
1187 if (TIL.TheKind != TypeTestResolution::Unsat)
1188 ExportGlobal("global_addr", TIL.OffsetedGlobal);
1189
1190 if (TIL.TheKind == TypeTestResolution::ByteArray ||
1191 TIL.TheKind == TypeTestResolution::Inline ||
1192 TIL.TheKind == TypeTestResolution::AllOnes) {
1193 ExportConstant("align", TTRes.AlignLog2, TIL.AlignLog2);
1194 ExportConstant("size_m1", TTRes.SizeM1, TIL.SizeM1);
1195
1196 uint64_t BitSize = cast<ConstantInt>(TIL.SizeM1)->getZExtValue() + 1;
1197 if (TIL.TheKind == TypeTestResolution::Inline)
1198 TTRes.SizeM1BitWidth = (BitSize <= 32) ? 5 : 6;
1199 else
1200 TTRes.SizeM1BitWidth = (BitSize <= 128) ? 7 : 32;
1201 }
1202
1203 if (TIL.TheKind == TypeTestResolution::ByteArray) {
1204 ExportGlobal("byte_array", TIL.TheByteArray);
1205 if (shouldExportConstantsAsAbsoluteSymbols())
1206 ExportGlobal("bit_mask", TIL.BitMask);
1207 else
1208 return &TTRes.BitMask;
1209 }
1210
1211 if (TIL.TheKind == TypeTestResolution::Inline)
1212 ExportConstant("inline_bits", TTRes.InlineBits, TIL.InlineBits);
1213
1214 return nullptr;
1215}
1216
1217LowerTypeTestsModule::TypeIdLowering
1218LowerTypeTestsModule::importTypeId(StringRef TypeId) {
1219 const TypeIdSummary *TidSummary = ImportSummary->getTypeIdSummary(TypeId);
1220 if (!TidSummary)
1221 return {}; // Unsat: no globals match this type id.
1222 const TypeTestResolution &TTRes = TidSummary->TTRes;
1223
1224 TypeIdLowering TIL;
1225 TIL.TheKind = TTRes.TheKind;
1226
1227 auto ImportGlobal = [&](StringRef Name) {
1228 // Give the global a type of length 0 so that it is not assumed not to alias
1229 // with any other global.
1230 GlobalVariable *GV = M.getOrInsertGlobal(
1231 ("__typeid_" + TypeId + "_" + Name).str(), Int8Arr0Ty);
1233 return GV;
1234 };
1235
1236 auto ImportConstant = [&](StringRef Name, uint64_t Const, unsigned AbsWidth,
1237 Type *Ty) {
1238 if (!shouldExportConstantsAsAbsoluteSymbols()) {
1239 Constant *C =
1240 ConstantInt::get(isa<IntegerType>(Ty) ? Ty : Int64Ty, Const);
1241 if (!isa<IntegerType>(Ty))
1243 return C;
1244 }
1245
1246 Constant *C = ImportGlobal(Name);
1247 auto *GV = cast<GlobalVariable>(C->stripPointerCasts());
1248 if (isa<IntegerType>(Ty))
1250 if (GV->getMetadata(LLVMContext::MD_absolute_symbol))
1251 return C;
1252
1253 auto SetAbsRange = [&](uint64_t Min, uint64_t Max) {
1254 auto *MinC = ConstantAsMetadata::get(ConstantInt::get(IntPtrTy, Min));
1255 auto *MaxC = ConstantAsMetadata::get(ConstantInt::get(IntPtrTy, Max));
1256 GV->setMetadata(LLVMContext::MD_absolute_symbol,
1257 MDNode::get(M.getContext(), {MinC, MaxC}));
1258 };
1259 if (AbsWidth == IntPtrTy->getBitWidth()) {
1260 uint64_t AllOnes = IntPtrTy->getBitMask();
1261 SetAbsRange(AllOnes, AllOnes); // Full set.
1262 } else {
1263 SetAbsRange(0, 1ull << AbsWidth);
1264 }
1265 return C;
1266 };
1267
1268 if (TIL.TheKind != TypeTestResolution::Unsat) {
1269 auto *GV = ImportGlobal("global_addr");
1270 // This is either a vtable (in .data.rel.ro) or a jump table (in .text).
1271 // Either way it's expected to be in the low 2 GiB, so set the small code
1272 // model.
1273 //
1274 // For .data.rel.ro, we currently place all such sections in the low 2 GiB
1275 // [1], and for .text the sections are expected to be in the low 2 GiB under
1276 // the small and medium code models [2] and this pass only supports those
1277 // code models (e.g. jump tables use jmp instead of movabs/jmp).
1278 //
1279 // [1]https://github.com/llvm/llvm-project/pull/137742
1280 // [2]https://maskray.me/blog/2023-05-14-relocation-overflow-and-code-models
1282 TIL.OffsetedGlobal = GV;
1283 }
1284
1285 if (TIL.TheKind == TypeTestResolution::ByteArray ||
1286 TIL.TheKind == TypeTestResolution::Inline ||
1287 TIL.TheKind == TypeTestResolution::AllOnes) {
1288 TIL.AlignLog2 = ImportConstant("align", TTRes.AlignLog2, 8, IntPtrTy);
1289 TIL.SizeM1 =
1290 ImportConstant("size_m1", TTRes.SizeM1, TTRes.SizeM1BitWidth, IntPtrTy);
1291 }
1292
1293 if (TIL.TheKind == TypeTestResolution::ByteArray) {
1294 TIL.TheByteArray = ImportGlobal("byte_array");
1295 TIL.BitMask = ImportConstant("bit_mask", TTRes.BitMask, 8, PtrTy);
1296 }
1297
1298 if (TIL.TheKind == TypeTestResolution::Inline)
1299 TIL.InlineBits = ImportConstant(
1300 "inline_bits", TTRes.InlineBits, 1 << TTRes.SizeM1BitWidth,
1301 TTRes.SizeM1BitWidth <= 5 ? Int32Ty : Int64Ty);
1302
1303 return TIL;
1304}
1305
1306void LowerTypeTestsModule::importTypeTest(CallInst *CI) {
1307 auto TypeIdMDVal = dyn_cast<MetadataAsValue>(CI->getArgOperand(1));
1308 if (!TypeIdMDVal)
1309 report_fatal_error("Second argument of llvm.type.test must be metadata");
1310
1311 auto TypeIdStr = dyn_cast<MDString>(TypeIdMDVal->getMetadata());
1312 // If this is a local unpromoted type, which doesn't have a metadata string,
1313 // treat as Unknown and delay lowering, so that we can still utilize it for
1314 // later optimizations.
1315 if (!TypeIdStr)
1316 return;
1317
1318 TypeIdLowering TIL = importTypeId(TypeIdStr->getString());
1319 Value *Lowered = lowerTypeTestCall(TypeIdStr, CI, TIL);
1320 if (Lowered) {
1321 CI->replaceAllUsesWith(Lowered);
1322 CI->eraseFromParent();
1323 }
1324}
1325
1326void LowerTypeTestsModule::maybeReplaceComdat(Function *F,
1327 StringRef OriginalName) {
1328 // For COFF we should also rename the comdat if this function also
1329 // happens to be the key function. Even if the comdat name changes, this
1330 // should still be fine since comdat and symbol resolution happens
1331 // before LTO, so all symbols which would prevail have been selected.
1332 if (F->hasComdat() && ObjectFormat == Triple::COFF &&
1333 F->getComdat()->getName() == OriginalName) {
1334 Comdat *OldComdat = F->getComdat();
1335 Comdat *NewComdat = M.getOrInsertComdat(F->getName());
1336 for (GlobalObject &GO : M.global_objects()) {
1337 if (GO.getComdat() == OldComdat)
1338 GO.setComdat(NewComdat);
1339 }
1340 }
1341}
1342
1343// ThinLTO backend: the function F has a jump table entry; update this module
1344// accordingly. isJumpTableCanonical describes the type of the jump table entry.
1345void LowerTypeTestsModule::importFunction(Function *F,
1346 bool isJumpTableCanonical) {
1347 assert(F->getType()->getAddressSpace() == 0);
1348
1349 GlobalValue::VisibilityTypes Visibility = F->getVisibility();
1350 std::string Name = std::string(F->getName());
1351
1352 if (F->isDeclarationForLinker() && isJumpTableCanonical) {
1353 // Non-dso_local functions may be overriden at run time,
1354 // don't short curcuit them
1355 if (!F->isDSOLocal())
1356 return;
1357 if (F->isDeclaration()) {
1358 // Direct calls do not need the type check, so let them skip the jump
1359 // table and call the real function directly.
1360 Function *RealF = Function::Create(F->getFunctionType(),
1362 F->getAddressSpace(),
1363 Name + ".cfi", &M);
1365 replaceDirectCalls(F, RealF);
1366 return;
1367 }
1368 // Otherwise F is an available_externally definition imported from
1369 // another module. Handle it like a local definition below: the body is
1370 // renamed to Name.cfi and stays the target of direct calls, so it remains
1371 // inlinable, while address-taken uses are redirected to the jump table
1372 // entry. If the body is not inlined and is dropped later, the reference
1373 // to Name.cfi resolves to the real function at link time, exactly as for
1374 // a declaration.
1375 }
1376
1377 Function *FDecl;
1378 if (!isJumpTableCanonical) {
1379 // Either a declaration of an external function or a reference to a locally
1380 // defined jump table.
1381 FDecl = Function::Create(F->getFunctionType(), GlobalValue::ExternalLinkage,
1382 F->getAddressSpace(), Name + ".cfi_jt", &M);
1384 } else {
1385 F->setName(Name + ".cfi");
1386 maybeReplaceComdat(F, Name);
1387 FDecl = Function::Create(F->getFunctionType(), GlobalValue::ExternalLinkage,
1388 F->getAddressSpace(), Name, &M);
1389 FDecl->setVisibility(Visibility);
1390 FDecl->setDSOLocal(F->isDSOLocal());
1391 Visibility = GlobalValue::HiddenVisibility;
1392
1393 // Update aliases pointing to this function to also include the ".cfi" suffix,
1394 // We expect the jump table entry to either point to the real function or an
1395 // alias. Redirect all other users to the jump table entry.
1396 for (auto &U : F->uses()) {
1397 if (auto *A = dyn_cast<GlobalAlias>(U.getUser())) {
1398 std::string AliasName = A->getName().str() + ".cfi";
1399 Function *AliasDecl = Function::Create(
1400 F->getFunctionType(), GlobalValue::ExternalLinkage,
1401 F->getAddressSpace(), "", &M);
1402 AliasDecl->takeName(A);
1403 A->replaceAllUsesWith(AliasDecl);
1404 A->setName(AliasName);
1405 AliasDecl->setDSOLocal(A->isDSOLocal());
1406 }
1407 }
1408 }
1409
1410 if (F->hasExternalWeakLinkage())
1411 replaceWeakDeclarationWithJumpTablePtr(F, FDecl, isJumpTableCanonical);
1412 else
1413 replaceCfiUses(F, FDecl, isJumpTableCanonical);
1414
1415 // Set visibility late because it's used in replaceCfiUses() to determine
1416 // whether uses need to be replaced.
1417 F->setVisibility(Visibility);
1418}
1419
1420static auto
1422 const DenseMap<GlobalTypeMember *, uint64_t> &GlobalLayout) {
1424 // Pre-populate the map with interesting type identifiers.
1425 for (Metadata *TypeId : TypeIds)
1426 OffsetsByTypeID[TypeId];
1427 for (const auto &[Mem, MemOff] : GlobalLayout) {
1428 for (MDNode *Type : Mem->types()) {
1429 auto It = OffsetsByTypeID.find(Type->getOperand(1));
1430 if (It == OffsetsByTypeID.end())
1431 continue;
1434 cast<ConstantAsMetadata>(Type->getOperand(0))->getValue())
1435 ->getZExtValue();
1436 It->second.push_back(MemOff + Offset);
1437 }
1438 }
1439
1441 BitSets.reserve(TypeIds.size());
1442 for (Metadata *TypeId : TypeIds) {
1443 BitSets.emplace_back(TypeId, buildBitSet(OffsetsByTypeID[TypeId]));
1444 LLVM_DEBUG({
1445 if (auto MDS = dyn_cast<MDString>(TypeId))
1446 dbgs() << MDS->getString() << ": ";
1447 else
1448 dbgs() << "<unnamed>: ";
1449 BitSets.back().second.print(dbgs());
1450 });
1451 }
1452
1453 return BitSets;
1454}
1455
1456void LowerTypeTestsModule::lowerTypeTestCalls(
1457 ArrayRef<Metadata *> TypeIds, Constant *CombinedGlobalAddr,
1458 const DenseMap<GlobalTypeMember *, uint64_t> &GlobalLayout) {
1459 // For each type identifier in this disjoint set...
1460 for (const auto &[TypeId, BSI] : buildBitSets(TypeIds, GlobalLayout)) {
1461 ByteArrayInfo *BAI = nullptr;
1462 TypeIdLowering TIL;
1463
1464 uint64_t GlobalOffset =
1465 BSI.ByteOffset + ((BSI.BitSize - 1) << BSI.AlignLog2);
1466 TIL.OffsetedGlobal = ConstantExpr::getPtrAdd(
1467 CombinedGlobalAddr, ConstantInt::get(IntPtrTy, GlobalOffset)),
1468 TIL.AlignLog2 = ConstantInt::get(IntPtrTy, BSI.AlignLog2);
1469 TIL.SizeM1 = ConstantInt::get(IntPtrTy, BSI.BitSize - 1);
1470 if (BSI.isAllOnes()) {
1471 TIL.TheKind = (BSI.BitSize == 1) ? TypeTestResolution::Single
1472 : TypeTestResolution::AllOnes;
1473 } else if (BSI.BitSize <= IntPtrTy->getBitWidth()) {
1474 TIL.TheKind = TypeTestResolution::Inline;
1475 uint64_t InlineBits = 0;
1476 for (auto Bit : BSI.Bits)
1477 InlineBits |= uint64_t(1) << Bit;
1478 if (InlineBits == 0)
1479 TIL.TheKind = TypeTestResolution::Unsat;
1480 else
1481 TIL.InlineBits = ConstantInt::get(
1482 (BSI.BitSize <= 32) ? Int32Ty : Int64Ty, InlineBits);
1483 } else {
1484 TIL.TheKind = TypeTestResolution::ByteArray;
1485 ++NumByteArraysCreated;
1486 BAI = createByteArray(BSI);
1487 TIL.TheByteArray = BAI->ByteArray;
1488 TIL.BitMask = BAI->MaskGlobal;
1489 }
1490
1491 TypeIdUserInfo &TIUI = TypeIdUsers[TypeId];
1492
1493 if (TIUI.IsExported) {
1494 uint8_t *MaskPtr = exportTypeId(cast<MDString>(TypeId)->getString(), TIL);
1495 if (BAI)
1496 BAI->MaskPtr = MaskPtr;
1497 }
1498
1499 // Lower each call to llvm.type.test for this type identifier.
1500 for (CallInst *CI : TIUI.CallSites) {
1501 ++NumTypeTestCallsLowered;
1502 Value *Lowered = lowerTypeTestCall(TypeId, CI, TIL);
1503 if (Lowered) {
1504 CI->replaceAllUsesWith(Lowered);
1505 CI->eraseFromParent();
1506 }
1507 }
1508 }
1509}
1510
1511void LowerTypeTestsModule::verifyTypeMDNode(GlobalObject *GO, MDNode *Type) {
1512 if (Type->getNumOperands() != 2)
1513 report_fatal_error("All operands of type metadata must have 2 elements");
1514
1515 if (GO->isThreadLocal())
1516 report_fatal_error("Bit set element may not be thread-local");
1517 if (isa<GlobalVariable>(GO) && GO->hasSection())
1519 "A member of a type identifier may not have an explicit section");
1520
1521 // FIXME: We previously checked that global var member of a type identifier
1522 // must be a definition, but the IR linker may leave type metadata on
1523 // declarations. We should restore this check after fixing PR31759.
1524
1525 auto OffsetConstMD = dyn_cast<ConstantAsMetadata>(Type->getOperand(0));
1526 if (!OffsetConstMD)
1527 report_fatal_error("Type offset must be a constant");
1528 auto OffsetInt = dyn_cast<ConstantInt>(OffsetConstMD->getValue());
1529 if (!OffsetInt)
1530 report_fatal_error("Type offset must be an integer constant");
1531}
1532
1533static const unsigned kX86JumpTableEntrySize = 8;
1534static const unsigned kX86IBTJumpTableEntrySize = 16;
1535static const unsigned kARMJumpTableEntrySize = 4;
1536static const unsigned kARMBTIJumpTableEntrySize = 8;
1537static const unsigned kARMv6MJumpTableEntrySize = 16;
1538static const unsigned kRISCVJumpTableEntrySize = 8;
1539static const unsigned kLOONGARCH64JumpTableEntrySize = 8;
1540static const unsigned kHexagonJumpTableEntrySize = 4;
1541
1542bool LowerTypeTestsModule::hasBranchTargetEnforcement() {
1543 if (HasBranchTargetEnforcement == -1) {
1544 // First time this query has been called. Find out the answer by checking
1545 // the module flags.
1546 if (const auto *BTE = mdconst::extract_or_null<ConstantInt>(
1547 M.getModuleFlag("branch-target-enforcement")))
1548 HasBranchTargetEnforcement = !BTE->isZero();
1549 else
1550 HasBranchTargetEnforcement = 0;
1551 }
1552 return HasBranchTargetEnforcement;
1553}
1554
1555unsigned
1556LowerTypeTestsModule::getJumpTableEntrySize(Triple::ArchType JumpTableArch) {
1557 switch (JumpTableArch) {
1558 case Triple::x86:
1559 case Triple::x86_64:
1560 if (const auto *MD = mdconst::extract_or_null<ConstantInt>(
1561 M.getModuleFlag("cf-protection-branch")))
1562 if (MD->getZExtValue())
1565 case Triple::arm:
1567 case Triple::thumb:
1568 if (CanUseThumbBWJumpTable) {
1569 if (hasBranchTargetEnforcement())
1572 } else {
1574 }
1575 case Triple::aarch64:
1576 if (hasBranchTargetEnforcement())
1579 case Triple::riscv32:
1580 case Triple::riscv64:
1584 case Triple::hexagon:
1586 default:
1587 report_fatal_error("Unsupported architecture for jump tables");
1588 }
1589}
1590
1591// Create an inline asm constant representing a jump table entry for the target.
1592// This consists of an instruction sequence containing a relative branch to
1593// Dest.
1594InlineAsm *
1595LowerTypeTestsModule::createJumpTableEntryAsm(Triple::ArchType JumpTableArch) {
1596 std::string Asm;
1597 raw_string_ostream AsmOS(Asm);
1598
1599 if (JumpTableArch == Triple::x86 || JumpTableArch == Triple::x86_64) {
1600 bool Endbr = false;
1601 if (const auto *MD = mdconst::extract_or_null<ConstantInt>(
1602 M.getModuleFlag("cf-protection-branch")))
1603 Endbr = !MD->isZero();
1604 if (Endbr)
1605 AsmOS << (JumpTableArch == Triple::x86 ? "endbr32\n" : "endbr64\n");
1606 AsmOS << "jmp ${0:c}@plt\n";
1607 if (Endbr)
1608 AsmOS << ".balign 16, 0xcc\n";
1609 else
1610 AsmOS << "int3\nint3\nint3\n";
1611 } else if (JumpTableArch == Triple::arm) {
1612 AsmOS << "b $0\n";
1613 } else if (JumpTableArch == Triple::aarch64) {
1614 if (hasBranchTargetEnforcement())
1615 AsmOS << "bti c\n";
1616 AsmOS << "b $0\n";
1617 } else if (JumpTableArch == Triple::thumb) {
1618 if (!CanUseThumbBWJumpTable) {
1619 // In Armv6-M, this sequence will generate a branch without corrupting
1620 // any registers. We use two stack words; in the second, we construct the
1621 // address we'll pop into pc, and the first is used to save and restore
1622 // r0 which we use as a temporary register.
1623 //
1624 // To support position-independent use cases, the offset of the target
1625 // function is stored as a relative offset (which will expand into an
1626 // R_ARM_REL32 relocation in ELF, and presumably the equivalent in other
1627 // object file types), and added to pc after we load it. (The alternative
1628 // B.W is automatically pc-relative.)
1629 //
1630 // There are five 16-bit Thumb instructions here, so the .balign 4 adds a
1631 // sixth halfword of padding, and then the offset consumes a further 4
1632 // bytes, for a total of 16, which is very convenient since entries in
1633 // this jump table need to have power-of-two size.
1634 AsmOS << "push {r0,r1}\n"
1635 << "ldr r0, 1f\n"
1636 << "0: add r0, r0, pc\n"
1637 << "str r0, [sp, #4]\n"
1638 << "pop {r0,pc}\n"
1639 << ".balign 4\n"
1640 << "1: .word $0 - (0b + 4)\n";
1641 } else {
1642 if (hasBranchTargetEnforcement())
1643 AsmOS << "bti\n";
1644 AsmOS << "b.w $0\n";
1645 }
1646 } else if (JumpTableArch == Triple::riscv32 ||
1647 JumpTableArch == Triple::riscv64) {
1648 AsmOS << "tail $0@plt\n";
1649 } else if (JumpTableArch == Triple::loongarch64) {
1650 AsmOS << "pcalau12i $$t0, %pc_hi20($0)\n"
1651 << "jirl $$r0, $$t0, %pc_lo12($0)\n";
1652 } else if (JumpTableArch == Triple::hexagon) {
1653 AsmOS << "jump $0\n";
1654 } else {
1655 report_fatal_error("Unsupported architecture for jump tables");
1656 }
1657
1658 return InlineAsm::get(
1659 FunctionType::get(Type::getVoidTy(M.getContext()), PtrTy, false),
1660 AsmOS.str(), "s",
1661 /*hasSideEffects=*/true);
1662}
1663
1664/// Given a disjoint set of type identifiers and functions, build the bit sets
1665/// and lower the llvm.type.test calls, architecture dependently.
1666void LowerTypeTestsModule::buildBitSetsFromFunctions(
1668 if (Arch == Triple::x86 || Arch == Triple::x86_64 || Arch == Triple::arm ||
1669 Arch == Triple::thumb || Arch == Triple::aarch64 ||
1670 Arch == Triple::riscv32 || Arch == Triple::riscv64 ||
1671 Arch == Triple::loongarch64 || Arch == Triple::hexagon)
1672 buildBitSetsFromFunctionsNative(TypeIds, Functions);
1673 else if (Arch == Triple::wasm32 || Arch == Triple::wasm64)
1674 buildBitSetsFromFunctionsWASM(TypeIds, Functions);
1675 else
1676 report_fatal_error("Unsupported architecture for jump tables");
1677}
1678
1679void LowerTypeTestsModule::moveInitializerToModuleConstructor(
1680 GlobalVariable *GV) {
1681 if (WeakInitializerFn == nullptr) {
1682 WeakInitializerFn = Function::Create(
1683 FunctionType::get(Type::getVoidTy(M.getContext()),
1684 /* IsVarArg */ false),
1686 M.getDataLayout().getProgramAddressSpace(),
1687 "__cfi_global_var_init", &M);
1688 BasicBlock *BB =
1689 BasicBlock::Create(M.getContext(), "entry", WeakInitializerFn);
1690 ReturnInst::Create(M.getContext(), BB);
1691 WeakInitializerFn->setSection(
1692 ObjectFormat == Triple::MachO
1693 ? "__TEXT,__StaticInit,regular,pure_instructions"
1694 : ".text.startup");
1695 // This code is equivalent to relocation application, and should run at the
1696 // earliest possible time (i.e. with the highest priority).
1697 appendToGlobalCtors(M, WeakInitializerFn, /* Priority */ 0);
1698 }
1699
1700 IRBuilder<> IRB(WeakInitializerFn->getEntryBlock().getTerminator());
1701 GV->setConstant(false);
1702 IRB.CreateAlignedStore(GV->getInitializer(), GV, GV->getAlign());
1704}
1705
1706void LowerTypeTestsModule::findGlobalVariableUsersOf(
1707 Constant *C, SmallSetVector<GlobalVariable *, 8> &Out) {
1708 for (auto *U : C->users()){
1709 if (auto *GV = dyn_cast<GlobalVariable>(U))
1710 Out.insert(GV);
1711 else if (auto *C2 = dyn_cast<Constant>(U))
1712 findGlobalVariableUsersOf(C2, Out);
1713 }
1714}
1715
1716// Replace all uses of F with (F ? JT : 0).
1717void LowerTypeTestsModule::replaceWeakDeclarationWithJumpTablePtr(
1718 Function *F, Constant *JT, bool IsJumpTableCanonical) {
1719 // The target expression can not appear in a constant initializer on most
1720 // (all?) targets. Switch to a runtime initializer.
1721 SmallSetVector<GlobalVariable *, 8> GlobalVarUsers;
1722 findGlobalVariableUsersOf(F, GlobalVarUsers);
1723 for (auto *GV : GlobalVarUsers) {
1724 if (GV == GlobalAnnotation)
1725 continue;
1726 moveInitializerToModuleConstructor(GV);
1727 }
1728
1729 // Can not RAUW F with an expression that uses F. Replace with a temporary
1730 // placeholder first.
1731 Function *PlaceholderFn =
1733 F->getAddressSpace(), "", &M);
1734 replaceCfiUses(F, PlaceholderFn, IsJumpTableCanonical);
1735
1737 // Don't use range based loop, because use list will be modified.
1738 while (!PlaceholderFn->use_empty()) {
1739 Use &U = *PlaceholderFn->use_begin();
1740 auto *InsertPt = dyn_cast<Instruction>(U.getUser());
1741 assert(InsertPt && "Non-instruction users should have been eliminated");
1742 auto *PN = dyn_cast<PHINode>(InsertPt);
1743 if (PN)
1744 InsertPt = PN->getIncomingBlock(U)->getTerminator();
1745 IRBuilder Builder(InsertPt);
1746 Value *ICmp = Builder.CreateICmp(CmpInst::ICMP_NE, F,
1747 Constant::getNullValue(F->getType()));
1748 Value *Select = Builder.CreateSelect(ICmp, JT,
1749 Constant::getNullValue(F->getType()));
1750
1751 if (auto *SI = dyn_cast<SelectInst>(Select))
1753 // For phi nodes, we need to update the incoming value for all operands
1754 // with the same predecessor.
1755 if (PN)
1756 PN->setIncomingValueForBlock(InsertPt->getParent(), Select);
1757 else
1758 U.set(Select);
1759 }
1760 PlaceholderFn->eraseFromParent();
1761}
1762
1763static bool isThumbFunction(Function *F, Triple::ArchType ModuleArch) {
1764 Attribute TFAttr = F->getFnAttribute("target-features");
1765 if (TFAttr.isValid()) {
1767 TFAttr.getValueAsString().split(Features, ',');
1768 for (StringRef Feature : Features) {
1769 if (Feature == "-thumb-mode")
1770 return false;
1771 else if (Feature == "+thumb-mode")
1772 return true;
1773 }
1774 }
1775
1776 return ModuleArch == Triple::thumb;
1777}
1778
1779// Each jump table must be either ARM or Thumb as a whole for the bit-test math
1780// to work. Pick one that matches the majority of members to minimize interop
1781// veneers inserted by the linker.
1782Triple::ArchType LowerTypeTestsModule::selectJumpTableArmEncoding(
1783 ArrayRef<GlobalTypeMember *> Functions) {
1784 if (Arch != Triple::arm && Arch != Triple::thumb)
1785 return Arch;
1786
1787 if (!CanUseThumbBWJumpTable && CanUseArmJumpTable) {
1788 // In architectures that provide Arm and Thumb-1 but not Thumb-2,
1789 // we should always prefer the Arm jump table format, because the
1790 // Thumb-1 one is larger and slower.
1791 return Triple::arm;
1792 }
1793
1794 // Otherwise, go with majority vote.
1795 unsigned ArmCount = 0, ThumbCount = 0;
1796 for (const auto GTM : Functions) {
1797 if (!GTM->isJumpTableCanonical()) {
1798 // PLT stubs are always ARM.
1799 // FIXME: This is the wrong heuristic for non-canonical jump tables.
1800 ++ArmCount;
1801 continue;
1802 }
1803
1804 Function *F = cast<Function>(GTM->getGlobal());
1805 ++(isThumbFunction(F, Arch) ? ThumbCount : ArmCount);
1806 }
1807
1808 return ArmCount > ThumbCount ? Triple::arm : Triple::thumb;
1809}
1810
1811// Create location for each function entry which should look like this:
1812// frame #0: c::c() (.cfi_jt) at sanitizer/ubsan_interface.h:0:0
1813// frame #1: __ubsan_check_cfi_icall_jt at sanitizer/ubsan_interface.h:0
1816 Module &M = *F->getParent();
1817 DICompileUnit *CU = nullptr;
1818 auto CUs = M.debug_compile_units();
1819 if (!CUs.empty())
1820 CU = *CUs.begin();
1821
1822 DIBuilder DIB(M, /*AllowUnresolved=*/true, CU);
1823 DIFile *File = DIB.createFile("ubsan_interface.h", "sanitizer");
1824 if (!CU) {
1825 // Synthetic module (like ld-temp.o), it frequently lacks a DICompileUnit
1826 // even if the rest of the program has debug info.
1827 CU = DIB.createCompileUnit(
1828 DISourceLanguageName(dwarf::DW_LANG_C), File, "llvm", true, "", 0, "",
1830 }
1831
1832 DISubroutineType *DIFnTy = DIB.createSubroutineType(nullptr);
1833
1834 DISubprogram *UbsanSP = DIB.createFunction(
1835 CU, "__ubsan_check_cfi_icall_jt", {}, File, 0, DIFnTy, 0,
1836 DINode::FlagArtificial, DISubprogram::SPFlagDefinition);
1837
1838 F->setSubprogram(UbsanSP);
1839
1840 DILocation *UbsanLoc = DILocation::get(M.getContext(), 0, 0, UbsanSP);
1841
1842 SmallVector<DILocation *> Locations;
1843 Locations.reserve(Functions.size());
1844
1845 for (auto *Func : Functions) {
1846 StringRef FuncName = Func->getGlobal()->getName();
1847 FuncName.consume_back(".cfi");
1848 DISubprogram *JumpSP = DIB.createFunction(
1849 CU, (FuncName + ".cfi_jt").str(), {}, File, 0, DIFnTy, 0,
1850 DINode::FlagArtificial, DISubprogram::SPFlagDefinition);
1851
1852 DILocation *EntryLoc =
1853 DILocation::get(M.getContext(), 0, 0, JumpSP, UbsanLoc);
1854
1855 Locations.push_back(EntryLoc);
1856 }
1857
1858 DIB.finalize();
1859
1860 return Locations;
1861}
1862
1863void LowerTypeTestsModule::createJumpTable(
1865 Triple::ArchType JumpTableArch) {
1866 unsigned JumpTableEntrySize = getJumpTableEntrySize(JumpTableArch);
1867 // Give the jumptable section this type in order to enable jumptable
1868 // relaxation. Only do this if cross-DSO CFI is disabled because jumptable
1869 // relaxation violates cross-DSO CFI's restrictions on the ordering of the
1870 // jumptable relative to other sections.
1871 if (!CrossDsoCfi)
1872 F->setMetadata(LLVMContext::MD_elf_section_properties,
1873 MDNode::get(F->getContext(),
1875 ConstantAsMetadata::get(ConstantInt::get(
1876 Int64Ty, ELF::SHT_LLVM_CFI_JUMP_TABLE)),
1877 ConstantAsMetadata::get(ConstantInt::get(
1878 Int64Ty, JumpTableEntrySize))}));
1879
1880 BasicBlock *BB = BasicBlock::Create(M.getContext(), "entry", F);
1881 IRBuilder<> IRB(BB);
1882
1884 if (M.getDwarfVersion() != 0 && Opts.lowertypetests_jump_table_debug_info)
1885 Locations = createJumpTableDebugInfo(F, Functions);
1886
1887 InlineAsm *JumpTableAsm = createJumpTableEntryAsm(JumpTableArch);
1888
1889 // Check if all entries have the NoUnwind attribute.
1890 // If all entries have it, we can safely mark the
1891 // cfi.jumptable as NoUnwind, otherwise, direct calls
1892 // to the jump table will not handle exceptions properly
1893 bool areAllEntriesNounwind = true;
1894 assert(Locations.empty() || Functions.size() == Locations.size());
1895 for (auto [GTM, Loc] : zip_longest(Functions, Locations)) {
1896 if (Loc.has_value())
1897 IRB.SetCurrentDebugLocation(*Loc);
1898 if (!cast<Function>((*GTM)->getGlobal())
1899 ->hasFnAttribute(Attribute::NoUnwind)) {
1900 areAllEntriesNounwind = false;
1901 }
1902 IRB.CreateCall(JumpTableAsm, (*GTM)->getGlobal());
1903 }
1904 IRB.CreateUnreachable();
1905
1906 // Align the whole table by entry size.
1907 F->setPreferredAlignment(Align(JumpTableEntrySize));
1908 F->addFnAttr(Attribute::Naked);
1909 if (JumpTableArch == Triple::arm)
1910 F->addFnAttr("target-features", "-thumb-mode");
1911 if (JumpTableArch == Triple::thumb) {
1912 if (hasBranchTargetEnforcement()) {
1913 // If we're generating a Thumb jump table with BTI, add a target-features
1914 // setting to ensure BTI can be assembled.
1915 F->addFnAttr("target-features", "+thumb-mode,+pacbti");
1916 } else {
1917 F->addFnAttr("target-features", "+thumb-mode");
1918 if (CanUseThumbBWJumpTable) {
1919 // Thumb jump table assembly needs Thumb2. The following attribute is
1920 // added by Clang for -march=armv7.
1921 F->addFnAttr("target-cpu", "cortex-a8");
1922 }
1923 }
1924 }
1925 // When -mbranch-protection= is used, the inline asm adds a BTI. Suppress BTI
1926 // for the function to avoid double BTI. This is a no-op without
1927 // -mbranch-protection=.
1928 if (JumpTableArch == Triple::aarch64 || JumpTableArch == Triple::thumb) {
1929 if (F->hasFnAttribute("branch-target-enforcement"))
1930 F->removeFnAttr("branch-target-enforcement");
1931 if (F->hasFnAttribute("sign-return-address"))
1932 F->removeFnAttr("sign-return-address");
1933 }
1934 if (JumpTableArch == Triple::riscv32 || JumpTableArch == Triple::riscv64) {
1935 // Make sure the jump table assembly is not modified by the assembler or
1936 // the linker.
1937 F->addFnAttr("target-features", "-c,-relax");
1938 }
1939 // When -fcf-protection= is used, the inline asm adds an ENDBR. Suppress ENDBR
1940 // for the function to avoid double ENDBR. This is a no-op without
1941 // -fcf-protection=.
1942 if (JumpTableArch == Triple::x86 || JumpTableArch == Triple::x86_64)
1943 F->addFnAttr(Attribute::NoCfCheck);
1944
1945 // Make sure we don't emit .eh_frame for this function if it isn't needed.
1946 if (areAllEntriesNounwind)
1947 F->addFnAttr(Attribute::NoUnwind);
1948
1949 // Make sure we do not inline any calls to the cfi.jumptable.
1950 F->addFnAttr(Attribute::NoInline);
1951}
1952
1953/// Given a disjoint set of type identifiers and functions, build a jump table
1954/// for the functions, build the bit sets and lower the llvm.type.test calls.
1955void LowerTypeTestsModule::buildBitSetsFromFunctionsNative(
1957 // Unlike the global bitset builder, the function bitset builder cannot
1958 // re-arrange functions in a particular order and base its calculations on the
1959 // layout of the functions' entry points, as we have no idea how large a
1960 // particular function will end up being (the size could even depend on what
1961 // this pass does!) Instead, we build a jump table, which is a block of code
1962 // consisting of one branch instruction for each of the functions in the bit
1963 // set that branches to the target function, and redirect any taken function
1964 // addresses to the corresponding jump table entry. In the object file's
1965 // symbol table, the symbols for the target functions also refer to the jump
1966 // table entries, so that addresses taken outside the module will pass any
1967 // verification done inside the module.
1968 //
1969 // In more concrete terms, suppose we have three functions f, g, h which are
1970 // of the same type, and a function foo that returns their addresses:
1971 //
1972 // f:
1973 // mov 0, %eax
1974 // ret
1975 //
1976 // g:
1977 // mov 1, %eax
1978 // ret
1979 //
1980 // h:
1981 // mov 2, %eax
1982 // ret
1983 //
1984 // foo:
1985 // mov f, %eax
1986 // mov g, %edx
1987 // mov h, %ecx
1988 // ret
1989 //
1990 // We output the jump table as module-level inline asm string. The end result
1991 // will (conceptually) look like this:
1992 //
1993 // f = .cfi.jumptable
1994 // g = .cfi.jumptable + 4
1995 // h = .cfi.jumptable + 8
1996 // .cfi.jumptable:
1997 // jmp f.cfi ; 5 bytes
1998 // int3 ; 1 byte
1999 // int3 ; 1 byte
2000 // int3 ; 1 byte
2001 // jmp g.cfi ; 5 bytes
2002 // int3 ; 1 byte
2003 // int3 ; 1 byte
2004 // int3 ; 1 byte
2005 // jmp h.cfi ; 5 bytes
2006 // int3 ; 1 byte
2007 // int3 ; 1 byte
2008 // int3 ; 1 byte
2009 //
2010 // f.cfi:
2011 // mov 0, %eax
2012 // ret
2013 //
2014 // g.cfi:
2015 // mov 1, %eax
2016 // ret
2017 //
2018 // h.cfi:
2019 // mov 2, %eax
2020 // ret
2021 //
2022 // foo:
2023 // mov f, %eax
2024 // mov g, %edx
2025 // mov h, %ecx
2026 // ret
2027 //
2028 // Because the addresses of f, g, h are evenly spaced at a power of 2, in the
2029 // normal case the check can be carried out using the same kind of simple
2030 // arithmetic that we normally use for globals.
2031
2032 // FIXME: find a better way to represent the jumptable in the IR.
2033 assert(!Functions.empty());
2034
2035 // Decide on the jump table encoding, so that we know how big the
2036 // entries will be.
2037 Triple::ArchType JumpTableArch = selectJumpTableArmEncoding(Functions);
2038
2039 // Build a simple layout based on the regular layout of jump tables.
2040 DenseMap<GlobalTypeMember *, uint64_t> GlobalLayout;
2041 unsigned EntrySize = getJumpTableEntrySize(JumpTableArch);
2042 for (unsigned I = 0; I != Functions.size(); ++I)
2043 GlobalLayout[Functions[I]] = I * EntrySize;
2044
2045 Function *JumpTableFn =
2047 /* IsVarArg */ false),
2049 M.getDataLayout().getProgramAddressSpace(),
2050 ".cfi.jumptable", &M);
2051 ArrayType *JumpTableEntryType = ArrayType::get(Int8Ty, EntrySize);
2053 ArrayType::get(JumpTableEntryType, Functions.size());
2055 JumpTableFn, PointerType::getUnqual(M.getContext()));
2056
2057 lowerTypeTestCalls(TypeIds, JumpTable, GlobalLayout);
2058
2059 // Build aliases pointing to offsets into the jump table, and replace
2060 // references to the original functions with references to the aliases.
2061 for (unsigned I = 0; I != Functions.size(); ++I) {
2062 Function *F = cast<Function>(Functions[I]->getGlobal());
2063 bool IsJumpTableCanonical = Functions[I]->isJumpTableCanonical();
2064
2065 Constant *CombinedGlobalElemPtr = ConstantExpr::getGetElementPtr(
2066 F->getDataLayout(), JumpTableType, JumpTable,
2067 {ConstantInt::get(IntPtrTy, 0), ConstantInt::get(IntPtrTy, I)},
2069
2070 const bool IsExported = Functions[I]->isExported();
2071 if (!IsJumpTableCanonical) {
2074 GlobalAlias *JtAlias = GlobalAlias::create(JumpTableEntryType, 0, LT,
2075 F->getName() + ".cfi_jt",
2076 CombinedGlobalElemPtr, &M);
2077 if (IsExported)
2079 else
2080 appendToUsed(M, {JtAlias});
2081 }
2082
2083 if (IsExported) {
2084 GlobalValue::GUID GUID = F->getGUID();
2085 if (IsJumpTableCanonical)
2086 ExportSummary->cfiFunctionDefs().addSymbolWithThinLTOGUID(F->getName(),
2087 GUID);
2088 else
2089 ExportSummary->cfiFunctionDecls().addSymbolWithThinLTOGUID(F->getName(),
2090 GUID);
2091 }
2092
2093 if (!IsJumpTableCanonical) {
2094 if (F->hasExternalWeakLinkage())
2095 replaceWeakDeclarationWithJumpTablePtr(F, CombinedGlobalElemPtr,
2096 IsJumpTableCanonical);
2097 else
2098 replaceCfiUses(F, CombinedGlobalElemPtr, IsJumpTableCanonical);
2099 } else {
2100 assert(F->getType()->getAddressSpace() == 0);
2101
2102 GlobalAlias *FAlias =
2103 GlobalAlias::create(JumpTableEntryType, 0, F->getLinkage(), "",
2104 CombinedGlobalElemPtr, &M);
2105 FAlias->setVisibility(F->getVisibility());
2106 FAlias->setDSOLocal(F->isDSOLocal());
2107 FAlias->takeName(F);
2108 if (FAlias->hasName()) {
2109 F->setName(FAlias->getName() + ".cfi");
2110 maybeReplaceComdat(F, FAlias->getName());
2111 }
2112 replaceCfiUses(F, FAlias, IsJumpTableCanonical);
2113 if (!F->hasLocalLinkage())
2114 F->setVisibility(GlobalVariable::HiddenVisibility);
2115 }
2116 }
2117
2118 createJumpTable(JumpTableFn, Functions, JumpTableArch);
2119}
2120
2121/// Assign a dummy layout using an incrementing counter, tag each function
2122/// with its index represented as metadata, and lower each type test to an
2123/// integer range comparison. During generation of the indirect function call
2124/// table in the backend, it will assign the given indexes.
2125/// Note: Dynamic linking is not supported, as the WebAssembly ABI has not yet
2126/// been finalized.
2127void LowerTypeTestsModule::buildBitSetsFromFunctionsWASM(
2129 assert(!Functions.empty());
2130
2131 // Build consecutive monotonic integer ranges for each call target set
2132 DenseMap<GlobalTypeMember *, uint64_t> GlobalLayout;
2133
2134 for (GlobalTypeMember *GTM : Functions) {
2135 Function *F = cast<Function>(GTM->getGlobal());
2136
2137 // Skip functions that are not address taken, to avoid bloating the table
2138 if (!F->hasAddressTaken())
2139 continue;
2140
2141 // Store metadata with the index for each function
2142 MDNode *MD = MDNode::get(F->getContext(),
2144 ConstantInt::get(Int64Ty, IndirectIndex))));
2145 F->setMetadata("wasm.index", MD);
2146
2147 // Assign the counter value
2148 GlobalLayout[GTM] = IndirectIndex++;
2149 }
2150
2151 // The indirect function table index space starts at zero, so pass a NULL
2152 // pointer as the subtracted "jump table" offset.
2153 lowerTypeTestCalls(TypeIds, ConstantPointerNull::get(PtrTy),
2154 GlobalLayout);
2155}
2156
2157void LowerTypeTestsModule::buildBitSetsFromDisjointSet(
2159 ArrayRef<ICallBranchFunnel *> ICallBranchFunnels) {
2160 DenseMap<Metadata *, uint64_t> TypeIdIndices;
2161 for (unsigned I = 0; I != TypeIds.size(); ++I)
2162 TypeIdIndices[TypeIds[I]] = I;
2163
2164 // For each type identifier, build a set of indices that refer to members of
2165 // the type identifier.
2166 std::vector<std::set<uint64_t>> TypeMembers(TypeIds.size());
2167 unsigned GlobalIndex = 0;
2168 DenseMap<GlobalTypeMember *, uint64_t> GlobalIndices;
2169 for (GlobalTypeMember *GTM : Globals) {
2170 for (MDNode *Type : GTM->types()) {
2171 // Type = { offset, type identifier }
2172 auto I = TypeIdIndices.find(Type->getOperand(1));
2173 if (I != TypeIdIndices.end())
2174 TypeMembers[I->second].insert(GlobalIndex);
2175 }
2176 GlobalIndices[GTM] = GlobalIndex;
2177 GlobalIndex++;
2178 }
2179
2180 for (ICallBranchFunnel *JT : ICallBranchFunnels) {
2181 TypeMembers.emplace_back();
2182 std::set<uint64_t> &TMSet = TypeMembers.back();
2183 for (GlobalTypeMember *T : JT->targets())
2184 TMSet.insert(GlobalIndices[T]);
2185 }
2186
2187 // Order the sets of indices by size. The GlobalLayoutBuilder works best
2188 // when given small index sets first.
2189 llvm::stable_sort(TypeMembers, [](const std::set<uint64_t> &O1,
2190 const std::set<uint64_t> &O2) {
2191 return O1.size() < O2.size();
2192 });
2193
2194 bool IsGlobalSet =
2195 Globals.empty() || isa<GlobalVariable>(Globals[0]->getGlobal());
2196
2197 unique_function<bool(uint64_t, uint64_t)> Less;
2198 if (!IsGlobalSet && !FunctionSummaryHotness.empty() &&
2199 Opts.reorder_cfi_jump_tables_profiles) {
2200 // Estimated weight of each jump entry.
2201 std::vector<CfiFunctionHotness> GTMHotness;
2202 GTMHotness.reserve(Globals.size());
2203 for (GlobalTypeMember *GTM : Globals) {
2204 GTMHotness.push_back(
2205 FunctionSummaryHotness.lookup(cast<Function>(GTM->getGlobal())));
2206 }
2207
2208 // Order jump table entries by hotness ascending so that the hottest
2209 // entry is placed at the end of the jump table:
2210 // 1. Under jump table relaxation (SHT_LLVM_CFI_JUMP_TABLE), the linker
2211 // moves the jump table directly before the target of the last entry
2212 // and deletes its branch so the target function body acts as the
2213 // last entry.
2214 // 2. The jump table is placed into the output section of that last
2215 // target. Jump tables are critical to performance; if the last
2216 // entry were a cold function, the jump table would be dragged into a
2217 // cold binary section (such as .text.unlikely). Placing the hottest
2218 // entry at the end ensures the jump table lands in a hot section and
2219 // the hottest callee benefits from fall-through without a branch.
2220 Less = [GTMHotness = std::move(GTMHotness)](uint64_t A, uint64_t B) {
2221 return GTMHotness[A] < GTMHotness[B];
2222 };
2223 }
2224
2225 // Create a GlobalLayoutBuilder and provide it with index sets as layout
2226 // fragments. The GlobalLayoutBuilder tries to lay out members of fragments as
2227 // close together as possible.
2228 GlobalLayoutBuilder GLB(Globals.size(), std::move(Less));
2229 for (auto &&MemSet : TypeMembers)
2230 GLB.addFragment(MemSet);
2231
2232 // Build a vector of globals with the computed layout.
2233 std::vector<GlobalTypeMember *> OrderedGTMs(Globals.size());
2234 auto OGTMI = OrderedGTMs.begin();
2235 for (uint64_t Offset : GLB.build()) {
2236 if (IsGlobalSet != isa<GlobalVariable>(Globals[Offset]->getGlobal()))
2237 report_fatal_error("Type identifier may not contain both global "
2238 "variables and functions");
2239 *OGTMI++ = Globals[Offset];
2240 }
2241
2242 // Build the bitsets from this disjoint set.
2243 if (IsGlobalSet)
2244 buildBitSetsFromGlobalVariables(TypeIds, OrderedGTMs);
2245 else
2246 buildBitSetsFromFunctions(TypeIds, OrderedGTMs);
2247}
2248
2249/// Lower all type tests in this module.
2250LowerTypeTestsModule::LowerTypeTestsModule(
2251 Module &M, ModuleAnalysisManager &AM, ModuleSummaryIndex *ExportSummary,
2252 const ModuleSummaryIndex *ImportSummary)
2253 : Opts(getIPOOptions(M)), M(M), ExportSummary(ExportSummary),
2254 ImportSummary(ImportSummary) {
2255 assert(!(ExportSummary && ImportSummary));
2256 Triple TargetTriple(M.getTargetTriple());
2257 Arch = TargetTriple.getArch();
2258 auto &FAM = AM.getResult<FunctionAnalysisManagerModuleProxy>(M).getManager();
2259
2260 if (Arch == Triple::arm)
2261 CanUseArmJumpTable = true;
2262 if (Arch == Triple::arm || Arch == Triple::thumb) {
2263 for (Function &F : M) {
2264 // Skip declarations since we should not query the TTI for them.
2265 if (F.isDeclaration())
2266 continue;
2267 auto &TTI = FAM.getResult<TargetIRAnalysis>(F);
2268 if (TTI.hasArmWideBranch(false))
2269 CanUseArmJumpTable = true;
2270 if (TTI.hasArmWideBranch(true))
2271 CanUseThumbBWJumpTable = true;
2272 }
2273 }
2274 OS = TargetTriple.getOS();
2275 ObjectFormat = TargetTriple.getObjectFormat();
2276
2277 // Function annotation describes or applies to function itself, and
2278 // shouldn't be associated with jump table thunk generated for CFI.
2279 GlobalAnnotation = M.getGlobalVariable("llvm.global.annotations");
2280 if (GlobalAnnotation && GlobalAnnotation->hasInitializer()) {
2281 const ConstantArray *CA =
2282 cast<ConstantArray>(GlobalAnnotation->getInitializer());
2283 FunctionAnnotations.insert_range(CA->operands());
2284 }
2285}
2286
2287bool LowerTypeTestsModule::runForTesting(Module &M, ModuleAnalysisManager &AM) {
2288 const IPOOptions &Opts = getIPOOptions(M);
2289 StringRef ReadSummary = Opts.lowertypetests_read_summary;
2290 StringRef WriteSummary = Opts.lowertypetests_write_summary;
2291 PassSummaryAction SummaryAction = Opts.lowertypetests_summary_action;
2292 std::unique_ptr<ModuleSummaryIndex> Summary;
2293
2294 // Handle the command-line summary arguments. This code is for testing
2295 // purposes only, so we handle errors directly.
2296 if (!ReadSummary.empty()) {
2297 ExitOnError ExitOnErr(
2298 ("-lowertypetests-read-summary: " + ReadSummary + ": ").str());
2299 auto ReadSummaryFile = ExitOnErr(
2300 errorOrToExpected(MemoryBuffer::getFile(ReadSummary, /*IsText=*/true)));
2301 // TODO: Convert the rest of tests (some YAML features are missing from
2302 // textual summary assembly) and remove YAML from this file.
2303 if (ReadSummaryFile->getBuffer().starts_with("---")) {
2304 Summary = std::make_unique<ModuleSummaryIndex>(/*HaveGVs=*/false);
2305 yaml::Input In(ReadSummaryFile->getBuffer());
2306 In >> *Summary;
2307 ExitOnErr(errorCodeToError(In.error()));
2308 } else {
2309 SMDiagnostic Err;
2310 Summary =
2311 parseSummaryIndexAssembly(ReadSummaryFile->getMemBufferRef(), Err);
2312 if (!Summary) {
2313 Err.print(ReadSummary.str().c_str(), errs());
2314 report_fatal_error("Failed to parse summary index assembly");
2315 }
2316 }
2317 } else {
2318 Summary = std::make_unique<ModuleSummaryIndex>(/*HaveGVs=*/false);
2319 }
2320
2321 bool Changed =
2322 LowerTypeTestsModule(
2323 M, AM,
2324 SummaryAction == PassSummaryAction::Export ? Summary.get() : nullptr,
2325 SummaryAction == PassSummaryAction::Import ? Summary.get() : nullptr)
2326 .lower();
2327
2328 if (!WriteSummary.empty()) {
2329 ExitOnError ExitOnErr(
2330 ("-lowertypetests-write-summary: " + WriteSummary + ": ").str());
2331 std::error_code EC;
2332 raw_fd_ostream OS(WriteSummary, EC, sys::fs::OF_TextWithCRLF);
2333 ExitOnErr(errorCodeToError(EC));
2334
2335 yaml::Output Out(OS);
2336 Out << *Summary;
2337 }
2338
2339 return Changed;
2340}
2341
2342static bool isDirectCall(Use& U) {
2343 auto *Usr = dyn_cast<CallInst>(U.getUser());
2344 return Usr && Usr->isCallee(&U);
2345}
2346
2347void LowerTypeTestsModule::replaceCfiUses(Function *Old, Value *New,
2348 bool IsJumpTableCanonical) {
2349 SmallSetVector<Constant *, 4> Constants;
2350 for (Use &U : llvm::make_early_inc_range(Old->uses())) {
2351 // Skip no_cfi values, which refer to the function body instead of the jump
2352 // table.
2353 if (isa<NoCFIValue>(U.getUser()))
2354 continue;
2355
2356 // Skip direct calls to externally defined or dso_local functions.
2357 if (isDirectCall(U) && (Old->isDSOLocal() || !IsJumpTableCanonical))
2358 continue;
2359
2360 // Skip function annotation.
2361 if (isFunctionAnnotation(U.getUser()))
2362 continue;
2363
2364 // Must handle Constants specially, we cannot call replaceUsesOfWith on a
2365 // constant because they are uniqued.
2366 if (auto *C = dyn_cast<Constant>(U.getUser())) {
2367 if (!isa<GlobalValue>(C)) {
2368 // Save unique users to avoid processing operand replacement
2369 // more than once.
2370 Constants.insert(C);
2371 continue;
2372 }
2373 }
2374
2375 U.set(New);
2376 }
2377
2378 // Process operand replacement of saved constants.
2379 for (auto *C : Constants)
2380 C->handleOperandChange(Old, New);
2381}
2382
2383void LowerTypeTestsModule::replaceDirectCalls(Value *Old, Value *New) {
2385}
2386
2387// Sound wherever the caller has already dropped the type tests: the check
2388// folds to true, the trap branch becomes dead, and later passes fold it
2389// away. Required because the backend cannot select these intrinsics
2390// ("must be lowered by the LowerTypeTests pass before code generation").
2392 bool IsRelative) {
2393 bool Changed = false;
2394 for (User *User : llvm::make_early_inc_range(CheckedLoadFn.users())) {
2396 if (!I)
2397 continue;
2398 IRBuilder<> IRB(I);
2399 Value *Ptr = I->getOperand(0);
2400 Value *Offset = I->getOperand(1);
2401 Type *PtrTy = I->getType()->getStructElementType(0);
2402 ConstantInt *True = ConstantInt::getTrue(M.getContext());
2404 if (IsRelative) {
2406 Intrinsic::load_relative, {Offset->getType()}, {Ptr, Offset},
2407 /*FMFSource=*/nullptr, "rel_load");
2408 } else {
2409 Value *PtrAdd = IRB.CreatePtrAddWithSExtOrTrunc(Ptr, Offset);
2410 Load = IRB.CreateLoad(PtrTy, PtrAdd, "vfunc");
2411 }
2412
2413 Value *Replacement = PoisonValue::get(I->getType());
2414 Replacement = IRB.CreateInsertValue(Replacement, True, {1});
2415 Replacement = IRB.CreateInsertValue(Replacement, Load, {0});
2416 I->replaceAllUsesWith(Replacement);
2417
2418 LLVM_DEBUG(dbgs() << DEBUG_TYPE << ": erase " << *I << "\n");
2419 I->eraseFromParent();
2420 Changed = true;
2421 }
2422 if (Changed)
2423 CheckedLoadFn.eraseFromParent();
2424 return Changed;
2425}
2426
2427static void dropTypeTests(Module &M, Function &TypeTestFunc,
2428 bool ShouldDropAll) {
2429 for (Use &U : llvm::make_early_inc_range(TypeTestFunc.uses())) {
2430 auto *CI = cast<CallInst>(U.getUser());
2431 // Find and erase llvm.assume intrinsics for this llvm.type.test call.
2432 for (Use &CIU : llvm::make_early_inc_range(CI->uses()))
2433 if (auto *Assume = dyn_cast<AssumeInst>(CIU.getUser()))
2434 Assume->eraseFromParent();
2435 // If the assume was merged with another assume, we might have a use on a
2436 // phi or select (which will feed the assume). Simply replace the use on
2437 // the phi/select with "true" and leave the merged assume.
2438 //
2439 // If ShouldDropAll is set, then we we need to update any remaining uses,
2440 // regardless of the instruction type.
2441 if (!CI->use_empty()) {
2442 assert(ShouldDropAll || all_of(CI->users(), [](User *U) -> bool {
2443 return isa<PHINode>(U) || isa<SelectInst>(U);
2444 }));
2445 CI->replaceAllUsesWith(ConstantInt::getTrue(M.getContext()));
2446 }
2447 CI->eraseFromParent();
2448 }
2449}
2450
2451static bool dropTypeTests(Module &M, bool ShouldDropAll) {
2452 Function *TypeTestFunc =
2453 Intrinsic::getDeclarationIfExists(&M, Intrinsic::type_test);
2454 if (TypeTestFunc)
2455 dropTypeTests(M, *TypeTestFunc, ShouldDropAll);
2456 // Only drop checked loads when dropping everything: in Assume mode a
2457 // checked load may feed a CFI trap check, which must keep diagnosing
2458 // loudly instead of being turned to true.
2459 bool DroppedCheckedLoads = false;
2460 if (ShouldDropAll) {
2461 if (Function *F =
2462 Intrinsic::getDeclarationIfExists(&M, Intrinsic::type_checked_load))
2463 DroppedCheckedLoads |=
2466 &M, Intrinsic::type_checked_load_relative))
2467 DroppedCheckedLoads |=
2469 }
2470 // Normally we'd have already removed all @llvm.public.type.test calls,
2471 // except for in the case where we originally were performing ThinLTO but
2472 // decided not to in the backend.
2473 Function *PublicTypeTestFunc =
2474 Intrinsic::getDeclarationIfExists(&M, Intrinsic::public_type_test);
2475 if (PublicTypeTestFunc)
2476 dropTypeTests(M, *PublicTypeTestFunc, ShouldDropAll);
2477 if (TypeTestFunc || PublicTypeTestFunc || DroppedCheckedLoads) {
2478 // We have deleted the type intrinsics, so we no longer have enough
2479 // information to reason about the liveness of virtual function pointers
2480 // in GlobalDCE.
2481 for (GlobalVariable &GV : M.globals())
2482 GV.eraseMetadata(LLVMContext::MD_vcall_visibility);
2483 return true;
2484 }
2485 return false;
2486}
2487
2488bool LowerTypeTestsModule::lower() {
2489 Function *TypeTestFunc =
2490 Intrinsic::getDeclarationIfExists(&M, Intrinsic::type_test);
2491
2492 // If only some of the modules were split, we cannot correctly perform
2493 // this transformation. We already checked for the presense of type tests
2494 // with partially split modules during the thin link, and would have emitted
2495 // an error if any were found, so here we can simply return.
2496 if ((ExportSummary && ExportSummary->partiallySplitLTOUnits()) ||
2497 (ImportSummary && ImportSummary->partiallySplitLTOUnits()))
2498 return false;
2499
2500 Function *ICallBranchFunnelFunc =
2501 Intrinsic::getDeclarationIfExists(&M, Intrinsic::icall_branch_funnel);
2502 if ((!TypeTestFunc || TypeTestFunc->use_empty()) &&
2503 (!ICallBranchFunnelFunc || ICallBranchFunnelFunc->use_empty()) &&
2504 !ExportSummary && !ImportSummary)
2505 return false;
2506
2507 if (ImportSummary) {
2508 if (TypeTestFunc)
2509 for (Use &U : llvm::make_early_inc_range(TypeTestFunc->uses()))
2510 importTypeTest(cast<CallInst>(U.getUser()));
2511
2512 if (ICallBranchFunnelFunc && !ICallBranchFunnelFunc->use_empty())
2514 "unexpected call to llvm.icall.branch.funnel during import phase");
2515
2516 // For internal linkage cfiFunction defs/decls, we only needed the alias
2517 // through the linker. We can replace those aliases with the aliased
2518 // function here.
2520 for (auto &A : llvm::make_early_inc_range(M.aliases())) {
2521 if (A.hasLocalLinkage())
2522 continue;
2523 if (ImportSummary->cfiFunctionDefs().contains(A.getName()) ||
2524 ImportSummary->cfiFunctionDecls().contains(A.getName())) {
2525 if (auto *F = dyn_cast_or_null<Function>(A.getAliaseeObject())) {
2526 if (F->hasExternalLinkage()) {
2527 // The original internal linkage function was independently promoted
2528 // by thinlink. While, pre-link, all static references to it
2529 // (implicitly, module-internal) were replaced with references to
2530 // the alias, thinlink might decide to promote it because (for
2531 // example) it turns out to be a hot indirect call target in a
2532 // different module.
2533 // In that case, we need to remember its thinlink-promoted name
2534 // because it's potentially referenced elsewhere, and make sure
2535 // there's an alias to it.
2536 PromotedFuncs.emplace_back(F, F->getName());
2537 } else {
2538 F->setLinkage(GlobalValue::ExternalLinkage);
2539 F->setVisibility(GlobalValue::HiddenVisibility);
2540 }
2541 A.replaceAllUsesWith(F);
2542 F->takeName(&A);
2543 A.eraseFromParent();
2544 }
2545 }
2546 }
2547
2550 for (auto &F : M) {
2551 // CFI functions are either external, or promoted. A local function may
2552 // have the same name, but it's not the one we are looking for.
2553 if (F.hasLocalLinkage())
2554 continue;
2555 if (ImportSummary->cfiFunctionDefs().contains(F.getName()))
2556 Defs.push_back(&F);
2557 else if (ImportSummary->cfiFunctionDecls().contains(F.getName()))
2558 Decls.push_back(&F);
2559 }
2560
2561 {
2562 ScopedSaveAliaseesAndUsed S(M);
2563 for (auto *F : Defs)
2564 importFunction(F, /*isJumpTableCanonical*/ true);
2565 for (auto *F : Decls)
2566 importFunction(F, /*isJumpTableCanonical*/ false);
2567 }
2568 // Add an alias with the thinlink promotion name.
2569 for (auto &[F, Name] : PromotedFuncs)
2570 GlobalAlias::create(GlobalValue::LinkageTypes::ExternalLinkage, Name, F);
2571
2572 return true;
2573 }
2574
2575 // Equivalence class set containing type identifiers and the globals that
2576 // reference them. This is used to partition the set of type identifiers in
2577 // the module into disjoint sets.
2578 using GlobalClassesTy = EquivalenceClasses<
2579 PointerUnion<GlobalTypeMember *, Metadata *, ICallBranchFunnel *>>;
2580 GlobalClassesTy GlobalClasses;
2581
2582 // Verify the type metadata and build a few data structures to let us
2583 // efficiently enumerate the type identifiers associated with a global:
2584 // a list of GlobalTypeMembers (a GlobalObject stored alongside a vector
2585 // of associated type metadata) and a mapping from type identifiers to their
2586 // list of GlobalTypeMembers and last observed index in the list of globals.
2587 // The indices will be used later to deterministically order the list of type
2588 // identifiers.
2590 struct TIInfo {
2591 unsigned UniqueId;
2592 std::vector<GlobalTypeMember *> RefGlobals;
2593 };
2594 DenseMap<Metadata *, TIInfo> TypeIdInfo;
2595 unsigned CurUniqueId = 0;
2597
2598 struct ExportedFunctionInfo {
2599 CfiFunctionLinkage Linkage;
2600 MDNode *FuncMD; // {name, linkage, type[, type...]}
2601 };
2602 MapVector<StringRef, ExportedFunctionInfo> ExportedFunctions;
2603 if (ExportSummary) {
2604 NamedMDNode *CfiFunctionsMD = M.getNamedMetadata("cfi.functions");
2605 if (CfiFunctionsMD) {
2606 // A set of all functions that are address taken by a live global object.
2607 DenseSet<GlobalValue::GUID> AddressTaken;
2608 for (auto &I : *ExportSummary)
2609 for (auto &GVS : I.second.getSummaryList())
2610 if (GVS->isLive())
2611 for (const auto &Ref : GVS->refs()) {
2612 AddressTaken.insert(Ref.getGUID());
2613 for (auto &RefGVS : Ref.getSummaryList())
2614 if (auto Alias = dyn_cast<AliasSummary>(RefGVS.get()))
2615 AddressTaken.insert(Alias->getAliaseeGUID());
2616 }
2618 if (AddressTaken.count(GUID))
2619 return true;
2620 auto VI = ExportSummary->getValueInfo(GUID);
2621 if (!VI)
2622 return false;
2623 for (auto &I : VI.getSummaryList())
2624 if (auto Alias = dyn_cast<AliasSummary>(I.get()))
2625 if (AddressTaken.count(Alias->getAliaseeGUID()))
2626 return true;
2627 return false;
2628 };
2629 for (auto *FuncMD : CfiFunctionsMD->operands()) {
2630 assert(FuncMD->getNumOperands() >= 2);
2631 StringRef FunctionName =
2632 cast<MDString>(FuncMD->getOperand(0))->getString();
2633 CfiFunctionLinkage Linkage = decodeCfiFunctionLinkage(
2634 cast<ConstantAsMetadata>(FuncMD->getOperand(1))
2635 ->getValue()
2636 ->getUniqueInteger()
2637 .getZExtValue());
2638 const GlobalValue::GUID GUID =
2639 cast<ConstantAsMetadata>(FuncMD->getOperand(2))
2640 ->getValue()
2641 ->getUniqueInteger()
2642 .getZExtValue();
2643 // Do not emit jumptable entries for functions that are not-live and
2644 // have no live references (and are not exported with cross-DSO CFI.)
2645 if (!ExportSummary->isGUIDLive(GUID))
2646 continue;
2647 if (!IsAddressTaken(GUID)) {
2648 if (!CrossDsoCfi || Linkage != CfiFunctionLinkage::Definition)
2649 continue;
2650
2651 bool Exported = false;
2652 if (auto VI = ExportSummary->getValueInfo(GUID))
2653 for (const auto &GVS : VI.getSummaryList())
2654 if (GVS->isLive() && !GlobalValue::isLocalLinkage(GVS->linkage()))
2655 Exported = true;
2656
2657 if (!Exported)
2658 continue;
2659 }
2660 auto P = ExportedFunctions.insert({FunctionName, {Linkage, FuncMD}});
2661 if (!P.second &&
2662 P.first->second.Linkage != CfiFunctionLinkage::Definition)
2663 P.first->second = {Linkage, FuncMD};
2664 }
2665
2666 for (const auto &P : ExportedFunctions) {
2667 StringRef FunctionName = P.first;
2668 CfiFunctionLinkage Linkage = P.second.Linkage;
2669 MDNode *FuncMD = P.second.FuncMD;
2670 Function *F = M.getFunction(FunctionName);
2671 if (F && F->hasLocalLinkage()) {
2672 // Locally defined function that happens to have the same name as a
2673 // function defined in a ThinLTO module. Rename it to move it out of
2674 // the way of the external reference that we're about to create.
2675 // Note that setName will find a unique name for the function, so even
2676 // if there is an existing function with the suffix there won't be a
2677 // name collision.
2678 F->setName(F->getName() + ".1");
2679 F = nullptr;
2680 }
2681
2682 if (!F) {
2684 FunctionType::get(Type::getVoidTy(M.getContext()), false),
2685 GlobalVariable::ExternalLinkage,
2686 M.getDataLayout().getProgramAddressSpace(), FunctionName, &M);
2687 F->setMetadata(
2688 LLVMContext::MD_guid,
2689 MDTuple::get(M.getContext(), {FuncMD->getOperand(2).get()}));
2690 if (ExportSummary) {
2693 ->getValue()
2694 ->getUniqueInteger()
2695 .getZExtValue();
2696 if (auto VI = ExportSummary->getValueInfo(GUID))
2697 F->setDSOLocal(
2698 VI.isDSOLocal(ExportSummary->withDSOLocalPropagation()));
2699 }
2700 }
2701 // If the function is available_externally, remove its definition so
2702 // that it is handled the same way as a declaration. Later we will try
2703 // to create an alias using this function's linkage, which will fail if
2704 // the linkage is available_externally. This will also result in us
2705 // following the code path below to replace the type metadata.
2706 if (F->hasAvailableExternallyLinkage()) {
2707 // Maintain !guid metadata.
2708 auto *OrigGUIDMD = F->getMetadata(LLVMContext::MD_guid);
2709 F->setLinkage(GlobalValue::ExternalLinkage);
2710 F->deleteBody();
2711 F->setComdat(nullptr);
2712 F->clearMetadata();
2713 F->setMetadata(LLVMContext::MD_guid, OrigGUIDMD);
2714 }
2715
2716 // Update the linkage for extern_weak declarations when a definition
2717 // exists.
2718 if (Linkage == CfiFunctionLinkage::Definition &&
2719 F->hasExternalWeakLinkage())
2720 F->setLinkage(GlobalValue::ExternalLinkage);
2721
2722 // If the function in the full LTO module is a declaration, replace its
2723 // type metadata with the type metadata we found in cfi.functions. That
2724 // metadata is presumed to be more accurate than the metadata attached
2725 // to the declaration.
2726 if (F->isDeclaration()) {
2727 if (Linkage == CfiFunctionLinkage::WeakDeclaration)
2729
2730 F->eraseMetadata(LLVMContext::MD_type);
2731 for (unsigned I = 3; I < FuncMD->getNumOperands(); ++I)
2732 F->addMetadata(LLVMContext::MD_type,
2733 *cast<MDNode>(FuncMD->getOperand(I).get()));
2734 }
2735 uint8_t Encoded = cast<ConstantAsMetadata>(FuncMD->getOperand(1))
2736 ->getValue()
2737 ->getUniqueInteger()
2738 .getZExtValue();
2739 // TODO: Implement for Full LTO.
2740 FunctionSummaryHotness[F] = decodeCfiFunctionHotness(Encoded);
2741 }
2742 }
2743 }
2744
2745 struct AliasToCreate {
2746 Function *Alias;
2747 std::string TargetName;
2748 };
2749 std::vector<AliasToCreate> AliasesToCreate;
2750
2751 // Parse alias data to replace stand-in function declarations for aliases
2752 // with an alias to the intended target.
2753 if (ExportSummary) {
2754 if (NamedMDNode *AliasesMD = M.getNamedMetadata("aliases")) {
2755 for (auto *AliasMD : AliasesMD->operands()) {
2757 for (MDString *MDS : make_isa_range<MDString>(AliasMD->operands())) {
2758 StringRef AliasName = MDS->getString();
2759 if (!ExportedFunctions.count(AliasName))
2760 continue;
2761 auto *AliasF = M.getFunction(AliasName);
2762 if (AliasF)
2763 Aliases.push_back(AliasF);
2764 }
2765
2766 if (Aliases.empty())
2767 continue;
2768
2769 for (unsigned I = 1; I != Aliases.size(); ++I) {
2770 auto *AliasF = Aliases[I];
2771 ExportedFunctions.erase(AliasF->getName());
2772 AliasesToCreate.push_back(
2773 {AliasF, std::string(Aliases[0]->getName())});
2774 }
2775 }
2776 }
2777 }
2778
2779 DenseMap<GlobalObject *, GlobalTypeMember *> GlobalTypeMembers;
2780 for (GlobalObject &GO : M.global_objects()) {
2782 continue;
2783
2784 Types.clear();
2785 GO.getMetadata(LLVMContext::MD_type, Types);
2786
2787 bool IsJumpTableCanonical = false;
2788 bool IsExported = false;
2789 if (Function *F = dyn_cast<Function>(&GO)) {
2790 IsJumpTableCanonical = isJumpTableCanonical(F);
2791 if (auto It = ExportedFunctions.find(F->getName());
2792 It != ExportedFunctions.end()) {
2793 IsJumpTableCanonical |=
2794 It->second.Linkage == CfiFunctionLinkage::Definition;
2795 IsExported = true;
2796 // TODO: The logic here checks only that the function is address taken,
2797 // not that the address takers are live. This can be updated to check
2798 // their liveness and emit fewer jumptable entries once monolithic LTO
2799 // builds also emit summaries.
2800 } else if (!F->hasAddressTaken()) {
2801 if (!CrossDsoCfi || !IsJumpTableCanonical || F->hasLocalLinkage())
2802 continue;
2803 }
2804
2805 // TODO: Pre-fill for full LTO.
2806 // if (!ExportSummary)
2807 // FunctionSummaryHotness[F] = getHotness(*F, PSI, BFIGetter);
2808 }
2809
2810 auto *GTM = GlobalTypeMember::create(Alloc, &GO, IsJumpTableCanonical,
2811 IsExported, Types);
2812 GlobalTypeMembers[&GO] = GTM;
2813 for (MDNode *Type : Types) {
2814 verifyTypeMDNode(&GO, Type);
2815 auto &Info = TypeIdInfo[Type->getOperand(1)];
2816 Info.UniqueId = ++CurUniqueId;
2817 Info.RefGlobals.push_back(GTM);
2818 }
2819 }
2820
2821 auto AddTypeIdUse = [&](Metadata *TypeId) -> TypeIdUserInfo & {
2822 // Add the call site to the list of call sites for this type identifier. We
2823 // also use TypeIdUsers to keep track of whether we have seen this type
2824 // identifier before. If we have, we don't need to re-add the referenced
2825 // globals to the equivalence class.
2826 auto Ins = TypeIdUsers.insert({TypeId, {}});
2827 if (Ins.second) {
2828 // Add the type identifier to the equivalence class.
2829 auto &GCI = GlobalClasses.insert(TypeId);
2830 GlobalClassesTy::member_iterator CurSet = GlobalClasses.findLeader(GCI);
2831
2832 // Add the referenced globals to the type identifier's equivalence class.
2833 for (GlobalTypeMember *GTM : TypeIdInfo[TypeId].RefGlobals)
2834 CurSet = GlobalClasses.unionSets(
2835 CurSet, GlobalClasses.findLeader(GlobalClasses.insert(GTM)));
2836 }
2837
2838 return Ins.first->second;
2839 };
2840
2841 if (TypeTestFunc) {
2842 for (const Use &U : TypeTestFunc->uses()) {
2843 auto CI = cast<CallInst>(U.getUser());
2844 // If this type test is only used by llvm.assume instructions, it
2845 // was used for whole program devirtualization, and is being kept
2846 // for use by other optimization passes. We do not need or want to
2847 // lower it here. We also don't want to rewrite any associated globals
2848 // unnecessarily. These will be removed by a subsequent LTT invocation
2849 // with the DropTypeTests flag set.
2850 bool OnlyAssumeUses = !CI->use_empty();
2851 for (const Use &CIU : CI->uses()) {
2852 if (isa<AssumeInst>(CIU.getUser()))
2853 continue;
2854 OnlyAssumeUses = false;
2855 break;
2856 }
2857 if (OnlyAssumeUses)
2858 continue;
2859
2860 auto TypeIdMDVal = dyn_cast<MetadataAsValue>(CI->getArgOperand(1));
2861 if (!TypeIdMDVal)
2862 report_fatal_error("Second argument of llvm.type.test must be metadata");
2863 auto TypeId = TypeIdMDVal->getMetadata();
2864 AddTypeIdUse(TypeId).CallSites.push_back(CI);
2865 }
2866 }
2867
2868 if (ICallBranchFunnelFunc) {
2869 for (const Use &U : ICallBranchFunnelFunc->uses()) {
2870 if (Arch != Triple::x86_64)
2872 "llvm.icall.branch.funnel not supported on this target");
2873
2874 auto CI = cast<CallInst>(U.getUser());
2875
2876 std::vector<GlobalTypeMember *> Targets;
2877 if (CI->arg_size() % 2 != 1)
2878 report_fatal_error("number of arguments should be odd");
2879
2880 GlobalClassesTy::member_iterator CurSet;
2881 for (unsigned I = 1; I != CI->arg_size(); I += 2) {
2882 int64_t Offset;
2884 CI->getOperand(I), Offset, M.getDataLayout()));
2885 if (!Base)
2887 "Expected branch funnel operand to be global value");
2888
2889 auto It = GlobalTypeMembers.find(Base);
2890 if (It == GlobalTypeMembers.end())
2891 reportFatalUsageError("Expected branch funnel operand to be a "
2892 "defined global value with type metadata");
2893 GlobalTypeMember *GTM = It->second;
2894 Targets.push_back(GTM);
2895 GlobalClassesTy::member_iterator NewSet =
2896 GlobalClasses.findLeader(GlobalClasses.insert(GTM));
2897 if (I == 1)
2898 CurSet = NewSet;
2899 else
2900 CurSet = GlobalClasses.unionSets(CurSet, NewSet);
2901 }
2902
2903 GlobalClasses.unionSets(
2904 CurSet, GlobalClasses.findLeader(
2905 GlobalClasses.insert(ICallBranchFunnel::create(
2906 Alloc, CI, Targets, ++CurUniqueId))));
2907 }
2908 }
2909
2910 if (ExportSummary) {
2911 DenseMap<GlobalValue::GUID, TinyPtrVector<Metadata *>> MetadataByGUID;
2912 for (auto &P : TypeIdInfo) {
2913 if (auto *TypeId = dyn_cast<MDString>(P.first))
2915 TypeId->getString())]
2916 .push_back(TypeId);
2917 }
2918
2919 for (auto &P : *ExportSummary) {
2920 for (auto &S : P.second.getSummaryList()) {
2921 if (!ExportSummary->isGlobalValueLive(S.get()))
2922 continue;
2923 if (auto *FS = dyn_cast<FunctionSummary>(S->getBaseObject()))
2924 for (GlobalValue::GUID G : FS->type_tests())
2925 for (Metadata *MD : MetadataByGUID[G])
2926 AddTypeIdUse(MD).IsExported = true;
2927 }
2928 }
2929 }
2930
2931 if (GlobalClasses.empty())
2932 return false;
2933
2934 {
2935 ScopedSaveAliaseesAndUsed S(M);
2936 // For each disjoint set we found...
2937 for (const auto &C : GlobalClasses) {
2938 if (!C->isLeader())
2939 continue;
2940
2941 ++NumTypeIdDisjointSets;
2942 // Build the list of type identifiers in this disjoint set.
2943 std::vector<Metadata *> TypeIds;
2944 std::vector<GlobalTypeMember *> Globals;
2945 std::vector<ICallBranchFunnel *> ICallBranchFunnels;
2946 for (auto M : GlobalClasses.members(*C)) {
2947 if (isa<Metadata *>(M))
2948 TypeIds.push_back(cast<Metadata *>(M));
2949 else if (isa<GlobalTypeMember *>(M))
2950 Globals.push_back(cast<GlobalTypeMember *>(M));
2951 else
2952 ICallBranchFunnels.push_back(cast<ICallBranchFunnel *>(M));
2953 }
2954
2955 // Order type identifiers by unique ID for determinism. This ordering is
2956 // stable as there is a one-to-one mapping between metadata and unique
2957 // IDs.
2958 llvm::sort(TypeIds, [&](Metadata *M1, Metadata *M2) {
2959 return TypeIdInfo[M1].UniqueId < TypeIdInfo[M2].UniqueId;
2960 });
2961
2962 // Same for the branch funnels.
2963 llvm::sort(ICallBranchFunnels,
2964 [&](ICallBranchFunnel *F1, ICallBranchFunnel *F2) {
2965 return F1->UniqueId < F2->UniqueId;
2966 });
2967
2968 // Build bitsets for this disjoint set.
2969 buildBitSetsFromDisjointSet(TypeIds, Globals, ICallBranchFunnels);
2970 }
2971 }
2972
2973 allocateByteArrays();
2974
2975 for (auto A : AliasesToCreate) {
2976 auto *Target = M.getNamedValue(A.TargetName);
2977 if (!isa<GlobalAlias>(Target))
2978 continue;
2979 auto *AliasGA = GlobalAlias::create("", Target);
2980 AliasGA->setVisibility(A.Alias->getVisibility());
2981 AliasGA->setLinkage(A.Alias->getLinkage());
2982 AliasGA->setDSOLocal(A.Alias->isDSOLocal());
2983 AliasGA->takeName(A.Alias);
2984 A.Alias->replaceAllUsesWith(AliasGA);
2985 A.Alias->eraseFromParent();
2986 }
2987
2988 // Emit .symver directives for exported functions, if they exist.
2989 if (ExportSummary) {
2990 if (NamedMDNode *SymversMD = M.getNamedMetadata("symvers")) {
2991 for (auto *Symver : SymversMD->operands()) {
2992 assert(Symver->getNumOperands() >= 2);
2993 StringRef SymbolName =
2994 cast<MDString>(Symver->getOperand(0))->getString();
2995 StringRef Alias = cast<MDString>(Symver->getOperand(1))->getString();
2996
2997 if (!ExportedFunctions.count(SymbolName))
2998 continue;
2999
3000 M.appendModuleInlineAsm(
3001 (llvm::Twine(".symver ") + SymbolName + ", " + Alias).str());
3002 }
3003 }
3004 }
3005
3006 return true;
3007}
3008
3011 bool Changed;
3012 if (UseCommandLine)
3013 Changed = LowerTypeTestsModule::runForTesting(M, AM);
3014 else
3015 Changed = LowerTypeTestsModule(M, AM, ExportSummary, ImportSummary).lower();
3016 if (!Changed)
3017 return PreservedAnalyses::all();
3018 return PreservedAnalyses::none();
3019}
3020
3022 raw_ostream &OS, function_ref<StringRef(StringRef)> MapClassName2PassName) {
3023 static_cast<PassInfoMixin<DropTypeTestsPass> *>(this)->printPipeline(
3024 OS, MapClassName2PassName);
3025 OS << '<';
3026 switch (Kind) {
3027 case DropTestKind::Assume:
3028 OS << "assume";
3029 break;
3030 case DropTestKind::All:
3031 OS << "all";
3032 break;
3033 }
3034 OS << '>';
3035}
3036
3041
3044 bool Changed = false;
3045 // Figure out whether inlining has exposed a constant address to a lowered
3046 // type test, and remove the test if so and the address is known to pass the
3047 // test. Unfortunately this pass ends up needing to reverse engineer what
3048 // LowerTypeTests did; this is currently inherent to the design of ThinLTO
3049 // importing where LowerTypeTests needs to run at the start.
3050 //
3051 // We look for things like:
3052 //
3053 // sub (i64 ptrtoint (ptr @_Z2fpv to i64), i64 ptrtoint (ptr
3054 // @__typeid__ZTSFvvE_global_addr to i64))
3055 //
3056 // which gets replaced with 0 if _Z2fpv (more specifically _Z2fpv.cfi, the
3057 // function referred to by the jump table) is a member of the type _ZTSFvv, as
3058 // well as things like
3059 //
3060 // icmp eq ptr @_Z2fpv, @__typeid__ZTSFvvE_global_addr
3061 //
3062 // which gets replaced with true if _Z2fpv is a member.
3063 for (auto &GV : M.globals()) {
3064 if (!GV.getName().starts_with("__typeid_") ||
3065 !GV.getName().ends_with("_global_addr"))
3066 continue;
3067 // __typeid_foo_global_addr -> foo
3068 auto *MD = MDString::get(M.getContext(),
3069 GV.getName().substr(9, GV.getName().size() - 21));
3070 auto MaySimplifyPtr = [&](Value *Ptr) {
3071 if (auto *GV = dyn_cast<GlobalValue>(Ptr))
3072 if (auto *CFIGV = M.getNamedValue((GV->getName() + ".cfi").str()))
3073 Ptr = CFIGV;
3074 return isKnownTypeIdMember(MD, M.getDataLayout(), Ptr, 0);
3075 };
3076 auto MaySimplifyInt = [&](Value *Op) {
3077 auto *PtrAsInt = dyn_cast<ConstantExpr>(Op);
3078 if (!PtrAsInt || PtrAsInt->getOpcode() != Instruction::PtrToInt)
3079 return false;
3080 return MaySimplifyPtr(PtrAsInt->getOperand(0));
3081 };
3082 for (User *U : make_early_inc_range(GV.users())) {
3083 if (auto *CI = dyn_cast<ICmpInst>(U)) {
3084 if (CI->getPredicate() == CmpInst::ICMP_EQ &&
3085 MaySimplifyPtr(CI->getOperand(0))) {
3086 // This is an equality comparison (TypeTestResolution::Single case in
3087 // lowerTypeTestCall). In this case we just replace the comparison
3088 // with true.
3089 CI->replaceAllUsesWith(ConstantInt::getTrue(M.getContext()));
3090 CI->eraseFromParent();
3091 Changed = true;
3092 continue;
3093 }
3094 }
3095 auto *CE = dyn_cast<ConstantExpr>(U);
3096 if (!CE || CE->getOpcode() != Instruction::PtrToInt)
3097 continue;
3098 for (Use &U : make_early_inc_range(CE->uses())) {
3099 auto *CE = dyn_cast<ConstantExpr>(U.getUser());
3100 if (U.getOperandNo() == 0 && CE &&
3101 CE->getOpcode() == Instruction::Sub &&
3102 MaySimplifyInt(CE->getOperand(1))) {
3103 // This is a computation of PtrOffset as generated by
3104 // LowerTypeTestsModule::lowerTypeTestCall above. If
3105 // isKnownTypeIdMember passes we just pretend it evaluated to 0. This
3106 // should cause later passes to remove the range and alignment checks.
3107 // The bitset checks won't be removed but those are uncommon.
3108 CE->replaceAllUsesWith(ConstantInt::get(CE->getType(), 0));
3109 Changed = true;
3110 }
3111 auto *CI = dyn_cast<ICmpInst>(U.getUser());
3112 if (U.getOperandNo() == 1 && CI &&
3113 CI->getPredicate() == CmpInst::ICMP_EQ &&
3114 MaySimplifyInt(CI->getOperand(0))) {
3115 // This is an equality comparison. Unlike in the case above it
3116 // remained as an integer compare.
3117 CI->replaceAllUsesWith(ConstantInt::getTrue(M.getContext()));
3118 CI->eraseFromParent();
3119 Changed = true;
3120 }
3121 }
3122 }
3123 }
3124
3125 if (!Changed)
3126 return PreservedAnalyses::all();
3130 PA.preserve<LoopAnalysis>();
3131 return PA;
3132}
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
uint64_t uint64_t
AMDGPU Register Bank Select
This file implements a class to represent arbitrary precision integral constant values and operations...
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
This file defines the BumpPtrAllocator interface.
This file contains the simple types necessary to represent the attributes associated with functions a...
bpf unwind lower
static GCRegistry::Add< ShadowStackGC > C("shadow-stack", "Very portable GC for uncooperative code generators")
static GCRegistry::Add< ErlangGC > A("erlang", "erlang-compatible garbage collector")
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
This file contains the declarations for the subclasses of Constant, which represent the different fla...
DXIL Finalize Linkage
dxil translate DXIL Translate Metadata
This file defines the DenseMap class.
Generic implementation of equivalence classes through the use Tarjan's efficient union-find algorithm...
This file provides a collection of function (or more generally, callable) type erasure utilities supp...
#define DEBUG_TYPE
Hexagon Common GEP
Module.h This file contains the declarations for the Module class.
This header defines various interfaces for pass management in LLVM.
This defines the Use class.
static const unsigned kARMJumpTableEntrySize
static const unsigned kLOONGARCH64JumpTableEntrySize
static bool isKnownTypeIdMember(Metadata *TypeId, const DataLayout &DL, Value *V, uint64_t COffset)
static const unsigned kX86IBTJumpTableEntrySize
static SmallVector< DILocation * > createJumpTableDebugInfo(Function *F, ArrayRef< GlobalTypeMember * > Functions)
static ConstantInt * extractNumericTypeId(MDNode &MD)
Extracts a numeric type identifier from an MDNode containing type metadata.
static const unsigned kRISCVJumpTableEntrySize
static auto buildBitSets(ArrayRef< Metadata * > TypeIds, const DenseMap< GlobalTypeMember *, uint64_t > &GlobalLayout)
static void dropTypeTests(Module &M, Function &TypeTestFunc, bool ShouldDropAll)
static Value * createMaskedBitTest(IRBuilder<> &B, Value *Bits, Value *BitOffset)
Build a test that bit BitOffset mod sizeof(Bits)*8 is set in Bits.
static bool isThumbFunction(Function *F, Triple::ArchType ModuleArch)
static const unsigned kX86JumpTableEntrySize
static void createCfiSymversMetadata(Module &DestM, const Module &SrcM)
static const unsigned kARMBTIJumpTableEntrySize
static CfiFunctionLinkage decodeCfiFunctionLinkage(uint8_t Encoded)
static void createCfiFunctionsMetadata(Module &DestM, ArrayRef< GlobalValue * > CfiFunctions, ProfileSummaryInfo &PSI, function_ref< const BlockFrequencyInfo &(Function &)> BFIGetter)
static BitSetInfo buildBitSet(ArrayRef< uint64_t > Offsets)
Build a bit set for list of offsets.
static const unsigned kARMv6MJumpTableEntrySize
static uint8_t encodeCfiFunctionLinkage(CfiFunctionLinkage Linkage, CfiFunctionHotness Hotness)
static CfiFunctionHotness decodeCfiFunctionHotness(uint8_t Encoded)
static const unsigned kHexagonJumpTableEntrySize
static void createCfiAliasesMetadata(Module &DestM, const Module &SrcM)
#define F(x, y, z)
Definition MD5.cpp:54
#define I(x, y, z)
Definition MD5.cpp:57
#define G(x, y, z)
Definition MD5.cpp:55
Machine Check Debug Module
This file implements a map that provides insertion order iteration.
This file contains the declarations for metadata subclasses.
#define T
ModuleSummaryIndex.h This file contains the declarations the classes that hold the module index and s...
#define P(N)
FunctionAnalysisManager FAM
This file defines the PointerUnion class, which is a discriminated union of pointer types.
This file contains the declarations for profiling metadata utility functions.
static StringRef getName(Value *V)
This file contains some templates that are useful if you are working with the STL at all.
This file implements a set that has insertion order iteration characteristics.
This file defines the SmallVector class.
This file defines the 'Statistic' class, which is designed to be an easy way to expose various metric...
#define STATISTIC(VARNAME, DESC)
Definition Statistic.h:171
#define LLVM_DEBUG(...)
Definition Debug.h:119
This pass exposes codegen information to IR-level passes.
This header defines support for implementing classes that have some trailing object (or arrays of obj...
static bool isDirectCall(const MCInst &Inst)
Class for arbitrary precision integers.
Definition APInt.h:78
uint64_t getZExtValue() const
Get zero extended value.
Definition APInt.h:1560
PassT::Result & getResult(IRUnitT &IR, ExtraArgTs... ExtraArgs)
Get the result of an analysis pass for a given IR unit.
Represent a constant reference to an array (0 or more elements consecutively in memory),...
Definition ArrayRef.h:40
size_t size() const
Get the array size.
Definition ArrayRef.h:141
bool empty() const
Check if the array is empty.
Definition ArrayRef.h:136
static LLVM_ABI ArrayType * get(Type *ElementType, uint64_t NumElements)
This static method is the primary way to construct an ArrayType.
Functions, function parameters, and return types can have attributes to indicate how they should be t...
Definition Attributes.h:106
LLVM_ABI StringRef getValueAsString() const
Return the attribute's value as a string.
bool isValid() const
Return true if the attribute is any kind of attribute.
Definition Attributes.h:262
LLVM_ABI BasicBlock * splitBasicBlock(iterator I, const Twine &BBName="")
Split the basic block into two basic blocks at the specified instruction.
static BasicBlock * Create(LLVMContext &Context, const Twine &Name="", Function *Parent=nullptr, BasicBlock *InsertBefore=nullptr)
Creates a new BasicBlock.
Definition BasicBlock.h:206
const Instruction * getTerminator() const LLVM_READONLY
Returns the terminator instruction; assumes that the block is well-formed.
Definition BasicBlock.h:237
BlockFrequencyInfo pass uses BlockFrequencyInfoImpl implementation to estimate IR basic block frequen...
Value * getArgOperand(unsigned i) const
unsigned arg_size() const
void addSymbolWithThinLTOGUID(StringRef Name, GlobalValue::GUID GUID)
Add the function name and the GUID that ThinLTO uses for it.
bool contains(StringRef Name) const
@ ICMP_NE
not equal
Definition InstrTypes.h:762
static CondBrInst * Create(Value *Cond, BasicBlock *IfTrue, BasicBlock *IfFalse, InsertPosition InsertBefore=nullptr)
static LLVM_ABI ConstantAggregateZero * get(Type *Ty)
ConstantArray - Constant Array Declarations.
Definition Constants.h:590
static ConstantAsMetadata * get(Constant *C)
Definition Metadata.h:548
static Constant * get(LLVMContext &Context, ArrayRef< ElementTy > Elts)
get() constructor - Return a constant with array type with an element count and element type matching...
Definition Constants.h:878
static LLVM_ABI Constant * getIntToPtr(Constant *C, Type *Ty, bool OnlyIfReduced=false)
static LLVM_ABI Constant * getPointerCast(Constant *C, Type *Ty)
Create a BitCast, AddrSpaceCast, or a PtrToInt cast constant expression.
static LLVM_SUPPRESS_DEPRECATED_DECLARATIONS_POP Constant * getInBoundsPtrAdd(Constant *Ptr, Constant *Offset)
Create a getelementptr inbounds i8, ptr, offset constant expression.
Definition Constants.h:1550
static Constant * getPtrAdd(Constant *Ptr, Constant *Offset, GEPNoWrapFlags NW=GEPNoWrapFlags::none(), std::optional< ConstantRange > InRange=std::nullopt, Type *OnlyIfReduced=nullptr)
Create a getelementptr i8, ptr, offset constant expression.
Definition Constants.h:1518
static LLVM_ABI Constant * getPtrToInt(Constant *C, Type *Ty, bool OnlyIfReduced=false)
static LLVM_SUPPRESS_DEPRECATED_DECLARATIONS_PUSH Constant * getGetElementPtr(Type *Ty, Constant *C, ArrayRef< Constant * > IdxList, GEPNoWrapFlags NW=GEPNoWrapFlags::none(), std::optional< ConstantRange > InRange=std::nullopt, Type *OnlyIfReducedTy=nullptr)
Getelementptr form.
Definition Constants.h:1477
This is the shared class of boolean and integer constants.
Definition Constants.h:87
static LLVM_ABI ConstantInt * getTrue(LLVMContext &Context)
static LLVM_ABI ConstantInt * getFalse(LLVMContext &Context)
static LLVM_ABI ConstantPointerNull * get(PointerType *T)
Static factory methods - Return objects of the specified value.
static Constant * getAnon(ArrayRef< Constant * > V, bool Packed=false)
Return an anonymous struct that has the specified elements.
Definition Constants.h:643
static LLVM_ABI Constant * getNullValue(Type *Ty)
Constructor to create a '0' constant of arbitrary type.
LLVM_ABI void finalize()
Construct any deferred debug info descriptors.
Definition DIBuilder.cpp:73
LLVM_ABI DISubroutineType * createSubroutineType(DITypeArray ParameterTypes, DINode::DIFlags Flags=DINode::FlagZero, unsigned CC=0)
Create subroutine type.
LLVM_ABI DISubprogram * createFunction(DIScope *Scope, StringRef Name, StringRef LinkageName, DIFile *File, unsigned LineNo, DISubroutineType *Ty, unsigned ScopeLine, DINode::DIFlags Flags=DINode::FlagZero, DISubprogram::DISPFlags SPFlags=DISubprogram::SPFlagZero, DITemplateParameterArray TParams=nullptr, DISubprogram *Decl=nullptr, DITypeArray ThrownTypes=nullptr, DINodeArray Annotations=nullptr, StringRef TargetFuncName="", bool UseKeyInstructions=false)
Create a new descriptor for the specified subprogram.
LLVM_ABI DICompileUnit * createCompileUnit(DISourceLanguageName Lang, DIFile *File, StringRef Producer, bool isOptimized, StringRef Flags, unsigned RV, StringRef SplitName=StringRef(), DICompileUnit::DebugEmissionKind Kind=DICompileUnit::DebugEmissionKind::FullDebug, uint64_t DWOId=0, bool SplitDebugInlining=true, bool DebugInfoForProfiling=false, DICompileUnit::DebugNameTableKind NameTableKind=DICompileUnit::DebugNameTableKind::Default, bool RangesBaseAddress=false, StringRef SysRoot={}, StringRef SDK={})
A CompileUnit provides an anchor for all debugging information generated during this instance of comp...
LLVM_ABI DIFile * createFile(StringRef Filename, StringRef Directory, std::optional< DIFile::ChecksumInfo< StringRef > > Checksum=std::nullopt, std::optional< StringRef > Source=std::nullopt)
Create a file descriptor to hold debugging information for a file.
Wrapper structure that holds source language identity metadata that includes language name,...
Subprogram description. Uses SubclassData1.
Type array for a subprogram.
A parsed version of the target data layout string in and methods for querying it.
Definition DataLayout.h:64
bool empty() const
Definition DenseMap.h:716
iterator find(const_arg_type_t< KeyT > Val)
Definition DenseMap.h:766
iterator end()
Definition DenseMap.h:686
ValueT lookup(const_arg_type_t< KeyT > Val) const
Return the entry for the specified key, or a default constructed value if no such entry exists.
Definition DenseMap.h:793
std::pair< iterator, bool > insert(const std::pair< KeyT, ValueT > &KV)
Definition DenseMap.h:827
Analysis pass which computes a DominatorTree.
Definition Dominators.h:241
LLVM_ABI PreservedAnalyses run(Module &M, ModuleAnalysisManager &AM)
LLVM_ABI void printPipeline(raw_ostream &OS, function_ref< StringRef(StringRef)> MapClassName2PassName)
static LLVM_ABI FunctionType * get(Type *Result, ArrayRef< Type * > Params, bool isVarArg)
This static method is the primary way of constructing a FunctionType.
static Function * Create(FunctionType *Ty, LinkageTypes Linkage, unsigned AddrSpace, const Twine &N="", Module *M=nullptr)
Definition Function.h:169
const BasicBlock & getEntryBlock() const
Definition Function.h:794
void eraseFromParent()
eraseFromParent - This method unlinks 'this' from the containing module and deletes it.
Definition Function.cpp:451
static GEPNoWrapFlags inBounds()
static LLVM_ABI GlobalAlias * create(Type *Ty, unsigned AddressSpace, LinkageTypes Linkage, const Twine &Name, Constant *Aliasee, Module *Parent)
If a parent module is specified, the alias is automatically inserted into the end of the specified mo...
Definition Globals.cpp:692
LLVM_ABI void setMetadata(unsigned KindID, MDNode *Node)
Set a particular kind of metadata attachment.
bool hasMetadata() const
Return true if this GlobalObject has any metadata attached to it.
LLVM_ABI void setComdat(Comdat *C)
Definition Globals.cpp:287
LLVM_ABI void setSection(StringRef S)
Change the section for this global.
Definition Globals.cpp:348
const Comdat * getComdat() const
LLVM_ABI bool eraseMetadata(unsigned KindID)
Erase all metadata attachments with the given kind.
MDNode * getMetadata(unsigned KindID) const
Get the metadata of given kind attached to this GlobalObject.
bool hasSection() const
Check if this global has a custom object file section.
static LLVM_ABI GUID getGUIDAssumingExternalLinkage(StringRef GlobalName)
Return a 64-bit global unique ID constructed from the name of a global symbol.
Definition Globals.cpp:80
bool isDSOLocal() const
bool isThreadLocal() const
If the value is "Thread Local", its value isn't shared by the threads.
VisibilityTypes getVisibility() const
static bool isLocalLinkage(LinkageTypes Linkage)
LinkageTypes getLinkage() const
uint64_t GUID
Declare a type to represent a global unique identifier for a global value.
bool isDeclarationForLinker() const
void setDSOLocal(bool Local)
PointerType * getType() const
Global values are always pointers.
VisibilityTypes
An enumeration for the kinds of visibility of global values.
Definition GlobalValue.h:67
@ HiddenVisibility
The GV is hidden.
Definition GlobalValue.h:69
void setVisibility(VisibilityTypes V)
LinkageTypes
An enumeration for the kinds of linkage for global values.
Definition GlobalValue.h:52
@ PrivateLinkage
Like Internal, but omit from symbol table.
Definition GlobalValue.h:61
@ InternalLinkage
Rename collisions when linking (static functions).
Definition GlobalValue.h:60
@ ExternalLinkage
Externally visible function.
Definition GlobalValue.h:53
@ ExternalWeakLinkage
ExternalWeak linkage description.
Definition GlobalValue.h:62
Type * getValueType() const
const Constant * getInitializer() const
getInitializer - Return the initializer for this global variable.
LLVM_ABI void setInitializer(Constant *InitVal)
setInitializer - Sets the initializer for this global variable, removing any existing initializer if ...
Definition Globals.cpp:613
bool hasInitializer() const
Definitions have initializers, declarations don't.
MaybeAlign getAlign() const
Returns the alignment of the given variable.
void setConstant(bool Val)
LLVM_ABI void setCodeModel(CodeModel::Model CM)
Change the code model for this global.
Definition Globals.cpp:660
LLVM_ABI void eraseFromParent()
eraseFromParent - This method unlinks 'this' from the containing module and deletes it.
Definition Globals.cpp:609
LLVM_ABI CallInst * CreateIntrinsicWithoutFolding(Intrinsic::ID ID, ArrayRef< Type * > OverloadTypes, ArrayRef< Value * > Args, FMFSource FMFSource={}, const Twine &Name="", ArrayRef< OperandBundleDef > OpBundles={})
Create a call to intrinsic ID with Args, mangled using OverloadTypes.
Value * CreateInsertValue(Value *Agg, Value *Val, ArrayRef< unsigned > Idxs, const Twine &Name="")
Definition IRBuilder.h:2763
Value * CreatePtrAddWithSExtOrTrunc(Value *Ptr, Value *Offset, const Twine &Name="", GEPNoWrapFlags NW=GEPNoWrapFlags::none())
Create a ptradd where the offset is sign-extended or truncated to the index type.
Definition IRBuilder.h:2128
LoadInst * CreateLoad(Type *Ty, Value *Ptr, const char *Name)
Provided to resolve 'CreateLoad(Ty, Ptr, "...")' correctly, instead of converting the string to 'bool...
Definition IRBuilder.h:1907
This provides a uniform API for creating instructions and inserting them into a basic block: either a...
Definition IRBuilder.h:2949
static LLVM_ABI InlineAsm * get(FunctionType *Ty, StringRef AsmString, StringRef Constraints, bool hasSideEffects, bool isAlignStack=false, AsmDialect asmDialect=AD_ATT, bool canThrow=false)
InlineAsm::get - Return the specified uniqued inline asm string.
Definition InlineAsm.cpp:43
LLVM_ABI InstListType::iterator eraseFromParent()
This method unlinks 'this' from the containing basic block and deletes it.
iterator_range< user_iterator > users()
LLVM_ABI void setMetadata(unsigned KindID, MDNode *Node)
Set the metadata of the specified kind to the specified node.
user_iterator user_begin()
Analysis pass that exposes the LoopInfo for a function.
Definition LoopInfo.h:594
LLVM_ABI PreservedAnalyses run(Module &M, ModuleAnalysisManager &AM)
Metadata node.
Definition Metadata.h:1081
const MDOperand & getOperand(unsigned I) const
Definition Metadata.h:1437
static MDTuple * get(LLVMContext &Context, ArrayRef< Metadata * > MDs)
Definition Metadata.h:1579
unsigned getNumOperands() const
Return number of MDNode operands.
Definition Metadata.h:1443
Metadata * get() const
Definition Metadata.h:931
static LLVM_ABI MDString * get(LLVMContext &Context, StringRef Str)
Definition Metadata.cpp:595
static MDTuple * get(LLVMContext &Context, ArrayRef< Metadata * > MDs)
Definition Metadata.h:1525
This class implements a map that also provides access to all stored values in a deterministic order.
Definition MapVector.h:39
bool empty() const
Definition MapVector.h:80
std::pair< iterator, bool > insert(const std::pair< KeyT, ValueT > &KV)
Definition MapVector.h:127
static ErrorOr< std::unique_ptr< MemoryBuffer > > getFile(const Twine &Filename, bool IsText=false, bool RequiresNullTerminator=true, bool IsVolatile=false, std::optional< Align > Alignment=std::nullopt)
Open the specified file as a MemoryBuffer, returning a new MemoryBuffer if successful,...
Root of the metadata hierarchy.
Definition Metadata.h:64
TypeIdSummary & getOrInsertTypeIdSummary(StringRef TypeId)
Return an existing or new TypeIdSummary entry for TypeId.
const TypeIdSummary * getTypeIdSummary(StringRef TypeId) const
This returns either a pointer to the type id summary (if present in the summary map) or null (if not ...
CfiFunctionIndex & cfiFunctionDecls()
CfiFunctionIndex & cfiFunctionDefs()
static LLVM_ABI void CollectAsmSymvers(const Module &M, function_ref< void(StringRef, StringRef)> AsmSymver)
Parse inline ASM and collect the symvers directives that are defined in the current module.
A Module instance is used to store all the information related to an LLVM module.
Definition Module.h:68
LLVMContext & getContext() const
Get the global data context.
Definition Module.h:332
Function * getFunction(StringRef Name) const
Look up the specified function in the module symbol table.
Definition Module.cpp:235
iterator_range< alias_iterator > aliases()
Definition Module.h:853
NamedMDNode * getOrInsertNamedMetadata(StringRef Name)
Return the named MDNode in the module with the specified name.
Definition Module.cpp:308
A tuple of MDNodes.
Definition Metadata.h:1797
iterator_range< op_iterator > operands()
Definition Metadata.h:1893
LLVM_ABI void addOperand(MDNode *M)
static PointerType * getUnqual(LLVMContext &C)
This constructs an opaque pointer to an object in the default address space (address space zero).
unsigned getAddressSpace() const
Return the address space of the Pointer type.
static LLVM_ABI PoisonValue * get(Type *T)
Static factory methods - Return an 'poison' object of the specified type.
Analysis pass which computes a PostDominatorTree.
A set of analyses that are preserved following a run of a transformation pass.
Definition Analysis.h:112
static PreservedAnalyses none()
Convenience factory function for the empty preserved set.
Definition Analysis.h:115
static PreservedAnalyses all()
Construct a special preserved set that preserves all passes.
Definition Analysis.h:118
PreservedAnalyses & preserve()
Mark an analysis as preserved.
Definition Analysis.h:132
Analysis providing profile information.
bool isFunctionColdInCallGraph(const FuncT *F, BFIT &BFI) const
Returns true if F contains only cold code.
LLVM_ABI bool isFunctionHotnessUnknown(const Function &F) const
Returns true if the hotness of F is unknown.
bool isFunctionHotInCallGraph(const FuncT *F, BFIT &BFI) const
Returns true if F contains hot code.
LLVM_ABI bool hasPartialSampleProfile() const
Returns true if module M has partial-profile sample profile.
static ReturnInst * Create(LLVMContext &C, Value *retVal=nullptr, InsertPosition InsertBefore=nullptr)
LLVM_ABI void print(const char *ProgName, raw_ostream &S, bool ShowColors=true, bool ShowKindLabel=true, bool ShowLocation=true) const
A vector that has set insertion semantics.
Definition SetVector.h:57
bool insert(const value_type &X)
Insert a new element into the SetVector.
Definition SetVector.h:157
LLVM_ABI PreservedAnalyses run(Module &M, ModuleAnalysisManager &AM)
reference emplace_back(ArgTypes &&... Args)
void reserve(size_type N)
iterator erase(const_iterator CI)
void resize(size_type N)
void push_back(const T &Elt)
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
Represent a constant reference to a string, i.e.
Definition StringRef.h:56
std::pair< StringRef, StringRef > split(char Separator) const
Split into two substrings around the first occurrence of a separator character.
Definition StringRef.h:736
bool consume_back(StringRef Suffix)
Returns true if this StringRef has the given suffix and removes that suffix.
Definition StringRef.h:691
std::string str() const
Get the contents as an std::string.
Definition StringRef.h:222
constexpr StringRef substr(size_t Start, size_t N=npos) const
Return a reference to the substring from [Start, Start + N).
Definition StringRef.h:597
bool starts_with(StringRef Prefix) const
Check if this string starts with the given Prefix.
Definition StringRef.h:258
constexpr bool empty() const
Check if the string is empty.
Definition StringRef.h:141
constexpr size_t size() const
Get the string size.
Definition StringRef.h:144
bool ends_with(StringRef Suffix) const
Check if this string ends with the given Suffix.
Definition StringRef.h:270
Type * getElementType(unsigned N) const
Analysis pass providing the TargetTransformInfo.
See the file comment for details on the usage of the TrailingObjects type.
Triple - Helper class for working with autoconf configuration names.
Definition Triple.h:48
@ loongarch64
Definition Triple.h:66
The instances of the Type class are immutable: once they are created, they are never changed.
Definition Type.h:46
static LLVM_ABI IntegerType * getInt64Ty(LLVMContext &C)
Definition Type.cpp:300
static LLVM_ABI Type * getVoidTy(LLVMContext &C)
Definition Type.cpp:272
static LLVM_ABI IntegerType * getInt8Ty(LLVMContext &C)
Definition Type.cpp:297
A Use represents the edge between a Value definition and its users.
Definition Use.h:35
op_range operands()
Definition User.h:267
Value * getOperand(unsigned i) const
Definition User.h:207
LLVM Value Representation.
Definition Value.h:75
Type * getType() const
All values are typed, get the type of this value.
Definition Value.h:257
bool hasOneUse() const
Return true if there is exactly one use of this value.
Definition Value.h:441
LLVM_ABI void replaceAllUsesWith(Value *V)
Change all uses of this to point to a new Value.
Definition Value.cpp:548
iterator_range< user_iterator > users()
Definition Value.h:428
use_iterator use_begin()
Definition Value.h:366
bool use_empty() const
Definition Value.h:348
LLVM_ABI bool replaceUsesWithIf(Value *New, llvm::function_ref< bool(Use &U)> ShouldReplace)
Go through the uses list for this definition and make each use point to "V" if the callback ShouldRep...
Definition Value.cpp:556
iterator_range< use_iterator > uses()
Definition Value.h:382
bool hasName() const
Definition Value.h:263
LLVM_ABI StringRef getName() const
Return a constant reference to the value's name.
Definition Value.cpp:314
LLVM_ABI void takeName(Value *V)
Transfer the name from V to this value.
Definition Value.cpp:395
std::pair< iterator, bool > insert(const ValueT &V)
Definition DenseSet.h:210
bool contains(const_arg_type_t< ValueT > V) const
Check if the set contains the given element.
Definition DenseSet.h:183
void insert_range(Range &&R)
Definition DenseSet.h:236
size_type count(const_arg_type_t< ValueT > V) const
Return 1 if the specified key is in the set, 0 otherwise.
Definition DenseSet.h:188
An efficient, type-erasing, non-owning reference to a callable.
const ParentTy * getParent() const
Definition ilist_node.h:34
self_iterator getIterator()
Definition ilist_node.h:123
NodeTy * getNextNode()
Get the next node, or nullptr for the list tail.
Definition ilist_node.h:348
This class implements a layout algorithm for globals referenced by bit sets that tries to keep member...
LLVM_ABI const std::vector< uint64_t > & build()
Flatten fragments into a single layout and return it.
LLVM_ABI void addFragment(const std::set< uint64_t > &F)
Add F to the layout while trying to keep its indices contiguous.
This class implements an extremely fast bulk output stream that can only output to a stream.
Definition raw_ostream.h:53
CallInst * Call
constexpr char Align[]
Key for Kernel::Arg::Metadata::mAlign.
constexpr char SymbolName[]
Key for Kernel::Metadata::mSymbolName.
constexpr std::underlying_type_t< E > Mask()
Get a bitmask with 1s in all places up to the high-order bit of E's largest value.
@ BasicBlock
Various leaf nodes.
Definition ISDOpcodes.h:83
LLVM_ABI Function * getDeclarationIfExists(const Module *M, ID id)
Look up the Function declaration of the intrinsic id in the Module M and return it if it exists.
LLVM_ABI SetVector< uint64_t > findCfiTypeIds(const Module &M)
Finds all 64-bit numeric type identifiers in M used for cross-DSO CFI.
LLVM_ABI bool cleanUpTypeCheckedLoad(Module &M, Function &CheckedLoadFn, bool IsRelative)
Lower @llvm.type.checked.load[.relative] calls to the guarded load with the check assumed true,...
LLVM_ABI void createCfiMetadata(Module &DestM, const Module &SrcM, ArrayRef< GlobalValue * > CfiFunctions, ProfileSummaryInfo &PSI, function_ref< const BlockFrequencyInfo &(Function &)> BFIGetter)
Creates cfi.functions, aliases, and symvers named metadata in DestM for CFI functions in CfiFunctions...
LLVM_ABI bool isJumpTableCanonical(Function *F)
LLVM_ABI bool hasTypeMetadata(const GlobalObject &GO)
Returns whether a global or its associated global has attached type metadata.
LLVM_ABI SetVector< GlobalValue * > findCfiFunctions(Module &M)
Finds all functions and aliases in M that may need CFI jump table entries.
std::enable_if_t< detail::IsValidPointer< X, Y >::value, X * > extract_or_null(Y &&MD)
Extract a Value from Metadata, allowing null.
Definition Metadata.h:694
SmallVector< unsigned char, 0 > ByteArray
Definition PropertySet.h:25
NodeAddr< PhiNode * > Phi
Definition RDFGraph.h:390
NodeAddr< UseNode * > Use
Definition RDFGraph.h:385
@ OF_TextWithCRLF
The file should be opened in text mode and use a carriage linefeed '\r '.
Definition FileSystem.h:802
This is an optimization pass for GlobalISel generic memory operations.
LLVM_ABI void ReplaceInstWithInst(BasicBlock *BB, BasicBlock::iterator &BI, Instruction *I)
Replace the instruction specified by BI with the instruction specified by I.
@ Offset
Definition DWP.cpp:577
bool operator<(int64_t V1, const APSInt &V2)
Definition APSInt.h:360
void stable_sort(R &&Range)
Definition STLExtras.h:2132
bool all_of(R &&range, UnaryPredicate P)
Provide wrappers to std::all_of which take ranges instead of having to pass begin/end explicitly.
Definition STLExtras.h:1755
detail::zip_longest_range< T, U, Args... > zip_longest(T &&t, U &&u, Args &&... args)
Iterate over two or more iterators at the same time.
Definition STLExtras.h:997
@ Unknown
Not known to have no common set bits.
LLVM_ABI void setExplicitlyUnknownBranchWeightsIfProfiled(Instruction &I, StringRef PassName, const Function *F=nullptr)
Like setExplicitlyUnknownBranchWeights(...), but only sets unknown branch weights in the new instruct...
decltype(auto) dyn_cast(const From &Val)
dyn_cast<X> - Return the argument parameter cast to the specified type.
Definition Casting.h:643
@ Load
The value being inserted comes from a load (InsertElement only).
PassSummaryAction
What to do with the summary when running passes that operate on it.
Definition IPO.h:37
void append_range(Container &C, Range &&R)
Wrapper function to append range R to container C.
Definition STLExtras.h:2224
Value * GetPointerBaseWithConstantOffset(Value *Ptr, int64_t &Offset, const DataLayout &DL, bool AllowNonInbounds=true)
Analyze the specified pointer to see if it can be expressed as a base pointer plus a constant offset.
iterator_range< early_inc_iterator_impl< detail::IterOfRange< RangeT > > > make_early_inc_range(RangeT &&Range)
Make a range that does early increment to allow mutation of the underlying range without disrupting i...
Definition STLExtras.h:649
InnerAnalysisManagerProxy< FunctionAnalysisManager, Module > FunctionAnalysisManagerModuleProxy
Provide the FunctionAnalysisManager to Module proxy.
@ O1
Optimize quickly without destroying debuggability.
@ O2
Optimize for fast execution as much as possible without triggering significant incremental compile ti...
bool operator==(const AddressRangeValuePair &LHS, const AddressRangeValuePair &RHS)
RelativeUniformCounterPtr ValuesPtrExpr VTableAddr Value
Definition InstrProf.h:143
int countr_zero(T Val)
Count number of 0's from the least significant bit to the most stopping at the first 1.
Definition bit.h:204
unsigned M1(unsigned Val)
Definition VE.h:394
auto make_isa_range(RangeT &&Range)
Return a range over Range containing only elements for which isa<T> holds, casting each of them to T.
Definition STLExtras.h:567
auto dyn_cast_or_null(const Y &Val)
Definition Casting.h:753
LLVM_ABI bool convertUsersOfConstantsToInstructions(ArrayRef< Constant * > Consts, Function *RestrictToFunc=nullptr, bool RemoveDeadConstants=true, bool IncludeSelf=false)
Replace constant expressions users of the given constants with instructions.
const IPOOptions & getIPOOptions(const LLVMContext &C)
Definition IPOOptions.h:33
void sort(IteratorTy Start, IteratorTy End)
Definition STLExtras.h:1652
LLVM_ABI raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
Definition Debug.cpp:209
IRBuilder(LLVMContext &, FolderTy, InserterTy) -> IRBuilder< FolderTy, InserterTy >
LLVM_ABI void report_fatal_error(Error Err, bool gen_crash_diag=true)
Definition Error.cpp:163
constexpr uint64_t alignTo(uint64_t Size, Align A)
Returns a multiple of A needed to store Size bytes.
Definition Alignment.h:149
class LLVM_GSL_OWNER SmallVector
Forward declaration of SmallVector so that calculateSmallVectorDefaultInlinedElements can reference s...
bool isa(const From &Val)
isa<X> - Return true if the parameter to the template is an instance of one of the template type argu...
Definition Casting.h:547
LLVM_ABI raw_fd_ostream & errs()
This returns a reference to a raw_ostream for standard error.
@ Ref
The access may reference the value stored in memory.
Definition ModRef.h:32
@ Other
Any other memory.
Definition ModRef.h:68
TargetTransformInfo TTI
LLVM_ABI void appendToCompilerUsed(Module &M, ArrayRef< GlobalValue * > Values)
Adds global values to the llvm.compiler.used list.
IntPtrTy
Definition InstrProf.h:82
DWARFExpression::Operation Op
Expected< T > errorOrToExpected(ErrorOr< T > &&EO)
Convert an ErrorOr<T> to an Expected<T>.
Definition Error.h:1261
ArrayRef(const T &OneElt) -> ArrayRef< T >
OutputIt copy(R &&Range, OutputIt Out)
Definition STLExtras.h:1901
constexpr unsigned BitWidth
LLVM_ABI void appendToGlobalCtors(Module &M, Function *F, int Priority, Constant *Data=nullptr)
Append F to the list of global ctors of module M with the given Priority.
decltype(auto) cast(const From &Val)
cast<X> - Return the argument parameter cast to the specified type.
Definition Casting.h:559
void erase_if(Container &C, UnaryPredicate P)
Provide a container algorithm similar to C++ Library Fundamentals v2's erase_if which is equivalent t...
Definition STLExtras.h:2208
LLVM_ABI Error errorCodeToError(std::error_code EC)
Helper for converting an std::error_code to a Error.
Definition Error.cpp:107
LLVM_ABI Instruction * SplitBlockAndInsertIfThen(Value *Cond, BasicBlock::iterator SplitBefore, bool Unreachable, MDNode *BranchWeights=nullptr, DomTreeUpdater *DTU=nullptr, LoopInfo *LI=nullptr, BasicBlock *ThenBlock=nullptr)
Split the containing block at the specified instruction - everything before SplitBefore stays in the ...
BumpPtrAllocatorImpl<> BumpPtrAllocator
The standard BumpPtrAllocator which just uses the default template parameters.
Definition Allocator.h:391
LLVM_ABI void appendToUsed(Module &M, ArrayRef< GlobalValue * > Values)
Adds global values to the llvm.used list.
LLVM_ABI std::unique_ptr< ModuleSummaryIndex > parseSummaryIndexAssembly(MemoryBufferRef F, SMDiagnostic &Err)
Parse LLVM Assembly for summary index from a MemoryBuffer.
Definition Parser.cpp:168
AnalysisManager< Module > ModuleAnalysisManager
Convenience typedef for the Module analysis manager.
Definition MIRParser.h:39
constexpr uint64_t NextPowerOf2(uint64_t A)
Returns the next power of two (in 64-bits) that is strictly greater than A.
Definition MathExtras.h:368
LLVM_ABI GlobalVariable * collectUsedGlobalVariables(const Module &M, SmallVectorImpl< GlobalValue * > &Vec, bool CompilerUsed)
Given "llvm.used" or "llvm.compiler.used" as a global name, collect the initializer elements of that ...
Definition Module.cpp:966
LLVM_ABI void reportFatalUsageError(Error Err)
Report a fatal error that does not indicate a bug in LLVM.
Definition Error.cpp:177
TypeTestResolution TTRes
Kind
Specifies which kind of type check we should emit for this byte array.
@ Unknown
Unknown (analysis not performed, don't lower)
@ Single
Single element (last example in "Short Inline Bit Vectors")
@ Inline
Inlined bit vector ("Short Inline Bit Vectors")
@ Unsat
Unsatisfiable type (i.e. no global has this type metadata)
@ AllOnes
All-ones bit vector ("Eliminating Bit Vector Checks for All-Ones Bit Vectors")
@ ByteArray
Test a byte array (first example)
unsigned SizeM1BitWidth
Range of size-1 expressed as a bit width.
enum llvm::TypeTestResolution::Kind TheKind
SmallVector< uint64_t, 16 > Offsets
LLVM_ABI bool containsGlobalOffset(uint64_t Offset) const
LLVM_ABI void print(raw_ostream &OS) const
This class is used to build a byte array containing overlapping bit sets.
uint64_t BitAllocs[BitsPerByte]
The number of bytes allocated so far for each of the bits.
std::vector< uint8_t > Bytes
The byte array built so far.
LLVM_ABI void allocate(const std::set< uint64_t > &Bits, uint64_t BitSize, uint64_t &AllocByteOffset, uint8_t &AllocMask)
Allocate BitSize bits in the byte array where Bits contains the bits to set.