LLVM: lib/Target/Sparc/MCTargetDesc/SparcMCCodeEmitter.cpp Source File (original) (raw)

1

2

3

4

5

6

7

8

9

10

11

12

31#include

32#include

33

34using namespace llvm;

35

36#define DEBUG_TYPE "mccodeemitter"

37

38STATISTIC(MCNumEmitted, "Number of MC instructions emitted");

39

40namespace {

41

44

45public:

47 : Ctx(ctx) {}

48 SparcMCCodeEmitter(const SparcMCCodeEmitter &) = delete;

49 SparcMCCodeEmitter &operator=(const SparcMCCodeEmitter &) = delete;

50 ~SparcMCCodeEmitter() override = default;

51

52 void encodeInstruction(const MCInst &MI, SmallVectorImpl &CB,

53 SmallVectorImpl &Fixups,

54 const MCSubtargetInfo &STI) const override;

55

56

57

58 uint64_t getBinaryCodeForInstr(const MCInst &MI,

59 SmallVectorImpl &Fixups,

60 const MCSubtargetInfo &STI) const;

61

62

63

64 unsigned getMachineOpValue(const MCInst &MI, const MCOperand &MO,

65 SmallVectorImpl &Fixups,

66 const MCSubtargetInfo &STI) const;

67 unsigned getCallTargetOpValue(const MCInst &MI, unsigned OpNo,

68 SmallVectorImpl &Fixups,

69 const MCSubtargetInfo &STI) const;

71 SmallVectorImpl &Fixups,

72 const MCSubtargetInfo &STI) const;

73 unsigned getSImm5OpValue(const MCInst &MI, unsigned OpNo,

74 SmallVectorImpl &Fixups,

75 const MCSubtargetInfo &STI) const;

76 unsigned getSImm13OpValue(const MCInst &MI, unsigned OpNo,

77 SmallVectorImpl &Fixups,

78 const MCSubtargetInfo &STI) const;

79 unsigned getBranchPredTargetOpValue(const MCInst &MI, unsigned OpNo,

80 SmallVectorImpl &Fixups,

81 const MCSubtargetInfo &STI) const;

82 unsigned getBranchOnRegTargetOpValue(const MCInst &MI, unsigned OpNo,

83 SmallVectorImpl &Fixups,

84 const MCSubtargetInfo &STI) const;

85 unsigned getCompareAndBranchTargetOpValue(const MCInst &MI, unsigned OpNo,

86 SmallVectorImpl &Fixups,

87 const MCSubtargetInfo &STI) const;

88};

89

90}

91

94 bool PCRel = false;

95 switch (Kind) {

96 case ELF::R_SPARC_PC10:

97 case ELF::R_SPARC_PC22:

98 case ELF::R_SPARC_WDISP10:

99 case ELF::R_SPARC_WDISP16:

100 case ELF::R_SPARC_WDISP19:

101 case ELF::R_SPARC_WDISP22:

103 PCRel = true;

104 }

106}

107

108void SparcMCCodeEmitter::encodeInstruction(const MCInst &MI,

112 unsigned Bits = getBinaryCodeForInstr(MI, Fixups, STI);

117

118

119 unsigned SymOpNo = 0;

120 switch (MI.getOpcode()) {

121 default: break;

122 case SP::TLS_CALL: SymOpNo = 1; break;

123 case SP::GDOP_LDrr:

124 case SP::GDOP_LDXrr:

125 case SP::TLS_ADDrr:

126 case SP::TLS_LDrr:

127 case SP::TLS_LDXrr: SymOpNo = 3; break;

128 }

129 if (SymOpNo != 0) {

130 const MCOperand &MO = MI.getOperand(SymOpNo);

131 uint64_t op = getMachineOpValue(MI, MO, Fixups, STI);

132 assert(op == 0 && "Unexpected operand value!");

133 (void)op;

134 }

135

136 ++MCNumEmitted;

137}

138

139unsigned SparcMCCodeEmitter::

140getMachineOpValue(const MCInst &MI, const MCOperand &MO,

141 SmallVectorImpl &Fixups,

142 const MCSubtargetInfo &STI) const {

145

148

150 const MCExpr *Expr = MO.getExpr();

152 addFixup(Fixups, 0, Expr, SExpr->getSpecifier());

153 return 0;

154 }

155

156 int64_t Res;

157 if (Expr->evaluateAsAbsolute(Res))

158 return Res;

159

161 return 0;

162}

163

164unsigned SparcMCCodeEmitter::getSImm5OpValue(const MCInst &MI, unsigned OpNo,

165 SmallVectorImpl &Fixups,

166 const MCSubtargetInfo &STI) const {

167 const MCOperand &MO = MI.getOperand(OpNo);

168

171

173 "getSImm5OpValue expects only expressions or an immediate");

174

175 const MCExpr *Expr = MO.getExpr();

176

177

179 return CE->getValue();

180

182 addFixup(Fixups, 0, Expr, SExpr->getSpecifier());

183 return 0;

184 }

185 addFixup(Fixups, 0, Expr, ELF::R_SPARC_5);

