LLVM 23.0.0git
NVPTXMarkKernelPtrsGlobal.cpp
Go to the documentation of this file.
1//===-- NVPTXMarkKernelPtrsGlobal.cpp - Mark kernel pointers as global ----===//
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// For CUDA kernels, pointers loaded from byval parameters are known to be in
10// global address space. This pass inserts addrspacecast pairs to make that
11// explicit, enabling later address-space inference to propagate the global AS.
12// It also handles the pattern where a pointer is loaded as an integer and then
13// converted via inttoptr.
14//
15//===----------------------------------------------------------------------===//
16
17#include "NVPTX.h"
18#include "NVPTXUtilities.h"
23#include "llvm/Pass.h"
25
26using namespace llvm;
27using namespace NVPTXAS;
28
29static void markPointerAsAS(Value *Ptr, unsigned AS) {
31 return;
32
33 BasicBlock::iterator InsertPt;
34 if (auto *Arg = dyn_cast<Argument>(Ptr)) {
35 InsertPt = Arg->getParent()->getEntryBlock().begin();
36 } else {
37 InsertPt = ++cast<Instruction>(Ptr)->getIterator();
38 assert(InsertPt != InsertPt->getParent()->end() &&
39 "We don't call this function with Ptr being a terminator.");
40 }
41
42 Instruction *PtrInGlobal = new AddrSpaceCastInst(
43 Ptr, PointerType::get(Ptr->getContext(), AS), Ptr->getName(), InsertPt);
44 Value *PtrInGeneric = new AddrSpaceCastInst(PtrInGlobal, Ptr->getType(),
45 Ptr->getName(), InsertPt);
46 Ptr->replaceAllUsesWith(PtrInGeneric);
47 PtrInGlobal->setOperand(0, Ptr);
48}
49
53
54static void handleIntToPtr(Value &V) {
55 if (!all_of(V.users(), [](User *U) { return isa<IntToPtrInst>(U); }))
56 return;
57
58 SmallVector<User *, 16> UsersToUpdate(V.users());
59 for (User *U : UsersToUpdate)
61}
62
64 if (!isKernelFunction(F))
65 return false;
66
67 // Copying of byval aggregates + SROA may result in pointers being loaded as
68 // integers, followed by inttoptr. We mark those as global too, but only if
69 // the loaded integer is used exclusively for conversion to a pointer.
70 for (auto &I : instructions(F)) {
71 auto *LI = dyn_cast<LoadInst>(&I);
72 if (!LI)
73 continue;
74
75 if (LI->getType()->isPointerTy() || LI->getType()->isIntegerTy()) {
76 Value *UO = getUnderlyingObject(LI->getPointerOperand());
77 if (auto *Arg = dyn_cast<Argument>(UO)) {
78 if (Arg->hasByValAttr()) {
79 if (LI->getType()->isPointerTy())
81 else
82 handleIntToPtr(*LI);
83 }
84 }
85 }
86 }
87
88 for (Argument &Arg : F.args())
89 if (Arg.getType()->isIntegerTy())
90 handleIntToPtr(Arg);
91
92 return true;
93}
94
95namespace {
96
97class NVPTXMarkKernelPtrsGlobalLegacyPass : public FunctionPass {
98public:
99 static char ID;
100 NVPTXMarkKernelPtrsGlobalLegacyPass() : FunctionPass(ID) {}
101 bool runOnFunction(Function &F) override;
102};
103
104} // namespace
105
106INITIALIZE_PASS(NVPTXMarkKernelPtrsGlobalLegacyPass,
107 "nvptx-mark-kernel-ptrs-global",
108 "NVPTX Mark Kernel Pointers Global", false, false)
109
110bool NVPTXMarkKernelPtrsGlobalLegacyPass::runOnFunction(Function &F) {
111 return markKernelPtrsGlobal(F);
112}
113
114char NVPTXMarkKernelPtrsGlobalLegacyPass::ID = 0;
115
117 return new NVPTXMarkKernelPtrsGlobalLegacyPass();
118}
119
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
Expand Atomic instructions
static bool runOnFunction(Function &F, bool PostInlining)
#define F(x, y, z)
Definition MD5.cpp:54
#define I(x, y, z)
Definition MD5.cpp:57
NVPTX address space definition.
static bool markKernelPtrsGlobal(Function &F)
static void markPointerAsAS(Value *Ptr, unsigned AS)
static void handleIntToPtr(Value &V)
static void markPointerAsGlobal(Value *Ptr)
#define INITIALIZE_PASS(passName, arg, name, cfg, analysis)
Definition PassSupport.h:56
This class represents a conversion between pointers from one address space to another.
This class represents an incoming formal argument to a Function.
Definition Argument.h:32
InstListType::iterator iterator
Instruction iterators...
Definition BasicBlock.h:170
FunctionPass class - This class is used to implement most global optimizations.
Definition Pass.h:314
static LLVM_ABI PointerType * get(Type *ElementType, unsigned AddressSpace)
This constructs a pointer to an object of the specified type in a numbered address space.
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
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
LLVM_ABI unsigned getPointerAddressSpace() const
Get the address space of this pointer or pointer vector type.
void setOperand(unsigned i, Value *Val)
Definition User.h:212
LLVM Value Representation.
Definition Value.h:75
Type * getType() const
All values are typed, get the type of this value.
Definition Value.h:256
LLVM_ABI void replaceAllUsesWith(Value *V)
Change all uses of this to point to a new Value.
Definition Value.cpp:553
LLVMContext & getContext() const
All values hold a context through their type.
Definition Value.h:259
LLVM_ABI StringRef getName() const
Return a constant reference to the value's name.
Definition Value.cpp:322
This is an optimization pass for GlobalISel generic memory operations.
Definition Types.h:26
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:1739
decltype(auto) dyn_cast(const From &Val)
dyn_cast<X> - Return the argument parameter cast to the specified type.
Definition Casting.h:643
FunctionPass * createNVPTXMarkKernelPtrsGlobalPass()
bool isKernelFunction(const Function &F)
decltype(auto) cast(const From &Val)
cast<X> - Return the argument parameter cast to the specified type.
Definition Casting.h:559
AnalysisManager< Function > FunctionAnalysisManager
Convenience typedef for the Function analysis manager.
LLVM_ABI const Value * getUnderlyingObject(const Value *V, unsigned MaxLookup=MaxLookupSearchDepth)
This method strips off any GEP address adjustments, pointer casts or llvm.threadlocal....
PreservedAnalyses run(Function &F, FunctionAnalysisManager &AM)