Coverage Report

Created: 2019-02-20 07:29

/Users/buildslave/jenkins/workspace/clang-stage2-coverage-R/llvm/include/llvm/MC/MCInst.h
Line
Count
Source (jump to first uncovered line)
1
//===- llvm/MC/MCInst.h - MCInst class --------------------------*- C++ -*-===//
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 contains the declaration of the MCInst and MCOperand classes, which
10
// is the basic representation used to represent low-level machine code
11
// instructions.
12
//
13
//===----------------------------------------------------------------------===//
14
15
#ifndef LLVM_MC_MCINST_H
16
#define LLVM_MC_MCINST_H
17
18
#include "llvm/ADT/SmallVector.h"
19
#include "llvm/ADT/StringRef.h"
20
#include "llvm/Support/SMLoc.h"
21
#include <cassert>
22
#include <cstddef>
23
#include <cstdint>
24
25
namespace llvm {
26
27
class MCExpr;
28
class MCInst;
29
class MCInstPrinter;
30
class raw_ostream;
31
32
/// Instances of this class represent operands of the MCInst class.
33
/// This is a simple discriminated union.
34
0
class MCOperand {
35
  enum MachineOperandType : unsigned char {
36
    kInvalid,     ///< Uninitialized.
37
    kRegister,    ///< Register operand.
38
    kImmediate,   ///< Immediate operand.
39
    kFPImmediate, ///< Floating-point immediate operand.
40
    kExpr,        ///< Relocatable immediate operand.
41
    kInst         ///< Sub-instruction operand.
42
  };
43
  MachineOperandType Kind = kInvalid;
44
45
0
  union {
46
    unsigned RegVal;
47
    int64_t ImmVal;
48
    double FPImmVal;
49
    const MCExpr *ExprVal;
50
    const MCInst *InstVal;
51
  };
52
53
public:
54
131M
  MCOperand() : FPImmVal(0.0) {}
55
56
614k
  bool isValid() const { return Kind != kInvalid; }
57
49.8M
  bool isReg() const { return Kind == kRegister; }
58
16.2M
  bool isImm() const { return Kind == kImmediate; }
59
26.7k
  bool isFPImm() const { return Kind == kFPImmediate; }
60
56.5M
  bool isExpr() const { return Kind == kExpr; }
61
0
  bool isInst() const { return Kind == kInst; }
62
63
  /// Returns the register number.
64
52.2M
  unsigned getReg() const {
65
52.2M
    assert(isReg() && "This is not a register operand!");
66
52.2M
    return RegVal;
67
52.2M
  }
68
69
  /// Set the register number.
70
2.15k
  void setReg(unsigned Reg) {
71
2.15k
    assert(isReg() && "This is not a register operand!");
72
2.15k
    RegVal = Reg;
73
2.15k
  }
74
75
20.0M
  int64_t getImm() const {
76
20.0M
    assert(isImm() && "This is not an immediate");
77
20.0M
    return ImmVal;
78
20.0M
  }
79
80
35.1k
  void setImm(int64_t Val) {
81
35.1k
    assert(isImm() && "This is not an immediate");
82
35.1k
    ImmVal = Val;
83
35.1k
  }
84
85
259
  double getFPImm() const {
86
259
    assert(isFPImm() && "This is not an FP immediate");
87
259
    return FPImmVal;
88
259
  }
89
90
0
  void setFPImm(double Val) {
91
0
    assert(isFPImm() && "This is not an FP immediate");
92
0
    FPImmVal = Val;
93
0
  }
94
95
9.59M
  const MCExpr *getExpr() const {
96
9.59M
    assert(isExpr() && "This is not an expression");
97
9.59M
    return ExprVal;
98
9.59M
  }
99
100
8
  void setExpr(const MCExpr *Val) {
101
8
    assert(isExpr() && "This is not an expression");
102
8
    ExprVal = Val;
103
8
  }
104
105
566k
  const MCInst *getInst() const {
106
566k
    assert(isInst() && "This is not a sub-instruction");
107
566k
    return InstVal;
108
566k
  }
109
110
1.58k
  void setInst(const MCInst *Val) {
111
1.58k
    assert(isInst() && "This is not a sub-instruction");
112
1.58k
    InstVal = Val;
113
1.58k
  }
114
115
41.3M
  static MCOperand createReg(unsigned Reg) {
116
41.3M
    MCOperand Op;
117
41.3M
    Op.Kind = kRegister;
118
41.3M
    Op.RegVal = Reg;
119
41.3M
    return Op;
120
41.3M
  }
121
122
19.5M
  static MCOperand createImm(int64_t Val) {
123
19.5M
    MCOperand Op;
124
19.5M
    Op.Kind = kImmediate;
125
19.5M
    Op.ImmVal = Val;
126
19.5M
    return Op;
127
19.5M
  }
128
129
249
  static MCOperand createFPImm(double Val) {
130
249
    MCOperand Op;
131
249
    Op.Kind = kFPImmediate;
132
249
    Op.FPImmVal = Val;
133
249
    return Op;
134
249
  }
135
136
4.69M
  static MCOperand createExpr(const MCExpr *Val) {
137
4.69M
    MCOperand Op;
138
4.69M
    Op.Kind = kExpr;
139
4.69M
    Op.ExprVal = Val;
140
4.69M
    return Op;
141
4.69M
  }
142
143
229k
  static MCOperand createInst(const MCInst *Val) {
144
229k
    MCOperand Op;
145
229k
    Op.Kind = kInst;
146
229k
    Op.InstVal = Val;
147
229k
    return Op;
148
229k
  }
149
150
  void print(raw_ostream &OS) const;
151
  void dump() const;
152
  bool isBareSymbolRef() const;
153
  bool evaluateAsConstantImm(int64_t &Imm) const;
154
};
155
156
/// Instances of this class represent a single low-level machine
157
/// instruction.
158
0
class MCInst {
159
  unsigned Opcode = 0;
160
  SMLoc Loc;
161
  SmallVector<MCOperand, 8> Operands;
162
  // These flags could be used to pass some info from one target subcomponent
163
  // to another, for example, from disassembler to asm printer. The values of
164
  // the flags have any sense on target level only (e.g. prefixes on x86).
165
  unsigned Flags = 0;
166
167
public:
168
380M
  MCInst() = default;
169
170
21.0M
  void setOpcode(unsigned Op) { Opcode = Op; }
171
104M
  unsigned getOpcode() const { return Opcode; }
172
173
515k
  void setFlags(unsigned F) { Flags = F; }
174
6.49M
  unsigned getFlags() const { return Flags; }
175
176
564k
  void setLoc(SMLoc loc) { Loc = loc; }
177
5.45M
  SMLoc getLoc() const { return Loc; }
178
179
139M
  const MCOperand &getOperand(unsigned i) const { return Operands[i]; }
180
880k
  MCOperand &getOperand(unsigned i) { return Operands[i]; }
181
25.4M
  unsigned getNumOperands() const { return Operands.size(); }
182
183
66.0M
  void addOperand(const MCOperand &Op) { Operands.push_back(Op); }
184
185
  using iterator = SmallVectorImpl<MCOperand>::iterator;
186
  using const_iterator = SmallVectorImpl<MCOperand>::const_iterator;
187
188
1.31M
  void clear() { Operands.clear(); }
189
8.34k
  void erase(iterator I) { Operands.erase(I); }
190
244k
  size_t size() const { return Operands.size(); }
191
62.2k
  iterator begin() { return Operands.begin(); }
192
228k
  const_iterator begin() const { return Operands.begin(); }
193
138k
  iterator end() { return Operands.end(); }
194
463k
  const_iterator end() const { return Operands.end(); }
195
196
34.1k
  iterator insert(iterator I, const MCOperand &Op) {
197
34.1k
    return Operands.insert(I, Op);
198
34.1k
  }
199
200
  void print(raw_ostream &OS) const;
201
  void dump() const;
202
203
  /// Dump the MCInst as prettily as possible using the additional MC
204
  /// structures, if given. Operators are separated by the \p Separator
205
  /// string.
206
  void dump_pretty(raw_ostream &OS, const MCInstPrinter *Printer = nullptr,
207
                   StringRef Separator = " ") const;
208
  void dump_pretty(raw_ostream &OS, StringRef Name,
209
                   StringRef Separator = " ") const;
210
};
211
212
709
inline raw_ostream& operator<<(raw_ostream &OS, const MCOperand &MO) {
213
709
  MO.print(OS);
214
709
  return OS;
215
709
}
216
217
0
inline raw_ostream& operator<<(raw_ostream &OS, const MCInst &MI) {
218
0
  MI.print(OS);
219
0
  return OS;
220
0
}
221
222
} // end namespace llvm
223
224
#endif // LLVM_MC_MCINST_H