File: SystemZAsmPrinter.h

package info (click to toggle)
llvm-toolchain-19 1%3A19.1.7-3
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid, trixie
  • size: 1,998,520 kB
  • sloc: cpp: 6,951,680; ansic: 1,486,157; asm: 913,598; python: 232,024; f90: 80,126; objc: 75,281; lisp: 37,276; pascal: 16,990; sh: 10,009; ml: 5,058; perl: 4,724; awk: 3,523; makefile: 3,167; javascript: 2,504; xml: 892; fortran: 664; cs: 573
file content (131 lines) | stat: -rw-r--r-- 4,789 bytes parent folder | download | duplicates (4)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
//===-- SystemZAsmPrinter.h - SystemZ LLVM assembly printer ----*- C++ -*--===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//

#ifndef LLVM_LIB_TARGET_SYSTEMZ_SYSTEMZASMPRINTER_H
#define LLVM_LIB_TARGET_SYSTEMZ_SYSTEMZASMPRINTER_H

#include "SystemZMCInstLower.h"
#include "SystemZTargetMachine.h"
#include "SystemZTargetStreamer.h"
#include "llvm/CodeGen/AsmPrinter.h"
#include "llvm/CodeGen/StackMaps.h"
#include "llvm/MC/MCInstBuilder.h"
#include "llvm/Support/Compiler.h"

namespace llvm {
class MCStreamer;
class MachineInstr;
class Module;
class raw_ostream;

class LLVM_LIBRARY_VISIBILITY SystemZAsmPrinter : public AsmPrinter {
private:
  MCSymbol *CurrentFnPPA1Sym;     // PPA1 Symbol.
  MCSymbol *CurrentFnEPMarkerSym; // Entry Point Marker.
  MCSymbol *PPA2Sym;

  SystemZTargetStreamer *getTargetStreamer() {
    MCTargetStreamer *TS = OutStreamer->getTargetStreamer();
    assert(TS && "do not have a target streamer");
    return static_cast<SystemZTargetStreamer *>(TS);
  }

  /// Call type information for XPLINK.
  enum class CallType {
    BASR76 = 0,   // b'x000' == BASR  r7,r6
    BRAS7 = 1,    // b'x001' == BRAS  r7,ep
    RESVD_2 = 2,  // b'x010'
    BRASL7 = 3,   // b'x011' == BRASL r7,ep
    RESVD_4 = 4,  // b'x100'
    RESVD_5 = 5,  // b'x101'
    BALR1415 = 6, // b'x110' == BALR  r14,r15
    BASR33 = 7,   // b'x111' == BASR  r3,r3
  };

  // The Associated Data Area (ADA) contains descriptors which help locating
  // external symbols. For each symbol and type, the displacement into the ADA
  // is stored.
  class AssociatedDataAreaTable {
  public:
    using DisplacementTable =
        MapVector<std::pair<const MCSymbol *, unsigned>, uint32_t>;

  private:
    const uint64_t PointerSize;

    /// The mapping of name/slot type pairs to displacements.
    DisplacementTable Displacements;

    /// The next available displacement value. Incremented when new entries into
    /// the ADA are created.
    uint32_t NextDisplacement = 0;

  public:
    AssociatedDataAreaTable(uint64_t PointerSize) : PointerSize(PointerSize) {}

    /// @brief Add a function descriptor to the ADA.
    /// @param MI Pointer to an ADA_ENTRY instruction.
    /// @return The displacement of the descriptor into the ADA.
    uint32_t insert(const MachineOperand MO);

    /// @brief Get the displacement into associated data area (ADA) for a name.
    /// If no  displacement is already associated with the name, assign one and
    /// return it.
    /// @param Sym The symbol for which the displacement should be returned.
    /// @param SlotKind The ADA type.
    /// @return The displacement of the descriptor into the ADA.
    uint32_t insert(const MCSymbol *Sym, unsigned SlotKind);

    /// Get the table of GOFF displacements.  This is 'const' since it should
    /// never be modified by anything except the APIs on this class.
    const DisplacementTable &getTable() const { return Displacements; }

    uint32_t getNextDisplacement() const { return NextDisplacement; }
  };

  AssociatedDataAreaTable ADATable;

  void emitPPA1(MCSymbol *FnEndSym);
  void emitPPA2(Module &M);
  void emitADASection();
  void emitIDRLSection(Module &M);

public:
  SystemZAsmPrinter(TargetMachine &TM, std::unique_ptr<MCStreamer> Streamer)
      : AsmPrinter(TM, std::move(Streamer)), CurrentFnPPA1Sym(nullptr),
        CurrentFnEPMarkerSym(nullptr), PPA2Sym(nullptr),
        ADATable(TM.getPointerSize(0)) {}

  // Override AsmPrinter.
  StringRef getPassName() const override { return "SystemZ Assembly Printer"; }
  void emitInstruction(const MachineInstr *MI) override;
  void emitMachineConstantPoolValue(MachineConstantPoolValue *MCPV) override;
  void emitEndOfAsmFile(Module &M) override;
  bool PrintAsmOperand(const MachineInstr *MI, unsigned OpNo,
                       const char *ExtraCode, raw_ostream &OS) override;
  bool PrintAsmMemoryOperand(const MachineInstr *MI, unsigned OpNo,
                             const char *ExtraCode, raw_ostream &OS) override;

  bool doInitialization(Module &M) override {
    SM.reset();
    return AsmPrinter::doInitialization(M);
  }
  void emitFunctionEntryLabel() override;
  void emitFunctionBodyEnd() override;
  void emitStartOfAsmFile(Module &M) override;

private:
  void emitCallInformation(CallType CT);
  void LowerFENTRY_CALL(const MachineInstr &MI, SystemZMCInstLower &MCIL);
  void LowerSTACKMAP(const MachineInstr &MI);
  void LowerPATCHPOINT(const MachineInstr &MI, SystemZMCInstLower &Lower);
  void emitAttributes(Module &M);
};
} // end namespace llvm

#endif