Line data Source code
1 : //===- MIRParser.cpp - MIR serialization format parser implementation -----===//
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 implements the class that parses the optional LLVM IR and machine
11 : // functions that are stored in MIR files.
12 : //
13 : //===----------------------------------------------------------------------===//
14 :
15 : #include "llvm/CodeGen/MIRParser/MIRParser.h"
16 : #include "MIParser.h"
17 : #include "llvm/ADT/DenseMap.h"
18 : #include "llvm/ADT/STLExtras.h"
19 : #include "llvm/ADT/StringMap.h"
20 : #include "llvm/ADT/StringRef.h"
21 : #include "llvm/AsmParser/Parser.h"
22 : #include "llvm/AsmParser/SlotMapping.h"
23 : #include "llvm/CodeGen/GlobalISel/RegisterBank.h"
24 : #include "llvm/CodeGen/GlobalISel/RegisterBankInfo.h"
25 : #include "llvm/CodeGen/MIRYamlMapping.h"
26 : #include "llvm/CodeGen/MachineConstantPool.h"
27 : #include "llvm/CodeGen/MachineFrameInfo.h"
28 : #include "llvm/CodeGen/MachineFunction.h"
29 : #include "llvm/CodeGen/MachineModuleInfo.h"
30 : #include "llvm/CodeGen/MachineRegisterInfo.h"
31 : #include "llvm/IR/BasicBlock.h"
32 : #include "llvm/IR/DebugInfo.h"
33 : #include "llvm/IR/DiagnosticInfo.h"
34 : #include "llvm/IR/Instructions.h"
35 : #include "llvm/IR/LLVMContext.h"
36 : #include "llvm/IR/Module.h"
37 : #include "llvm/IR/ValueSymbolTable.h"
38 : #include "llvm/Support/LineIterator.h"
39 : #include "llvm/Support/MemoryBuffer.h"
40 : #include "llvm/Support/SMLoc.h"
41 : #include "llvm/Support/SourceMgr.h"
42 : #include "llvm/Support/YAMLTraits.h"
43 : #include <memory>
44 :
45 : using namespace llvm;
46 :
47 : namespace llvm {
48 :
49 : /// This class implements the parsing of LLVM IR that's embedded inside a MIR
50 : /// file.
51 : class MIRParserImpl {
52 : SourceMgr SM;
53 : yaml::Input In;
54 : StringRef Filename;
55 : LLVMContext &Context;
56 : SlotMapping IRSlots;
57 : /// Maps from register class names to register classes.
58 : Name2RegClassMap Names2RegClasses;
59 : /// Maps from register bank names to register banks.
60 : Name2RegBankMap Names2RegBanks;
61 : /// True when the MIR file doesn't have LLVM IR. Dummy IR functions are
62 : /// created and inserted into the given module when this is true.
63 : bool NoLLVMIR = false;
64 : /// True when a well formed MIR file does not contain any MIR/machine function
65 : /// parts.
66 : bool NoMIRDocuments = false;
67 :
68 : public:
69 : MIRParserImpl(std::unique_ptr<MemoryBuffer> Contents,
70 : StringRef Filename, LLVMContext &Context);
71 :
72 : void reportDiagnostic(const SMDiagnostic &Diag);
73 :
74 : /// Report an error with the given message at unknown location.
75 : ///
76 : /// Always returns true.
77 : bool error(const Twine &Message);
78 :
79 : /// Report an error with the given message at the given location.
80 : ///
81 : /// Always returns true.
82 : bool error(SMLoc Loc, const Twine &Message);
83 :
84 : /// Report a given error with the location translated from the location in an
85 : /// embedded string literal to a location in the MIR file.
86 : ///
87 : /// Always returns true.
88 : bool error(const SMDiagnostic &Error, SMRange SourceRange);
89 :
90 : /// Try to parse the optional LLVM module and the machine functions in the MIR
91 : /// file.
92 : ///
93 : /// Return null if an error occurred.
94 : std::unique_ptr<Module> parseIRModule();
95 :
96 : bool parseMachineFunctions(Module &M, MachineModuleInfo &MMI);
97 :
98 : /// Parse the machine function in the current YAML document.
99 : ///
100 : ///
101 : /// Return true if an error occurred.
102 : bool parseMachineFunction(Module &M, MachineModuleInfo &MMI);
103 :
104 : /// Initialize the machine function to the state that's described in the MIR
105 : /// file.
106 : ///
107 : /// Return true if error occurred.
108 : bool initializeMachineFunction(const yaml::MachineFunction &YamlMF,
109 : MachineFunction &MF);
110 :
111 : bool parseRegisterInfo(PerFunctionMIParsingState &PFS,
112 : const yaml::MachineFunction &YamlMF);
113 :
114 : bool setupRegisterInfo(const PerFunctionMIParsingState &PFS,
115 : const yaml::MachineFunction &YamlMF);
116 :
117 : bool initializeFrameInfo(PerFunctionMIParsingState &PFS,
118 : const yaml::MachineFunction &YamlMF);
119 :
120 : bool parseCalleeSavedRegister(PerFunctionMIParsingState &PFS,
121 : std::vector<CalleeSavedInfo> &CSIInfo,
122 : const yaml::StringValue &RegisterSource,
123 : bool IsRestored, int FrameIdx);
124 :
125 : template <typename T>
126 : bool parseStackObjectsDebugInfo(PerFunctionMIParsingState &PFS,
127 : const T &Object,
128 : int FrameIdx);
129 :
130 : bool initializeConstantPool(PerFunctionMIParsingState &PFS,
131 : MachineConstantPool &ConstantPool,
132 : const yaml::MachineFunction &YamlMF);
133 :
134 : bool initializeJumpTableInfo(PerFunctionMIParsingState &PFS,
135 : const yaml::MachineJumpTable &YamlJTI);
136 :
137 : private:
138 : bool parseMDNode(PerFunctionMIParsingState &PFS, MDNode *&Node,
139 : const yaml::StringValue &Source);
140 :
141 : bool parseMBBReference(PerFunctionMIParsingState &PFS,
142 : MachineBasicBlock *&MBB,
143 : const yaml::StringValue &Source);
144 :
145 : /// Return a MIR diagnostic converted from an MI string diagnostic.
146 : SMDiagnostic diagFromMIStringDiag(const SMDiagnostic &Error,
147 : SMRange SourceRange);
148 :
149 : /// Return a MIR diagnostic converted from a diagnostic located in a YAML
150 : /// block scalar string.
151 : SMDiagnostic diagFromBlockStringDiag(const SMDiagnostic &Error,
152 : SMRange SourceRange);
153 :
154 : void initNames2RegClasses(const MachineFunction &MF);
155 : void initNames2RegBanks(const MachineFunction &MF);
156 :
157 : /// Check if the given identifier is a name of a register class.
158 : ///
159 : /// Return null if the name isn't a register class.
160 : const TargetRegisterClass *getRegClass(const MachineFunction &MF,
161 : StringRef Name);
162 :
163 : /// Check if the given identifier is a name of a register bank.
164 : ///
165 : /// Return null if the name isn't a register bank.
166 : const RegisterBank *getRegBank(const MachineFunction &MF, StringRef Name);
167 :
168 : void computeFunctionProperties(MachineFunction &MF);
169 : };
170 :
171 : } // end namespace llvm
172 :
173 5 : static void handleYAMLDiag(const SMDiagnostic &Diag, void *Context) {
174 5 : reinterpret_cast<MIRParserImpl *>(Context)->reportDiagnostic(Diag);
175 5 : }
176 :
177 1258 : MIRParserImpl::MIRParserImpl(std::unique_ptr<MemoryBuffer> Contents,
178 1258 : StringRef Filename, LLVMContext &Context)
179 : : SM(),
180 : In(SM.getMemoryBuffer(
181 1258 : SM.AddNewSourceBuffer(std::move(Contents), SMLoc()))->getBuffer(),
182 : nullptr, handleYAMLDiag, this),
183 : Filename(Filename),
184 5032 : Context(Context) {
185 1258 : In.setContext(&In);
186 1258 : }
187 :
188 3 : bool MIRParserImpl::error(const Twine &Message) {
189 3 : Context.diagnose(DiagnosticInfoMIRParser(
190 6 : DS_Error, SMDiagnostic(Filename, SourceMgr::DK_Error, Message.str())));
191 3 : return true;
192 : }
193 :
194 9 : bool MIRParserImpl::error(SMLoc Loc, const Twine &Message) {
195 9 : Context.diagnose(DiagnosticInfoMIRParser(
196 27 : DS_Error, SM.GetMessage(Loc, SourceMgr::DK_Error, Message)));
197 9 : return true;
198 : }
199 :
200 7 : bool MIRParserImpl::error(const SMDiagnostic &Error, SMRange SourceRange) {
201 : assert(Error.getKind() == SourceMgr::DK_Error && "Expected an error");
202 7 : reportDiagnostic(diagFromMIStringDiag(Error, SourceRange));
203 7 : return true;
204 : }
205 :
206 108 : void MIRParserImpl::reportDiagnostic(const SMDiagnostic &Diag) {
207 : DiagnosticSeverity Kind;
208 108 : switch (Diag.getKind()) {
209 108 : case SourceMgr::DK_Error:
210 : Kind = DS_Error;
211 108 : break;
212 0 : case SourceMgr::DK_Warning:
213 : Kind = DS_Warning;
214 0 : break;
215 0 : case SourceMgr::DK_Note:
216 : Kind = DS_Note;
217 0 : break;
218 : case SourceMgr::DK_Remark:
219 : llvm_unreachable("remark unexpected");
220 : break;
221 : }
222 216 : Context.diagnose(DiagnosticInfoMIRParser(Kind, Diag));
223 108 : }
224 :
225 1258 : std::unique_ptr<Module> MIRParserImpl::parseIRModule() {
226 1258 : if (!In.setCurrentDocument()) {
227 2 : if (In.error())
228 : return nullptr;
229 : // Create an empty module when the MIR file is empty.
230 2 : NoMIRDocuments = true;
231 2 : return llvm::make_unique<Module>(Filename, Context);
232 : }
233 :
234 1256 : std::unique_ptr<Module> M;
235 : // Parse the block scalar manually so that we can return unique pointer
236 : // without having to go trough YAML traits.
237 : if (const auto *BSN =
238 1256 : dyn_cast_or_null<yaml::BlockScalarNode>(In.getCurrentNode())) {
239 899 : SMDiagnostic Error;
240 2700 : M = parseAssembly(MemoryBufferRef(BSN->getValue(), Filename), Error,
241 900 : Context, &IRSlots, /*UpgradeDebugInfo=*/false);
242 900 : if (!M) {
243 1 : reportDiagnostic(diagFromBlockStringDiag(Error, BSN->getSourceRange()));
244 1 : return nullptr;
245 : }
246 899 : In.nextDocument();
247 899 : if (!In.setCurrentDocument())
248 2 : NoMIRDocuments = true;
249 : } else {
250 : // Create an new, empty module.
251 356 : M = llvm::make_unique<Module>(Filename, Context);
252 356 : NoLLVMIR = true;
253 : }
254 : return M;
255 : }
256 :
257 1257 : bool MIRParserImpl::parseMachineFunctions(Module &M, MachineModuleInfo &MMI) {
258 1257 : if (NoMIRDocuments)
259 : return false;
260 :
261 : // Parse the machine functions.
262 : do {
263 4585 : if (parseMachineFunction(M, MMI))
264 : return true;
265 4428 : In.nextDocument();
266 4428 : } while (In.setCurrentDocument());
267 :
268 : return false;
269 : }
270 :
271 : /// Create an empty function with the given name.
272 1206 : static Function *createDummyFunction(StringRef Name, Module &M) {
273 1206 : auto &Context = M.getContext();
274 1206 : Function *F = cast<Function>(M.getOrInsertFunction(
275 : Name, FunctionType::get(Type::getVoidTy(Context), false)));
276 1206 : BasicBlock *BB = BasicBlock::Create(Context, "entry", F);
277 1206 : new UnreachableInst(Context, BB);
278 1206 : return F;
279 : }
280 :
281 4585 : bool MIRParserImpl::parseMachineFunction(Module &M, MachineModuleInfo &MMI) {
282 : // Parse the yaml.
283 9132 : yaml::MachineFunction YamlMF;
284 : yaml::EmptyContext Ctx;
285 4585 : yaml::yamlize(In, YamlMF, false, Ctx);
286 4585 : if (In.error())
287 : return true;
288 :
289 : // Search for the corresponding IR function.
290 4580 : StringRef FunctionName = YamlMF.Name;
291 4580 : Function *F = M.getFunction(FunctionName);
292 4580 : if (!F) {
293 1207 : if (NoLLVMIR) {
294 1206 : F = createDummyFunction(FunctionName, M);
295 : } else {
296 1 : return error(Twine("function '") + FunctionName +
297 1 : "' isn't defined in the provided LLVM IR");
298 : }
299 : }
300 4579 : if (MMI.getMachineFunction(*F) != nullptr)
301 1 : return error(Twine("redefinition of machine function '") + FunctionName +
302 1 : "'");
303 :
304 : // Create the MachineFunction.
305 4578 : MachineFunction &MF = MMI.getOrCreateMachineFunction(*F);
306 4578 : if (initializeMachineFunction(YamlMF, MF))
307 112 : return true;
308 :
309 : return false;
310 : }
311 :
312 4466 : static bool isSSA(const MachineFunction &MF) {
313 4466 : const MachineRegisterInfo &MRI = MF.getRegInfo();
314 20423 : for (unsigned I = 0, E = MRI.getNumVirtRegs(); I != E; ++I) {
315 : unsigned Reg = TargetRegisterInfo::index2VirtReg(I);
316 17092 : if (!MRI.hasOneDef(Reg) && !MRI.def_empty(Reg))
317 : return false;
318 : }
319 : return true;
320 : }
321 :
322 4466 : void MIRParserImpl::computeFunctionProperties(MachineFunction &MF) {
323 : MachineFunctionProperties &Properties = MF.getProperties();
324 :
325 : bool HasPHI = false;
326 : bool HasInlineAsm = false;
327 10770 : for (const MachineBasicBlock &MBB : MF) {
328 40810 : for (const MachineInstr &MI : MBB) {
329 : if (MI.isPHI())
330 : HasPHI = true;
331 34506 : if (MI.isInlineAsm())
332 : HasInlineAsm = true;
333 : }
334 : }
335 4466 : if (!HasPHI)
336 : Properties.set(MachineFunctionProperties::Property::NoPHIs);
337 : MF.setHasInlineAsm(HasInlineAsm);
338 :
339 4466 : if (isSSA(MF))
340 : Properties.set(MachineFunctionProperties::Property::IsSSA);
341 : else
342 : Properties.reset(MachineFunctionProperties::Property::IsSSA);
343 :
344 4466 : const MachineRegisterInfo &MRI = MF.getRegInfo();
345 4466 : if (MRI.getNumVirtRegs() == 0)
346 : Properties.set(MachineFunctionProperties::Property::NoVRegs);
347 4466 : }
348 :
349 : bool
350 4578 : MIRParserImpl::initializeMachineFunction(const yaml::MachineFunction &YamlMF,
351 : MachineFunction &MF) {
352 : // TODO: Recreate the machine function.
353 4578 : initNames2RegClasses(MF);
354 4578 : initNames2RegBanks(MF);
355 4578 : if (YamlMF.Alignment)
356 : MF.setAlignment(YamlMF.Alignment);
357 4578 : MF.setExposesReturnsTwice(YamlMF.ExposesReturnsTwice);
358 :
359 4578 : if (YamlMF.Legalized)
360 : MF.getProperties().set(MachineFunctionProperties::Property::Legalized);
361 4578 : if (YamlMF.RegBankSelected)
362 : MF.getProperties().set(
363 : MachineFunctionProperties::Property::RegBankSelected);
364 4578 : if (YamlMF.Selected)
365 : MF.getProperties().set(MachineFunctionProperties::Property::Selected);
366 4578 : if (YamlMF.FailedISel)
367 : MF.getProperties().set(MachineFunctionProperties::Property::FailedISel);
368 :
369 4578 : PerFunctionMIParsingState PFS(MF, SM, IRSlots, Names2RegClasses,
370 9118 : Names2RegBanks);
371 4578 : if (parseRegisterInfo(PFS, YamlMF))
372 : return true;
373 4573 : if (!YamlMF.Constants.empty()) {
374 20 : auto *ConstantPool = MF.getConstantPool();
375 : assert(ConstantPool && "Constant pool must be created");
376 20 : if (initializeConstantPool(PFS, *ConstantPool, YamlMF))
377 : return true;
378 : }
379 :
380 : StringRef BlockStr = YamlMF.Body.Value.Value;
381 4532 : SMDiagnostic Error;
382 : SourceMgr BlockSM;
383 4570 : BlockSM.AddNewSourceBuffer(
384 4570 : MemoryBuffer::getMemBuffer(BlockStr, "",/*RequiresNullTerminator=*/false),
385 4570 : SMLoc());
386 4570 : PFS.SM = &BlockSM;
387 4570 : if (parseMachineBasicBlockDefinitions(PFS, BlockStr, Error)) {
388 12 : reportDiagnostic(
389 24 : diagFromBlockStringDiag(Error, YamlMF.Body.Value.SourceRange));
390 12 : return true;
391 : }
392 4558 : PFS.SM = &SM;
393 :
394 : // Initialize the frame information after creating all the MBBs so that the
395 : // MBB references in the frame information can be resolved.
396 4558 : if (initializeFrameInfo(PFS, YamlMF))
397 : return true;
398 : // Initialize the jump table after creating all the MBBs so that the MBB
399 : // references can be resolved.
400 4561 : if (!YamlMF.JumpTableInfo.Entries.empty() &&
401 10 : initializeJumpTableInfo(PFS, YamlMF.JumpTableInfo))
402 : return true;
403 : // Parse the machine instructions after creating all of the MBBs so that the
404 : // parser can resolve the MBB references.
405 : StringRef InsnStr = YamlMF.Body.Value.Value;
406 : SourceMgr InsnSM;
407 4550 : InsnSM.AddNewSourceBuffer(
408 4550 : MemoryBuffer::getMemBuffer(InsnStr, "", /*RequiresNullTerminator=*/false),
409 4550 : SMLoc());
410 4550 : PFS.SM = &InsnSM;
411 4550 : if (parseMachineInstructions(PFS, InsnStr, Error)) {
412 83 : reportDiagnostic(
413 166 : diagFromBlockStringDiag(Error, YamlMF.Body.Value.SourceRange));
414 83 : return true;
415 : }
416 4467 : PFS.SM = &SM;
417 :
418 4467 : if (setupRegisterInfo(PFS, YamlMF))
419 : return true;
420 :
421 4466 : computeFunctionProperties(MF);
422 :
423 4466 : MF.getSubtarget().mirFileLoaded(MF);
424 :
425 4466 : MF.verify();
426 4428 : return false;
427 : }
428 :
429 4578 : bool MIRParserImpl::parseRegisterInfo(PerFunctionMIParsingState &PFS,
430 : const yaml::MachineFunction &YamlMF) {
431 4578 : MachineFunction &MF = PFS.MF;
432 4578 : MachineRegisterInfo &RegInfo = MF.getRegInfo();
433 : assert(RegInfo.tracksLiveness());
434 4578 : if (!YamlMF.TracksRegLiveness)
435 2358 : RegInfo.invalidateLiveness();
436 :
437 4578 : SMDiagnostic Error;
438 : // Parse the virtual register information.
439 17978 : for (const auto &VReg : YamlMF.VirtualRegisters) {
440 13402 : VRegInfo &Info = PFS.getVRegInfo(VReg.ID.Value);
441 13402 : if (Info.Explicit)
442 1 : return error(VReg.ID.SourceRange.Start,
443 1 : Twine("redefinition of virtual register '%") +
444 2 : Twine(VReg.ID.Value) + "'");
445 13401 : Info.Explicit = true;
446 :
447 : if (StringRef(VReg.Class.Value).equals("_")) {
448 4085 : Info.Kind = VRegInfo::GENERIC;
449 4085 : Info.D.RegBank = nullptr;
450 : } else {
451 9316 : const auto *RC = getRegClass(MF, VReg.Class.Value);
452 9316 : if (RC) {
453 5768 : Info.Kind = VRegInfo::NORMAL;
454 5768 : Info.D.RC = RC;
455 : } else {
456 3548 : const RegisterBank *RegBank = getRegBank(MF, VReg.Class.Value);
457 3548 : if (!RegBank)
458 1 : return error(
459 : VReg.Class.SourceRange.Start,
460 1 : Twine("use of undefined register class or register bank '") +
461 2 : VReg.Class.Value + "'");
462 3547 : Info.Kind = VRegInfo::REGBANK;
463 3547 : Info.D.RegBank = RegBank;
464 : }
465 : }
466 :
467 13400 : if (!VReg.PreferredRegister.Value.empty()) {
468 12 : if (Info.Kind != VRegInfo::NORMAL)
469 0 : return error(VReg.Class.SourceRange.Start,
470 0 : Twine("preferred register can only be set for normal vregs"));
471 :
472 12 : if (parseRegisterReference(PFS, Info.PreferredReg,
473 : VReg.PreferredRegister.Value, Error))
474 0 : return error(Error, VReg.PreferredRegister.SourceRange);
475 : }
476 : }
477 :
478 : // Parse the liveins.
479 6324 : for (const auto &LiveIn : YamlMF.LiveIns) {
480 1751 : unsigned Reg = 0;
481 1751 : if (parseNamedRegisterReference(PFS, Reg, LiveIn.Register.Value, Error))
482 3 : return error(Error, LiveIn.Register.SourceRange);
483 : unsigned VReg = 0;
484 1749 : if (!LiveIn.VirtualRegister.Value.empty()) {
485 : VRegInfo *Info;
486 1133 : if (parseVirtualRegisterReference(PFS, Info, LiveIn.VirtualRegister.Value,
487 : Error))
488 1 : return error(Error, LiveIn.VirtualRegister.SourceRange);
489 1132 : VReg = Info->VReg;
490 : }
491 1748 : RegInfo.addLiveIn(Reg, VReg);
492 : }
493 :
494 : // Parse the callee saved registers (Registers that will
495 : // be saved for the caller).
496 4573 : if (YamlMF.CalleeSavedRegisters) {
497 : SmallVector<MCPhysReg, 16> CalleeSavedRegisters;
498 754 : for (const auto &RegSource : YamlMF.CalleeSavedRegisters.getValue()) {
499 737 : unsigned Reg = 0;
500 737 : if (parseNamedRegisterReference(PFS, Reg, RegSource.Value, Error))
501 0 : return error(Error, RegSource.SourceRange);
502 737 : CalleeSavedRegisters.push_back(Reg);
503 : }
504 17 : RegInfo.setCalleeSavedRegs(CalleeSavedRegisters);
505 : }
506 :
507 : return false;
508 : }
509 :
510 4467 : bool MIRParserImpl::setupRegisterInfo(const PerFunctionMIParsingState &PFS,
511 : const yaml::MachineFunction &YamlMF) {
512 4467 : MachineFunction &MF = PFS.MF;
513 4467 : MachineRegisterInfo &MRI = MF.getRegInfo();
514 4467 : bool Error = false;
515 : // Create VRegs
516 : auto populateVRegInfo = [&] (const VRegInfo &Info, Twine Name) {
517 : unsigned Reg = Info.VReg;
518 : switch (Info.Kind) {
519 : case VRegInfo::UNKNOWN:
520 : error(Twine("Cannot determine class/bank of virtual register ") +
521 : Name + " in function '" + MF.getName() + "'");
522 : Error = true;
523 : break;
524 : case VRegInfo::NORMAL:
525 : MRI.setRegClass(Reg, Info.D.RC);
526 : if (Info.PreferredReg != 0)
527 : MRI.setSimpleHint(Reg, Info.PreferredReg);
528 : break;
529 : case VRegInfo::GENERIC:
530 : break;
531 : case VRegInfo::REGBANK:
532 : MRI.setRegBank(Reg, *Info.D.RegBank);
533 : break;
534 : }
535 4467 : };
536 :
537 4467 : for (auto I = PFS.VRegInfosNamed.begin(), E = PFS.VRegInfosNamed.end();
538 4491 : I != E; I++) {
539 24 : const VRegInfo &Info = *I->second;
540 48 : populateVRegInfo(Info, Twine(I->first()));
541 : }
542 :
543 21670 : for (auto P : PFS.VRegInfos) {
544 : const VRegInfo &Info = *P.second;
545 17203 : populateVRegInfo(Info, Twine(P.first));
546 : }
547 :
548 : // Compute MachineRegisterInfo::UsedPhysRegMask
549 10772 : for (const MachineBasicBlock &MBB : MF) {
550 40814 : for (const MachineInstr &MI : MBB) {
551 135054 : for (const MachineOperand &MO : MI.operands()) {
552 100545 : if (!MO.isRegMask())
553 : continue;
554 220 : MRI.addPhysRegsUsedFromRegMask(MO.getRegMask());
555 : }
556 : }
557 : }
558 :
559 : // FIXME: This is a temporary workaround until the reserved registers can be
560 : // serialized.
561 4467 : MRI.freezeReservedRegs(MF);
562 4467 : return Error;
563 : }
564 :
565 4558 : bool MIRParserImpl::initializeFrameInfo(PerFunctionMIParsingState &PFS,
566 : const yaml::MachineFunction &YamlMF) {
567 4558 : MachineFunction &MF = PFS.MF;
568 4558 : MachineFrameInfo &MFI = MF.getFrameInfo();
569 4558 : const Function &F = MF.getFunction();
570 4558 : const yaml::MachineFrameInfo &YamlMFI = YamlMF.FrameInfo;
571 4558 : MFI.setFrameAddressIsTaken(YamlMFI.IsFrameAddressTaken);
572 4558 : MFI.setReturnAddressIsTaken(YamlMFI.IsReturnAddressTaken);
573 4558 : MFI.setHasStackMap(YamlMFI.HasStackMap);
574 4558 : MFI.setHasPatchPoint(YamlMFI.HasPatchPoint);
575 4558 : MFI.setStackSize(YamlMFI.StackSize);
576 4558 : MFI.setOffsetAdjustment(YamlMFI.OffsetAdjustment);
577 4558 : if (YamlMFI.MaxAlignment)
578 310 : MFI.ensureMaxAlignment(YamlMFI.MaxAlignment);
579 4558 : MFI.setAdjustsStack(YamlMFI.AdjustsStack);
580 4558 : MFI.setHasCalls(YamlMFI.HasCalls);
581 4558 : if (YamlMFI.MaxCallFrameSize != ~0u)
582 : MFI.setMaxCallFrameSize(YamlMFI.MaxCallFrameSize);
583 4558 : MFI.setCVBytesOfCalleeSavedRegisters(YamlMFI.CVBytesOfCalleeSavedRegisters);
584 4558 : MFI.setHasOpaqueSPAdjustment(YamlMFI.HasOpaqueSPAdjustment);
585 4558 : MFI.setHasVAStart(YamlMFI.HasVAStart);
586 4558 : MFI.setHasMustTailInVarArgFunc(YamlMFI.HasMustTailInVarArgFunc);
587 4558 : MFI.setLocalFrameSize(YamlMFI.LocalFrameSize);
588 4558 : if (!YamlMFI.SavePoint.Value.empty()) {
589 1 : MachineBasicBlock *MBB = nullptr;
590 1 : if (parseMBBReference(PFS, MBB, YamlMFI.SavePoint))
591 0 : return true;
592 1 : MFI.setSavePoint(MBB);
593 : }
594 4558 : if (!YamlMFI.RestorePoint.Value.empty()) {
595 1 : MachineBasicBlock *MBB = nullptr;
596 1 : if (parseMBBReference(PFS, MBB, YamlMFI.RestorePoint))
597 0 : return true;
598 1 : MFI.setRestorePoint(MBB);
599 : }
600 :
601 : std::vector<CalleeSavedInfo> CSIInfo;
602 : // Initialize the fixed frame objects.
603 4708 : for (const auto &Object : YamlMF.FixedStackObjects) {
604 : int ObjectIdx;
605 152 : if (Object.Type != yaml::FixedMachineStackObject::SpillSlot)
606 184 : ObjectIdx = MFI.CreateFixedObject(Object.Size, Object.Offset,
607 92 : Object.IsImmutable, Object.IsAliased);
608 : else
609 60 : ObjectIdx = MFI.CreateFixedSpillStackObject(Object.Size, Object.Offset);
610 152 : MFI.setObjectAlignment(ObjectIdx, Object.Alignment);
611 152 : MFI.setStackID(ObjectIdx, Object.StackID);
612 304 : if (!PFS.FixedStackObjectSlots.insert(std::make_pair(Object.ID.Value,
613 152 : ObjectIdx))
614 152 : .second)
615 1 : return error(Object.ID.SourceRange.Start,
616 1 : Twine("redefinition of fixed stack object '%fixed-stack.") +
617 2 : Twine(Object.ID.Value) + "'");
618 151 : if (parseCalleeSavedRegister(PFS, CSIInfo, Object.CalleeSavedRegister,
619 151 : Object.CalleeSavedRestored, ObjectIdx))
620 : return true;
621 150 : if (parseStackObjectsDebugInfo(PFS, Object, ObjectIdx))
622 : return true;
623 : }
624 :
625 : // Initialize the ordinary frame objects.
626 4832 : for (const auto &Object : YamlMF.StackObjects) {
627 : int ObjectIdx;
628 : const AllocaInst *Alloca = nullptr;
629 280 : const yaml::StringValue &Name = Object.Name;
630 280 : if (!Name.Value.empty()) {
631 105 : Alloca = dyn_cast_or_null<AllocaInst>(
632 : F.getValueSymbolTable()->lookup(Name.Value));
633 : if (!Alloca)
634 1 : return error(Name.SourceRange.Start,
635 2 : "alloca instruction named '" + Name.Value +
636 2 : "' isn't defined in the function '" + F.getName() +
637 1 : "'");
638 : }
639 279 : if (Object.Type == yaml::MachineStackObject::VariableSized)
640 4 : ObjectIdx = MFI.CreateVariableSizedObject(Object.Alignment, Alloca);
641 : else
642 550 : ObjectIdx = MFI.CreateStackObject(
643 275 : Object.Size, Object.Alignment,
644 : Object.Type == yaml::MachineStackObject::SpillSlot, Alloca);
645 279 : MFI.setObjectOffset(ObjectIdx, Object.Offset);
646 279 : MFI.setStackID(ObjectIdx, Object.StackID);
647 :
648 279 : if (!PFS.StackObjectSlots.insert(std::make_pair(Object.ID.Value, ObjectIdx))
649 279 : .second)
650 1 : return error(Object.ID.SourceRange.Start,
651 1 : Twine("redefinition of stack object '%stack.") +
652 2 : Twine(Object.ID.Value) + "'");
653 278 : if (parseCalleeSavedRegister(PFS, CSIInfo, Object.CalleeSavedRegister,
654 278 : Object.CalleeSavedRestored, ObjectIdx))
655 : return true;
656 278 : if (Object.LocalOffset)
657 57 : MFI.mapLocalFrameObject(ObjectIdx, Object.LocalOffset.getValue());
658 278 : if (parseStackObjectsDebugInfo(PFS, Object, ObjectIdx))
659 : return true;
660 : }
661 : MFI.setCalleeSavedInfo(CSIInfo);
662 4552 : if (!CSIInfo.empty())
663 : MFI.setCalleeSavedInfoValid(true);
664 :
665 : // Initialize the various stack object references after initializing the
666 : // stack objects.
667 4552 : if (!YamlMFI.StackProtector.Value.empty()) {
668 1 : SMDiagnostic Error;
669 : int FI;
670 2 : if (parseStackObjectReference(PFS, FI, YamlMFI.StackProtector.Value, Error))
671 1 : return error(Error, YamlMFI.StackProtector.SourceRange);
672 1 : MFI.setStackProtectorIndex(FI);
673 : }
674 : return false;
675 : }
676 :
677 429 : bool MIRParserImpl::parseCalleeSavedRegister(PerFunctionMIParsingState &PFS,
678 : std::vector<CalleeSavedInfo> &CSIInfo,
679 : const yaml::StringValue &RegisterSource, bool IsRestored, int FrameIdx) {
680 429 : if (RegisterSource.Value.empty())
681 : return false;
682 121 : unsigned Reg = 0;
683 121 : SMDiagnostic Error;
684 121 : if (parseNamedRegisterReference(PFS, Reg, RegisterSource.Value, Error))
685 1 : return error(Error, RegisterSource.SourceRange);
686 120 : CalleeSavedInfo CSI(Reg, FrameIdx);
687 : CSI.setRestored(IsRestored);
688 120 : CSIInfo.push_back(CSI);
689 120 : return false;
690 : }
691 :
692 : /// Verify that given node is of a certain type. Return true on error.
693 : template <typename T>
694 0 : static bool typecheckMDNode(T *&Result, MDNode *Node,
695 : const yaml::StringValue &Source,
696 : StringRef TypeString, MIRParserImpl &Parser) {
697 0 : if (!Node)
698 0 : return false;
699 0 : Result = dyn_cast<T>(Node);
700 0 : if (!Result)
701 0 : return Parser.error(Source.SourceRange.Start,
702 0 : "expected a reference to a '" + TypeString +
703 : "' metadata node");
704 : return false;
705 : }
706 0 :
707 : template <typename T>
708 : bool MIRParserImpl::parseStackObjectsDebugInfo(PerFunctionMIParsingState &PFS,
709 0 : const T &Object, int FrameIdx) {
710 0 : // Debug information can only be attached to stack objects; Fixed stack
711 0 : // objects aren't supported.
712 0 : MDNode *Var = nullptr, *Expr = nullptr, *Loc = nullptr;
713 0 : if (parseMDNode(PFS, Var, Object.DebugVar) ||
714 0 : parseMDNode(PFS, Expr, Object.DebugExpr) ||
715 : parseMDNode(PFS, Loc, Object.DebugLoc))
716 : return true;
717 : if (!Var && !Expr && !Loc)
718 0 : return false;
719 : DILocalVariable *DIVar = nullptr;
720 : DIExpression *DIExpr = nullptr;
721 0 : DILocation *DILoc = nullptr;
722 0 : if (typecheckMDNode(DIVar, Var, Object.DebugVar, "DILocalVariable", *this) ||
723 0 : typecheckMDNode(DIExpr, Expr, Object.DebugExpr, "DIExpression", *this) ||
724 0 : typecheckMDNode(DILoc, Loc, Object.DebugLoc, "DILocation", *this))
725 0 : return true;
726 0 : PFS.MF.setVariableDbgInfo(DIVar, DIExpr, FrameIdx, DILoc);
727 : return false;
728 : }
729 :
730 0 : bool MIRParserImpl::parseMDNode(PerFunctionMIParsingState &PFS,
731 : MDNode *&Node, const yaml::StringValue &Source) {
732 : if (Source.Value.empty())
733 0 : return false;
734 0 : SMDiagnostic Error;
735 0 : if (llvm::parseMDNode(PFS, Node, Source.Value, Error))
736 0 : return error(Error, Source.SourceRange);
737 0 : return false;
738 0 : }
739 :
740 : bool MIRParserImpl::initializeConstantPool(PerFunctionMIParsingState &PFS,
741 : MachineConstantPool &ConstantPool, const yaml::MachineFunction &YamlMF) {
742 : DenseMap<unsigned, unsigned> &ConstantPoolSlots = PFS.ConstantPoolSlots;
743 : const MachineFunction &MF = PFS.MF;
744 428 : const auto &M = *MF.getFunction().getParent();
745 : SMDiagnostic Error;
746 : for (const auto &YamlConstant : YamlMF.Constants) {
747 : if (YamlConstant.IsTargetSpecific)
748 428 : // FIXME: Support target-specific constant pools
749 855 : return error(YamlConstant.Value.SourceRange.Start,
750 855 : "Can't parse target-specific constant pool entries yet");
751 427 : const Constant *Value = dyn_cast_or_null<Constant>(
752 1 : parseConstantValue(YamlConstant.Value.Value, Error, M));
753 427 : if (!Value)
754 : return error(Error, YamlConstant.Value.SourceRange);
755 3 : unsigned Alignment =
756 3 : YamlConstant.Alignment
757 3 : ? YamlConstant.Alignment
758 5 : : M.getDataLayout().getPrefTypeAlignment(Value->getType());
759 5 : unsigned Index = ConstantPool.getConstantPoolIndex(Value, Alignment);
760 2 : if (!ConstantPoolSlots.insert(std::make_pair(YamlConstant.ID.Value, Index))
761 1 : .second)
762 2 : return error(YamlConstant.ID.SourceRange.Start,
763 2 : Twine("redefinition of constant pool item '%const.") +
764 : Twine(YamlConstant.ID.Value) + "'");
765 278 : }
766 : return false;
767 : }
768 :
769 278 : bool MIRParserImpl::initializeJumpTableInfo(PerFunctionMIParsingState &PFS,
770 555 : const yaml::MachineJumpTable &YamlJTI) {
771 555 : MachineJumpTableInfo *JTI = PFS.MF.getOrCreateJumpTableInfo(YamlJTI.Kind);
772 277 : for (const auto &Entry : YamlJTI.Entries) {
773 1 : std::vector<MachineBasicBlock *> Blocks;
774 277 : for (const auto &MBBSource : Entry.Blocks) {
775 : MachineBasicBlock *MBB = nullptr;
776 2 : if (parseMBBReference(PFS, MBB, MBBSource.Value))
777 2 : return true;
778 2 : Blocks.push_back(MBB);
779 3 : }
780 3 : unsigned Index = JTI->createJumpTableIndex(Blocks);
781 1 : if (!PFS.JumpTableSlots.insert(std::make_pair(Entry.ID.Value, Index))
782 1 : .second)
783 1 : return error(Entry.ID.SourceRange.Start,
784 1 : Twine("redefinition of jump table entry '%jump-table.") +
785 : Twine(Entry.ID.Value) + "'");
786 150 : }
787 : return false;
788 : }
789 :
790 150 : bool MIRParserImpl::parseMBBReference(PerFunctionMIParsingState &PFS,
791 300 : MachineBasicBlock *&MBB,
792 300 : const yaml::StringValue &Source) {
793 150 : SMDiagnostic Error;
794 0 : if (llvm::parseMBBReference(PFS, MBB, Source.Value, Error))
795 150 : return error(Error, Source.SourceRange);
796 : return false;
797 1 : }
798 1 :
799 1 : SMDiagnostic MIRParserImpl::diagFromMIStringDiag(const SMDiagnostic &Error,
800 2 : SMRange SourceRange) {
801 2 : assert(SourceRange.isValid() && "Invalid source range");
802 1 : SMLoc Loc = SourceRange.Start;
803 0 : bool HasQuote = Loc.getPointer() < SourceRange.End.getPointer() &&
804 1 : *Loc.getPointer() == '\'';
805 1 : // Translate the location of the error from the location in the MI string to
806 : // the corresponding location in the MIR file.
807 : Loc = Loc.getFromPointer(Loc.getPointer() + Error.getColumnNo() +
808 1282 : (HasQuote ? 1 : 0));
809 :
810 1282 : // TODO: Translate any source ranges as well.
811 : return SM.GetMessage(Loc, Error.getKind(), Error.getMessage(), None,
812 10 : Error.getFixIts());
813 10 : }
814 1 :
815 : SMDiagnostic MIRParserImpl::diagFromBlockStringDiag(const SMDiagnostic &Error,
816 : SMRange SourceRange) {
817 : assert(SourceRange.isValid());
818 20 :
819 : // Translate the location of the error from the location in the llvm IR string
820 20 : // to the corresponding location in the MIR file.
821 20 : auto LineAndColumn = SM.getLineAndColumn(SourceRange.Start);
822 20 : unsigned Line = LineAndColumn.first + Error.getLineNo() - 1;
823 20 : unsigned Column = Error.getColumnNo();
824 47 : StringRef LineStr = Error.getLineContents();
825 30 : SMLoc Loc = Error.getLoc();
826 :
827 1 : // Get the full line and adjust the column number by taking the indentation of
828 : // LLVM IR into account.
829 29 : for (line_iterator L(*SM.getMemoryBuffer(SM.getMainFileID()), false), E;
830 : L != E; ++L) {
831 : if (L.line_number() == Line) {
832 1 : LineStr = *L;
833 : Loc = SMLoc::getFromPointer(LineStr.data());
834 28 : auto Indent = LineStr.find(Error.getLineContents());
835 28 : if (Indent != StringRef::npos)
836 8 : Column += Indent;
837 28 : break;
838 28 : }
839 28 : }
840 1 :
841 1 : return SMDiagnostic(SM, Loc, Filename, Line, Column, Error.getKind(),
842 2 : Error.getMessage(), LineStr, Error.getRanges(),
843 : Error.getFixIts());
844 : }
845 :
846 : void MIRParserImpl::initNames2RegClasses(const MachineFunction &MF) {
847 10 : if (!Names2RegClasses.empty())
848 : return;
849 10 : const TargetRegisterInfo *TRI = MF.getSubtarget().getRegisterInfo();
850 20 : for (unsigned I = 0, E = TRI->getNumRegClasses(); I < E; ++I) {
851 : const auto *RC = TRI->getRegClass(I);
852 101 : Names2RegClasses.insert(
853 90 : std::make_pair(StringRef(TRI->getRegClassName(RC)).lower(), RC));
854 180 : }
855 0 : }
856 90 :
857 : void MIRParserImpl::initNames2RegBanks(const MachineFunction &MF) {
858 11 : if (!Names2RegBanks.empty())
859 11 : return;
860 11 : const RegisterBankInfo *RBI = MF.getSubtarget().getRegBankInfo();
861 1 : // If the target does not support GlobalISel, we may not have a
862 1 : // register bank info.
863 2 : if (!RBI)
864 : return;
865 : for (unsigned I = 0, E = RBI->getNumRegBanks(); I < E; ++I) {
866 : const auto &RegBank = RBI->getRegBank(I);
867 : Names2RegBanks.insert(
868 92 : std::make_pair(StringRef(RegBank.getName()).lower(), &RegBank));
869 : }
870 : }
871 92 :
872 92 : const TargetRegisterClass *MIRParserImpl::getRegClass(const MachineFunction &MF,
873 0 : StringRef Name) {
874 : auto RegClassInfo = Names2RegClasses.find(Name);
875 : if (RegClassInfo == Names2RegClasses.end())
876 : return nullptr;
877 7 : return RegClassInfo->getValue();
878 : }
879 :
880 7 : const RegisterBank *MIRParserImpl::getRegBank(const MachineFunction &MF,
881 7 : StringRef Name) {
882 7 : auto RegBankInfo = Names2RegBanks.find(Name);
883 : if (RegBankInfo == Names2RegBanks.end())
884 : return nullptr;
885 7 : return RegBankInfo->getValue();
886 7 : }
887 :
888 : MIRParser::MIRParser(std::unique_ptr<MIRParserImpl> Impl)
889 7 : : Impl(std::move(Impl)) {}
890 14 :
891 : MIRParser::~MIRParser() {}
892 :
893 96 : std::unique_ptr<Module> MIRParser::parseIRModule() {
894 : return Impl->parseIRModule();
895 : }
896 :
897 : bool MIRParser::parseMachineFunctions(Module &M, MachineModuleInfo &MMI) {
898 : return Impl->parseMachineFunctions(M, MMI);
899 96 : }
900 96 :
901 96 : std::unique_ptr<MIRParser> llvm::createMIRParserFromFile(StringRef Filename,
902 96 : SMDiagnostic &Error,
903 96 : LLVMContext &Context) {
904 : auto FileOrErr = MemoryBuffer::getFileOrSTDIN(Filename);
905 : if (std::error_code EC = FileOrErr.getError()) {
906 : Error = SMDiagnostic(Filename, SourceMgr::DK_Error,
907 96 : "Could not open input file: " + EC.message());
908 : return nullptr;
909 2171 : }
910 96 : return createMIRParser(std::move(FileOrErr.get()), Context);
911 96 : }
912 96 :
913 96 : std::unique_ptr<MIRParser>
914 96 : llvm::createMIRParser(std::unique_ptr<MemoryBuffer> Contents,
915 : LLVMContext &Context) {
916 : auto Filename = Contents->getBufferIdentifier();
917 : if (Context.shouldDiscardValueNames()) {
918 : Context.diagnose(DiagnosticInfoMIRParser(
919 : DS_Error,
920 : SMDiagnostic(
921 96 : Filename, SourceMgr::DK_Error,
922 : "Can't read MIR with a Context that discards named Values")));
923 : return nullptr;
924 4578 : }
925 4578 : return llvm::make_unique<MIRParser>(
926 : llvm::make_unique<MIRParserImpl>(std::move(Contents), Filename, Context));
927 1248 : }
|