186 return 0;

187}

188

189unsigned

190SparcMCCodeEmitter::getSImm13OpValue(const MCInst &MI, unsigned OpNo,

191 SmallVectorImpl &Fixups,

192 const MCSubtargetInfo &STI) const {

193 const MCOperand &MO = MI.getOperand(OpNo);

194

197

199 "getSImm13OpValue expects only expressions or an immediate");

200

201 const MCExpr *Expr = MO.getExpr();

202

203

205 return CE->getValue();

206

208 addFixup(Fixups, 0, Expr, SExpr->getSpecifier());

209 return 0;

210 }

212 return 0;

213}

214

215unsigned SparcMCCodeEmitter::

216getCallTargetOpValue(const MCInst &MI, unsigned OpNo,

217 SmallVectorImpl &Fixups,

218 const MCSubtargetInfo &STI) const {

219 if (MI.getOpcode() == SP::TLS_CALL) {

220

221

222 return 0;

223 }

224

225 const MCOperand &MO = MI.getOperand(OpNo);

227 return 0;

228}

229

230unsigned SparcMCCodeEmitter::

231getBranchTargetOpValue(const MCInst &MI, unsigned OpNo,

232 SmallVectorImpl &Fixups,

233 const MCSubtargetInfo &STI) const {

234 const MCOperand &MO = MI.getOperand(OpNo);

236 return getMachineOpValue(MI, MO, Fixups, STI);

237

239 return 0;

240}

241

242unsigned SparcMCCodeEmitter::getBranchPredTargetOpValue(

243 const MCInst &MI, unsigned OpNo, SmallVectorImpl &Fixups,

244 const MCSubtargetInfo &STI) const {

245 const MCOperand &MO = MI.getOperand(OpNo);

247 return getMachineOpValue(MI, MO, Fixups, STI);

248

250 return 0;

251}

252

253unsigned SparcMCCodeEmitter::getBranchOnRegTargetOpValue(

254 const MCInst &MI, unsigned OpNo, SmallVectorImpl &Fixups,

255 const MCSubtargetInfo &STI) const {

256 const MCOperand &MO = MI.getOperand(OpNo);

258 return getMachineOpValue(MI, MO, Fixups, STI);

259

261 return 0;

262}

263

264unsigned SparcMCCodeEmitter::getCompareAndBranchTargetOpValue(

265 const MCInst &MI, unsigned OpNo, SmallVectorImpl &Fixups,

266 const MCSubtargetInfo &STI) const {

267 const MCOperand &MO = MI.getOperand(OpNo);

269 return getMachineOpValue(MI, MO, Fixups, STI);

270

272 return 0;

273}

274

275#include "SparcGenMCCodeEmitter.inc"

276

279 return new SparcMCCodeEmitter(MCII, Ctx);

280}

static void addFixup(SmallVectorImpl< MCFixup > &Fixups, uint32_t Offset, const MCExpr *Value, uint16_t Kind, bool PCRel=false)

assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")

static uint32_t getBranchTargetOpValue(const MCInst &MI, unsigned OpIdx, unsigned FixupKind, SmallVectorImpl< MCFixup > &Fixups, const MCSubtargetInfo &STI)

getBranchTargetOpValue - Helper function to get the branch target operand, which is either an immedia...

This file defines the SmallVector class.

This file defines the 'Statistic' class, which is designed to be an easy way to expose various metric...

#define STATISTIC(VARNAME, DESC)

bool isLittleEndian() const

True if the target is little endian.

MCCodeEmitter - Generic instruction encoding interface.

Context object for machine code objects.

const MCRegisterInfo * getRegisterInfo() const

const MCAsmInfo * getAsmInfo() const

Base class for the full range of assembler expressions which are needed for parsing.

static MCFixup create(uint32_t Offset, const MCExpr *Value, MCFixupKind Kind, bool PCRel=false)

Consider bit fields if we need more flags.

Instances of this class represent a single low-level machine instruction.

Interface to description of machine instruction set.

MCRegister getReg() const

Returns the register number.

const MCExpr * getExpr() const

uint16_t getEncodingValue(MCRegister Reg) const

Returns the encoding for Reg.

Generic base class for all target subtargets.

This class consists of common code factored out of the SmallVector class to reduce code duplication b...

LLVM Value Representation.

#define llvm_unreachable(msg)

Marks that the current location is not supposed to be reachable.

@ fixup_sparc_13

fixup_sparc_13 - 13-bit fixup

@ CE

Windows NT (Windows on ARM)

void write(void *memory, value_type value, endianness endian)

Write a value to memory with a particular endianness.

This is an optimization pass for GlobalISel generic memory operations.

decltype(auto) dyn_cast(const From &Val)

dyn_cast - Return the argument parameter cast to the specified type.

static void addFixup(SmallVectorImpl< MCFixup > &Fixups, uint32_t Offset, const MCExpr *Value, uint16_t Kind)

MCCodeEmitter * createSparcMCCodeEmitter(const MCInstrInfo &MCII, MCContext &Ctx)

Definition SparcMCCodeEmitter.cpp:277