blob: 8dc863f723e2e260ef57f61b888786c124769612 [file] [log] [blame]
Tom Stellard347ac792015-06-26 21:15:07 +00001//===-- AMDGPUTargetStreamer.cpp - Mips Target Streamer Methods -----------===//
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// This file provides AMDGPU specific target streamer methods.
11//
12//===----------------------------------------------------------------------===//
13
Yaxun Liud6fbe652016-11-10 21:18:49 +000014#include "AMDGPU.h"
Tom Stellard347ac792015-06-26 21:15:07 +000015#include "AMDGPUTargetStreamer.h"
Tom Stellardff7416b2015-06-26 21:58:31 +000016#include "SIDefines.h"
Tom Stellarde135ffd2015-09-25 21:41:28 +000017#include "Utils/AMDGPUBaseInfo.h"
Sam Koltona2e5c882016-09-09 10:08:02 +000018#include "Utils/AMDKernelCodeTUtils.h"
Tom Stellard347ac792015-06-26 21:15:07 +000019#include "llvm/ADT/Twine.h"
Yaxun Liud6fbe652016-11-10 21:18:49 +000020#include "llvm/IR/Constants.h"
21#include "llvm/IR/Function.h"
22#include "llvm/IR/Metadata.h"
23#include "llvm/IR/Module.h"
Tom Stellard347ac792015-06-26 21:15:07 +000024#include "llvm/MC/MCContext.h"
25#include "llvm/MC/MCELFStreamer.h"
Tom Stellardff7416b2015-06-26 21:58:31 +000026#include "llvm/MC/MCObjectFileInfo.h"
Tom Stellard347ac792015-06-26 21:15:07 +000027#include "llvm/MC/MCSectionELF.h"
28#include "llvm/Support/ELF.h"
29#include "llvm/Support/FormattedStream.h"
30
Yaxun Liud6fbe652016-11-10 21:18:49 +000031namespace llvm {
32#include "AMDGPUPTNote.h"
33}
34
Tom Stellard347ac792015-06-26 21:15:07 +000035using namespace llvm;
Yaxun Liud6fbe652016-11-10 21:18:49 +000036using namespace llvm::AMDGPU;
Tom Stellard347ac792015-06-26 21:15:07 +000037
Konstantin Zhuravlyov7498cd62017-03-22 22:32:22 +000038//===----------------------------------------------------------------------===//
39// AMDGPUTargetStreamer
40//===----------------------------------------------------------------------===//
41
Tom Stellard347ac792015-06-26 21:15:07 +000042AMDGPUTargetStreamer::AMDGPUTargetStreamer(MCStreamer &S)
Yaxun Liud6fbe652016-11-10 21:18:49 +000043 : MCTargetStreamer(S) {}
Tom Stellard347ac792015-06-26 21:15:07 +000044
Konstantin Zhuravlyov4cbb6892017-03-22 23:27:09 +000045void AMDGPUTargetStreamer::EmitStartOfCodeObjectMetadata(const Module &Mod) {
46 CodeObjectMetadataStreamer.begin(Mod);
Konstantin Zhuravlyov7498cd62017-03-22 22:32:22 +000047}
48
Konstantin Zhuravlyovca0e7f62017-03-22 22:54:39 +000049void AMDGPUTargetStreamer::EmitKernelCodeObjectMetadata(
50 const Function &Func, const amd_kernel_code_t &KernelCode) {
51 CodeObjectMetadataStreamer.emitKernel(Func, KernelCode);
Konstantin Zhuravlyov7498cd62017-03-22 22:32:22 +000052}
53
Konstantin Zhuravlyov4cbb6892017-03-22 23:27:09 +000054void AMDGPUTargetStreamer::EmitEndOfCodeObjectMetadata() {
Konstantin Zhuravlyov7498cd62017-03-22 22:32:22 +000055 CodeObjectMetadataStreamer.end();
Konstantin Zhuravlyov4cbb6892017-03-22 23:27:09 +000056 EmitCodeObjectMetadata(CodeObjectMetadataStreamer.toYamlString().get());
Konstantin Zhuravlyov7498cd62017-03-22 22:32:22 +000057}
58
Tom Stellard347ac792015-06-26 21:15:07 +000059//===----------------------------------------------------------------------===//
60// AMDGPUTargetAsmStreamer
61//===----------------------------------------------------------------------===//
62
63AMDGPUTargetAsmStreamer::AMDGPUTargetAsmStreamer(MCStreamer &S,
64 formatted_raw_ostream &OS)
65 : AMDGPUTargetStreamer(S), OS(OS) { }
66
67void
68AMDGPUTargetAsmStreamer::EmitDirectiveHSACodeObjectVersion(uint32_t Major,
69 uint32_t Minor) {
70 OS << "\t.hsa_code_object_version " <<
71 Twine(Major) << "," << Twine(Minor) << '\n';
72}
73
74void
75AMDGPUTargetAsmStreamer::EmitDirectiveHSACodeObjectISA(uint32_t Major,
76 uint32_t Minor,
77 uint32_t Stepping,
78 StringRef VendorName,
79 StringRef ArchName) {
80 OS << "\t.hsa_code_object_isa " <<
81 Twine(Major) << "," << Twine(Minor) << "," << Twine(Stepping) <<
82 ",\"" << VendorName << "\",\"" << ArchName << "\"\n";
83
84}
85
Tom Stellardff7416b2015-06-26 21:58:31 +000086void
87AMDGPUTargetAsmStreamer::EmitAMDKernelCodeT(const amd_kernel_code_t &Header) {
Sam Koltona2e5c882016-09-09 10:08:02 +000088 OS << "\t.amd_kernel_code_t\n";
89 dumpAmdKernelCode(&Header, OS, "\t\t");
90 OS << "\t.end_amd_kernel_code_t\n";
Tom Stellardff7416b2015-06-26 21:58:31 +000091}
92
Tom Stellard1e1b05d2015-11-06 11:45:14 +000093void AMDGPUTargetAsmStreamer::EmitAMDGPUSymbolType(StringRef SymbolName,
94 unsigned Type) {
95 switch (Type) {
96 default: llvm_unreachable("Invalid AMDGPU symbol type");
97 case ELF::STT_AMDGPU_HSA_KERNEL:
98 OS << "\t.amdgpu_hsa_kernel " << SymbolName << '\n' ;
99 break;
100 }
101}
102
Tom Stellard00f2f912015-12-02 19:47:57 +0000103void AMDGPUTargetAsmStreamer::EmitAMDGPUHsaModuleScopeGlobal(
104 StringRef GlobalName) {
105 OS << "\t.amdgpu_hsa_module_global " << GlobalName << '\n';
106}
107
108void AMDGPUTargetAsmStreamer::EmitAMDGPUHsaProgramScopeGlobal(
109 StringRef GlobalName) {
110 OS << "\t.amdgpu_hsa_program_global " << GlobalName << '\n';
111}
112
Konstantin Zhuravlyov4cbb6892017-03-22 23:27:09 +0000113bool AMDGPUTargetAsmStreamer::EmitCodeObjectMetadata(StringRef YamlString) {
114 auto VerifiedYamlString = CodeObjectMetadataStreamer.toYamlString(YamlString);
Konstantin Zhuravlyov7498cd62017-03-22 22:32:22 +0000115 if (!VerifiedYamlString)
116 return false;
Sam Kolton69c8aa22016-12-19 11:43:15 +0000117
Konstantin Zhuravlyov7498cd62017-03-22 22:32:22 +0000118 OS << '\t' << AMDGPU::CodeObject::MetadataAssemblerDirectiveBegin << '\n';
119 OS << VerifiedYamlString.get();
120 OS << '\t' << AMDGPU::CodeObject::MetadataAssemblerDirectiveEnd << '\n';
Konstantin Zhuravlyov972948b2017-02-27 07:55:17 +0000121
Konstantin Zhuravlyov7498cd62017-03-22 22:32:22 +0000122 return true;
Sam Kolton69c8aa22016-12-19 11:43:15 +0000123}
124
Tom Stellard347ac792015-06-26 21:15:07 +0000125//===----------------------------------------------------------------------===//
126// AMDGPUTargetELFStreamer
127//===----------------------------------------------------------------------===//
128
129AMDGPUTargetELFStreamer::AMDGPUTargetELFStreamer(MCStreamer &S)
Yaxun Liud6fbe652016-11-10 21:18:49 +0000130 : AMDGPUTargetStreamer(S), Streamer(S) {}
Tom Stellard347ac792015-06-26 21:15:07 +0000131
132MCELFStreamer &AMDGPUTargetELFStreamer::getStreamer() {
133 return static_cast<MCELFStreamer &>(Streamer);
134}
135
Benjamin Kramer061f4a52017-01-13 14:39:03 +0000136void AMDGPUTargetELFStreamer::EmitAMDGPUNote(
Yaxun Liu874d26a2017-03-10 19:35:43 +0000137 const MCExpr *DescSZ, ElfNote::NoteType Type,
Benjamin Kramer061f4a52017-01-13 14:39:03 +0000138 function_ref<void(MCELFStreamer &)> EmitDesc) {
Sam Kolton69c8aa22016-12-19 11:43:15 +0000139 auto &S = getStreamer();
140 auto &Context = S.getContext();
Tom Stellard347ac792015-06-26 21:15:07 +0000141
Yaxun Liu874d26a2017-03-10 19:35:43 +0000142 auto NameSZ = sizeof(ElfNote::NoteName);
Sam Kolton69c8aa22016-12-19 11:43:15 +0000143
144 S.PushSection();
145 S.SwitchSection(Context.getELFSection(
Yaxun Liu874d26a2017-03-10 19:35:43 +0000146 ElfNote::SectionName, ELF::SHT_NOTE, ELF::SHF_ALLOC));
Sam Kolton69c8aa22016-12-19 11:43:15 +0000147 S.EmitIntValue(NameSZ, 4); // namesz
148 S.EmitValue(DescSZ, 4); // descz
Yaxun Liu874d26a2017-03-10 19:35:43 +0000149 S.EmitIntValue(Type, 4); // type
150 S.EmitBytes(StringRef(ElfNote::NoteName, NameSZ)); // name
Sam Kolton69c8aa22016-12-19 11:43:15 +0000151 S.EmitValueToAlignment(4, 0, 1, 0); // padding 0
152 EmitDesc(S); // desc
153 S.EmitValueToAlignment(4, 0, 1, 0); // padding 0
154 S.PopSection();
155}
156
157void
158AMDGPUTargetELFStreamer::EmitDirectiveHSACodeObjectVersion(uint32_t Major,
159 uint32_t Minor) {
160
161 EmitAMDGPUNote(
162 MCConstantExpr::create(8, getContext()),
Yaxun Liu874d26a2017-03-10 19:35:43 +0000163 ElfNote::NT_AMDGPU_HSA_CODE_OBJECT_VERSION,
Sam Kolton69c8aa22016-12-19 11:43:15 +0000164 [&](MCELFStreamer &OS){
165 OS.EmitIntValue(Major, 4);
166 OS.EmitIntValue(Minor, 4);
167 }
168 );
Tom Stellard347ac792015-06-26 21:15:07 +0000169}
170
171void
172AMDGPUTargetELFStreamer::EmitDirectiveHSACodeObjectISA(uint32_t Major,
173 uint32_t Minor,
174 uint32_t Stepping,
175 StringRef VendorName,
176 StringRef ArchName) {
Tom Stellard347ac792015-06-26 21:15:07 +0000177 uint16_t VendorNameSize = VendorName.size() + 1;
178 uint16_t ArchNameSize = ArchName.size() + 1;
Matt Arsenaultb4493e92017-02-10 02:42:31 +0000179
Tom Stellard347ac792015-06-26 21:15:07 +0000180 unsigned DescSZ = sizeof(VendorNameSize) + sizeof(ArchNameSize) +
Sam Kolton69c8aa22016-12-19 11:43:15 +0000181 sizeof(Major) + sizeof(Minor) + sizeof(Stepping) +
182 VendorNameSize + ArchNameSize;
Tom Stellard347ac792015-06-26 21:15:07 +0000183
Sam Kolton69c8aa22016-12-19 11:43:15 +0000184 EmitAMDGPUNote(
185 MCConstantExpr::create(DescSZ, getContext()),
Yaxun Liu874d26a2017-03-10 19:35:43 +0000186 ElfNote::NT_AMDGPU_HSA_ISA,
Sam Kolton69c8aa22016-12-19 11:43:15 +0000187 [&](MCELFStreamer &OS) {
188 OS.EmitIntValue(VendorNameSize, 2);
189 OS.EmitIntValue(ArchNameSize, 2);
190 OS.EmitIntValue(Major, 4);
191 OS.EmitIntValue(Minor, 4);
192 OS.EmitIntValue(Stepping, 4);
193 OS.EmitBytes(VendorName);
194 OS.EmitIntValue(0, 1); // NULL terminate VendorName
195 OS.EmitBytes(ArchName);
196 OS.EmitIntValue(0, 1); // NULL terminte ArchName
197 }
198 );
Tom Stellard347ac792015-06-26 21:15:07 +0000199}
Tom Stellardff7416b2015-06-26 21:58:31 +0000200
201void
202AMDGPUTargetELFStreamer::EmitAMDKernelCodeT(const amd_kernel_code_t &Header) {
203
204 MCStreamer &OS = getStreamer();
205 OS.PushSection();
Tom Stellardff7416b2015-06-26 21:58:31 +0000206 OS.EmitBytes(StringRef((const char*)&Header, sizeof(Header)));
207 OS.PopSection();
208}
Tom Stellard1e1b05d2015-11-06 11:45:14 +0000209
210void AMDGPUTargetELFStreamer::EmitAMDGPUSymbolType(StringRef SymbolName,
211 unsigned Type) {
212 MCSymbolELF *Symbol = cast<MCSymbolELF>(
213 getStreamer().getContext().getOrCreateSymbol(SymbolName));
214 Symbol->setType(ELF::STT_AMDGPU_HSA_KERNEL);
215}
Tom Stellard00f2f912015-12-02 19:47:57 +0000216
217void AMDGPUTargetELFStreamer::EmitAMDGPUHsaModuleScopeGlobal(
218 StringRef GlobalName) {
219
220 MCSymbolELF *Symbol = cast<MCSymbolELF>(
221 getStreamer().getContext().getOrCreateSymbol(GlobalName));
222 Symbol->setType(ELF::STT_OBJECT);
223 Symbol->setBinding(ELF::STB_LOCAL);
224}
225
226void AMDGPUTargetELFStreamer::EmitAMDGPUHsaProgramScopeGlobal(
227 StringRef GlobalName) {
228
229 MCSymbolELF *Symbol = cast<MCSymbolELF>(
230 getStreamer().getContext().getOrCreateSymbol(GlobalName));
231 Symbol->setType(ELF::STT_OBJECT);
232 Symbol->setBinding(ELF::STB_GLOBAL);
233}
Yaxun Liud6fbe652016-11-10 21:18:49 +0000234
Konstantin Zhuravlyov4cbb6892017-03-22 23:27:09 +0000235bool AMDGPUTargetELFStreamer::EmitCodeObjectMetadata(StringRef YamlString) {
236 auto VerifiedYamlString = CodeObjectMetadataStreamer.toYamlString(YamlString);
Konstantin Zhuravlyov7498cd62017-03-22 22:32:22 +0000237 if (!VerifiedYamlString)
238 return false;
Konstantin Zhuravlyov972948b2017-02-27 07:55:17 +0000239
Yaxun Liud6fbe652016-11-10 21:18:49 +0000240 // Create two labels to mark the beginning and end of the desc field
241 // and a MCExpr to calculate the size of the desc field.
Sam Kolton69c8aa22016-12-19 11:43:15 +0000242 auto &Context = getContext();
Yaxun Liud6fbe652016-11-10 21:18:49 +0000243 auto *DescBegin = Context.createTempSymbol();
244 auto *DescEnd = Context.createTempSymbol();
245 auto *DescSZ = MCBinaryExpr::createSub(
Sam Kolton69c8aa22016-12-19 11:43:15 +0000246 MCSymbolRefExpr::create(DescEnd, Context),
247 MCSymbolRefExpr::create(DescBegin, Context), Context);
Yaxun Liud6fbe652016-11-10 21:18:49 +0000248
Sam Kolton69c8aa22016-12-19 11:43:15 +0000249 EmitAMDGPUNote(
250 DescSZ,
Konstantin Zhuravlyov7498cd62017-03-22 22:32:22 +0000251 ElfNote::NT_AMDGPU_HSA_CODE_OBJECT_METADATA,
Sam Kolton69c8aa22016-12-19 11:43:15 +0000252 [&](MCELFStreamer &OS) {
253 OS.EmitLabel(DescBegin);
Konstantin Zhuravlyov7498cd62017-03-22 22:32:22 +0000254 OS.EmitBytes(VerifiedYamlString.get());
Sam Kolton69c8aa22016-12-19 11:43:15 +0000255 OS.EmitLabel(DescEnd);
256 }
257 );
Konstantin Zhuravlyov972948b2017-02-27 07:55:17 +0000258
Konstantin Zhuravlyov7498cd62017-03-22 22:32:22 +0000259 return true;
Yaxun Liud6fbe652016-11-10 21:18:49 +0000260}