blob: a9e25e48d5cbe42a0721a4e15183a71950ef550d [file] [log] [blame]
Matt Arsenault39319482015-11-06 18:01:57 +00001//===-- AMDGPUAnnotateKernelFeaturesPass.cpp ------------------------------===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
10/// \file This pass adds target attributes to functions which use intrinsics
11/// which will impact calling convention lowering.
12//
13//===----------------------------------------------------------------------===//
14
15#include "AMDGPU.h"
16#include "llvm/IR/Instructions.h"
17#include "llvm/IR/Module.h"
18
19#define DEBUG_TYPE "amdgpu-annotate-kernel-features"
20
21using namespace llvm;
22
23namespace {
24
25class AMDGPUAnnotateKernelFeatures : public ModulePass {
26private:
27 void addAttrToCallers(Function *Intrin, StringRef AttrName);
28 bool addAttrsForIntrinsics(Module &M, ArrayRef<StringRef[2]>);
29
30public:
31 static char ID;
32
33 AMDGPUAnnotateKernelFeatures() : ModulePass(ID) { }
34 bool runOnModule(Module &M) override;
35 const char *getPassName() const override {
36 return "AMDGPU Annotate Kernel Features";
37 }
38
39 void getAnalysisUsage(AnalysisUsage &AU) const override {
40 AU.setPreservesAll();
41 ModulePass::getAnalysisUsage(AU);
42 }
43};
44
45}
46
47char AMDGPUAnnotateKernelFeatures::ID = 0;
48
49char &llvm::AMDGPUAnnotateKernelFeaturesID = AMDGPUAnnotateKernelFeatures::ID;
50
51
52INITIALIZE_PASS_BEGIN(AMDGPUAnnotateKernelFeatures, DEBUG_TYPE,
53 "Add AMDGPU function attributes", false, false)
54INITIALIZE_PASS_END(AMDGPUAnnotateKernelFeatures, DEBUG_TYPE,
55 "Add AMDGPU function attributes", false, false)
56
57
58void AMDGPUAnnotateKernelFeatures::addAttrToCallers(Function *Intrin,
59 StringRef AttrName) {
60 SmallPtrSet<Function *, 4> SeenFuncs;
61
62 for (User *U : Intrin->users()) {
63 // CallInst is the only valid user for an intrinsic.
64 CallInst *CI = cast<CallInst>(U);
65
66 Function *CallingFunction = CI->getParent()->getParent();
67 if (SeenFuncs.insert(CallingFunction).second)
68 CallingFunction->addFnAttr(AttrName);
69 }
70}
71
72bool AMDGPUAnnotateKernelFeatures::addAttrsForIntrinsics(
73 Module &M,
74 ArrayRef<StringRef[2]> IntrinsicToAttr) {
75 bool Changed = false;
76
77 for (const StringRef *Arr : IntrinsicToAttr) {
78 if (Function *Fn = M.getFunction(Arr[0])) {
79 addAttrToCallers(Fn, Arr[1]);
80 Changed = true;
81 }
82 }
83
84 return Changed;
85}
86
87bool AMDGPUAnnotateKernelFeatures::runOnModule(Module &M) {
88 Triple TT(M.getTargetTriple());
89
90 static const StringRef IntrinsicToAttr[][2] = {
91 // .x omitted
Matt Arsenault43976df2016-01-30 04:25:19 +000092 { "llvm.amdgcn.workitem.id.y", "amdgpu-work-item-id-y" },
93 { "llvm.amdgcn.workitem.id.z", "amdgpu-work-item-id-z" },
94
95 { "llvm.amdgcn.workgroup.id.y", "amdgpu-work-group-id-y" },
96 { "llvm.amdgcn.workgroup.id.z", "amdgpu-work-group-id-z" },
97
Matt Arsenault39319482015-11-06 18:01:57 +000098 { "llvm.r600.read.tgid.y", "amdgpu-work-group-id-y" },
99 { "llvm.r600.read.tgid.z", "amdgpu-work-group-id-z" },
100
101 // .x omitted
102 { "llvm.r600.read.tidig.y", "amdgpu-work-item-id-y" },
103 { "llvm.r600.read.tidig.z", "amdgpu-work-item-id-z" }
104
105 };
106
107 static const StringRef HSAIntrinsicToAttr[][2] = {
108 { "llvm.r600.read.local.size.x", "amdgpu-dispatch-ptr" },
109 { "llvm.r600.read.local.size.y", "amdgpu-dispatch-ptr" },
110 { "llvm.r600.read.local.size.z", "amdgpu-dispatch-ptr" },
111
112 { "llvm.r600.read.global.size.x", "amdgpu-dispatch-ptr" },
113 { "llvm.r600.read.global.size.y", "amdgpu-dispatch-ptr" },
Tom Stellard48f29f22015-11-26 00:43:29 +0000114 { "llvm.r600.read.global.size.z", "amdgpu-dispatch-ptr" },
115 { "llvm.amdgcn.dispatch.ptr", "amdgpu-dispatch-ptr" }
Matt Arsenault39319482015-11-06 18:01:57 +0000116 };
117
118 // TODO: Intrinsics that require queue ptr.
119
120 // We do not need to note the x workitem or workgroup id because they are
121 // always initialized.
122
123 bool Changed = addAttrsForIntrinsics(M, IntrinsicToAttr);
124 if (TT.getOS() == Triple::AMDHSA)
125 Changed |= addAttrsForIntrinsics(M, HSAIntrinsicToAttr);
126
127 return Changed;
128}
129
130ModulePass *llvm::createAMDGPUAnnotateKernelFeaturesPass() {
131 return new AMDGPUAnnotateKernelFeatures();
132}