1//===- MIRPrinter.cpp - MIR serialization format printer ------------------===//
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 file implements the class that prints out the LLVM IR and machine
10// functions using the MIR serialization format.
11//
12//===----------------------------------------------------------------------===//
13
14#include "llvm/CodeGen/MIRPrinter.h"
15#include "llvm/ADT/DenseMap.h"
16#include "llvm/ADT/STLExtras.h"
17#include "llvm/ADT/SmallBitVector.h"
18#include "llvm/ADT/SmallPtrSet.h"
19#include "llvm/ADT/SmallVector.h"
20#include "llvm/ADT/StringRef.h"
21#include "llvm/CodeGen/MIRYamlMapping.h"
22#include "llvm/CodeGen/MachineBasicBlock.h"
23#include "llvm/CodeGen/MachineConstantPool.h"
24#include "llvm/CodeGen/MachineFrameInfo.h"
25#include "llvm/CodeGen/MachineFunction.h"
26#include "llvm/CodeGen/MachineInstr.h"
27#include "llvm/CodeGen/MachineJumpTableInfo.h"
28#include "llvm/CodeGen/MachineMemOperand.h"
29#include "llvm/CodeGen/MachineModuleSlotTracker.h"
30#include "llvm/CodeGen/MachineOperand.h"
31#include "llvm/CodeGen/MachineRegisterInfo.h"
32#include "llvm/CodeGen/TargetFrameLowering.h"
33#include "llvm/CodeGen/TargetInstrInfo.h"
34#include "llvm/CodeGen/TargetRegisterInfo.h"
35#include "llvm/CodeGen/TargetSubtargetInfo.h"
36#include "llvm/CodeGenTypes/LowLevelType.h"
37#include "llvm/IR/DebugInfoMetadata.h"
38#include "llvm/IR/DebugLoc.h"
39#include "llvm/IR/Function.h"
40#include "llvm/IR/IRPrintingPasses.h"
41#include "llvm/IR/Instructions.h"
42#include "llvm/IR/Module.h"
43#include "llvm/IR/ModuleSlotTracker.h"
44#include "llvm/IR/Value.h"
45#include "llvm/MC/LaneBitmask.h"
46#include "llvm/Support/BranchProbability.h"
47#include "llvm/Support/Casting.h"
48#include "llvm/Support/CommandLine.h"
49#include "llvm/Support/ErrorHandling.h"
50#include "llvm/Support/Format.h"
51#include "llvm/Support/YAMLTraits.h"
52#include "llvm/Support/raw_ostream.h"
53#include "llvm/Target/TargetMachine.h"
54#include <algorithm>
55#include <cassert>
56#include <cinttypes>
57#include <cstdint>
58#include <iterator>
59#include <string>
60#include <utility>
61#include <vector>
62
63using namespace llvm;
64
65static cl::opt<bool> SimplifyMIR(
66 "simplify-mir", cl::Hidden,
67 cl::desc("Leave out unnecessary information when printing MIR"));
68
69static cl::opt<bool> PrintLocations("mir-debug-loc", cl::Hidden, cl::init(Val: true),
70 cl::desc("Print MIR debug-locations"));
71
72extern cl::opt<bool> WriteNewDbgInfoFormat;
73
74namespace {
75
76/// This structure describes how to print out stack object references.
77struct FrameIndexOperand {
78 std::string Name;
79 unsigned ID;
80 bool IsFixed;
81
82 FrameIndexOperand(StringRef Name, unsigned ID, bool IsFixed)
83 : Name(Name.str()), ID(ID), IsFixed(IsFixed) {}
84
85 /// Return an ordinary stack object reference.
86 static FrameIndexOperand create(StringRef Name, unsigned ID) {
87 return FrameIndexOperand(Name, ID, /*IsFixed=*/false);
88 }
89
90 /// Return a fixed stack object reference.
91 static FrameIndexOperand createFixed(unsigned ID) {
92 return FrameIndexOperand("", ID, /*IsFixed=*/true);
93 }
94};
95
96} // end anonymous namespace
97
98namespace llvm {
99
100/// This class prints out the machine functions using the MIR serialization
101/// format.
102class MIRPrinter {
103 raw_ostream &OS;
104 DenseMap<const uint32_t *, unsigned> RegisterMaskIds;
105 /// Maps from stack object indices to operand indices which will be used when
106 /// printing frame index machine operands.
107 DenseMap<int, FrameIndexOperand> StackObjectOperandMapping;
108
109public:
110 MIRPrinter(raw_ostream &OS) : OS(OS) {}
111
112 void print(const MachineFunction &MF);
113
114 void convert(yaml::MachineFunction &MF, const MachineRegisterInfo &RegInfo,
115 const TargetRegisterInfo *TRI);
116 void convert(ModuleSlotTracker &MST, yaml::MachineFrameInfo &YamlMFI,
117 const MachineFrameInfo &MFI);
118 void convert(yaml::MachineFunction &MF,
119 const MachineConstantPool &ConstantPool);
120 void convert(ModuleSlotTracker &MST, yaml::MachineJumpTable &YamlJTI,
121 const MachineJumpTableInfo &JTI);
122 void convertStackObjects(yaml::MachineFunction &YMF,
123 const MachineFunction &MF, ModuleSlotTracker &MST);
124 void convertEntryValueObjects(yaml::MachineFunction &YMF,
125 const MachineFunction &MF,
126 ModuleSlotTracker &MST);
127 void convertCallSiteObjects(yaml::MachineFunction &YMF,
128 const MachineFunction &MF,
129 ModuleSlotTracker &MST);
130 void convertMachineMetadataNodes(yaml::MachineFunction &YMF,
131 const MachineFunction &MF,
132 MachineModuleSlotTracker &MST);
133
134private:
135 void initRegisterMaskIds(const MachineFunction &MF);
136};
137
138/// This class prints out the machine instructions using the MIR serialization
139/// format.
140class MIPrinter {
141 raw_ostream &OS;
142 ModuleSlotTracker &MST;
143 const DenseMap<const uint32_t *, unsigned> &RegisterMaskIds;
144 const DenseMap<int, FrameIndexOperand> &StackObjectOperandMapping;
145 /// Synchronization scope names registered with LLVMContext.
146 SmallVector<StringRef, 8> SSNs;
147
148 bool canPredictBranchProbabilities(const MachineBasicBlock &MBB) const;
149 bool canPredictSuccessors(const MachineBasicBlock &MBB) const;
150
151public:
152 MIPrinter(raw_ostream &OS, ModuleSlotTracker &MST,
153 const DenseMap<const uint32_t *, unsigned> &RegisterMaskIds,
154 const DenseMap<int, FrameIndexOperand> &StackObjectOperandMapping)
155 : OS(OS), MST(MST), RegisterMaskIds(RegisterMaskIds),
156 StackObjectOperandMapping(StackObjectOperandMapping) {}
157
158 void print(const MachineBasicBlock &MBB);
159
160 void print(const MachineInstr &MI);
161 void printStackObjectReference(int FrameIndex);
162 void print(const MachineInstr &MI, unsigned OpIdx,
163 const TargetRegisterInfo *TRI, const TargetInstrInfo *TII,
164 bool ShouldPrintRegisterTies, LLT TypeToPrint,
165 bool PrintDef = true);
166};
167
168} // end namespace llvm
169
170namespace llvm {
171namespace yaml {
172
173/// This struct serializes the LLVM IR module.
174template <> struct BlockScalarTraits<Module> {
175 static void output(const Module &Mod, void *Ctxt, raw_ostream &OS) {
176 Mod.print(OS, AAW: nullptr);
177 }
178
179 static StringRef input(StringRef Str, void *Ctxt, Module &Mod) {
180 llvm_unreachable("LLVM Module is supposed to be parsed separately");
181 return "";
182 }
183};
184
185} // end namespace yaml
186} // end namespace llvm
187
188static void printRegMIR(unsigned Reg, yaml::StringValue &Dest,
189 const TargetRegisterInfo *TRI) {
190 raw_string_ostream OS(Dest.Value);
191 OS << printReg(Reg, TRI);
192}
193
194void MIRPrinter::print(const MachineFunction &MF) {
195 initRegisterMaskIds(MF);
196
197 yaml::MachineFunction YamlMF;
198 YamlMF.Name = MF.getName();
199 YamlMF.Alignment = MF.getAlignment();
200 YamlMF.ExposesReturnsTwice = MF.exposesReturnsTwice();
201 YamlMF.HasWinCFI = MF.hasWinCFI();
202
203 YamlMF.CallsEHReturn = MF.callsEHReturn();
204 YamlMF.CallsUnwindInit = MF.callsUnwindInit();
205 YamlMF.HasEHCatchret = MF.hasEHCatchret();
206 YamlMF.HasEHScopes = MF.hasEHScopes();
207 YamlMF.HasEHFunclets = MF.hasEHFunclets();
208 YamlMF.IsOutlined = MF.isOutlined();
209 YamlMF.UseDebugInstrRef = MF.useDebugInstrRef();
210
211 YamlMF.Legalized = MF.getProperties().hasProperty(
212 P: MachineFunctionProperties::Property::Legalized);
213 YamlMF.RegBankSelected = MF.getProperties().hasProperty(
214 P: MachineFunctionProperties::Property::RegBankSelected);
215 YamlMF.Selected = MF.getProperties().hasProperty(
216 P: MachineFunctionProperties::Property::Selected);
217 YamlMF.FailedISel = MF.getProperties().hasProperty(
218 P: MachineFunctionProperties::Property::FailedISel);
219 YamlMF.FailsVerification = MF.getProperties().hasProperty(
220 P: MachineFunctionProperties::Property::FailsVerification);
221 YamlMF.TracksDebugUserValues = MF.getProperties().hasProperty(
222 P: MachineFunctionProperties::Property::TracksDebugUserValues);
223
224 convert(MF&: YamlMF, RegInfo: MF.getRegInfo(), TRI: MF.getSubtarget().getRegisterInfo());
225 MachineModuleSlotTracker MST(&MF);
226 MST.incorporateFunction(F: MF.getFunction());
227 convert(MST, YamlMFI&: YamlMF.FrameInfo, MFI: MF.getFrameInfo());
228 convertStackObjects(YMF&: YamlMF, MF, MST);
229 convertEntryValueObjects(YMF&: YamlMF, MF, MST);
230 convertCallSiteObjects(YMF&: YamlMF, MF, MST);
231 for (const auto &Sub : MF.DebugValueSubstitutions) {
232 const auto &SubSrc = Sub.Src;
233 const auto &SubDest = Sub.Dest;
234 YamlMF.DebugValueSubstitutions.push_back(x: {.SrcInst: SubSrc.first, .SrcOp: SubSrc.second,
235 .DstInst: SubDest.first,
236 .DstOp: SubDest.second,
237 .Subreg: Sub.Subreg});
238 }
239 if (const auto *ConstantPool = MF.getConstantPool())
240 convert(MF&: YamlMF, ConstantPool: *ConstantPool);
241 if (const auto *JumpTableInfo = MF.getJumpTableInfo())
242 convert(MST, YamlJTI&: YamlMF.JumpTableInfo, JTI: *JumpTableInfo);
243
244 const TargetMachine &TM = MF.getTarget();
245 YamlMF.MachineFuncInfo =
246 std::unique_ptr<yaml::MachineFunctionInfo>(TM.convertFuncInfoToYAML(MF));
247
248 raw_string_ostream StrOS(YamlMF.Body.Value.Value);
249 bool IsNewlineNeeded = false;
250 for (const auto &MBB : MF) {
251 if (IsNewlineNeeded)
252 StrOS << "\n";
253 MIPrinter(StrOS, MST, RegisterMaskIds, StackObjectOperandMapping)
254 .print(MBB);
255 IsNewlineNeeded = true;
256 }
257 StrOS.flush();
258 // Convert machine metadata collected during the print of the machine
259 // function.
260 convertMachineMetadataNodes(YMF&: YamlMF, MF, MST);
261
262 yaml::Output Out(OS);
263 if (!SimplifyMIR)
264 Out.setWriteDefaultValues(true);
265 Out << YamlMF;
266}
267
268static void printCustomRegMask(const uint32_t *RegMask, raw_ostream &OS,
269 const TargetRegisterInfo *TRI) {
270 assert(RegMask && "Can't print an empty register mask");
271 OS << StringRef("CustomRegMask(");
272
273 bool IsRegInRegMaskFound = false;
274 for (int I = 0, E = TRI->getNumRegs(); I < E; I++) {
275 // Check whether the register is asserted in regmask.
276 if (RegMask[I / 32] & (1u << (I % 32))) {
277 if (IsRegInRegMaskFound)
278 OS << ',';
279 OS << printReg(Reg: I, TRI);
280 IsRegInRegMaskFound = true;
281 }
282 }
283
284 OS << ')';
285}
286
287static void printRegClassOrBank(unsigned Reg, yaml::StringValue &Dest,
288 const MachineRegisterInfo &RegInfo,
289 const TargetRegisterInfo *TRI) {
290 raw_string_ostream OS(Dest.Value);
291 OS << printRegClassOrBank(Reg, RegInfo, TRI);
292}
293
294template <typename T>
295static void
296printStackObjectDbgInfo(const MachineFunction::VariableDbgInfo &DebugVar,
297 T &Object, ModuleSlotTracker &MST) {
298 std::array<std::string *, 3> Outputs{{&Object.DebugVar.Value,
299 &Object.DebugExpr.Value,
300 &Object.DebugLoc.Value}};
301 std::array<const Metadata *, 3> Metas{._M_elems: {DebugVar.Var,
302 DebugVar.Expr,
303 DebugVar.Loc}};
304 for (unsigned i = 0; i < 3; ++i) {
305 raw_string_ostream StrOS(*Outputs[i]);
306 Metas[i]->printAsOperand(OS&: StrOS, MST);
307 }
308}
309
310void MIRPrinter::convert(yaml::MachineFunction &MF,
311 const MachineRegisterInfo &RegInfo,
312 const TargetRegisterInfo *TRI) {
313 MF.TracksRegLiveness = RegInfo.tracksLiveness();
314
315 // Print the virtual register definitions.
316 for (unsigned I = 0, E = RegInfo.getNumVirtRegs(); I < E; ++I) {
317 Register Reg = Register::index2VirtReg(Index: I);
318 yaml::VirtualRegisterDefinition VReg;
319 VReg.ID = I;
320 if (RegInfo.getVRegName(Reg) != "")
321 continue;
322 ::printRegClassOrBank(Reg, Dest&: VReg.Class, RegInfo, TRI);
323 Register PreferredReg = RegInfo.getSimpleHint(VReg: Reg);
324 if (PreferredReg)
325 printRegMIR(Reg: PreferredReg, Dest&: VReg.PreferredRegister, TRI);
326 MF.VirtualRegisters.push_back(x: VReg);
327 }
328
329 // Print the live ins.
330 for (std::pair<unsigned, unsigned> LI : RegInfo.liveins()) {
331 yaml::MachineFunctionLiveIn LiveIn;
332 printRegMIR(Reg: LI.first, Dest&: LiveIn.Register, TRI);
333 if (LI.second)
334 printRegMIR(Reg: LI.second, Dest&: LiveIn.VirtualRegister, TRI);
335 MF.LiveIns.push_back(x: LiveIn);
336 }
337
338 // Prints the callee saved registers.
339 if (RegInfo.isUpdatedCSRsInitialized()) {
340 const MCPhysReg *CalleeSavedRegs = RegInfo.getCalleeSavedRegs();
341 std::vector<yaml::FlowStringValue> CalleeSavedRegisters;
342 for (const MCPhysReg *I = CalleeSavedRegs; *I; ++I) {
343 yaml::FlowStringValue Reg;
344 printRegMIR(Reg: *I, Dest&: Reg, TRI);
345 CalleeSavedRegisters.push_back(x: Reg);
346 }
347 MF.CalleeSavedRegisters = CalleeSavedRegisters;
348 }
349}
350
351void MIRPrinter::convert(ModuleSlotTracker &MST,
352 yaml::MachineFrameInfo &YamlMFI,
353 const MachineFrameInfo &MFI) {
354 YamlMFI.IsFrameAddressTaken = MFI.isFrameAddressTaken();
355 YamlMFI.IsReturnAddressTaken = MFI.isReturnAddressTaken();
356 YamlMFI.HasStackMap = MFI.hasStackMap();
357 YamlMFI.HasPatchPoint = MFI.hasPatchPoint();
358 YamlMFI.StackSize = MFI.getStackSize();
359 YamlMFI.OffsetAdjustment = MFI.getOffsetAdjustment();
360 YamlMFI.MaxAlignment = MFI.getMaxAlign().value();
361 YamlMFI.AdjustsStack = MFI.adjustsStack();
362 YamlMFI.HasCalls = MFI.hasCalls();
363 YamlMFI.MaxCallFrameSize = MFI.isMaxCallFrameSizeComputed()
364 ? MFI.getMaxCallFrameSize() : ~0u;
365 YamlMFI.CVBytesOfCalleeSavedRegisters =
366 MFI.getCVBytesOfCalleeSavedRegisters();
367 YamlMFI.HasOpaqueSPAdjustment = MFI.hasOpaqueSPAdjustment();
368 YamlMFI.HasVAStart = MFI.hasVAStart();
369 YamlMFI.HasMustTailInVarArgFunc = MFI.hasMustTailInVarArgFunc();
370 YamlMFI.HasTailCall = MFI.hasTailCall();
371 YamlMFI.LocalFrameSize = MFI.getLocalFrameSize();
372 if (MFI.getSavePoint()) {
373 raw_string_ostream StrOS(YamlMFI.SavePoint.Value);
374 StrOS << printMBBReference(MBB: *MFI.getSavePoint());
375 }
376 if (MFI.getRestorePoint()) {
377 raw_string_ostream StrOS(YamlMFI.RestorePoint.Value);
378 StrOS << printMBBReference(MBB: *MFI.getRestorePoint());
379 }
380}
381
382void MIRPrinter::convertEntryValueObjects(yaml::MachineFunction &YMF,
383 const MachineFunction &MF,
384 ModuleSlotTracker &MST) {
385 const TargetRegisterInfo *TRI = MF.getSubtarget().getRegisterInfo();
386 for (const MachineFunction::VariableDbgInfo &DebugVar :
387 MF.getEntryValueVariableDbgInfo()) {
388 yaml::EntryValueObject &Obj = YMF.EntryValueObjects.emplace_back();
389 printStackObjectDbgInfo(DebugVar, Object&: Obj, MST);
390 MCRegister EntryValReg = DebugVar.getEntryValueRegister();
391 printRegMIR(Reg: EntryValReg, Dest&: Obj.EntryValueRegister, TRI);
392 }
393}
394
395void MIRPrinter::convertStackObjects(yaml::MachineFunction &YMF,
396 const MachineFunction &MF,
397 ModuleSlotTracker &MST) {
398 const MachineFrameInfo &MFI = MF.getFrameInfo();
399 const TargetRegisterInfo *TRI = MF.getSubtarget().getRegisterInfo();
400
401 // Process fixed stack objects.
402 assert(YMF.FixedStackObjects.empty());
403 SmallVector<int, 32> FixedStackObjectsIdx;
404 const int BeginIdx = MFI.getObjectIndexBegin();
405 if (BeginIdx < 0)
406 FixedStackObjectsIdx.reserve(N: -BeginIdx);
407
408 unsigned ID = 0;
409 for (int I = BeginIdx; I < 0; ++I, ++ID) {
410 FixedStackObjectsIdx.push_back(Elt: -1); // Fill index for possible dead.
411 if (MFI.isDeadObjectIndex(ObjectIdx: I))
412 continue;
413
414 yaml::FixedMachineStackObject YamlObject;
415 YamlObject.ID = ID;
416 YamlObject.Type = MFI.isSpillSlotObjectIndex(ObjectIdx: I)
417 ? yaml::FixedMachineStackObject::SpillSlot
418 : yaml::FixedMachineStackObject::DefaultType;
419 YamlObject.Offset = MFI.getObjectOffset(ObjectIdx: I);
420 YamlObject.Size = MFI.getObjectSize(ObjectIdx: I);
421 YamlObject.Alignment = MFI.getObjectAlign(ObjectIdx: I);
422 YamlObject.StackID = (TargetStackID::Value)MFI.getStackID(ObjectIdx: I);
423 YamlObject.IsImmutable = MFI.isImmutableObjectIndex(ObjectIdx: I);
424 YamlObject.IsAliased = MFI.isAliasedObjectIndex(ObjectIdx: I);
425 // Save the ID' position in FixedStackObjects storage vector.
426 FixedStackObjectsIdx[ID] = YMF.FixedStackObjects.size();
427 YMF.FixedStackObjects.push_back(x: YamlObject);
428 StackObjectOperandMapping.insert(
429 KV: std::make_pair(x&: I, y: FrameIndexOperand::createFixed(ID)));
430 }
431
432 // Process ordinary stack objects.
433 assert(YMF.StackObjects.empty());
434 SmallVector<unsigned, 32> StackObjectsIdx;
435 const int EndIdx = MFI.getObjectIndexEnd();
436 if (EndIdx > 0)
437 StackObjectsIdx.reserve(N: EndIdx);
438 ID = 0;
439 for (int I = 0; I < EndIdx; ++I, ++ID) {
440 StackObjectsIdx.push_back(Elt: -1); // Fill index for possible dead.
441 if (MFI.isDeadObjectIndex(ObjectIdx: I))
442 continue;
443
444 yaml::MachineStackObject YamlObject;
445 YamlObject.ID = ID;
446 if (const auto *Alloca = MFI.getObjectAllocation(ObjectIdx: I))
447 YamlObject.Name.Value = std::string(
448 Alloca->hasName() ? Alloca->getName() : "");
449 YamlObject.Type = MFI.isSpillSlotObjectIndex(ObjectIdx: I)
450 ? yaml::MachineStackObject::SpillSlot
451 : MFI.isVariableSizedObjectIndex(ObjectIdx: I)
452 ? yaml::MachineStackObject::VariableSized
453 : yaml::MachineStackObject::DefaultType;
454 YamlObject.Offset = MFI.getObjectOffset(ObjectIdx: I);
455 YamlObject.Size = MFI.getObjectSize(ObjectIdx: I);
456 YamlObject.Alignment = MFI.getObjectAlign(ObjectIdx: I);
457 YamlObject.StackID = (TargetStackID::Value)MFI.getStackID(ObjectIdx: I);
458
459 // Save the ID' position in StackObjects storage vector.
460 StackObjectsIdx[ID] = YMF.StackObjects.size();
461 YMF.StackObjects.push_back(x: YamlObject);
462 StackObjectOperandMapping.insert(KV: std::make_pair(
463 x&: I, y: FrameIndexOperand::create(Name: YamlObject.Name.Value, ID)));
464 }
465
466 for (const auto &CSInfo : MFI.getCalleeSavedInfo()) {
467 const int FrameIdx = CSInfo.getFrameIdx();
468 if (!CSInfo.isSpilledToReg() && MFI.isDeadObjectIndex(ObjectIdx: FrameIdx))
469 continue;
470
471 yaml::StringValue Reg;
472 printRegMIR(Reg: CSInfo.getReg(), Dest&: Reg, TRI);
473 if (!CSInfo.isSpilledToReg()) {
474 assert(FrameIdx >= MFI.getObjectIndexBegin() &&
475 FrameIdx < MFI.getObjectIndexEnd() &&
476 "Invalid stack object index");
477 if (FrameIdx < 0) { // Negative index means fixed objects.
478 auto &Object =
479 YMF.FixedStackObjects
480 [FixedStackObjectsIdx[FrameIdx + MFI.getNumFixedObjects()]];
481 Object.CalleeSavedRegister = Reg;
482 Object.CalleeSavedRestored = CSInfo.isRestored();
483 } else {
484 auto &Object = YMF.StackObjects[StackObjectsIdx[FrameIdx]];
485 Object.CalleeSavedRegister = Reg;
486 Object.CalleeSavedRestored = CSInfo.isRestored();
487 }
488 }
489 }
490 for (unsigned I = 0, E = MFI.getLocalFrameObjectCount(); I < E; ++I) {
491 auto LocalObject = MFI.getLocalFrameObjectMap(i: I);
492 assert(LocalObject.first >= 0 && "Expected a locally mapped stack object");
493 YMF.StackObjects[StackObjectsIdx[LocalObject.first]].LocalOffset =
494 LocalObject.second;
495 }
496
497 // Print the stack object references in the frame information class after
498 // converting the stack objects.
499 if (MFI.hasStackProtectorIndex()) {
500 raw_string_ostream StrOS(YMF.FrameInfo.StackProtector.Value);
501 MIPrinter(StrOS, MST, RegisterMaskIds, StackObjectOperandMapping)
502 .printStackObjectReference(FrameIndex: MFI.getStackProtectorIndex());
503 }
504
505 if (MFI.hasFunctionContextIndex()) {
506 raw_string_ostream StrOS(YMF.FrameInfo.FunctionContext.Value);
507 MIPrinter(StrOS, MST, RegisterMaskIds, StackObjectOperandMapping)
508 .printStackObjectReference(FrameIndex: MFI.getFunctionContextIndex());
509 }
510
511 // Print the debug variable information.
512 for (const MachineFunction::VariableDbgInfo &DebugVar :
513 MF.getInStackSlotVariableDbgInfo()) {
514 int Idx = DebugVar.getStackSlot();
515 assert(Idx >= MFI.getObjectIndexBegin() && Idx < MFI.getObjectIndexEnd() &&
516 "Invalid stack object index");
517 if (Idx < 0) { // Negative index means fixed objects.
518 auto &Object =
519 YMF.FixedStackObjects[FixedStackObjectsIdx[Idx +
520 MFI.getNumFixedObjects()]];
521 printStackObjectDbgInfo(DebugVar, Object, MST);
522 } else {
523 auto &Object = YMF.StackObjects[StackObjectsIdx[Idx]];
524 printStackObjectDbgInfo(DebugVar, Object, MST);
525 }
526 }
527}
528
529void MIRPrinter::convertCallSiteObjects(yaml::MachineFunction &YMF,
530 const MachineFunction &MF,
531 ModuleSlotTracker &MST) {
532 const auto *TRI = MF.getSubtarget().getRegisterInfo();
533 for (auto CSInfo : MF.getCallSitesInfo()) {
534 yaml::CallSiteInfo YmlCS;
535 yaml::CallSiteInfo::MachineInstrLoc CallLocation;
536
537 // Prepare instruction position.
538 MachineBasicBlock::const_instr_iterator CallI = CSInfo.first->getIterator();
539 CallLocation.BlockNum = CallI->getParent()->getNumber();
540 // Get call instruction offset from the beginning of block.
541 CallLocation.Offset =
542 std::distance(first: CallI->getParent()->instr_begin(), last: CallI);
543 YmlCS.CallLocation = CallLocation;
544 // Construct call arguments and theirs forwarding register info.
545 for (auto ArgReg : CSInfo.second.ArgRegPairs) {
546 yaml::CallSiteInfo::ArgRegPair YmlArgReg;
547 YmlArgReg.ArgNo = ArgReg.ArgNo;
548 printRegMIR(Reg: ArgReg.Reg, Dest&: YmlArgReg.Reg, TRI);
549 YmlCS.ArgForwardingRegs.emplace_back(args&: YmlArgReg);
550 }
551 YMF.CallSitesInfo.push_back(x: YmlCS);
552 }
553
554 // Sort call info by position of call instructions.
555 llvm::sort(Start: YMF.CallSitesInfo.begin(), End: YMF.CallSitesInfo.end(),
556 Comp: [](yaml::CallSiteInfo A, yaml::CallSiteInfo B) {
557 if (A.CallLocation.BlockNum == B.CallLocation.BlockNum)
558 return A.CallLocation.Offset < B.CallLocation.Offset;
559 return A.CallLocation.BlockNum < B.CallLocation.BlockNum;
560 });
561}
562
563void MIRPrinter::convertMachineMetadataNodes(yaml::MachineFunction &YMF,
564 const MachineFunction &MF,
565 MachineModuleSlotTracker &MST) {
566 MachineModuleSlotTracker::MachineMDNodeListType MDList;
567 MST.collectMachineMDNodes(L&: MDList);
568 for (auto &MD : MDList) {
569 std::string NS;
570 raw_string_ostream StrOS(NS);
571 MD.second->print(OS&: StrOS, MST, M: MF.getFunction().getParent());
572 YMF.MachineMetadataNodes.push_back(x: StrOS.str());
573 }
574}
575
576void MIRPrinter::convert(yaml::MachineFunction &MF,
577 const MachineConstantPool &ConstantPool) {
578 unsigned ID = 0;
579 for (const MachineConstantPoolEntry &Constant : ConstantPool.getConstants()) {
580 std::string Str;
581 raw_string_ostream StrOS(Str);
582 if (Constant.isMachineConstantPoolEntry()) {
583 Constant.Val.MachineCPVal->print(O&: StrOS);
584 } else {
585 Constant.Val.ConstVal->printAsOperand(O&: StrOS);
586 }
587
588 yaml::MachineConstantPoolValue YamlConstant;
589 YamlConstant.ID = ID++;
590 YamlConstant.Value = StrOS.str();
591 YamlConstant.Alignment = Constant.getAlign();
592 YamlConstant.IsTargetSpecific = Constant.isMachineConstantPoolEntry();
593
594 MF.Constants.push_back(x: YamlConstant);
595 }
596}
597
598void MIRPrinter::convert(ModuleSlotTracker &MST,
599 yaml::MachineJumpTable &YamlJTI,
600 const MachineJumpTableInfo &JTI) {
601 YamlJTI.Kind = JTI.getEntryKind();
602 unsigned ID = 0;
603 for (const auto &Table : JTI.getJumpTables()) {
604 std::string Str;
605 yaml::MachineJumpTable::Entry Entry;
606 Entry.ID = ID++;
607 for (const auto *MBB : Table.MBBs) {
608 raw_string_ostream StrOS(Str);
609 StrOS << printMBBReference(MBB: *MBB);
610 Entry.Blocks.push_back(x: StrOS.str());
611 Str.clear();
612 }
613 YamlJTI.Entries.push_back(x: Entry);
614 }
615}
616
617void MIRPrinter::initRegisterMaskIds(const MachineFunction &MF) {
618 const auto *TRI = MF.getSubtarget().getRegisterInfo();
619 unsigned I = 0;
620 for (const uint32_t *Mask : TRI->getRegMasks())
621 RegisterMaskIds.insert(KV: std::make_pair(x&: Mask, y: I++));
622}
623
624void llvm::guessSuccessors(const MachineBasicBlock &MBB,
625 SmallVectorImpl<MachineBasicBlock*> &Result,
626 bool &IsFallthrough) {
627 SmallPtrSet<MachineBasicBlock*,8> Seen;
628
629 for (const MachineInstr &MI : MBB) {
630 if (MI.isPHI())
631 continue;
632 for (const MachineOperand &MO : MI.operands()) {
633 if (!MO.isMBB())
634 continue;
635 MachineBasicBlock *Succ = MO.getMBB();
636 auto RP = Seen.insert(Ptr: Succ);
637 if (RP.second)
638 Result.push_back(Elt: Succ);
639 }
640 }
641 MachineBasicBlock::const_iterator I = MBB.getLastNonDebugInstr();
642 IsFallthrough = I == MBB.end() || !I->isBarrier();
643}
644
645bool
646MIPrinter::canPredictBranchProbabilities(const MachineBasicBlock &MBB) const {
647 if (MBB.succ_size() <= 1)
648 return true;
649 if (!MBB.hasSuccessorProbabilities())
650 return true;
651
652 SmallVector<BranchProbability,8> Normalized(MBB.Probs.begin(),
653 MBB.Probs.end());
654 BranchProbability::normalizeProbabilities(Begin: Normalized.begin(),
655 End: Normalized.end());
656 SmallVector<BranchProbability,8> Equal(Normalized.size());
657 BranchProbability::normalizeProbabilities(Begin: Equal.begin(), End: Equal.end());
658
659 return std::equal(first1: Normalized.begin(), last1: Normalized.end(), first2: Equal.begin());
660}
661
662bool MIPrinter::canPredictSuccessors(const MachineBasicBlock &MBB) const {
663 SmallVector<MachineBasicBlock*,8> GuessedSuccs;
664 bool GuessedFallthrough;
665 guessSuccessors(MBB, Result&: GuessedSuccs, IsFallthrough&: GuessedFallthrough);
666 if (GuessedFallthrough) {
667 const MachineFunction &MF = *MBB.getParent();
668 MachineFunction::const_iterator NextI = std::next(x: MBB.getIterator());
669 if (NextI != MF.end()) {
670 MachineBasicBlock *Next = const_cast<MachineBasicBlock*>(&*NextI);
671 if (!is_contained(Range&: GuessedSuccs, Element: Next))
672 GuessedSuccs.push_back(Elt: Next);
673 }
674 }
675 if (GuessedSuccs.size() != MBB.succ_size())
676 return false;
677 return std::equal(first1: MBB.succ_begin(), last1: MBB.succ_end(), first2: GuessedSuccs.begin());
678}
679
680void MIPrinter::print(const MachineBasicBlock &MBB) {
681 assert(MBB.getNumber() >= 0 && "Invalid MBB number");
682 MBB.printName(os&: OS,
683 printNameFlags: MachineBasicBlock::PrintNameIr |
684 MachineBasicBlock::PrintNameAttributes,
685 moduleSlotTracker: &MST);
686 OS << ":\n";
687
688 bool HasLineAttributes = false;
689 // Print the successors
690 bool canPredictProbs = canPredictBranchProbabilities(MBB);
691 // Even if the list of successors is empty, if we cannot guess it,
692 // we need to print it to tell the parser that the list is empty.
693 // This is needed, because MI model unreachable as empty blocks
694 // with an empty successor list. If the parser would see that
695 // without the successor list, it would guess the code would
696 // fallthrough.
697 if ((!MBB.succ_empty() && !SimplifyMIR) || !canPredictProbs ||
698 !canPredictSuccessors(MBB)) {
699 OS.indent(NumSpaces: 2) << "successors:";
700 if (!MBB.succ_empty())
701 OS << " ";
702 for (auto I = MBB.succ_begin(), E = MBB.succ_end(); I != E; ++I) {
703 if (I != MBB.succ_begin())
704 OS << ", ";
705 OS << printMBBReference(MBB: **I);
706 if (!SimplifyMIR || !canPredictProbs)
707 OS << '('
708 << format(Fmt: "0x%08" PRIx32, Vals: MBB.getSuccProbability(Succ: I).getNumerator())
709 << ')';
710 }
711 OS << "\n";
712 HasLineAttributes = true;
713 }
714
715 // Print the live in registers.
716 const MachineRegisterInfo &MRI = MBB.getParent()->getRegInfo();
717 if (!MBB.livein_empty()) {
718 const TargetRegisterInfo &TRI = *MRI.getTargetRegisterInfo();
719 OS.indent(NumSpaces: 2) << "liveins: ";
720 bool First = true;
721 for (const auto &LI : MBB.liveins_dbg()) {
722 if (!First)
723 OS << ", ";
724 First = false;
725 OS << printReg(Reg: LI.PhysReg, TRI: &TRI);
726 if (!LI.LaneMask.all())
727 OS << ":0x" << PrintLaneMask(LaneMask: LI.LaneMask);
728 }
729 OS << "\n";
730 HasLineAttributes = true;
731 }
732
733 if (HasLineAttributes && !MBB.empty())
734 OS << "\n";
735 bool IsInBundle = false;
736 for (const MachineInstr &MI : MBB.instrs()) {
737 if (IsInBundle && !MI.isInsideBundle()) {
738 OS.indent(NumSpaces: 2) << "}\n";
739 IsInBundle = false;
740 }
741 OS.indent(NumSpaces: IsInBundle ? 4 : 2);
742 print(MI);
743 if (!IsInBundle && MI.getFlag(Flag: MachineInstr::BundledSucc)) {
744 OS << " {";
745 IsInBundle = true;
746 }
747 OS << "\n";
748 }
749 if (IsInBundle)
750 OS.indent(NumSpaces: 2) << "}\n";
751}
752
753void MIPrinter::print(const MachineInstr &MI) {
754 const auto *MF = MI.getMF();
755 const auto &MRI = MF->getRegInfo();
756 const auto &SubTarget = MF->getSubtarget();
757 const auto *TRI = SubTarget.getRegisterInfo();
758 assert(TRI && "Expected target register info");
759 const auto *TII = SubTarget.getInstrInfo();
760 assert(TII && "Expected target instruction info");
761 if (MI.isCFIInstruction())
762 assert(MI.getNumOperands() == 1 && "Expected 1 operand in CFI instruction");
763
764 SmallBitVector PrintedTypes(8);
765 bool ShouldPrintRegisterTies = MI.hasComplexRegisterTies();
766 unsigned I = 0, E = MI.getNumOperands();
767 for (; I < E && MI.getOperand(i: I).isReg() && MI.getOperand(i: I).isDef() &&
768 !MI.getOperand(i: I).isImplicit();
769 ++I) {
770 if (I)
771 OS << ", ";
772 print(MI, OpIdx: I, TRI, TII, ShouldPrintRegisterTies,
773 TypeToPrint: MI.getTypeToPrint(OpIdx: I, PrintedTypes, MRI),
774 /*PrintDef=*/false);
775 }
776
777 if (I)
778 OS << " = ";
779 if (MI.getFlag(Flag: MachineInstr::FrameSetup))
780 OS << "frame-setup ";
781 if (MI.getFlag(Flag: MachineInstr::FrameDestroy))
782 OS << "frame-destroy ";
783 if (MI.getFlag(Flag: MachineInstr::FmNoNans))
784 OS << "nnan ";
785 if (MI.getFlag(Flag: MachineInstr::FmNoInfs))
786 OS << "ninf ";
787 if (MI.getFlag(Flag: MachineInstr::FmNsz))
788 OS << "nsz ";
789 if (MI.getFlag(Flag: MachineInstr::FmArcp))
790 OS << "arcp ";
791 if (MI.getFlag(Flag: MachineInstr::FmContract))
792 OS << "contract ";
793 if (MI.getFlag(Flag: MachineInstr::FmAfn))
794 OS << "afn ";
795 if (MI.getFlag(Flag: MachineInstr::FmReassoc))
796 OS << "reassoc ";
797 if (MI.getFlag(Flag: MachineInstr::NoUWrap))
798 OS << "nuw ";
799 if (MI.getFlag(Flag: MachineInstr::NoSWrap))
800 OS << "nsw ";
801 if (MI.getFlag(Flag: MachineInstr::IsExact))
802 OS << "exact ";
803 if (MI.getFlag(Flag: MachineInstr::NoFPExcept))
804 OS << "nofpexcept ";
805 if (MI.getFlag(Flag: MachineInstr::NoMerge))
806 OS << "nomerge ";
807 if (MI.getFlag(Flag: MachineInstr::Unpredictable))
808 OS << "unpredictable ";
809 if (MI.getFlag(Flag: MachineInstr::NoConvergent))
810 OS << "noconvergent ";
811 if (MI.getFlag(Flag: MachineInstr::NonNeg))
812 OS << "nneg ";
813 if (MI.getFlag(Flag: MachineInstr::Disjoint))
814 OS << "disjoint ";
815
816 OS << TII->getName(Opcode: MI.getOpcode());
817 if (I < E)
818 OS << ' ';
819
820 bool NeedComma = false;
821 for (; I < E; ++I) {
822 if (NeedComma)
823 OS << ", ";
824 print(MI, OpIdx: I, TRI, TII, ShouldPrintRegisterTies,
825 TypeToPrint: MI.getTypeToPrint(OpIdx: I, PrintedTypes, MRI));
826 NeedComma = true;
827 }
828
829 // Print any optional symbols attached to this instruction as-if they were
830 // operands.
831 if (MCSymbol *PreInstrSymbol = MI.getPreInstrSymbol()) {
832 if (NeedComma)
833 OS << ',';
834 OS << " pre-instr-symbol ";
835 MachineOperand::printSymbol(OS, Sym&: *PreInstrSymbol);
836 NeedComma = true;
837 }
838 if (MCSymbol *PostInstrSymbol = MI.getPostInstrSymbol()) {
839 if (NeedComma)
840 OS << ',';
841 OS << " post-instr-symbol ";
842 MachineOperand::printSymbol(OS, Sym&: *PostInstrSymbol);
843 NeedComma = true;
844 }
845 if (MDNode *HeapAllocMarker = MI.getHeapAllocMarker()) {
846 if (NeedComma)
847 OS << ',';
848 OS << " heap-alloc-marker ";
849 HeapAllocMarker->printAsOperand(OS, MST);
850 NeedComma = true;
851 }
852 if (MDNode *PCSections = MI.getPCSections()) {
853 if (NeedComma)
854 OS << ',';
855 OS << " pcsections ";
856 PCSections->printAsOperand(OS, MST);
857 NeedComma = true;
858 }
859 if (MDNode *MMRA = MI.getMMRAMetadata()) {
860 if (NeedComma)
861 OS << ',';
862 OS << " mmra ";
863 MMRA->printAsOperand(OS, MST);
864 NeedComma = true;
865 }
866 if (uint32_t CFIType = MI.getCFIType()) {
867 if (NeedComma)
868 OS << ',';
869 OS << " cfi-type " << CFIType;
870 NeedComma = true;
871 }
872
873 if (auto Num = MI.peekDebugInstrNum()) {
874 if (NeedComma)
875 OS << ',';
876 OS << " debug-instr-number " << Num;
877 NeedComma = true;
878 }
879
880 if (PrintLocations) {
881 if (const DebugLoc &DL = MI.getDebugLoc()) {
882 if (NeedComma)
883 OS << ',';
884 OS << " debug-location ";
885 DL->printAsOperand(OS, MST);
886 }
887 }
888
889 if (!MI.memoperands_empty()) {
890 OS << " :: ";
891 const LLVMContext &Context = MF->getFunction().getContext();
892 const MachineFrameInfo &MFI = MF->getFrameInfo();
893 bool NeedComma = false;
894 for (const auto *Op : MI.memoperands()) {
895 if (NeedComma)
896 OS << ", ";
897 Op->print(OS, MST, SSNs, Context, MFI: &MFI, TII);
898 NeedComma = true;
899 }
900 }
901}
902
903void MIPrinter::printStackObjectReference(int FrameIndex) {
904 auto ObjectInfo = StackObjectOperandMapping.find(Val: FrameIndex);
905 assert(ObjectInfo != StackObjectOperandMapping.end() &&
906 "Invalid frame index");
907 const FrameIndexOperand &Operand = ObjectInfo->second;
908 MachineOperand::printStackObjectReference(OS, FrameIndex: Operand.ID, IsFixed: Operand.IsFixed,
909 Name: Operand.Name);
910}
911
912static std::string formatOperandComment(std::string Comment) {
913 if (Comment.empty())
914 return Comment;
915 return std::string(" /* " + Comment + " */");
916}
917
918void MIPrinter::print(const MachineInstr &MI, unsigned OpIdx,
919 const TargetRegisterInfo *TRI,
920 const TargetInstrInfo *TII,
921 bool ShouldPrintRegisterTies, LLT TypeToPrint,
922 bool PrintDef) {
923 const MachineOperand &Op = MI.getOperand(i: OpIdx);
924 std::string MOComment = TII->createMIROperandComment(MI, Op, OpIdx, TRI);
925
926 switch (Op.getType()) {
927 case MachineOperand::MO_Immediate:
928 if (MI.isOperandSubregIdx(OpIdx)) {
929 MachineOperand::printTargetFlags(OS, Op);
930 MachineOperand::printSubRegIdx(OS, Index: Op.getImm(), TRI);
931 break;
932 }
933 [[fallthrough]];
934 case MachineOperand::MO_Register:
935 case MachineOperand::MO_CImmediate:
936 case MachineOperand::MO_FPImmediate:
937 case MachineOperand::MO_MachineBasicBlock:
938 case MachineOperand::MO_ConstantPoolIndex:
939 case MachineOperand::MO_TargetIndex:
940 case MachineOperand::MO_JumpTableIndex:
941 case MachineOperand::MO_ExternalSymbol:
942 case MachineOperand::MO_GlobalAddress:
943 case MachineOperand::MO_RegisterLiveOut:
944 case MachineOperand::MO_Metadata:
945 case MachineOperand::MO_MCSymbol:
946 case MachineOperand::MO_CFIIndex:
947 case MachineOperand::MO_IntrinsicID:
948 case MachineOperand::MO_Predicate:
949 case MachineOperand::MO_BlockAddress:
950 case MachineOperand::MO_DbgInstrRef:
951 case MachineOperand::MO_ShuffleMask: {
952 unsigned TiedOperandIdx = 0;
953 if (ShouldPrintRegisterTies && Op.isReg() && Op.isTied() && !Op.isDef())
954 TiedOperandIdx = Op.getParent()->findTiedOperandIdx(OpIdx);
955 const TargetIntrinsicInfo *TII = MI.getMF()->getTarget().getIntrinsicInfo();
956 Op.print(os&: OS, MST, TypeToPrint, OpIdx, PrintDef, /*IsStandalone=*/false,
957 ShouldPrintRegisterTies, TiedOperandIdx, TRI, IntrinsicInfo: TII);
958 OS << formatOperandComment(Comment: MOComment);
959 break;
960 }
961 case MachineOperand::MO_FrameIndex:
962 printStackObjectReference(FrameIndex: Op.getIndex());
963 break;
964 case MachineOperand::MO_RegisterMask: {
965 auto RegMaskInfo = RegisterMaskIds.find(Val: Op.getRegMask());
966 if (RegMaskInfo != RegisterMaskIds.end())
967 OS << StringRef(TRI->getRegMaskNames()[RegMaskInfo->second]).lower();
968 else
969 printCustomRegMask(RegMask: Op.getRegMask(), OS, TRI);
970 break;
971 }
972 }
973}
974
975void MIRFormatter::printIRValue(raw_ostream &OS, const Value &V,
976 ModuleSlotTracker &MST) {
977 if (isa<GlobalValue>(Val: V)) {
978 V.printAsOperand(O&: OS, /*PrintType=*/false, MST);
979 return;
980 }
981 if (isa<Constant>(Val: V)) {
982 // Machine memory operands can load/store to/from constant value pointers.
983 OS << '`';
984 V.printAsOperand(O&: OS, /*PrintType=*/true, MST);
985 OS << '`';
986 return;
987 }
988 OS << "%ir.";
989 if (V.hasName()) {
990 printLLVMNameWithoutPrefix(OS, Name: V.getName());
991 return;
992 }
993 int Slot = MST.getCurrentFunction() ? MST.getLocalSlot(V: &V) : -1;
994 MachineOperand::printIRSlotNumber(OS, Slot);
995}
996
997void llvm::printMIR(raw_ostream &OS, const Module &M) {
998 ScopedDbgInfoFormatSetter FormatSetter(const_cast<Module &>(M),
999 WriteNewDbgInfoFormat);
1000
1001 yaml::Output Out(OS);
1002 Out << const_cast<Module &>(M);
1003}
1004
1005void llvm::printMIR(raw_ostream &OS, const MachineFunction &MF) {
1006 // RemoveDIs: as there's no textual form for DbgRecords yet, print debug-info
1007 // in dbg.value format.
1008 ScopedDbgInfoFormatSetter FormatSetter(
1009 const_cast<Function &>(MF.getFunction()), WriteNewDbgInfoFormat);
1010
1011 MIRPrinter Printer(OS);
1012 Printer.print(MF);
1013}
1014

source code of llvm/lib/CodeGen/MIRPrinter.cpp