LLVM  15.0.0git
ErlangGCPrinter.cpp
Go to the documentation of this file.
1 //===- ErlangGCPrinter.cpp - Erlang/OTP frametable emitter ----------------===//
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 compiler plugin that is used in order to emit
10 // garbage collection information in a convenient layout for parsing and
11 // loading in the Erlang/OTP runtime.
12 //
13 //===----------------------------------------------------------------------===//
14 
15 #include "llvm/BinaryFormat/ELF.h"
19 #include "llvm/IR/BuiltinGCs.h"
20 #include "llvm/IR/DataLayout.h"
21 #include "llvm/IR/Function.h"
22 #include "llvm/IR/Module.h"
23 #include "llvm/MC/MCContext.h"
24 #include "llvm/MC/MCSectionELF.h"
25 #include "llvm/MC/MCStreamer.h"
27 
28 using namespace llvm;
29 
30 namespace {
31 
32 class ErlangGCPrinter : public GCMetadataPrinter {
33 public:
34  void finishAssembly(Module &M, GCModuleInfo &Info, AsmPrinter &AP) override;
35 };
36 
37 } // end anonymous namespace
38 
40  X("erlang", "erlang-compatible garbage collector");
41 
42 void ErlangGCPrinter::finishAssembly(Module &M, GCModuleInfo &Info,
43  AsmPrinter &AP) {
44  MCStreamer &OS = *AP.OutStreamer;
45  unsigned IntPtrSize = M.getDataLayout().getPointerSize();
46 
47  // Put this in a custom .note section.
49  ".note.gc", ELF::SHT_PROGBITS, 0));
50 
51  // For each function...
52  for (GCModuleInfo::FuncInfoVec::iterator FI = Info.funcinfo_begin(),
53  IE = Info.funcinfo_end();
54  FI != IE; ++FI) {
55  GCFunctionInfo &MD = **FI;
56  if (MD.getStrategy().getName() != getStrategy().getName())
57  // this function is managed by some other GC
58  continue;
59  /** A compact GC layout. Emit this data structure:
60  *
61  * struct {
62  * int16_t PointCount;
63  * void *SafePointAddress[PointCount];
64  * int16_t StackFrameSize; (in words)
65  * int16_t StackArity;
66  * int16_t LiveCount;
67  * int16_t LiveOffsets[LiveCount];
68  * } __gcmap_<FUNCTIONNAME>;
69  **/
70 
71  // Align to address width.
72  AP.emitAlignment(IntPtrSize == 4 ? Align(4) : Align(8));
73 
74  // Emit PointCount.
75  OS.AddComment("safe point count");
76  AP.emitInt16(MD.size());
77 
78  // And each safe point...
79  for (const GCPoint &P : MD) {
80  // Emit the address of the safe point.
81  OS.AddComment("safe point address");
82  MCSymbol *Label = P.Label;
83  AP.emitLabelPlusOffset(Label /*Hi*/, 0 /*Offset*/, 4 /*Size*/);
84  }
85 
86  // Stack information never change in safe points! Only print info from the
87  // first call-site.
88  GCFunctionInfo::iterator PI = MD.begin();
89 
90  // Emit the stack frame size.
91  OS.AddComment("stack frame size (in words)");
92  AP.emitInt16(MD.getFrameSize() / IntPtrSize);
93 
94  // Emit stack arity, i.e. the number of stacked arguments.
95  unsigned RegisteredArgs = IntPtrSize == 4 ? 5 : 6;
96  unsigned StackArity = MD.getFunction().arg_size() > RegisteredArgs
97  ? MD.getFunction().arg_size() - RegisteredArgs
98  : 0;
99  OS.AddComment("stack arity");
100  AP.emitInt16(StackArity);
101 
102  // Emit the number of live roots in the function.
103  OS.AddComment("live root count");
104  AP.emitInt16(MD.live_size(PI));
105 
106  // And for each live root...
107  for (GCFunctionInfo::live_iterator LI = MD.live_begin(PI),
108  LE = MD.live_end(PI);
109  LI != LE; ++LI) {
110  // Emit live root's offset within the stack frame.
111  OS.AddComment("stack index (offset / wordsize)");
112  AP.emitInt16(LI->StackOffset / IntPtrSize);
113  }
114  }
115 }
116 
AsmPrinter.h
getName
static StringRef getName(Value *V)
Definition: ProvenanceAnalysisEvaluator.cpp:42
llvm
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:17
GCMetadata.h
llvm::MCSymbol
MCSymbol - Instances of this class represent a symbol name in the MC file, and MCSymbols are created ...
Definition: MCSymbol.h:41
M
We currently emits eax Perhaps this is what we really should generate is Is imull three or four cycles eax eax The current instruction priority is based on pattern complexity The former is more complex because it folds a load so the latter will not be emitted Perhaps we should use AddedComplexity to give LEA32r a higher priority We should always try to match LEA first since the LEA matching code does some estimate to determine whether the match is profitable if we care more about code then imull is better It s two bytes shorter than movl leal On a Pentium M
Definition: README.txt:252
P
This currently compiles esp xmm0 movsd esp eax eax esp ret We should use not the dag combiner This is because dagcombine2 needs to be able to see through the X86ISD::Wrapper which DAGCombine can t really do The code for turning x load into a single vector load is target independent and should be moved to the dag combiner The code for turning x load into a vector load can only handle a direct load from a global or a direct load from the stack It should be generalized to handle any load from P
Definition: README-SSE.txt:411
MCSectionELF.h
llvm::GCFunctionInfo
Garbage collection metadata for a single function.
Definition: GCMetadata.h:77
llvm::GCFunctionInfo::iterator
std::vector< GCPoint >::iterator iterator
Definition: GCMetadata.h:79
llvm::GCStrategy::getName
const std::string & getName() const
Return the name of the GC strategy.
Definition: GCStrategy.h:84
llvm::AsmPrinter::emitAlignment
void emitAlignment(Align Alignment, const GlobalObject *GV=nullptr, unsigned MaxBytesToEmit=0) const
Emit an alignment directive to the specified power of two boundary.
Definition: AsmPrinter.cpp:2676
Module.h
llvm::GCFunctionInfo::getStrategy
GCStrategy & getStrategy()
getStrategy - Return the GC strategy for the function.
Definition: GCMetadata.h:108
llvm::GCMetadataPrinter
GCMetadataPrinter - Emits GC metadata as assembly code.
Definition: GCMetadataPrinter.h:39
llvm::MCObjectFileInfo::getContext
MCContext & getContext() const
Definition: MCObjectFileInfo.h:244
llvm::MCStreamer
Streaming machine code generation interface.
Definition: MCStreamer.h:212
llvm::GCFunctionInfo::live_iterator
std::vector< GCRoot >::const_iterator live_iterator
Definition: GCMetadata.h:81
ELF.h
llvm::AsmPrinter::OutStreamer
std::unique_ptr< MCStreamer > OutStreamer
This is the MCStreamer object for the file we are generating.
Definition: AsmPrinter.h:96
MCContext.h
llvm::MCStreamer::switchSection
virtual void switchSection(MCSection *Section, const MCExpr *Subsection=nullptr)
Set the current section where code is being emitted to Section.
Definition: MCStreamer.cpp:1225
llvm::MCContext::getELFSection
MCSectionELF * getELFSection(const Twine &Section, unsigned Type, unsigned Flags)
Definition: MCContext.h:563
llvm::AArch64CC::LE
@ LE
Definition: AArch64BaseInfo.h:268
Info
Analysis containing CSE Info
Definition: CSEInfo.cpp:27
Align
uint64_t Align
Definition: ELFObjHandler.cpp:81
X
static GCMetadataPrinterRegistry::Add< ErlangGCPrinter > X("erlang", "erlang-compatible garbage collector")
llvm::ARM_PROC::IE
@ IE
Definition: ARMBaseInfo.h:27
llvm::AsmPrinter::emitLabelPlusOffset
void emitLabelPlusOffset(const MCSymbol *Label, uint64_t Offset, unsigned Size, bool IsSectionRelative=false) const
Emit something like ".long Label+Offset" where the size in bytes of the directive is specified by Siz...
Definition: AsmPrinter.cpp:2651
BuiltinGCs.h
llvm::Module
A Module instance is used to store all the information related to an LLVM module.
Definition: Module.h:65
DataLayout.h
llvm::GCFunctionInfo::size
size_t size() const
Definition: GCMetadata.h:136
TargetLoweringObjectFile.h
llvm::pdb::PDB_SymType::Label
@ Label
Function.h
llvm::AsmPrinter
This class is intended to be used as a driving class for all asm writers.
Definition: AsmPrinter.h:81
GCMetadataPrinter.h
llvm::ELF::SHT_PROGBITS
@ SHT_PROGBITS
Definition: ELF.h:955
llvm::AsmPrinter::getObjFileLowering
const TargetLoweringObjectFile & getObjFileLowering() const
Return information about object file lowering.
Definition: AsmPrinter.cpp:382
MCStreamer.h
llvm::GCPoint
GCPoint - Metadata for a collector-safe point in machine code.
Definition: GCMetadata.h:56
llvm::linkErlangGCPrinter
void linkErlangGCPrinter()
Creates an erlang-compatible metadata printer.
Definition: ErlangGCPrinter.cpp:117
llvm::Registry::Add
A static registration template.
Definition: Registry.h:114
llvm::GCModuleInfo
An analysis pass which caches information about the entire Module.
Definition: GCMetadata.h:152
llvm::AsmPrinter::emitInt16
void emitInt16(int Value) const
Emit a short directive and value.
Definition: AsmPrinter.cpp:2630
llvm::MCStreamer::AddComment
virtual void AddComment(const Twine &T, bool EOL=true)
Add a textual comment.
Definition: MCStreamer.h:355