OLD | NEW |
1 //===- subzero/src/IceInstX8632.h - Low-level x86 instructions --*- C++ -*-===// | 1 //===- subzero/src/IceInstX8632.h - Low-level x86 instructions --*- C++ -*-===// |
2 // | 2 // |
3 // The Subzero Code Generator | 3 // The Subzero Code Generator |
4 // | 4 // |
5 // This file is distributed under the University of Illinois Open Source | 5 // This file is distributed under the University of Illinois Open Source |
6 // License. See LICENSE.TXT for details. | 6 // License. See LICENSE.TXT for details. |
7 // | 7 // |
8 //===----------------------------------------------------------------------===// | 8 //===----------------------------------------------------------------------===// |
9 // | 9 // |
10 // This file declares the InstX8632 and OperandX8632 classes and | 10 // This file declares the InstX8632 and OperandX8632 classes and |
(...skipping 18 matching lines...) Expand all Loading... |
29 | 29 |
30 // OperandX8632 extends the Operand hierarchy. Its subclasses are | 30 // OperandX8632 extends the Operand hierarchy. Its subclasses are |
31 // OperandX8632Mem and VariableSplit. | 31 // OperandX8632Mem and VariableSplit. |
32 class OperandX8632 : public Operand { | 32 class OperandX8632 : public Operand { |
33 public: | 33 public: |
34 enum OperandKindX8632 { | 34 enum OperandKindX8632 { |
35 k__Start = Operand::kTarget, | 35 k__Start = Operand::kTarget, |
36 kMem, | 36 kMem, |
37 kSplit | 37 kSplit |
38 }; | 38 }; |
39 virtual void emit(const Cfg *Func) const = 0; | 39 void emit(const Cfg *Func) const override = 0; |
40 using Operand::dump; | 40 using Operand::dump; |
41 virtual void dump(const Cfg *, Ostream &Str) const { | 41 void dump(const Cfg *, Ostream &Str) const override { |
42 Str << "<OperandX8632>"; | 42 Str << "<OperandX8632>"; |
43 } | 43 } |
44 | 44 |
45 protected: | 45 protected: |
46 OperandX8632(OperandKindX8632 Kind, Type Ty) | 46 OperandX8632(OperandKindX8632 Kind, Type Ty) |
47 : Operand(static_cast<OperandKind>(Kind), Ty) {} | 47 : Operand(static_cast<OperandKind>(Kind), Ty) {} |
48 virtual ~OperandX8632() {} | 48 ~OperandX8632() override {} |
49 | 49 |
50 private: | 50 private: |
51 OperandX8632(const OperandX8632 &) LLVM_DELETED_FUNCTION; | 51 OperandX8632(const OperandX8632 &) LLVM_DELETED_FUNCTION; |
52 OperandX8632 &operator=(const OperandX8632 &) LLVM_DELETED_FUNCTION; | 52 OperandX8632 &operator=(const OperandX8632 &) LLVM_DELETED_FUNCTION; |
53 }; | 53 }; |
54 | 54 |
55 // OperandX8632Mem represents the m32 addressing mode, with optional | 55 // OperandX8632Mem represents the m32 addressing mode, with optional |
56 // base and index registers, a constant offset, and a fixed shift | 56 // base and index registers, a constant offset, and a fixed shift |
57 // value for the index register. | 57 // value for the index register. |
58 class OperandX8632Mem : public OperandX8632 { | 58 class OperandX8632Mem : public OperandX8632 { |
(...skipping 11 matching lines...) Expand all Loading... |
70 SegmentRegisters SegmentReg = DefaultSegment) { | 70 SegmentRegisters SegmentReg = DefaultSegment) { |
71 return new (Func->allocate<OperandX8632Mem>()) | 71 return new (Func->allocate<OperandX8632Mem>()) |
72 OperandX8632Mem(Func, Ty, Base, Offset, Index, Shift, SegmentReg); | 72 OperandX8632Mem(Func, Ty, Base, Offset, Index, Shift, SegmentReg); |
73 } | 73 } |
74 Variable *getBase() const { return Base; } | 74 Variable *getBase() const { return Base; } |
75 Constant *getOffset() const { return Offset; } | 75 Constant *getOffset() const { return Offset; } |
76 Variable *getIndex() const { return Index; } | 76 Variable *getIndex() const { return Index; } |
77 uint16_t getShift() const { return Shift; } | 77 uint16_t getShift() const { return Shift; } |
78 SegmentRegisters getSegmentRegister() const { return SegmentReg; } | 78 SegmentRegisters getSegmentRegister() const { return SegmentReg; } |
79 x86::Address toAsmAddress(Assembler *Asm) const; | 79 x86::Address toAsmAddress(Assembler *Asm) const; |
80 virtual void emit(const Cfg *Func) const; | 80 void emit(const Cfg *Func) const override; |
81 using OperandX8632::dump; | 81 using OperandX8632::dump; |
82 virtual void dump(const Cfg *Func, Ostream &Str) const; | 82 void dump(const Cfg *Func, Ostream &Str) const override; |
83 | 83 |
84 static bool classof(const Operand *Operand) { | 84 static bool classof(const Operand *Operand) { |
85 return Operand->getKind() == static_cast<OperandKind>(kMem); | 85 return Operand->getKind() == static_cast<OperandKind>(kMem); |
86 } | 86 } |
87 | 87 |
88 private: | 88 private: |
89 OperandX8632Mem(Cfg *Func, Type Ty, Variable *Base, Constant *Offset, | 89 OperandX8632Mem(Cfg *Func, Type Ty, Variable *Base, Constant *Offset, |
90 Variable *Index, uint16_t Shift, SegmentRegisters SegmentReg); | 90 Variable *Index, uint16_t Shift, SegmentRegisters SegmentReg); |
91 OperandX8632Mem(const OperandX8632Mem &) LLVM_DELETED_FUNCTION; | 91 OperandX8632Mem(const OperandX8632Mem &) LLVM_DELETED_FUNCTION; |
92 OperandX8632Mem &operator=(const OperandX8632Mem &) LLVM_DELETED_FUNCTION; | 92 OperandX8632Mem &operator=(const OperandX8632Mem &) LLVM_DELETED_FUNCTION; |
93 virtual ~OperandX8632Mem() {} | 93 ~OperandX8632Mem() override {} |
94 Variable *Base; | 94 Variable *Base; |
95 Constant *Offset; | 95 Constant *Offset; |
96 Variable *Index; | 96 Variable *Index; |
97 uint16_t Shift; | 97 uint16_t Shift; |
98 SegmentRegisters SegmentReg : 16; | 98 SegmentRegisters SegmentReg : 16; |
99 }; | 99 }; |
100 | 100 |
101 // VariableSplit is a way to treat an f64 memory location as a pair | 101 // VariableSplit is a way to treat an f64 memory location as a pair |
102 // of i32 locations (Low and High). This is needed for some cases | 102 // of i32 locations (Low and High). This is needed for some cases |
103 // of the Bitcast instruction. Since it's not possible for integer | 103 // of the Bitcast instruction. Since it's not possible for integer |
104 // registers to access the XMM registers and vice versa, the | 104 // registers to access the XMM registers and vice versa, the |
105 // lowering forces the f64 to be spilled to the stack and then | 105 // lowering forces the f64 to be spilled to the stack and then |
106 // accesses through the VariableSplit. | 106 // accesses through the VariableSplit. |
107 class VariableSplit : public OperandX8632 { | 107 class VariableSplit : public OperandX8632 { |
108 public: | 108 public: |
109 enum Portion { | 109 enum Portion { |
110 Low, | 110 Low, |
111 High | 111 High |
112 }; | 112 }; |
113 static VariableSplit *create(Cfg *Func, Variable *Var, Portion Part) { | 113 static VariableSplit *create(Cfg *Func, Variable *Var, Portion Part) { |
114 return new (Func->allocate<VariableSplit>()) VariableSplit(Func, Var, Part); | 114 return new (Func->allocate<VariableSplit>()) VariableSplit(Func, Var, Part); |
115 } | 115 } |
116 virtual void emit(const Cfg *Func) const; | 116 void emit(const Cfg *Func) const override; |
117 using OperandX8632::dump; | 117 using OperandX8632::dump; |
118 virtual void dump(const Cfg *Func, Ostream &Str) const; | 118 void dump(const Cfg *Func, Ostream &Str) const override; |
119 | 119 |
120 static bool classof(const Operand *Operand) { | 120 static bool classof(const Operand *Operand) { |
121 return Operand->getKind() == static_cast<OperandKind>(kSplit); | 121 return Operand->getKind() == static_cast<OperandKind>(kSplit); |
122 } | 122 } |
123 | 123 |
124 private: | 124 private: |
125 VariableSplit(Cfg *Func, Variable *Var, Portion Part) | 125 VariableSplit(Cfg *Func, Variable *Var, Portion Part) |
126 : OperandX8632(kSplit, IceType_i32), Func(Func), Var(Var), Part(Part) { | 126 : OperandX8632(kSplit, IceType_i32), Func(Func), Var(Var), Part(Part) { |
127 assert(Var->getType() == IceType_f64); | 127 assert(Var->getType() == IceType_f64); |
128 Vars = Func->allocateArrayOf<Variable *>(1); | 128 Vars = Func->allocateArrayOf<Variable *>(1); |
129 Vars[0] = Var; | 129 Vars[0] = Var; |
130 NumVars = 1; | 130 NumVars = 1; |
131 } | 131 } |
132 VariableSplit(const VariableSplit &) LLVM_DELETED_FUNCTION; | 132 VariableSplit(const VariableSplit &) LLVM_DELETED_FUNCTION; |
133 VariableSplit &operator=(const VariableSplit &) LLVM_DELETED_FUNCTION; | 133 VariableSplit &operator=(const VariableSplit &) LLVM_DELETED_FUNCTION; |
134 virtual ~VariableSplit() { Func->deallocateArrayOf<Variable *>(Vars); } | 134 ~VariableSplit() override { Func->deallocateArrayOf<Variable *>(Vars); } |
135 Cfg *Func; // Held only for the destructor. | 135 Cfg *Func; // Held only for the destructor. |
136 Variable *Var; | 136 Variable *Var; |
137 Portion Part; | 137 Portion Part; |
138 }; | 138 }; |
139 | 139 |
140 // SpillVariable decorates a Variable by linking it to another | 140 // SpillVariable decorates a Variable by linking it to another |
141 // Variable. When stack frame offsets are computed, the SpillVariable | 141 // Variable. When stack frame offsets are computed, the SpillVariable |
142 // is given a distinct stack slot only if its linked Variable has a | 142 // is given a distinct stack slot only if its linked Variable has a |
143 // register. If the linked Variable has a stack slot, then the | 143 // register. If the linked Variable has a stack slot, then the |
144 // Variable and SpillVariable share that slot. | 144 // Variable and SpillVariable share that slot. |
(...skipping 101 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
246 Subss, | 246 Subss, |
247 Test, | 247 Test, |
248 Ucomiss, | 248 Ucomiss, |
249 UD2, | 249 UD2, |
250 Xadd, | 250 Xadd, |
251 Xchg, | 251 Xchg, |
252 Xor | 252 Xor |
253 }; | 253 }; |
254 | 254 |
255 static const char *getWidthString(Type Ty); | 255 static const char *getWidthString(Type Ty); |
256 virtual void emit(const Cfg *Func) const = 0; | 256 void emit(const Cfg *Func) const override = 0; |
257 virtual void dump(const Cfg *Func) const; | 257 void dump(const Cfg *Func) const override; |
258 | 258 |
259 protected: | 259 protected: |
260 InstX8632(Cfg *Func, InstKindX8632 Kind, SizeT Maxsrcs, Variable *Dest) | 260 InstX8632(Cfg *Func, InstKindX8632 Kind, SizeT Maxsrcs, Variable *Dest) |
261 : InstTarget(Func, static_cast<InstKind>(Kind), Maxsrcs, Dest) {} | 261 : InstTarget(Func, static_cast<InstKind>(Kind), Maxsrcs, Dest) {} |
262 virtual ~InstX8632() {} | 262 ~InstX8632() override {} |
263 static bool isClassof(const Inst *Inst, InstKindX8632 MyKind) { | 263 static bool isClassof(const Inst *Inst, InstKindX8632 MyKind) { |
264 return Inst->getKind() == static_cast<InstKind>(MyKind); | 264 return Inst->getKind() == static_cast<InstKind>(MyKind); |
265 } | 265 } |
266 | 266 |
267 private: | 267 private: |
268 InstX8632(const InstX8632 &) LLVM_DELETED_FUNCTION; | 268 InstX8632(const InstX8632 &) LLVM_DELETED_FUNCTION; |
269 InstX8632 &operator=(const InstX8632 &) LLVM_DELETED_FUNCTION; | 269 InstX8632 &operator=(const InstX8632 &) LLVM_DELETED_FUNCTION; |
270 }; | 270 }; |
271 | 271 |
272 // InstX8632Label represents an intra-block label that is the | 272 // InstX8632Label represents an intra-block label that is the |
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
304 // | 304 // |
305 // The down-side is that "mov c, x" can never be dead-code eliminated | 305 // The down-side is that "mov c, x" can never be dead-code eliminated |
306 // even if there are no uses of c. As unlikely as this situation is, | 306 // even if there are no uses of c. As unlikely as this situation is, |
307 // it may be prevented by running dead code elimination before | 307 // it may be prevented by running dead code elimination before |
308 // lowering. | 308 // lowering. |
309 class InstX8632Label : public InstX8632 { | 309 class InstX8632Label : public InstX8632 { |
310 public: | 310 public: |
311 static InstX8632Label *create(Cfg *Func, TargetX8632 *Target) { | 311 static InstX8632Label *create(Cfg *Func, TargetX8632 *Target) { |
312 return new (Func->allocate<InstX8632Label>()) InstX8632Label(Func, Target); | 312 return new (Func->allocate<InstX8632Label>()) InstX8632Label(Func, Target); |
313 } | 313 } |
314 virtual uint32_t getEmitInstCount() const { return 0; } | 314 uint32_t getEmitInstCount() const override { return 0; } |
315 IceString getName(const Cfg *Func) const; | 315 IceString getName(const Cfg *Func) const; |
316 virtual void emit(const Cfg *Func) const; | 316 void emit(const Cfg *Func) const override; |
317 virtual void dump(const Cfg *Func) const; | 317 void dump(const Cfg *Func) const override; |
318 | 318 |
319 private: | 319 private: |
320 InstX8632Label(Cfg *Func, TargetX8632 *Target); | 320 InstX8632Label(Cfg *Func, TargetX8632 *Target); |
321 InstX8632Label(const InstX8632Label &) LLVM_DELETED_FUNCTION; | 321 InstX8632Label(const InstX8632Label &) LLVM_DELETED_FUNCTION; |
322 InstX8632Label &operator=(const InstX8632Label &) LLVM_DELETED_FUNCTION; | 322 InstX8632Label &operator=(const InstX8632Label &) LLVM_DELETED_FUNCTION; |
323 virtual ~InstX8632Label() {} | 323 ~InstX8632Label() override {} |
324 SizeT Number; // used only for unique label string generation | 324 SizeT Number; // used only for unique label string generation |
325 }; | 325 }; |
326 | 326 |
327 // Conditional and unconditional branch instruction. | 327 // Conditional and unconditional branch instruction. |
328 class InstX8632Br : public InstX8632 { | 328 class InstX8632Br : public InstX8632 { |
329 public: | 329 public: |
330 // Create a conditional branch to a node. | 330 // Create a conditional branch to a node. |
331 static InstX8632Br *create(Cfg *Func, CfgNode *TargetTrue, | 331 static InstX8632Br *create(Cfg *Func, CfgNode *TargetTrue, |
332 CfgNode *TargetFalse, CondX86::BrCond Condition) { | 332 CfgNode *TargetFalse, CondX86::BrCond Condition) { |
333 const InstX8632Label *NoLabel = NULL; | 333 const InstX8632Label *NoLabel = NULL; |
(...skipping 22 matching lines...) Expand all Loading... |
356 static InstX8632Br *create(Cfg *Func, InstX8632Label *Label, | 356 static InstX8632Br *create(Cfg *Func, InstX8632Label *Label, |
357 CondX86::BrCond Condition) { | 357 CondX86::BrCond Condition) { |
358 const CfgNode *NoCondTarget = NULL; | 358 const CfgNode *NoCondTarget = NULL; |
359 const CfgNode *NoUncondTarget = NULL; | 359 const CfgNode *NoUncondTarget = NULL; |
360 return new (Func->allocate<InstX8632Br>()) | 360 return new (Func->allocate<InstX8632Br>()) |
361 InstX8632Br(Func, NoCondTarget, NoUncondTarget, Label, Condition); | 361 InstX8632Br(Func, NoCondTarget, NoUncondTarget, Label, Condition); |
362 } | 362 } |
363 const CfgNode *getTargetTrue() const { return TargetTrue; } | 363 const CfgNode *getTargetTrue() const { return TargetTrue; } |
364 const CfgNode *getTargetFalse() const { return TargetFalse; } | 364 const CfgNode *getTargetFalse() const { return TargetFalse; } |
365 bool optimizeBranch(const CfgNode *NextNode); | 365 bool optimizeBranch(const CfgNode *NextNode); |
366 virtual uint32_t getEmitInstCount() const { | 366 uint32_t getEmitInstCount() const override { |
367 uint32_t Sum = 0; | 367 uint32_t Sum = 0; |
368 if (Label) | 368 if (Label) |
369 ++Sum; | 369 ++Sum; |
370 if (getTargetTrue()) | 370 if (getTargetTrue()) |
371 ++Sum; | 371 ++Sum; |
372 if (getTargetFalse()) | 372 if (getTargetFalse()) |
373 ++Sum; | 373 ++Sum; |
374 return Sum; | 374 return Sum; |
375 } | 375 } |
376 virtual void emit(const Cfg *Func) const; | 376 void emit(const Cfg *Func) const override; |
377 virtual void dump(const Cfg *Func) const; | 377 void dump(const Cfg *Func) const override; |
378 static bool classof(const Inst *Inst) { return isClassof(Inst, Br); } | 378 static bool classof(const Inst *Inst) { return isClassof(Inst, Br); } |
379 | 379 |
380 private: | 380 private: |
381 InstX8632Br(Cfg *Func, const CfgNode *TargetTrue, const CfgNode *TargetFalse, | 381 InstX8632Br(Cfg *Func, const CfgNode *TargetTrue, const CfgNode *TargetFalse, |
382 const InstX8632Label *Label, CondX86::BrCond Condition); | 382 const InstX8632Label *Label, CondX86::BrCond Condition); |
383 InstX8632Br(const InstX8632Br &) LLVM_DELETED_FUNCTION; | 383 InstX8632Br(const InstX8632Br &) LLVM_DELETED_FUNCTION; |
384 InstX8632Br &operator=(const InstX8632Br &) LLVM_DELETED_FUNCTION; | 384 InstX8632Br &operator=(const InstX8632Br &) LLVM_DELETED_FUNCTION; |
385 virtual ~InstX8632Br() {} | 385 ~InstX8632Br() override {} |
386 CondX86::BrCond Condition; | 386 CondX86::BrCond Condition; |
387 const CfgNode *TargetTrue; | 387 const CfgNode *TargetTrue; |
388 const CfgNode *TargetFalse; | 388 const CfgNode *TargetFalse; |
389 const InstX8632Label *Label; // Intra-block branch target | 389 const InstX8632Label *Label; // Intra-block branch target |
390 }; | 390 }; |
391 | 391 |
392 // AdjustStack instruction - subtracts esp by the given amount and | 392 // AdjustStack instruction - subtracts esp by the given amount and |
393 // updates the stack offset during code emission. | 393 // updates the stack offset during code emission. |
394 class InstX8632AdjustStack : public InstX8632 { | 394 class InstX8632AdjustStack : public InstX8632 { |
395 public: | 395 public: |
396 static InstX8632AdjustStack *create(Cfg *Func, SizeT Amount, Variable *Esp) { | 396 static InstX8632AdjustStack *create(Cfg *Func, SizeT Amount, Variable *Esp) { |
397 return new (Func->allocate<InstX8632AdjustStack>()) | 397 return new (Func->allocate<InstX8632AdjustStack>()) |
398 InstX8632AdjustStack(Func, Amount, Esp); | 398 InstX8632AdjustStack(Func, Amount, Esp); |
399 } | 399 } |
400 virtual void emit(const Cfg *Func) const; | 400 void emit(const Cfg *Func) const override; |
401 virtual void emitIAS(const Cfg *Func) const; | 401 void emitIAS(const Cfg *Func) const override; |
402 virtual void dump(const Cfg *Func) const; | 402 void dump(const Cfg *Func) const override; |
403 static bool classof(const Inst *Inst) { return isClassof(Inst, Adjuststack); } | 403 static bool classof(const Inst *Inst) { return isClassof(Inst, Adjuststack); } |
404 | 404 |
405 private: | 405 private: |
406 InstX8632AdjustStack(Cfg *Func, SizeT Amount, Variable *Esp); | 406 InstX8632AdjustStack(Cfg *Func, SizeT Amount, Variable *Esp); |
407 InstX8632AdjustStack(const InstX8632AdjustStack &) LLVM_DELETED_FUNCTION; | 407 InstX8632AdjustStack(const InstX8632AdjustStack &) LLVM_DELETED_FUNCTION; |
408 InstX8632AdjustStack &operator=(const InstX8632AdjustStack &) | 408 InstX8632AdjustStack &operator=(const InstX8632AdjustStack &) |
409 LLVM_DELETED_FUNCTION; | 409 LLVM_DELETED_FUNCTION; |
410 SizeT Amount; | 410 SizeT Amount; |
411 }; | 411 }; |
412 | 412 |
413 // Call instruction. Arguments should have already been pushed. | 413 // Call instruction. Arguments should have already been pushed. |
414 class InstX8632Call : public InstX8632 { | 414 class InstX8632Call : public InstX8632 { |
415 public: | 415 public: |
416 static InstX8632Call *create(Cfg *Func, Variable *Dest, Operand *CallTarget) { | 416 static InstX8632Call *create(Cfg *Func, Variable *Dest, Operand *CallTarget) { |
417 return new (Func->allocate<InstX8632Call>()) | 417 return new (Func->allocate<InstX8632Call>()) |
418 InstX8632Call(Func, Dest, CallTarget); | 418 InstX8632Call(Func, Dest, CallTarget); |
419 } | 419 } |
420 Operand *getCallTarget() const { return getSrc(0); } | 420 Operand *getCallTarget() const { return getSrc(0); } |
421 virtual void emit(const Cfg *Func) const; | 421 void emit(const Cfg *Func) const override; |
422 virtual void dump(const Cfg *Func) const; | 422 void dump(const Cfg *Func) const override; |
423 static bool classof(const Inst *Inst) { return isClassof(Inst, Call); } | 423 static bool classof(const Inst *Inst) { return isClassof(Inst, Call); } |
424 | 424 |
425 private: | 425 private: |
426 InstX8632Call(Cfg *Func, Variable *Dest, Operand *CallTarget); | 426 InstX8632Call(Cfg *Func, Variable *Dest, Operand *CallTarget); |
427 InstX8632Call(const InstX8632Call &) LLVM_DELETED_FUNCTION; | 427 InstX8632Call(const InstX8632Call &) LLVM_DELETED_FUNCTION; |
428 InstX8632Call &operator=(const InstX8632Call &) LLVM_DELETED_FUNCTION; | 428 InstX8632Call &operator=(const InstX8632Call &) LLVM_DELETED_FUNCTION; |
429 virtual ~InstX8632Call() {} | 429 ~InstX8632Call() override {} |
430 }; | 430 }; |
431 | 431 |
432 // Emit a one-operand (GPR) instruction. | 432 // Emit a one-operand (GPR) instruction. |
433 void emitIASVarTyGPR(const Cfg *Func, Type Ty, const Variable *Var, | 433 void emitIASVarTyGPR(const Cfg *Func, Type Ty, const Variable *Var, |
434 const x86::AssemblerX86::GPREmitterOneOp &Emitter); | 434 const x86::AssemblerX86::GPREmitterOneOp &Emitter); |
435 | 435 |
436 // Instructions of the form x := op(x). | 436 // Instructions of the form x := op(x). |
437 template <InstX8632::InstKindX8632 K> | 437 template <InstX8632::InstKindX8632 K> |
438 class InstX8632InplaceopGPR : public InstX8632 { | 438 class InstX8632InplaceopGPR : public InstX8632 { |
439 public: | 439 public: |
440 static InstX8632InplaceopGPR *create(Cfg *Func, Operand *SrcDest) { | 440 static InstX8632InplaceopGPR *create(Cfg *Func, Operand *SrcDest) { |
441 return new (Func->allocate<InstX8632InplaceopGPR>()) | 441 return new (Func->allocate<InstX8632InplaceopGPR>()) |
442 InstX8632InplaceopGPR(Func, SrcDest); | 442 InstX8632InplaceopGPR(Func, SrcDest); |
443 } | 443 } |
444 virtual void emit(const Cfg *Func) const { | 444 void emit(const Cfg *Func) const override { |
445 Ostream &Str = Func->getContext()->getStrEmit(); | 445 Ostream &Str = Func->getContext()->getStrEmit(); |
446 assert(getSrcSize() == 1); | 446 assert(getSrcSize() == 1); |
447 Str << "\t" << Opcode << "\t"; | 447 Str << "\t" << Opcode << "\t"; |
448 getSrc(0)->emit(Func); | 448 getSrc(0)->emit(Func); |
449 Str << "\n"; | 449 Str << "\n"; |
450 } | 450 } |
451 virtual void emitIAS(const Cfg *Func) const { | 451 void emitIAS(const Cfg *Func) const override { |
452 assert(getSrcSize() == 1); | 452 assert(getSrcSize() == 1); |
453 const Variable *Var = getDest(); | 453 const Variable *Var = getDest(); |
454 Type Ty = Var->getType(); | 454 Type Ty = Var->getType(); |
455 emitIASVarTyGPR(Func, Ty, Var, Emitter); | 455 emitIASVarTyGPR(Func, Ty, Var, Emitter); |
456 } | 456 } |
457 virtual void dump(const Cfg *Func) const { | 457 void dump(const Cfg *Func) const override { |
458 Ostream &Str = Func->getContext()->getStrDump(); | 458 Ostream &Str = Func->getContext()->getStrDump(); |
459 dumpDest(Func); | 459 dumpDest(Func); |
460 Str << " = " << Opcode << "." << getDest()->getType() << " "; | 460 Str << " = " << Opcode << "." << getDest()->getType() << " "; |
461 dumpSources(Func); | 461 dumpSources(Func); |
462 } | 462 } |
463 static bool classof(const Inst *Inst) { return isClassof(Inst, K); } | 463 static bool classof(const Inst *Inst) { return isClassof(Inst, K); } |
464 | 464 |
465 private: | 465 private: |
466 InstX8632InplaceopGPR(Cfg *Func, Operand *SrcDest) | 466 InstX8632InplaceopGPR(Cfg *Func, Operand *SrcDest) |
467 : InstX8632(Func, K, 1, llvm::dyn_cast<Variable>(SrcDest)) { | 467 : InstX8632(Func, K, 1, llvm::dyn_cast<Variable>(SrcDest)) { |
468 addSource(SrcDest); | 468 addSource(SrcDest); |
469 } | 469 } |
470 InstX8632InplaceopGPR(const InstX8632InplaceopGPR &) LLVM_DELETED_FUNCTION; | 470 InstX8632InplaceopGPR(const InstX8632InplaceopGPR &) LLVM_DELETED_FUNCTION; |
471 InstX8632InplaceopGPR & | 471 InstX8632InplaceopGPR & |
472 operator=(const InstX8632InplaceopGPR &) LLVM_DELETED_FUNCTION; | 472 operator=(const InstX8632InplaceopGPR &) LLVM_DELETED_FUNCTION; |
473 virtual ~InstX8632InplaceopGPR() {} | 473 ~InstX8632InplaceopGPR() override {} |
474 static const char *Opcode; | 474 static const char *Opcode; |
475 static const x86::AssemblerX86::GPREmitterOneOp Emitter; | 475 static const x86::AssemblerX86::GPREmitterOneOp Emitter; |
476 }; | 476 }; |
477 | 477 |
478 // Emit a two-operand (GPR) instruction, where the dest operand is a | 478 // Emit a two-operand (GPR) instruction, where the dest operand is a |
479 // Variable that's guaranteed to be a register. | 479 // Variable that's guaranteed to be a register. |
480 void emitIASRegOpTyGPR(const Cfg *Func, Type Ty, const Variable *Dst, | 480 void emitIASRegOpTyGPR(const Cfg *Func, Type Ty, const Variable *Dst, |
481 const Operand *Src, | 481 const Operand *Src, |
482 const x86::AssemblerX86::GPREmitterRegOp &Emitter); | 482 const x86::AssemblerX86::GPREmitterRegOp &Emitter); |
483 | 483 |
484 // Instructions of the form x := op(y) | 484 // Instructions of the form x := op(y) |
485 template <InstX8632::InstKindX8632 K> | 485 template <InstX8632::InstKindX8632 K> |
486 class InstX8632UnaryopGPR : public InstX8632 { | 486 class InstX8632UnaryopGPR : public InstX8632 { |
487 public: | 487 public: |
488 static InstX8632UnaryopGPR *create(Cfg *Func, Variable *Dest, Operand *Src) { | 488 static InstX8632UnaryopGPR *create(Cfg *Func, Variable *Dest, Operand *Src) { |
489 return new (Func->allocate<InstX8632UnaryopGPR>()) | 489 return new (Func->allocate<InstX8632UnaryopGPR>()) |
490 InstX8632UnaryopGPR(Func, Dest, Src); | 490 InstX8632UnaryopGPR(Func, Dest, Src); |
491 } | 491 } |
492 virtual void emit(const Cfg *Func) const { | 492 void emit(const Cfg *Func) const override { |
493 Ostream &Str = Func->getContext()->getStrEmit(); | 493 Ostream &Str = Func->getContext()->getStrEmit(); |
494 assert(getSrcSize() == 1); | 494 assert(getSrcSize() == 1); |
495 Str << "\t" << Opcode << "\t"; | 495 Str << "\t" << Opcode << "\t"; |
496 getDest()->emit(Func); | 496 getDest()->emit(Func); |
497 Str << ", "; | 497 Str << ", "; |
498 getSrc(0)->emit(Func); | 498 getSrc(0)->emit(Func); |
499 Str << "\n"; | 499 Str << "\n"; |
500 } | 500 } |
501 virtual void emitIAS(const Cfg *Func) const { | 501 void emitIAS(const Cfg *Func) const override { |
502 assert(getSrcSize() == 1); | 502 assert(getSrcSize() == 1); |
503 const Variable *Var = getDest(); | 503 const Variable *Var = getDest(); |
504 Type Ty = Var->getType(); | 504 Type Ty = Var->getType(); |
505 const Operand *Src = getSrc(0); | 505 const Operand *Src = getSrc(0); |
506 emitIASRegOpTyGPR(Func, Ty, Var, Src, Emitter); | 506 emitIASRegOpTyGPR(Func, Ty, Var, Src, Emitter); |
507 } | 507 } |
508 virtual void dump(const Cfg *Func) const { | 508 void dump(const Cfg *Func) const override { |
509 Ostream &Str = Func->getContext()->getStrDump(); | 509 Ostream &Str = Func->getContext()->getStrDump(); |
510 dumpDest(Func); | 510 dumpDest(Func); |
511 Str << " = " << Opcode << "." << getDest()->getType() << " "; | 511 Str << " = " << Opcode << "." << getDest()->getType() << " "; |
512 dumpSources(Func); | 512 dumpSources(Func); |
513 } | 513 } |
514 static bool classof(const Inst *Inst) { return isClassof(Inst, K); } | 514 static bool classof(const Inst *Inst) { return isClassof(Inst, K); } |
515 | 515 |
516 private: | 516 private: |
517 InstX8632UnaryopGPR(Cfg *Func, Variable *Dest, Operand *Src) | 517 InstX8632UnaryopGPR(Cfg *Func, Variable *Dest, Operand *Src) |
518 : InstX8632(Func, K, 1, Dest) { | 518 : InstX8632(Func, K, 1, Dest) { |
519 addSource(Src); | 519 addSource(Src); |
520 } | 520 } |
521 InstX8632UnaryopGPR(const InstX8632UnaryopGPR &) LLVM_DELETED_FUNCTION; | 521 InstX8632UnaryopGPR(const InstX8632UnaryopGPR &) LLVM_DELETED_FUNCTION; |
522 InstX8632UnaryopGPR & | 522 InstX8632UnaryopGPR & |
523 operator=(const InstX8632UnaryopGPR &) LLVM_DELETED_FUNCTION; | 523 operator=(const InstX8632UnaryopGPR &) LLVM_DELETED_FUNCTION; |
524 virtual ~InstX8632UnaryopGPR() {} | 524 ~InstX8632UnaryopGPR() override {} |
525 static const char *Opcode; | 525 static const char *Opcode; |
526 static const x86::AssemblerX86::GPREmitterRegOp Emitter; | 526 static const x86::AssemblerX86::GPREmitterRegOp Emitter; |
527 }; | 527 }; |
528 | 528 |
529 void emitIASVarOperandTyXMM(const Cfg *Func, Type Ty, const Variable *Var, | 529 void emitIASVarOperandTyXMM(const Cfg *Func, Type Ty, const Variable *Var, |
530 const Operand *Src, | 530 const Operand *Src, |
531 const x86::AssemblerX86::XmmEmitterTwoOps &Emitter); | 531 const x86::AssemblerX86::XmmEmitterTwoOps &Emitter); |
532 | 532 |
533 template <InstX8632::InstKindX8632 K> | 533 template <InstX8632::InstKindX8632 K> |
534 class InstX8632UnaryopXmm : public InstX8632 { | 534 class InstX8632UnaryopXmm : public InstX8632 { |
535 public: | 535 public: |
536 static InstX8632UnaryopXmm *create(Cfg *Func, Variable *Dest, Operand *Src) { | 536 static InstX8632UnaryopXmm *create(Cfg *Func, Variable *Dest, Operand *Src) { |
537 return new (Func->allocate<InstX8632UnaryopXmm>()) | 537 return new (Func->allocate<InstX8632UnaryopXmm>()) |
538 InstX8632UnaryopXmm(Func, Dest, Src); | 538 InstX8632UnaryopXmm(Func, Dest, Src); |
539 } | 539 } |
540 virtual void emit(const Cfg *Func) const { | 540 void emit(const Cfg *Func) const override { |
541 Ostream &Str = Func->getContext()->getStrEmit(); | 541 Ostream &Str = Func->getContext()->getStrEmit(); |
542 assert(getSrcSize() == 1); | 542 assert(getSrcSize() == 1); |
543 Str << "\t" << Opcode << "\t"; | 543 Str << "\t" << Opcode << "\t"; |
544 getDest()->emit(Func); | 544 getDest()->emit(Func); |
545 Str << ", "; | 545 Str << ", "; |
546 getSrc(0)->emit(Func); | 546 getSrc(0)->emit(Func); |
547 Str << "\n"; | 547 Str << "\n"; |
548 } | 548 } |
549 virtual void emitIAS(const Cfg *Func) const { | 549 void emitIAS(const Cfg *Func) const override { |
550 Type Ty = getDest()->getType(); | 550 Type Ty = getDest()->getType(); |
551 assert(getSrcSize() == 1); | 551 assert(getSrcSize() == 1); |
552 emitIASVarOperandTyXMM(Func, Ty, getDest(), getSrc(0), Emitter); | 552 emitIASVarOperandTyXMM(Func, Ty, getDest(), getSrc(0), Emitter); |
553 } | 553 } |
554 virtual void dump(const Cfg *Func) const { | 554 void dump(const Cfg *Func) const override { |
555 Ostream &Str = Func->getContext()->getStrDump(); | 555 Ostream &Str = Func->getContext()->getStrDump(); |
556 dumpDest(Func); | 556 dumpDest(Func); |
557 Str << " = " << Opcode << "." << getDest()->getType() << " "; | 557 Str << " = " << Opcode << "." << getDest()->getType() << " "; |
558 dumpSources(Func); | 558 dumpSources(Func); |
559 } | 559 } |
560 static bool classof(const Inst *Inst) { return isClassof(Inst, K); } | 560 static bool classof(const Inst *Inst) { return isClassof(Inst, K); } |
561 | 561 |
562 private: | 562 private: |
563 InstX8632UnaryopXmm(Cfg *Func, Variable *Dest, Operand *Src) | 563 InstX8632UnaryopXmm(Cfg *Func, Variable *Dest, Operand *Src) |
564 : InstX8632(Func, K, 1, Dest) { | 564 : InstX8632(Func, K, 1, Dest) { |
565 addSource(Src); | 565 addSource(Src); |
566 } | 566 } |
567 InstX8632UnaryopXmm(const InstX8632UnaryopXmm &) LLVM_DELETED_FUNCTION; | 567 InstX8632UnaryopXmm(const InstX8632UnaryopXmm &) LLVM_DELETED_FUNCTION; |
568 InstX8632UnaryopXmm & | 568 InstX8632UnaryopXmm & |
569 operator=(const InstX8632UnaryopXmm &) LLVM_DELETED_FUNCTION; | 569 operator=(const InstX8632UnaryopXmm &) LLVM_DELETED_FUNCTION; |
570 virtual ~InstX8632UnaryopXmm() {} | 570 ~InstX8632UnaryopXmm() override {} |
571 static const char *Opcode; | 571 static const char *Opcode; |
572 static const x86::AssemblerX86::XmmEmitterTwoOps Emitter; | 572 static const x86::AssemblerX86::XmmEmitterTwoOps Emitter; |
573 }; | 573 }; |
574 | 574 |
575 // See the definition of emitTwoAddress() for a description of | 575 // See the definition of emitTwoAddress() for a description of |
576 // ShiftHack. | 576 // ShiftHack. |
577 void emitTwoAddress(const char *Opcode, const Inst *Inst, const Cfg *Func, | 577 void emitTwoAddress(const char *Opcode, const Inst *Inst, const Cfg *Func, |
578 bool ShiftHack = false); | 578 bool ShiftHack = false); |
579 | 579 |
580 template <InstX8632::InstKindX8632 K, bool ShiftHack = false> | 580 template <InstX8632::InstKindX8632 K, bool ShiftHack = false> |
581 class InstX8632Binop : public InstX8632 { | 581 class InstX8632Binop : public InstX8632 { |
582 public: | 582 public: |
583 // Create an ordinary binary-op instruction like add or sub. | 583 // Create an ordinary binary-op instruction like add or sub. |
584 static InstX8632Binop *create(Cfg *Func, Variable *Dest, Operand *Source) { | 584 static InstX8632Binop *create(Cfg *Func, Variable *Dest, Operand *Source) { |
585 return new (Func->allocate<InstX8632Binop>()) | 585 return new (Func->allocate<InstX8632Binop>()) |
586 InstX8632Binop(Func, Dest, Source); | 586 InstX8632Binop(Func, Dest, Source); |
587 } | 587 } |
588 virtual void emit(const Cfg *Func) const { | 588 void emit(const Cfg *Func) const override { |
589 emitTwoAddress(Opcode, this, Func, ShiftHack); | 589 emitTwoAddress(Opcode, this, Func, ShiftHack); |
590 } | 590 } |
591 virtual void dump(const Cfg *Func) const { | 591 void dump(const Cfg *Func) const override { |
592 Ostream &Str = Func->getContext()->getStrDump(); | 592 Ostream &Str = Func->getContext()->getStrDump(); |
593 dumpDest(Func); | 593 dumpDest(Func); |
594 Str << " = " << Opcode << "." << getDest()->getType() << " "; | 594 Str << " = " << Opcode << "." << getDest()->getType() << " "; |
595 dumpSources(Func); | 595 dumpSources(Func); |
596 } | 596 } |
597 static bool classof(const Inst *Inst) { return isClassof(Inst, K); } | 597 static bool classof(const Inst *Inst) { return isClassof(Inst, K); } |
598 | 598 |
599 private: | 599 private: |
600 InstX8632Binop(Cfg *Func, Variable *Dest, Operand *Source) | 600 InstX8632Binop(Cfg *Func, Variable *Dest, Operand *Source) |
601 : InstX8632(Func, K, 2, Dest) { | 601 : InstX8632(Func, K, 2, Dest) { |
602 addSource(Dest); | 602 addSource(Dest); |
603 addSource(Source); | 603 addSource(Source); |
604 } | 604 } |
605 InstX8632Binop(const InstX8632Binop &) LLVM_DELETED_FUNCTION; | 605 InstX8632Binop(const InstX8632Binop &) LLVM_DELETED_FUNCTION; |
606 InstX8632Binop &operator=(const InstX8632Binop &) LLVM_DELETED_FUNCTION; | 606 InstX8632Binop &operator=(const InstX8632Binop &) LLVM_DELETED_FUNCTION; |
607 virtual ~InstX8632Binop() {} | 607 ~InstX8632Binop() override {} |
608 static const char *Opcode; | 608 static const char *Opcode; |
609 }; | 609 }; |
610 | 610 |
611 template <InstX8632::InstKindX8632 K, bool NeedsElementType> | 611 template <InstX8632::InstKindX8632 K, bool NeedsElementType> |
612 class InstX8632BinopXmm : public InstX8632 { | 612 class InstX8632BinopXmm : public InstX8632 { |
613 public: | 613 public: |
614 // Create an XMM binary-op instruction like addss or addps. | 614 // Create an XMM binary-op instruction like addss or addps. |
615 static InstX8632BinopXmm *create(Cfg *Func, Variable *Dest, Operand *Source) { | 615 static InstX8632BinopXmm *create(Cfg *Func, Variable *Dest, Operand *Source) { |
616 return new (Func->allocate<InstX8632BinopXmm>()) | 616 return new (Func->allocate<InstX8632BinopXmm>()) |
617 InstX8632BinopXmm(Func, Dest, Source); | 617 InstX8632BinopXmm(Func, Dest, Source); |
618 } | 618 } |
619 virtual void emit(const Cfg *Func) const { | 619 void emit(const Cfg *Func) const override { |
620 const bool ShiftHack = false; | 620 const bool ShiftHack = false; |
621 emitTwoAddress(Opcode, this, Func, ShiftHack); | 621 emitTwoAddress(Opcode, this, Func, ShiftHack); |
622 } | 622 } |
623 virtual void emitIAS(const Cfg *Func) const { | 623 void emitIAS(const Cfg *Func) const override { |
624 Type Ty = getDest()->getType(); | 624 Type Ty = getDest()->getType(); |
625 if (NeedsElementType) | 625 if (NeedsElementType) |
626 Ty = typeElementType(Ty); | 626 Ty = typeElementType(Ty); |
627 assert(getSrcSize() == 2); | 627 assert(getSrcSize() == 2); |
628 emitIASVarOperandTyXMM(Func, Ty, getDest(), getSrc(1), Emitter); | 628 emitIASVarOperandTyXMM(Func, Ty, getDest(), getSrc(1), Emitter); |
629 } | 629 } |
630 virtual void dump(const Cfg *Func) const { | 630 void dump(const Cfg *Func) const override { |
631 Ostream &Str = Func->getContext()->getStrDump(); | 631 Ostream &Str = Func->getContext()->getStrDump(); |
632 dumpDest(Func); | 632 dumpDest(Func); |
633 Str << " = " << Opcode << "." << getDest()->getType() << " "; | 633 Str << " = " << Opcode << "." << getDest()->getType() << " "; |
634 dumpSources(Func); | 634 dumpSources(Func); |
635 } | 635 } |
636 static bool classof(const Inst *Inst) { return isClassof(Inst, K); } | 636 static bool classof(const Inst *Inst) { return isClassof(Inst, K); } |
637 | 637 |
638 private: | 638 private: |
639 InstX8632BinopXmm(Cfg *Func, Variable *Dest, Operand *Source) | 639 InstX8632BinopXmm(Cfg *Func, Variable *Dest, Operand *Source) |
640 : InstX8632(Func, K, 2, Dest) { | 640 : InstX8632(Func, K, 2, Dest) { |
641 addSource(Dest); | 641 addSource(Dest); |
642 addSource(Source); | 642 addSource(Source); |
643 } | 643 } |
644 InstX8632BinopXmm(const InstX8632BinopXmm &) LLVM_DELETED_FUNCTION; | 644 InstX8632BinopXmm(const InstX8632BinopXmm &) LLVM_DELETED_FUNCTION; |
645 InstX8632BinopXmm &operator=(const InstX8632BinopXmm &) LLVM_DELETED_FUNCTION; | 645 InstX8632BinopXmm &operator=(const InstX8632BinopXmm &) LLVM_DELETED_FUNCTION; |
646 virtual ~InstX8632BinopXmm() {} | 646 ~InstX8632BinopXmm() override {} |
647 static const char *Opcode; | 647 static const char *Opcode; |
648 static const x86::AssemblerX86::XmmEmitterTwoOps Emitter; | 648 static const x86::AssemblerX86::XmmEmitterTwoOps Emitter; |
649 }; | 649 }; |
650 | 650 |
651 template <InstX8632::InstKindX8632 K> class InstX8632Ternop : public InstX8632 { | 651 template <InstX8632::InstKindX8632 K> class InstX8632Ternop : public InstX8632 { |
652 public: | 652 public: |
653 // Create a ternary-op instruction like div or idiv. | 653 // Create a ternary-op instruction like div or idiv. |
654 static InstX8632Ternop *create(Cfg *Func, Variable *Dest, Operand *Source1, | 654 static InstX8632Ternop *create(Cfg *Func, Variable *Dest, Operand *Source1, |
655 Operand *Source2) { | 655 Operand *Source2) { |
656 return new (Func->allocate<InstX8632Ternop>()) | 656 return new (Func->allocate<InstX8632Ternop>()) |
657 InstX8632Ternop(Func, Dest, Source1, Source2); | 657 InstX8632Ternop(Func, Dest, Source1, Source2); |
658 } | 658 } |
659 virtual void emit(const Cfg *Func) const { | 659 void emit(const Cfg *Func) const override { |
660 Ostream &Str = Func->getContext()->getStrEmit(); | 660 Ostream &Str = Func->getContext()->getStrEmit(); |
661 assert(getSrcSize() == 3); | 661 assert(getSrcSize() == 3); |
662 Str << "\t" << Opcode << "\t"; | 662 Str << "\t" << Opcode << "\t"; |
663 getDest()->emit(Func); | 663 getDest()->emit(Func); |
664 Str << ", "; | 664 Str << ", "; |
665 getSrc(1)->emit(Func); | 665 getSrc(1)->emit(Func); |
666 Str << ", "; | 666 Str << ", "; |
667 getSrc(2)->emit(Func); | 667 getSrc(2)->emit(Func); |
668 Str << "\n"; | 668 Str << "\n"; |
669 } | 669 } |
670 virtual void dump(const Cfg *Func) const { | 670 void dump(const Cfg *Func) const override { |
671 Ostream &Str = Func->getContext()->getStrDump(); | 671 Ostream &Str = Func->getContext()->getStrDump(); |
672 dumpDest(Func); | 672 dumpDest(Func); |
673 Str << " = " << Opcode << "." << getDest()->getType() << " "; | 673 Str << " = " << Opcode << "." << getDest()->getType() << " "; |
674 dumpSources(Func); | 674 dumpSources(Func); |
675 } | 675 } |
676 static bool classof(const Inst *Inst) { return isClassof(Inst, K); } | 676 static bool classof(const Inst *Inst) { return isClassof(Inst, K); } |
677 | 677 |
678 private: | 678 private: |
679 InstX8632Ternop(Cfg *Func, Variable *Dest, Operand *Source1, Operand *Source2) | 679 InstX8632Ternop(Cfg *Func, Variable *Dest, Operand *Source1, Operand *Source2) |
680 : InstX8632(Func, K, 3, Dest) { | 680 : InstX8632(Func, K, 3, Dest) { |
681 addSource(Dest); | 681 addSource(Dest); |
682 addSource(Source1); | 682 addSource(Source1); |
683 addSource(Source2); | 683 addSource(Source2); |
684 } | 684 } |
685 InstX8632Ternop(const InstX8632Ternop &) LLVM_DELETED_FUNCTION; | 685 InstX8632Ternop(const InstX8632Ternop &) LLVM_DELETED_FUNCTION; |
686 InstX8632Ternop &operator=(const InstX8632Ternop &) LLVM_DELETED_FUNCTION; | 686 InstX8632Ternop &operator=(const InstX8632Ternop &) LLVM_DELETED_FUNCTION; |
687 virtual ~InstX8632Ternop() {} | 687 ~InstX8632Ternop() override {} |
688 static const char *Opcode; | 688 static const char *Opcode; |
689 }; | 689 }; |
690 | 690 |
691 // Instructions of the form x := y op z | 691 // Instructions of the form x := y op z |
692 template <InstX8632::InstKindX8632 K> | 692 template <InstX8632::InstKindX8632 K> |
693 class InstX8632ThreeAddressop : public InstX8632 { | 693 class InstX8632ThreeAddressop : public InstX8632 { |
694 public: | 694 public: |
695 static InstX8632ThreeAddressop *create(Cfg *Func, Variable *Dest, | 695 static InstX8632ThreeAddressop *create(Cfg *Func, Variable *Dest, |
696 Operand *Source0, Operand *Source1) { | 696 Operand *Source0, Operand *Source1) { |
697 return new (Func->allocate<InstX8632ThreeAddressop>()) | 697 return new (Func->allocate<InstX8632ThreeAddressop>()) |
698 InstX8632ThreeAddressop(Func, Dest, Source0, Source1); | 698 InstX8632ThreeAddressop(Func, Dest, Source0, Source1); |
699 } | 699 } |
700 virtual void emit(const Cfg *Func) const { | 700 void emit(const Cfg *Func) const override { |
701 Ostream &Str = Func->getContext()->getStrEmit(); | 701 Ostream &Str = Func->getContext()->getStrEmit(); |
702 assert(getSrcSize() == 2); | 702 assert(getSrcSize() == 2); |
703 Str << "\t" << Opcode << "\t"; | 703 Str << "\t" << Opcode << "\t"; |
704 getDest()->emit(Func); | 704 getDest()->emit(Func); |
705 Str << ", "; | 705 Str << ", "; |
706 getSrc(0)->emit(Func); | 706 getSrc(0)->emit(Func); |
707 Str << ", "; | 707 Str << ", "; |
708 getSrc(1)->emit(Func); | 708 getSrc(1)->emit(Func); |
709 Str << "\n"; | 709 Str << "\n"; |
710 } | 710 } |
711 virtual void dump(const Cfg *Func) const { | 711 void dump(const Cfg *Func) const override { |
712 Ostream &Str = Func->getContext()->getStrDump(); | 712 Ostream &Str = Func->getContext()->getStrDump(); |
713 dumpDest(Func); | 713 dumpDest(Func); |
714 Str << " = " << Opcode << "." << getDest()->getType() << " "; | 714 Str << " = " << Opcode << "." << getDest()->getType() << " "; |
715 dumpSources(Func); | 715 dumpSources(Func); |
716 } | 716 } |
717 static bool classof(const Inst *Inst) { return isClassof(Inst, K); } | 717 static bool classof(const Inst *Inst) { return isClassof(Inst, K); } |
718 | 718 |
719 private: | 719 private: |
720 InstX8632ThreeAddressop(Cfg *Func, Variable *Dest, Operand *Source0, | 720 InstX8632ThreeAddressop(Cfg *Func, Variable *Dest, Operand *Source0, |
721 Operand *Source1) | 721 Operand *Source1) |
722 : InstX8632(Func, K, 2, Dest) { | 722 : InstX8632(Func, K, 2, Dest) { |
723 addSource(Source0); | 723 addSource(Source0); |
724 addSource(Source1); | 724 addSource(Source1); |
725 } | 725 } |
726 InstX8632ThreeAddressop(const InstX8632ThreeAddressop &) | 726 InstX8632ThreeAddressop(const InstX8632ThreeAddressop &) |
727 LLVM_DELETED_FUNCTION; | 727 LLVM_DELETED_FUNCTION; |
728 InstX8632ThreeAddressop & | 728 InstX8632ThreeAddressop & |
729 operator=(const InstX8632ThreeAddressop &) LLVM_DELETED_FUNCTION; | 729 operator=(const InstX8632ThreeAddressop &) LLVM_DELETED_FUNCTION; |
730 virtual ~InstX8632ThreeAddressop() {} | 730 ~InstX8632ThreeAddressop() override {} |
731 static const char *Opcode; | 731 static const char *Opcode; |
732 }; | 732 }; |
733 | 733 |
734 bool checkForRedundantAssign(const Variable *Dest, const Operand *Source); | 734 bool checkForRedundantAssign(const Variable *Dest, const Operand *Source); |
735 | 735 |
736 // Base class for assignment instructions | 736 // Base class for assignment instructions |
737 template <InstX8632::InstKindX8632 K> | 737 template <InstX8632::InstKindX8632 K> |
738 class InstX8632Movlike : public InstX8632 { | 738 class InstX8632Movlike : public InstX8632 { |
739 public: | 739 public: |
740 static InstX8632Movlike *create(Cfg *Func, Variable *Dest, Operand *Source) { | 740 static InstX8632Movlike *create(Cfg *Func, Variable *Dest, Operand *Source) { |
741 return new (Func->allocate<InstX8632Movlike>()) | 741 return new (Func->allocate<InstX8632Movlike>()) |
742 InstX8632Movlike(Func, Dest, Source); | 742 InstX8632Movlike(Func, Dest, Source); |
743 } | 743 } |
744 virtual bool isRedundantAssign() const { | 744 bool isRedundantAssign() const override { |
745 return checkForRedundantAssign(getDest(), getSrc(0)); | 745 return checkForRedundantAssign(getDest(), getSrc(0)); |
746 } | 746 } |
747 virtual bool isSimpleAssign() const { return true; } | 747 bool isSimpleAssign() const override { return true; } |
748 virtual void emit(const Cfg *Func) const; | 748 void emit(const Cfg *Func) const override; |
749 virtual void dump(const Cfg *Func) const { | 749 void dump(const Cfg *Func) const override { |
750 Ostream &Str = Func->getContext()->getStrDump(); | 750 Ostream &Str = Func->getContext()->getStrDump(); |
751 Str << Opcode << "." << getDest()->getType() << " "; | 751 Str << Opcode << "." << getDest()->getType() << " "; |
752 dumpDest(Func); | 752 dumpDest(Func); |
753 Str << ", "; | 753 Str << ", "; |
754 dumpSources(Func); | 754 dumpSources(Func); |
755 } | 755 } |
756 static bool classof(const Inst *Inst) { return isClassof(Inst, K); } | 756 static bool classof(const Inst *Inst) { return isClassof(Inst, K); } |
757 | 757 |
758 private: | 758 private: |
759 InstX8632Movlike(Cfg *Func, Variable *Dest, Operand *Source) | 759 InstX8632Movlike(Cfg *Func, Variable *Dest, Operand *Source) |
760 : InstX8632(Func, K, 1, Dest) { | 760 : InstX8632(Func, K, 1, Dest) { |
761 addSource(Source); | 761 addSource(Source); |
762 } | 762 } |
763 InstX8632Movlike(const InstX8632Movlike &) LLVM_DELETED_FUNCTION; | 763 InstX8632Movlike(const InstX8632Movlike &) LLVM_DELETED_FUNCTION; |
764 InstX8632Movlike &operator=(const InstX8632Movlike &) LLVM_DELETED_FUNCTION; | 764 InstX8632Movlike &operator=(const InstX8632Movlike &) LLVM_DELETED_FUNCTION; |
765 virtual ~InstX8632Movlike() {} | 765 ~InstX8632Movlike() override {} |
766 | 766 |
767 static const char *Opcode; | 767 static const char *Opcode; |
768 }; | 768 }; |
769 | 769 |
770 typedef InstX8632InplaceopGPR<InstX8632::Bswap> InstX8632Bswap; | 770 typedef InstX8632InplaceopGPR<InstX8632::Bswap> InstX8632Bswap; |
771 typedef InstX8632InplaceopGPR<InstX8632::Neg> InstX8632Neg; | 771 typedef InstX8632InplaceopGPR<InstX8632::Neg> InstX8632Neg; |
772 typedef InstX8632UnaryopGPR<InstX8632::Bsf> InstX8632Bsf; | 772 typedef InstX8632UnaryopGPR<InstX8632::Bsf> InstX8632Bsf; |
773 typedef InstX8632UnaryopGPR<InstX8632::Bsr> InstX8632Bsr; | 773 typedef InstX8632UnaryopGPR<InstX8632::Bsr> InstX8632Bsr; |
774 typedef InstX8632UnaryopGPR<InstX8632::Lea> InstX8632Lea; | 774 typedef InstX8632UnaryopGPR<InstX8632::Lea> InstX8632Lea; |
775 // Cbwdq instruction - wrapper for cbw, cwd, and cdq | 775 // Cbwdq instruction - wrapper for cbw, cwd, and cdq |
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
837 protected: | 837 protected: |
838 bool Locked; | 838 bool Locked; |
839 | 839 |
840 InstX8632Lockable(Cfg *Func, InstKindX8632 Kind, SizeT Maxsrcs, | 840 InstX8632Lockable(Cfg *Func, InstKindX8632 Kind, SizeT Maxsrcs, |
841 Variable *Dest, bool Locked) | 841 Variable *Dest, bool Locked) |
842 : InstX8632(Func, Kind, Maxsrcs, Dest), Locked(Locked) { | 842 : InstX8632(Func, Kind, Maxsrcs, Dest), Locked(Locked) { |
843 // Assume that such instructions are used for Atomics and be careful | 843 // Assume that such instructions are used for Atomics and be careful |
844 // with optimizations. | 844 // with optimizations. |
845 HasSideEffects = Locked; | 845 HasSideEffects = Locked; |
846 } | 846 } |
847 virtual ~InstX8632Lockable() {} | 847 ~InstX8632Lockable() override {} |
848 | 848 |
849 private: | 849 private: |
850 InstX8632Lockable(const InstX8632Lockable &) LLVM_DELETED_FUNCTION; | 850 InstX8632Lockable(const InstX8632Lockable &) LLVM_DELETED_FUNCTION; |
851 InstX8632Lockable &operator=(const InstX8632Lockable &) LLVM_DELETED_FUNCTION; | 851 InstX8632Lockable &operator=(const InstX8632Lockable &) LLVM_DELETED_FUNCTION; |
852 }; | 852 }; |
853 | 853 |
854 // Mul instruction - unsigned multiply. | 854 // Mul instruction - unsigned multiply. |
855 class InstX8632Mul : public InstX8632 { | 855 class InstX8632Mul : public InstX8632 { |
856 public: | 856 public: |
857 static InstX8632Mul *create(Cfg *Func, Variable *Dest, Variable *Source1, | 857 static InstX8632Mul *create(Cfg *Func, Variable *Dest, Variable *Source1, |
858 Operand *Source2) { | 858 Operand *Source2) { |
859 return new (Func->allocate<InstX8632Mul>()) | 859 return new (Func->allocate<InstX8632Mul>()) |
860 InstX8632Mul(Func, Dest, Source1, Source2); | 860 InstX8632Mul(Func, Dest, Source1, Source2); |
861 } | 861 } |
862 virtual void emit(const Cfg *Func) const; | 862 void emit(const Cfg *Func) const override; |
863 virtual void dump(const Cfg *Func) const; | 863 void dump(const Cfg *Func) const override; |
864 static bool classof(const Inst *Inst) { return isClassof(Inst, Mul); } | 864 static bool classof(const Inst *Inst) { return isClassof(Inst, Mul); } |
865 | 865 |
866 private: | 866 private: |
867 InstX8632Mul(Cfg *Func, Variable *Dest, Variable *Source1, Operand *Source2); | 867 InstX8632Mul(Cfg *Func, Variable *Dest, Variable *Source1, Operand *Source2); |
868 InstX8632Mul(const InstX8632Mul &) LLVM_DELETED_FUNCTION; | 868 InstX8632Mul(const InstX8632Mul &) LLVM_DELETED_FUNCTION; |
869 InstX8632Mul &operator=(const InstX8632Mul &) LLVM_DELETED_FUNCTION; | 869 InstX8632Mul &operator=(const InstX8632Mul &) LLVM_DELETED_FUNCTION; |
870 virtual ~InstX8632Mul() {} | 870 ~InstX8632Mul() override {} |
871 }; | 871 }; |
872 | 872 |
873 // Shld instruction - shift across a pair of operands. TODO: Verify | 873 // Shld instruction - shift across a pair of operands. TODO: Verify |
874 // that the validator accepts the shld instruction. | 874 // that the validator accepts the shld instruction. |
875 class InstX8632Shld : public InstX8632 { | 875 class InstX8632Shld : public InstX8632 { |
876 public: | 876 public: |
877 static InstX8632Shld *create(Cfg *Func, Variable *Dest, Variable *Source1, | 877 static InstX8632Shld *create(Cfg *Func, Variable *Dest, Variable *Source1, |
878 Variable *Source2) { | 878 Variable *Source2) { |
879 return new (Func->allocate<InstX8632Shld>()) | 879 return new (Func->allocate<InstX8632Shld>()) |
880 InstX8632Shld(Func, Dest, Source1, Source2); | 880 InstX8632Shld(Func, Dest, Source1, Source2); |
881 } | 881 } |
882 virtual void emit(const Cfg *Func) const; | 882 void emit(const Cfg *Func) const override; |
883 virtual void dump(const Cfg *Func) const; | 883 void dump(const Cfg *Func) const override; |
884 static bool classof(const Inst *Inst) { return isClassof(Inst, Shld); } | 884 static bool classof(const Inst *Inst) { return isClassof(Inst, Shld); } |
885 | 885 |
886 private: | 886 private: |
887 InstX8632Shld(Cfg *Func, Variable *Dest, Variable *Source1, | 887 InstX8632Shld(Cfg *Func, Variable *Dest, Variable *Source1, |
888 Variable *Source2); | 888 Variable *Source2); |
889 InstX8632Shld(const InstX8632Shld &) LLVM_DELETED_FUNCTION; | 889 InstX8632Shld(const InstX8632Shld &) LLVM_DELETED_FUNCTION; |
890 InstX8632Shld &operator=(const InstX8632Shld &) LLVM_DELETED_FUNCTION; | 890 InstX8632Shld &operator=(const InstX8632Shld &) LLVM_DELETED_FUNCTION; |
891 virtual ~InstX8632Shld() {} | 891 ~InstX8632Shld() override {} |
892 }; | 892 }; |
893 | 893 |
894 // Shrd instruction - shift across a pair of operands. TODO: Verify | 894 // Shrd instruction - shift across a pair of operands. TODO: Verify |
895 // that the validator accepts the shrd instruction. | 895 // that the validator accepts the shrd instruction. |
896 class InstX8632Shrd : public InstX8632 { | 896 class InstX8632Shrd : public InstX8632 { |
897 public: | 897 public: |
898 static InstX8632Shrd *create(Cfg *Func, Variable *Dest, Variable *Source1, | 898 static InstX8632Shrd *create(Cfg *Func, Variable *Dest, Variable *Source1, |
899 Variable *Source2) { | 899 Variable *Source2) { |
900 return new (Func->allocate<InstX8632Shrd>()) | 900 return new (Func->allocate<InstX8632Shrd>()) |
901 InstX8632Shrd(Func, Dest, Source1, Source2); | 901 InstX8632Shrd(Func, Dest, Source1, Source2); |
902 } | 902 } |
903 virtual void emit(const Cfg *Func) const; | 903 void emit(const Cfg *Func) const override; |
904 virtual void dump(const Cfg *Func) const; | 904 void dump(const Cfg *Func) const override; |
905 static bool classof(const Inst *Inst) { return isClassof(Inst, Shrd); } | 905 static bool classof(const Inst *Inst) { return isClassof(Inst, Shrd); } |
906 | 906 |
907 private: | 907 private: |
908 InstX8632Shrd(Cfg *Func, Variable *Dest, Variable *Source1, | 908 InstX8632Shrd(Cfg *Func, Variable *Dest, Variable *Source1, |
909 Variable *Source2); | 909 Variable *Source2); |
910 InstX8632Shrd(const InstX8632Shrd &) LLVM_DELETED_FUNCTION; | 910 InstX8632Shrd(const InstX8632Shrd &) LLVM_DELETED_FUNCTION; |
911 InstX8632Shrd &operator=(const InstX8632Shrd &) LLVM_DELETED_FUNCTION; | 911 InstX8632Shrd &operator=(const InstX8632Shrd &) LLVM_DELETED_FUNCTION; |
912 virtual ~InstX8632Shrd() {} | 912 ~InstX8632Shrd() override {} |
913 }; | 913 }; |
914 | 914 |
915 // Conditional move instruction. | 915 // Conditional move instruction. |
916 class InstX8632Cmov : public InstX8632 { | 916 class InstX8632Cmov : public InstX8632 { |
917 public: | 917 public: |
918 static InstX8632Cmov *create(Cfg *Func, Variable *Dest, Operand *Source, | 918 static InstX8632Cmov *create(Cfg *Func, Variable *Dest, Operand *Source, |
919 CondX86::BrCond Cond) { | 919 CondX86::BrCond Cond) { |
920 return new (Func->allocate<InstX8632Cmov>()) | 920 return new (Func->allocate<InstX8632Cmov>()) |
921 InstX8632Cmov(Func, Dest, Source, Cond); | 921 InstX8632Cmov(Func, Dest, Source, Cond); |
922 } | 922 } |
923 virtual void emit(const Cfg *Func) const; | 923 void emit(const Cfg *Func) const override; |
924 virtual void emitIAS(const Cfg *Func) const; | 924 void emitIAS(const Cfg *Func) const override; |
925 virtual void dump(const Cfg *Func) const; | 925 void dump(const Cfg *Func) const override; |
926 static bool classof(const Inst *Inst) { return isClassof(Inst, Cmov); } | 926 static bool classof(const Inst *Inst) { return isClassof(Inst, Cmov); } |
927 | 927 |
928 private: | 928 private: |
929 InstX8632Cmov(Cfg *Func, Variable *Dest, Operand *Source, | 929 InstX8632Cmov(Cfg *Func, Variable *Dest, Operand *Source, |
930 CondX86::BrCond Cond); | 930 CondX86::BrCond Cond); |
931 InstX8632Cmov(const InstX8632Cmov &) LLVM_DELETED_FUNCTION; | 931 InstX8632Cmov(const InstX8632Cmov &) LLVM_DELETED_FUNCTION; |
932 InstX8632Cmov &operator=(const InstX8632Cmov &) LLVM_DELETED_FUNCTION; | 932 InstX8632Cmov &operator=(const InstX8632Cmov &) LLVM_DELETED_FUNCTION; |
933 virtual ~InstX8632Cmov() {} | 933 ~InstX8632Cmov() override {} |
934 | 934 |
935 CondX86::BrCond Condition; | 935 CondX86::BrCond Condition; |
936 }; | 936 }; |
937 | 937 |
938 // Cmpps instruction - compare packed singled-precision floating point | 938 // Cmpps instruction - compare packed singled-precision floating point |
939 // values | 939 // values |
940 class InstX8632Cmpps : public InstX8632 { | 940 class InstX8632Cmpps : public InstX8632 { |
941 public: | 941 public: |
942 static InstX8632Cmpps *create(Cfg *Func, Variable *Dest, Operand *Source, | 942 static InstX8632Cmpps *create(Cfg *Func, Variable *Dest, Operand *Source, |
943 CondX86::CmppsCond Condition) { | 943 CondX86::CmppsCond Condition) { |
944 return new (Func->allocate<InstX8632Cmpps>()) | 944 return new (Func->allocate<InstX8632Cmpps>()) |
945 InstX8632Cmpps(Func, Dest, Source, Condition); | 945 InstX8632Cmpps(Func, Dest, Source, Condition); |
946 } | 946 } |
947 virtual void emit(const Cfg *Func) const; | 947 void emit(const Cfg *Func) const override; |
948 virtual void emitIAS(const Cfg *Func) const; | 948 void emitIAS(const Cfg *Func) const override; |
949 virtual void dump(const Cfg *Func) const; | 949 void dump(const Cfg *Func) const override; |
950 static bool classof(const Inst *Inst) { return isClassof(Inst, Cmpps); } | 950 static bool classof(const Inst *Inst) { return isClassof(Inst, Cmpps); } |
951 | 951 |
952 private: | 952 private: |
953 InstX8632Cmpps(Cfg *Func, Variable *Dest, Operand *Source, | 953 InstX8632Cmpps(Cfg *Func, Variable *Dest, Operand *Source, |
954 CondX86::CmppsCond Cond); | 954 CondX86::CmppsCond Cond); |
955 InstX8632Cmpps(const InstX8632Cmpps &) LLVM_DELETED_FUNCTION; | 955 InstX8632Cmpps(const InstX8632Cmpps &) LLVM_DELETED_FUNCTION; |
956 InstX8632Cmpps &operator=(const InstX8632Cmpps &) LLVM_DELETED_FUNCTION; | 956 InstX8632Cmpps &operator=(const InstX8632Cmpps &) LLVM_DELETED_FUNCTION; |
957 virtual ~InstX8632Cmpps() {} | 957 ~InstX8632Cmpps() override {} |
958 | 958 |
959 CondX86::CmppsCond Condition; | 959 CondX86::CmppsCond Condition; |
960 }; | 960 }; |
961 | 961 |
962 // Cmpxchg instruction - cmpxchg <dest>, <desired> will compare if <dest> | 962 // Cmpxchg instruction - cmpxchg <dest>, <desired> will compare if <dest> |
963 // equals eax. If so, the ZF is set and <desired> is stored in <dest>. | 963 // equals eax. If so, the ZF is set and <desired> is stored in <dest>. |
964 // If not, ZF is cleared and <dest> is copied to eax (or subregister). | 964 // If not, ZF is cleared and <dest> is copied to eax (or subregister). |
965 // <dest> can be a register or memory, while <desired> must be a register. | 965 // <dest> can be a register or memory, while <desired> must be a register. |
966 // It is the user's responsiblity to mark eax with a FakeDef. | 966 // It is the user's responsiblity to mark eax with a FakeDef. |
967 class InstX8632Cmpxchg : public InstX8632Lockable { | 967 class InstX8632Cmpxchg : public InstX8632Lockable { |
968 public: | 968 public: |
969 static InstX8632Cmpxchg *create(Cfg *Func, Operand *DestOrAddr, Variable *Eax, | 969 static InstX8632Cmpxchg *create(Cfg *Func, Operand *DestOrAddr, Variable *Eax, |
970 Variable *Desired, bool Locked) { | 970 Variable *Desired, bool Locked) { |
971 return new (Func->allocate<InstX8632Cmpxchg>()) | 971 return new (Func->allocate<InstX8632Cmpxchg>()) |
972 InstX8632Cmpxchg(Func, DestOrAddr, Eax, Desired, Locked); | 972 InstX8632Cmpxchg(Func, DestOrAddr, Eax, Desired, Locked); |
973 } | 973 } |
974 virtual void emit(const Cfg *Func) const; | 974 void emit(const Cfg *Func) const override; |
975 virtual void emitIAS(const Cfg *Func) const; | 975 void emitIAS(const Cfg *Func) const override; |
976 virtual void dump(const Cfg *Func) const; | 976 void dump(const Cfg *Func) const override; |
977 static bool classof(const Inst *Inst) { return isClassof(Inst, Cmpxchg); } | 977 static bool classof(const Inst *Inst) { return isClassof(Inst, Cmpxchg); } |
978 | 978 |
979 private: | 979 private: |
980 InstX8632Cmpxchg(Cfg *Func, Operand *DestOrAddr, Variable *Eax, | 980 InstX8632Cmpxchg(Cfg *Func, Operand *DestOrAddr, Variable *Eax, |
981 Variable *Desired, bool Locked); | 981 Variable *Desired, bool Locked); |
982 InstX8632Cmpxchg(const InstX8632Cmpxchg &) LLVM_DELETED_FUNCTION; | 982 InstX8632Cmpxchg(const InstX8632Cmpxchg &) LLVM_DELETED_FUNCTION; |
983 InstX8632Cmpxchg &operator=(const InstX8632Cmpxchg &) LLVM_DELETED_FUNCTION; | 983 InstX8632Cmpxchg &operator=(const InstX8632Cmpxchg &) LLVM_DELETED_FUNCTION; |
984 virtual ~InstX8632Cmpxchg() {} | 984 ~InstX8632Cmpxchg() override {} |
985 }; | 985 }; |
986 | 986 |
987 // Cmpxchg8b instruction - cmpxchg8b <m64> will compare if <m64> | 987 // Cmpxchg8b instruction - cmpxchg8b <m64> will compare if <m64> |
988 // equals edx:eax. If so, the ZF is set and ecx:ebx is stored in <m64>. | 988 // equals edx:eax. If so, the ZF is set and ecx:ebx is stored in <m64>. |
989 // If not, ZF is cleared and <m64> is copied to edx:eax. | 989 // If not, ZF is cleared and <m64> is copied to edx:eax. |
990 // The caller is responsible for inserting FakeDefs to mark edx | 990 // The caller is responsible for inserting FakeDefs to mark edx |
991 // and eax as modified. | 991 // and eax as modified. |
992 // <m64> must be a memory operand. | 992 // <m64> must be a memory operand. |
993 class InstX8632Cmpxchg8b : public InstX8632Lockable { | 993 class InstX8632Cmpxchg8b : public InstX8632Lockable { |
994 public: | 994 public: |
995 static InstX8632Cmpxchg8b *create(Cfg *Func, OperandX8632Mem *Dest, | 995 static InstX8632Cmpxchg8b *create(Cfg *Func, OperandX8632Mem *Dest, |
996 Variable *Edx, Variable *Eax, Variable *Ecx, | 996 Variable *Edx, Variable *Eax, Variable *Ecx, |
997 Variable *Ebx, bool Locked) { | 997 Variable *Ebx, bool Locked) { |
998 return new (Func->allocate<InstX8632Cmpxchg8b>()) | 998 return new (Func->allocate<InstX8632Cmpxchg8b>()) |
999 InstX8632Cmpxchg8b(Func, Dest, Edx, Eax, Ecx, Ebx, Locked); | 999 InstX8632Cmpxchg8b(Func, Dest, Edx, Eax, Ecx, Ebx, Locked); |
1000 } | 1000 } |
1001 virtual void emit(const Cfg *Func) const; | 1001 void emit(const Cfg *Func) const override; |
1002 virtual void emitIAS(const Cfg *Func) const; | 1002 void emitIAS(const Cfg *Func) const override; |
1003 virtual void dump(const Cfg *Func) const; | 1003 void dump(const Cfg *Func) const override; |
1004 static bool classof(const Inst *Inst) { return isClassof(Inst, Cmpxchg8b); } | 1004 static bool classof(const Inst *Inst) { return isClassof(Inst, Cmpxchg8b); } |
1005 | 1005 |
1006 private: | 1006 private: |
1007 InstX8632Cmpxchg8b(Cfg *Func, OperandX8632Mem *Dest, Variable *Edx, | 1007 InstX8632Cmpxchg8b(Cfg *Func, OperandX8632Mem *Dest, Variable *Edx, |
1008 Variable *Eax, Variable *Ecx, Variable *Ebx, bool Locked); | 1008 Variable *Eax, Variable *Ecx, Variable *Ebx, bool Locked); |
1009 InstX8632Cmpxchg8b(const InstX8632Cmpxchg8b &) LLVM_DELETED_FUNCTION; | 1009 InstX8632Cmpxchg8b(const InstX8632Cmpxchg8b &) LLVM_DELETED_FUNCTION; |
1010 InstX8632Cmpxchg8b & | 1010 InstX8632Cmpxchg8b & |
1011 operator=(const InstX8632Cmpxchg8b &) LLVM_DELETED_FUNCTION; | 1011 operator=(const InstX8632Cmpxchg8b &) LLVM_DELETED_FUNCTION; |
1012 virtual ~InstX8632Cmpxchg8b() {} | 1012 ~InstX8632Cmpxchg8b() override {} |
1013 }; | 1013 }; |
1014 | 1014 |
1015 // Cvt instruction - wrapper for cvtsX2sY where X and Y are in {s,d,i} | 1015 // Cvt instruction - wrapper for cvtsX2sY where X and Y are in {s,d,i} |
1016 // as appropriate. s=float, d=double, i=int. X and Y are determined | 1016 // as appropriate. s=float, d=double, i=int. X and Y are determined |
1017 // from dest/src types. Sign and zero extension on the integer | 1017 // from dest/src types. Sign and zero extension on the integer |
1018 // operand needs to be done separately. | 1018 // operand needs to be done separately. |
1019 class InstX8632Cvt : public InstX8632 { | 1019 class InstX8632Cvt : public InstX8632 { |
1020 public: | 1020 public: |
1021 static InstX8632Cvt *create(Cfg *Func, Variable *Dest, Operand *Source, | 1021 static InstX8632Cvt *create(Cfg *Func, Variable *Dest, Operand *Source, |
1022 bool Trunc) { | 1022 bool Trunc) { |
1023 return new (Func->allocate<InstX8632Cvt>()) | 1023 return new (Func->allocate<InstX8632Cvt>()) |
1024 InstX8632Cvt(Func, Dest, Source, Trunc); | 1024 InstX8632Cvt(Func, Dest, Source, Trunc); |
1025 } | 1025 } |
1026 virtual void emit(const Cfg *Func) const; | 1026 void emit(const Cfg *Func) const override; |
1027 virtual void dump(const Cfg *Func) const; | 1027 void dump(const Cfg *Func) const override; |
1028 static bool classof(const Inst *Inst) { return isClassof(Inst, Cvt); } | 1028 static bool classof(const Inst *Inst) { return isClassof(Inst, Cvt); } |
1029 | 1029 |
1030 private: | 1030 private: |
1031 bool Trunc; | 1031 bool Trunc; |
1032 InstX8632Cvt(Cfg *Func, Variable *Dest, Operand *Source, bool Trunc); | 1032 InstX8632Cvt(Cfg *Func, Variable *Dest, Operand *Source, bool Trunc); |
1033 InstX8632Cvt(const InstX8632Cvt &) LLVM_DELETED_FUNCTION; | 1033 InstX8632Cvt(const InstX8632Cvt &) LLVM_DELETED_FUNCTION; |
1034 InstX8632Cvt &operator=(const InstX8632Cvt &) LLVM_DELETED_FUNCTION; | 1034 InstX8632Cvt &operator=(const InstX8632Cvt &) LLVM_DELETED_FUNCTION; |
1035 virtual ~InstX8632Cvt() {} | 1035 ~InstX8632Cvt() override {} |
1036 }; | 1036 }; |
1037 | 1037 |
1038 // cmp - Integer compare instruction. | 1038 // cmp - Integer compare instruction. |
1039 class InstX8632Icmp : public InstX8632 { | 1039 class InstX8632Icmp : public InstX8632 { |
1040 public: | 1040 public: |
1041 static InstX8632Icmp *create(Cfg *Func, Operand *Src1, Operand *Src2) { | 1041 static InstX8632Icmp *create(Cfg *Func, Operand *Src1, Operand *Src2) { |
1042 return new (Func->allocate<InstX8632Icmp>()) | 1042 return new (Func->allocate<InstX8632Icmp>()) |
1043 InstX8632Icmp(Func, Src1, Src2); | 1043 InstX8632Icmp(Func, Src1, Src2); |
1044 } | 1044 } |
1045 virtual void emit(const Cfg *Func) const; | 1045 void emit(const Cfg *Func) const override; |
1046 virtual void dump(const Cfg *Func) const; | 1046 void dump(const Cfg *Func) const override; |
1047 static bool classof(const Inst *Inst) { return isClassof(Inst, Icmp); } | 1047 static bool classof(const Inst *Inst) { return isClassof(Inst, Icmp); } |
1048 | 1048 |
1049 private: | 1049 private: |
1050 InstX8632Icmp(Cfg *Func, Operand *Src1, Operand *Src2); | 1050 InstX8632Icmp(Cfg *Func, Operand *Src1, Operand *Src2); |
1051 InstX8632Icmp(const InstX8632Icmp &) LLVM_DELETED_FUNCTION; | 1051 InstX8632Icmp(const InstX8632Icmp &) LLVM_DELETED_FUNCTION; |
1052 InstX8632Icmp &operator=(const InstX8632Icmp &) LLVM_DELETED_FUNCTION; | 1052 InstX8632Icmp &operator=(const InstX8632Icmp &) LLVM_DELETED_FUNCTION; |
1053 virtual ~InstX8632Icmp() {} | 1053 ~InstX8632Icmp() override {} |
1054 }; | 1054 }; |
1055 | 1055 |
1056 // ucomiss/ucomisd - floating-point compare instruction. | 1056 // ucomiss/ucomisd - floating-point compare instruction. |
1057 class InstX8632Ucomiss : public InstX8632 { | 1057 class InstX8632Ucomiss : public InstX8632 { |
1058 public: | 1058 public: |
1059 static InstX8632Ucomiss *create(Cfg *Func, Operand *Src1, Operand *Src2) { | 1059 static InstX8632Ucomiss *create(Cfg *Func, Operand *Src1, Operand *Src2) { |
1060 return new (Func->allocate<InstX8632Ucomiss>()) | 1060 return new (Func->allocate<InstX8632Ucomiss>()) |
1061 InstX8632Ucomiss(Func, Src1, Src2); | 1061 InstX8632Ucomiss(Func, Src1, Src2); |
1062 } | 1062 } |
1063 virtual void emit(const Cfg *Func) const; | 1063 void emit(const Cfg *Func) const override; |
1064 virtual void emitIAS(const Cfg *Func) const; | 1064 void emitIAS(const Cfg *Func) const override; |
1065 virtual void dump(const Cfg *Func) const; | 1065 void dump(const Cfg *Func) const override; |
1066 static bool classof(const Inst *Inst) { return isClassof(Inst, Ucomiss); } | 1066 static bool classof(const Inst *Inst) { return isClassof(Inst, Ucomiss); } |
1067 | 1067 |
1068 private: | 1068 private: |
1069 InstX8632Ucomiss(Cfg *Func, Operand *Src1, Operand *Src2); | 1069 InstX8632Ucomiss(Cfg *Func, Operand *Src1, Operand *Src2); |
1070 InstX8632Ucomiss(const InstX8632Ucomiss &) LLVM_DELETED_FUNCTION; | 1070 InstX8632Ucomiss(const InstX8632Ucomiss &) LLVM_DELETED_FUNCTION; |
1071 InstX8632Ucomiss &operator=(const InstX8632Ucomiss &) LLVM_DELETED_FUNCTION; | 1071 InstX8632Ucomiss &operator=(const InstX8632Ucomiss &) LLVM_DELETED_FUNCTION; |
1072 virtual ~InstX8632Ucomiss() {} | 1072 ~InstX8632Ucomiss() override {} |
1073 }; | 1073 }; |
1074 | 1074 |
1075 // UD2 instruction. | 1075 // UD2 instruction. |
1076 class InstX8632UD2 : public InstX8632 { | 1076 class InstX8632UD2 : public InstX8632 { |
1077 public: | 1077 public: |
1078 static InstX8632UD2 *create(Cfg *Func) { | 1078 static InstX8632UD2 *create(Cfg *Func) { |
1079 return new (Func->allocate<InstX8632UD2>()) InstX8632UD2(Func); | 1079 return new (Func->allocate<InstX8632UD2>()) InstX8632UD2(Func); |
1080 } | 1080 } |
1081 virtual void emit(const Cfg *Func) const; | 1081 void emit(const Cfg *Func) const override; |
1082 virtual void dump(const Cfg *Func) const; | 1082 void dump(const Cfg *Func) const override; |
1083 static bool classof(const Inst *Inst) { return isClassof(Inst, UD2); } | 1083 static bool classof(const Inst *Inst) { return isClassof(Inst, UD2); } |
1084 | 1084 |
1085 private: | 1085 private: |
1086 InstX8632UD2(Cfg *Func); | 1086 InstX8632UD2(Cfg *Func); |
1087 InstX8632UD2(const InstX8632UD2 &) LLVM_DELETED_FUNCTION; | 1087 InstX8632UD2(const InstX8632UD2 &) LLVM_DELETED_FUNCTION; |
1088 InstX8632UD2 &operator=(const InstX8632UD2 &) LLVM_DELETED_FUNCTION; | 1088 InstX8632UD2 &operator=(const InstX8632UD2 &) LLVM_DELETED_FUNCTION; |
1089 virtual ~InstX8632UD2() {} | 1089 ~InstX8632UD2() override {} |
1090 }; | 1090 }; |
1091 | 1091 |
1092 // Test instruction. | 1092 // Test instruction. |
1093 class InstX8632Test : public InstX8632 { | 1093 class InstX8632Test : public InstX8632 { |
1094 public: | 1094 public: |
1095 static InstX8632Test *create(Cfg *Func, Operand *Source1, Operand *Source2) { | 1095 static InstX8632Test *create(Cfg *Func, Operand *Source1, Operand *Source2) { |
1096 return new (Func->allocate<InstX8632Test>()) | 1096 return new (Func->allocate<InstX8632Test>()) |
1097 InstX8632Test(Func, Source1, Source2); | 1097 InstX8632Test(Func, Source1, Source2); |
1098 } | 1098 } |
1099 virtual void emit(const Cfg *Func) const; | 1099 void emit(const Cfg *Func) const override; |
1100 virtual void dump(const Cfg *Func) const; | 1100 void dump(const Cfg *Func) const override; |
1101 static bool classof(const Inst *Inst) { return isClassof(Inst, Test); } | 1101 static bool classof(const Inst *Inst) { return isClassof(Inst, Test); } |
1102 | 1102 |
1103 private: | 1103 private: |
1104 InstX8632Test(Cfg *Func, Operand *Source1, Operand *Source2); | 1104 InstX8632Test(Cfg *Func, Operand *Source1, Operand *Source2); |
1105 InstX8632Test(const InstX8632Test &) LLVM_DELETED_FUNCTION; | 1105 InstX8632Test(const InstX8632Test &) LLVM_DELETED_FUNCTION; |
1106 InstX8632Test &operator=(const InstX8632Test &) LLVM_DELETED_FUNCTION; | 1106 InstX8632Test &operator=(const InstX8632Test &) LLVM_DELETED_FUNCTION; |
1107 virtual ~InstX8632Test() {} | 1107 ~InstX8632Test() override {} |
1108 }; | 1108 }; |
1109 | 1109 |
1110 // Mfence instruction. | 1110 // Mfence instruction. |
1111 class InstX8632Mfence : public InstX8632 { | 1111 class InstX8632Mfence : public InstX8632 { |
1112 public: | 1112 public: |
1113 static InstX8632Mfence *create(Cfg *Func) { | 1113 static InstX8632Mfence *create(Cfg *Func) { |
1114 return new (Func->allocate<InstX8632Mfence>()) InstX8632Mfence(Func); | 1114 return new (Func->allocate<InstX8632Mfence>()) InstX8632Mfence(Func); |
1115 } | 1115 } |
1116 virtual void emit(const Cfg *Func) const; | 1116 void emit(const Cfg *Func) const override; |
1117 virtual void dump(const Cfg *Func) const; | 1117 void dump(const Cfg *Func) const override; |
1118 static bool classof(const Inst *Inst) { return isClassof(Inst, Mfence); } | 1118 static bool classof(const Inst *Inst) { return isClassof(Inst, Mfence); } |
1119 | 1119 |
1120 private: | 1120 private: |
1121 InstX8632Mfence(Cfg *Func); | 1121 InstX8632Mfence(Cfg *Func); |
1122 InstX8632Mfence(const InstX8632Mfence &) LLVM_DELETED_FUNCTION; | 1122 InstX8632Mfence(const InstX8632Mfence &) LLVM_DELETED_FUNCTION; |
1123 InstX8632Mfence &operator=(const InstX8632Mfence &) LLVM_DELETED_FUNCTION; | 1123 InstX8632Mfence &operator=(const InstX8632Mfence &) LLVM_DELETED_FUNCTION; |
1124 virtual ~InstX8632Mfence() {} | 1124 ~InstX8632Mfence() override {} |
1125 }; | 1125 }; |
1126 | 1126 |
1127 // This is essentially a "mov" instruction with an OperandX8632Mem | 1127 // This is essentially a "mov" instruction with an OperandX8632Mem |
1128 // operand instead of Variable as the destination. It's important | 1128 // operand instead of Variable as the destination. It's important |
1129 // for liveness that there is no Dest operand. | 1129 // for liveness that there is no Dest operand. |
1130 class InstX8632Store : public InstX8632 { | 1130 class InstX8632Store : public InstX8632 { |
1131 public: | 1131 public: |
1132 static InstX8632Store *create(Cfg *Func, Operand *Value, OperandX8632 *Mem) { | 1132 static InstX8632Store *create(Cfg *Func, Operand *Value, OperandX8632 *Mem) { |
1133 return new (Func->allocate<InstX8632Store>()) | 1133 return new (Func->allocate<InstX8632Store>()) |
1134 InstX8632Store(Func, Value, Mem); | 1134 InstX8632Store(Func, Value, Mem); |
1135 } | 1135 } |
1136 virtual void emit(const Cfg *Func) const; | 1136 void emit(const Cfg *Func) const override; |
1137 virtual void dump(const Cfg *Func) const; | 1137 void dump(const Cfg *Func) const override; |
1138 static bool classof(const Inst *Inst) { return isClassof(Inst, Store); } | 1138 static bool classof(const Inst *Inst) { return isClassof(Inst, Store); } |
1139 | 1139 |
1140 private: | 1140 private: |
1141 InstX8632Store(Cfg *Func, Operand *Value, OperandX8632 *Mem); | 1141 InstX8632Store(Cfg *Func, Operand *Value, OperandX8632 *Mem); |
1142 InstX8632Store(const InstX8632Store &) LLVM_DELETED_FUNCTION; | 1142 InstX8632Store(const InstX8632Store &) LLVM_DELETED_FUNCTION; |
1143 InstX8632Store &operator=(const InstX8632Store &) LLVM_DELETED_FUNCTION; | 1143 InstX8632Store &operator=(const InstX8632Store &) LLVM_DELETED_FUNCTION; |
1144 virtual ~InstX8632Store() {} | 1144 ~InstX8632Store() override {} |
1145 }; | 1145 }; |
1146 | 1146 |
1147 class InstX8632StoreP : public InstX8632 { | 1147 class InstX8632StoreP : public InstX8632 { |
1148 public: | 1148 public: |
1149 static InstX8632StoreP *create(Cfg *Func, Operand *Value, OperandX8632 *Mem) { | 1149 static InstX8632StoreP *create(Cfg *Func, Operand *Value, OperandX8632 *Mem) { |
1150 return new (Func->allocate<InstX8632StoreP>()) | 1150 return new (Func->allocate<InstX8632StoreP>()) |
1151 InstX8632StoreP(Func, Value, Mem); | 1151 InstX8632StoreP(Func, Value, Mem); |
1152 } | 1152 } |
1153 virtual void emit(const Cfg *Func) const; | 1153 void emit(const Cfg *Func) const override; |
1154 virtual void dump(const Cfg *Func) const; | 1154 void dump(const Cfg *Func) const override; |
1155 static bool classof(const Inst *Inst) { return isClassof(Inst, StoreP); } | 1155 static bool classof(const Inst *Inst) { return isClassof(Inst, StoreP); } |
1156 | 1156 |
1157 private: | 1157 private: |
1158 InstX8632StoreP(Cfg *Func, Operand *Value, OperandX8632 *Mem); | 1158 InstX8632StoreP(Cfg *Func, Operand *Value, OperandX8632 *Mem); |
1159 InstX8632StoreP(const InstX8632StoreP &) LLVM_DELETED_FUNCTION; | 1159 InstX8632StoreP(const InstX8632StoreP &) LLVM_DELETED_FUNCTION; |
1160 InstX8632StoreP &operator=(const InstX8632StoreP &) LLVM_DELETED_FUNCTION; | 1160 InstX8632StoreP &operator=(const InstX8632StoreP &) LLVM_DELETED_FUNCTION; |
1161 virtual ~InstX8632StoreP() {} | 1161 ~InstX8632StoreP() override {} |
1162 }; | 1162 }; |
1163 | 1163 |
1164 // This is essentially a "movq" instruction with an OperandX8632Mem | 1164 // This is essentially a "movq" instruction with an OperandX8632Mem |
1165 // operand instead of Variable as the destination. It's important | 1165 // operand instead of Variable as the destination. It's important |
1166 // for liveness that there is no Dest operand. | 1166 // for liveness that there is no Dest operand. |
1167 class InstX8632StoreQ : public InstX8632 { | 1167 class InstX8632StoreQ : public InstX8632 { |
1168 public: | 1168 public: |
1169 static InstX8632StoreQ *create(Cfg *Func, Operand *Value, OperandX8632 *Mem) { | 1169 static InstX8632StoreQ *create(Cfg *Func, Operand *Value, OperandX8632 *Mem) { |
1170 return new (Func->allocate<InstX8632StoreQ>()) | 1170 return new (Func->allocate<InstX8632StoreQ>()) |
1171 InstX8632StoreQ(Func, Value, Mem); | 1171 InstX8632StoreQ(Func, Value, Mem); |
1172 } | 1172 } |
1173 virtual void emit(const Cfg *Func) const; | 1173 void emit(const Cfg *Func) const override; |
1174 virtual void dump(const Cfg *Func) const; | 1174 void dump(const Cfg *Func) const override; |
1175 static bool classof(const Inst *Inst) { return isClassof(Inst, StoreQ); } | 1175 static bool classof(const Inst *Inst) { return isClassof(Inst, StoreQ); } |
1176 | 1176 |
1177 private: | 1177 private: |
1178 InstX8632StoreQ(Cfg *Func, Operand *Value, OperandX8632 *Mem); | 1178 InstX8632StoreQ(Cfg *Func, Operand *Value, OperandX8632 *Mem); |
1179 InstX8632StoreQ(const InstX8632StoreQ &) LLVM_DELETED_FUNCTION; | 1179 InstX8632StoreQ(const InstX8632StoreQ &) LLVM_DELETED_FUNCTION; |
1180 InstX8632StoreQ &operator=(const InstX8632StoreQ &) LLVM_DELETED_FUNCTION; | 1180 InstX8632StoreQ &operator=(const InstX8632StoreQ &) LLVM_DELETED_FUNCTION; |
1181 virtual ~InstX8632StoreQ() {} | 1181 ~InstX8632StoreQ() override {} |
1182 }; | 1182 }; |
1183 | 1183 |
1184 // Movsx - copy from a narrower integer type to a wider integer | 1184 // Movsx - copy from a narrower integer type to a wider integer |
1185 // type, with sign extension. | 1185 // type, with sign extension. |
1186 class InstX8632Movsx : public InstX8632 { | 1186 class InstX8632Movsx : public InstX8632 { |
1187 public: | 1187 public: |
1188 static InstX8632Movsx *create(Cfg *Func, Variable *Dest, Operand *Source) { | 1188 static InstX8632Movsx *create(Cfg *Func, Variable *Dest, Operand *Source) { |
1189 return new (Func->allocate<InstX8632Movsx>()) | 1189 return new (Func->allocate<InstX8632Movsx>()) |
1190 InstX8632Movsx(Func, Dest, Source); | 1190 InstX8632Movsx(Func, Dest, Source); |
1191 } | 1191 } |
1192 virtual void emit(const Cfg *Func) const; | 1192 void emit(const Cfg *Func) const override; |
1193 virtual void dump(const Cfg *Func) const; | 1193 void dump(const Cfg *Func) const override; |
1194 static bool classof(const Inst *Inst) { return isClassof(Inst, Movsx); } | 1194 static bool classof(const Inst *Inst) { return isClassof(Inst, Movsx); } |
1195 | 1195 |
1196 private: | 1196 private: |
1197 InstX8632Movsx(Cfg *Func, Variable *Dest, Operand *Source); | 1197 InstX8632Movsx(Cfg *Func, Variable *Dest, Operand *Source); |
1198 InstX8632Movsx(const InstX8632Movsx &) LLVM_DELETED_FUNCTION; | 1198 InstX8632Movsx(const InstX8632Movsx &) LLVM_DELETED_FUNCTION; |
1199 InstX8632Movsx &operator=(const InstX8632Movsx &) LLVM_DELETED_FUNCTION; | 1199 InstX8632Movsx &operator=(const InstX8632Movsx &) LLVM_DELETED_FUNCTION; |
1200 virtual ~InstX8632Movsx() {} | 1200 ~InstX8632Movsx() override {} |
1201 }; | 1201 }; |
1202 | 1202 |
1203 // Movzx - copy from a narrower integer type to a wider integer | 1203 // Movzx - copy from a narrower integer type to a wider integer |
1204 // type, with zero extension. | 1204 // type, with zero extension. |
1205 class InstX8632Movzx : public InstX8632 { | 1205 class InstX8632Movzx : public InstX8632 { |
1206 public: | 1206 public: |
1207 static InstX8632Movzx *create(Cfg *Func, Variable *Dest, Operand *Source) { | 1207 static InstX8632Movzx *create(Cfg *Func, Variable *Dest, Operand *Source) { |
1208 return new (Func->allocate<InstX8632Movzx>()) | 1208 return new (Func->allocate<InstX8632Movzx>()) |
1209 InstX8632Movzx(Func, Dest, Source); | 1209 InstX8632Movzx(Func, Dest, Source); |
1210 } | 1210 } |
1211 virtual void emit(const Cfg *Func) const; | 1211 void emit(const Cfg *Func) const override; |
1212 virtual void dump(const Cfg *Func) const; | 1212 void dump(const Cfg *Func) const override; |
1213 static bool classof(const Inst *Inst) { return isClassof(Inst, Movzx); } | 1213 static bool classof(const Inst *Inst) { return isClassof(Inst, Movzx); } |
1214 | 1214 |
1215 private: | 1215 private: |
1216 InstX8632Movzx(Cfg *Func, Variable *Dest, Operand *Source); | 1216 InstX8632Movzx(Cfg *Func, Variable *Dest, Operand *Source); |
1217 InstX8632Movzx(const InstX8632Movzx &) LLVM_DELETED_FUNCTION; | 1217 InstX8632Movzx(const InstX8632Movzx &) LLVM_DELETED_FUNCTION; |
1218 InstX8632Movzx &operator=(const InstX8632Movzx &) LLVM_DELETED_FUNCTION; | 1218 InstX8632Movzx &operator=(const InstX8632Movzx &) LLVM_DELETED_FUNCTION; |
1219 virtual ~InstX8632Movzx() {} | 1219 ~InstX8632Movzx() override {} |
1220 }; | 1220 }; |
1221 | 1221 |
1222 // Nop instructions of varying length | 1222 // Nop instructions of varying length |
1223 class InstX8632Nop : public InstX8632 { | 1223 class InstX8632Nop : public InstX8632 { |
1224 public: | 1224 public: |
1225 // TODO: Replace with enum. | 1225 // TODO: Replace with enum. |
1226 typedef unsigned NopVariant; | 1226 typedef unsigned NopVariant; |
1227 | 1227 |
1228 static InstX8632Nop *create(Cfg *Func, NopVariant Variant) { | 1228 static InstX8632Nop *create(Cfg *Func, NopVariant Variant) { |
1229 return new (Func->allocate<InstX8632Nop>()) InstX8632Nop(Func, Variant); | 1229 return new (Func->allocate<InstX8632Nop>()) InstX8632Nop(Func, Variant); |
1230 } | 1230 } |
1231 virtual void emit(const Cfg *Func) const; | 1231 void emit(const Cfg *Func) const override; |
1232 virtual void emitIAS(const Cfg *Func) const; | 1232 void emitIAS(const Cfg *Func) const override; |
1233 virtual void dump(const Cfg *Func) const; | 1233 void dump(const Cfg *Func) const override; |
1234 static bool classof(const Inst *Inst) { return isClassof(Inst, Nop); } | 1234 static bool classof(const Inst *Inst) { return isClassof(Inst, Nop); } |
1235 | 1235 |
1236 private: | 1236 private: |
1237 InstX8632Nop(Cfg *Func, SizeT Length); | 1237 InstX8632Nop(Cfg *Func, SizeT Length); |
1238 InstX8632Nop(const InstX8632Nop &) LLVM_DELETED_FUNCTION; | 1238 InstX8632Nop(const InstX8632Nop &) LLVM_DELETED_FUNCTION; |
1239 InstX8632Nop &operator=(const InstX8632Nop &) LLVM_DELETED_FUNCTION; | 1239 InstX8632Nop &operator=(const InstX8632Nop &) LLVM_DELETED_FUNCTION; |
1240 virtual ~InstX8632Nop() {} | 1240 ~InstX8632Nop() override {} |
1241 | 1241 |
1242 NopVariant Variant; | 1242 NopVariant Variant; |
1243 }; | 1243 }; |
1244 | 1244 |
1245 // Fld - load a value onto the x87 FP stack. | 1245 // Fld - load a value onto the x87 FP stack. |
1246 class InstX8632Fld : public InstX8632 { | 1246 class InstX8632Fld : public InstX8632 { |
1247 public: | 1247 public: |
1248 static InstX8632Fld *create(Cfg *Func, Operand *Src) { | 1248 static InstX8632Fld *create(Cfg *Func, Operand *Src) { |
1249 return new (Func->allocate<InstX8632Fld>()) InstX8632Fld(Func, Src); | 1249 return new (Func->allocate<InstX8632Fld>()) InstX8632Fld(Func, Src); |
1250 } | 1250 } |
1251 virtual void emit(const Cfg *Func) const; | 1251 void emit(const Cfg *Func) const override; |
1252 virtual void dump(const Cfg *Func) const; | 1252 void dump(const Cfg *Func) const override; |
1253 static bool classof(const Inst *Inst) { return isClassof(Inst, Fld); } | 1253 static bool classof(const Inst *Inst) { return isClassof(Inst, Fld); } |
1254 | 1254 |
1255 private: | 1255 private: |
1256 InstX8632Fld(Cfg *Func, Operand *Src); | 1256 InstX8632Fld(Cfg *Func, Operand *Src); |
1257 InstX8632Fld(const InstX8632Fld &) LLVM_DELETED_FUNCTION; | 1257 InstX8632Fld(const InstX8632Fld &) LLVM_DELETED_FUNCTION; |
1258 InstX8632Fld &operator=(const InstX8632Fld &) LLVM_DELETED_FUNCTION; | 1258 InstX8632Fld &operator=(const InstX8632Fld &) LLVM_DELETED_FUNCTION; |
1259 virtual ~InstX8632Fld() {} | 1259 ~InstX8632Fld() override {} |
1260 }; | 1260 }; |
1261 | 1261 |
1262 // Fstp - store x87 st(0) into memory and pop st(0). | 1262 // Fstp - store x87 st(0) into memory and pop st(0). |
1263 class InstX8632Fstp : public InstX8632 { | 1263 class InstX8632Fstp : public InstX8632 { |
1264 public: | 1264 public: |
1265 static InstX8632Fstp *create(Cfg *Func, Variable *Dest) { | 1265 static InstX8632Fstp *create(Cfg *Func, Variable *Dest) { |
1266 return new (Func->allocate<InstX8632Fstp>()) InstX8632Fstp(Func, Dest); | 1266 return new (Func->allocate<InstX8632Fstp>()) InstX8632Fstp(Func, Dest); |
1267 } | 1267 } |
1268 virtual void emit(const Cfg *Func) const; | 1268 void emit(const Cfg *Func) const override; |
1269 virtual void dump(const Cfg *Func) const; | 1269 void dump(const Cfg *Func) const override; |
1270 static bool classof(const Inst *Inst) { return isClassof(Inst, Fstp); } | 1270 static bool classof(const Inst *Inst) { return isClassof(Inst, Fstp); } |
1271 | 1271 |
1272 private: | 1272 private: |
1273 InstX8632Fstp(Cfg *Func, Variable *Dest); | 1273 InstX8632Fstp(Cfg *Func, Variable *Dest); |
1274 InstX8632Fstp(const InstX8632Fstp &) LLVM_DELETED_FUNCTION; | 1274 InstX8632Fstp(const InstX8632Fstp &) LLVM_DELETED_FUNCTION; |
1275 InstX8632Fstp &operator=(const InstX8632Fstp &) LLVM_DELETED_FUNCTION; | 1275 InstX8632Fstp &operator=(const InstX8632Fstp &) LLVM_DELETED_FUNCTION; |
1276 virtual ~InstX8632Fstp() {} | 1276 ~InstX8632Fstp() override {} |
1277 }; | 1277 }; |
1278 | 1278 |
1279 class InstX8632Pop : public InstX8632 { | 1279 class InstX8632Pop : public InstX8632 { |
1280 public: | 1280 public: |
1281 static InstX8632Pop *create(Cfg *Func, Variable *Dest) { | 1281 static InstX8632Pop *create(Cfg *Func, Variable *Dest) { |
1282 return new (Func->allocate<InstX8632Pop>()) InstX8632Pop(Func, Dest); | 1282 return new (Func->allocate<InstX8632Pop>()) InstX8632Pop(Func, Dest); |
1283 } | 1283 } |
1284 virtual void emit(const Cfg *Func) const; | 1284 void emit(const Cfg *Func) const override; |
1285 virtual void emitIAS(const Cfg *Func) const; | 1285 void emitIAS(const Cfg *Func) const override; |
1286 virtual void dump(const Cfg *Func) const; | 1286 void dump(const Cfg *Func) const override; |
1287 static bool classof(const Inst *Inst) { return isClassof(Inst, Pop); } | 1287 static bool classof(const Inst *Inst) { return isClassof(Inst, Pop); } |
1288 | 1288 |
1289 private: | 1289 private: |
1290 InstX8632Pop(Cfg *Func, Variable *Dest); | 1290 InstX8632Pop(Cfg *Func, Variable *Dest); |
1291 InstX8632Pop(const InstX8632Pop &) LLVM_DELETED_FUNCTION; | 1291 InstX8632Pop(const InstX8632Pop &) LLVM_DELETED_FUNCTION; |
1292 InstX8632Pop &operator=(const InstX8632Pop &) LLVM_DELETED_FUNCTION; | 1292 InstX8632Pop &operator=(const InstX8632Pop &) LLVM_DELETED_FUNCTION; |
1293 virtual ~InstX8632Pop() {} | 1293 ~InstX8632Pop() override {} |
1294 }; | 1294 }; |
1295 | 1295 |
1296 class InstX8632Push : public InstX8632 { | 1296 class InstX8632Push : public InstX8632 { |
1297 public: | 1297 public: |
1298 static InstX8632Push *create(Cfg *Func, Operand *Source, | 1298 static InstX8632Push *create(Cfg *Func, Operand *Source, |
1299 bool SuppressStackAdjustment) { | 1299 bool SuppressStackAdjustment) { |
1300 return new (Func->allocate<InstX8632Push>()) | 1300 return new (Func->allocate<InstX8632Push>()) |
1301 InstX8632Push(Func, Source, SuppressStackAdjustment); | 1301 InstX8632Push(Func, Source, SuppressStackAdjustment); |
1302 } | 1302 } |
1303 virtual void emit(const Cfg *Func) const; | 1303 void emit(const Cfg *Func) const override; |
1304 virtual void dump(const Cfg *Func) const; | 1304 void dump(const Cfg *Func) const override; |
1305 static bool classof(const Inst *Inst) { return isClassof(Inst, Push); } | 1305 static bool classof(const Inst *Inst) { return isClassof(Inst, Push); } |
1306 | 1306 |
1307 private: | 1307 private: |
1308 InstX8632Push(Cfg *Func, Operand *Source, bool SuppressStackAdjustment); | 1308 InstX8632Push(Cfg *Func, Operand *Source, bool SuppressStackAdjustment); |
1309 InstX8632Push(const InstX8632Push &) LLVM_DELETED_FUNCTION; | 1309 InstX8632Push(const InstX8632Push &) LLVM_DELETED_FUNCTION; |
1310 InstX8632Push &operator=(const InstX8632Push &) LLVM_DELETED_FUNCTION; | 1310 InstX8632Push &operator=(const InstX8632Push &) LLVM_DELETED_FUNCTION; |
1311 bool SuppressStackAdjustment; | 1311 bool SuppressStackAdjustment; |
1312 virtual ~InstX8632Push() {} | 1312 ~InstX8632Push() override {} |
1313 }; | 1313 }; |
1314 | 1314 |
1315 // Ret instruction. Currently only supports the "ret" version that | 1315 // Ret instruction. Currently only supports the "ret" version that |
1316 // does not pop arguments. This instruction takes a Source operand | 1316 // does not pop arguments. This instruction takes a Source operand |
1317 // (for non-void returning functions) for liveness analysis, though | 1317 // (for non-void returning functions) for liveness analysis, though |
1318 // a FakeUse before the ret would do just as well. | 1318 // a FakeUse before the ret would do just as well. |
1319 class InstX8632Ret : public InstX8632 { | 1319 class InstX8632Ret : public InstX8632 { |
1320 public: | 1320 public: |
1321 static InstX8632Ret *create(Cfg *Func, Variable *Source = NULL) { | 1321 static InstX8632Ret *create(Cfg *Func, Variable *Source = NULL) { |
1322 return new (Func->allocate<InstX8632Ret>()) InstX8632Ret(Func, Source); | 1322 return new (Func->allocate<InstX8632Ret>()) InstX8632Ret(Func, Source); |
1323 } | 1323 } |
1324 virtual void emit(const Cfg *Func) const; | 1324 void emit(const Cfg *Func) const override; |
1325 virtual void emitIAS(const Cfg *Func) const; | 1325 void emitIAS(const Cfg *Func) const override; |
1326 virtual void dump(const Cfg *Func) const; | 1326 void dump(const Cfg *Func) const override; |
1327 static bool classof(const Inst *Inst) { return isClassof(Inst, Ret); } | 1327 static bool classof(const Inst *Inst) { return isClassof(Inst, Ret); } |
1328 | 1328 |
1329 private: | 1329 private: |
1330 InstX8632Ret(Cfg *Func, Variable *Source); | 1330 InstX8632Ret(Cfg *Func, Variable *Source); |
1331 InstX8632Ret(const InstX8632Ret &) LLVM_DELETED_FUNCTION; | 1331 InstX8632Ret(const InstX8632Ret &) LLVM_DELETED_FUNCTION; |
1332 InstX8632Ret &operator=(const InstX8632Ret &) LLVM_DELETED_FUNCTION; | 1332 InstX8632Ret &operator=(const InstX8632Ret &) LLVM_DELETED_FUNCTION; |
1333 virtual ~InstX8632Ret() {} | 1333 ~InstX8632Ret() override {} |
1334 }; | 1334 }; |
1335 | 1335 |
1336 // Exchanging Add instruction. Exchanges the first operand (destination | 1336 // Exchanging Add instruction. Exchanges the first operand (destination |
1337 // operand) with the second operand (source operand), then loads the sum | 1337 // operand) with the second operand (source operand), then loads the sum |
1338 // of the two values into the destination operand. The destination may be | 1338 // of the two values into the destination operand. The destination may be |
1339 // a register or memory, while the source must be a register. | 1339 // a register or memory, while the source must be a register. |
1340 // | 1340 // |
1341 // Both the dest and source are updated. The caller should then insert a | 1341 // Both the dest and source are updated. The caller should then insert a |
1342 // FakeDef to reflect the second udpate. | 1342 // FakeDef to reflect the second udpate. |
1343 class InstX8632Xadd : public InstX8632Lockable { | 1343 class InstX8632Xadd : public InstX8632Lockable { |
1344 public: | 1344 public: |
1345 static InstX8632Xadd *create(Cfg *Func, Operand *Dest, Variable *Source, | 1345 static InstX8632Xadd *create(Cfg *Func, Operand *Dest, Variable *Source, |
1346 bool Locked) { | 1346 bool Locked) { |
1347 return new (Func->allocate<InstX8632Xadd>()) | 1347 return new (Func->allocate<InstX8632Xadd>()) |
1348 InstX8632Xadd(Func, Dest, Source, Locked); | 1348 InstX8632Xadd(Func, Dest, Source, Locked); |
1349 } | 1349 } |
1350 virtual void emit(const Cfg *Func) const; | 1350 void emit(const Cfg *Func) const override; |
1351 virtual void emitIAS(const Cfg *Func) const; | 1351 void emitIAS(const Cfg *Func) const override; |
1352 virtual void dump(const Cfg *Func) const; | 1352 void dump(const Cfg *Func) const override; |
1353 static bool classof(const Inst *Inst) { return isClassof(Inst, Xadd); } | 1353 static bool classof(const Inst *Inst) { return isClassof(Inst, Xadd); } |
1354 | 1354 |
1355 private: | 1355 private: |
1356 InstX8632Xadd(Cfg *Func, Operand *Dest, Variable *Source, bool Locked); | 1356 InstX8632Xadd(Cfg *Func, Operand *Dest, Variable *Source, bool Locked); |
1357 InstX8632Xadd(const InstX8632Xadd &) LLVM_DELETED_FUNCTION; | 1357 InstX8632Xadd(const InstX8632Xadd &) LLVM_DELETED_FUNCTION; |
1358 InstX8632Xadd &operator=(const InstX8632Xadd &) LLVM_DELETED_FUNCTION; | 1358 InstX8632Xadd &operator=(const InstX8632Xadd &) LLVM_DELETED_FUNCTION; |
1359 virtual ~InstX8632Xadd() {} | 1359 ~InstX8632Xadd() override {} |
1360 }; | 1360 }; |
1361 | 1361 |
1362 // Exchange instruction. Exchanges the first operand (destination | 1362 // Exchange instruction. Exchanges the first operand (destination |
1363 // operand) with the second operand (source operand). At least one of | 1363 // operand) with the second operand (source operand). At least one of |
1364 // the operands must be a register (and the other can be reg or mem). | 1364 // the operands must be a register (and the other can be reg or mem). |
1365 // Both the Dest and Source are updated. If there is a memory operand, | 1365 // Both the Dest and Source are updated. If there is a memory operand, |
1366 // then the instruction is automatically "locked" without the need for | 1366 // then the instruction is automatically "locked" without the need for |
1367 // a lock prefix. | 1367 // a lock prefix. |
1368 class InstX8632Xchg : public InstX8632 { | 1368 class InstX8632Xchg : public InstX8632 { |
1369 public: | 1369 public: |
1370 static InstX8632Xchg *create(Cfg *Func, Operand *Dest, Variable *Source) { | 1370 static InstX8632Xchg *create(Cfg *Func, Operand *Dest, Variable *Source) { |
1371 return new (Func->allocate<InstX8632Xchg>()) | 1371 return new (Func->allocate<InstX8632Xchg>()) |
1372 InstX8632Xchg(Func, Dest, Source); | 1372 InstX8632Xchg(Func, Dest, Source); |
1373 } | 1373 } |
1374 virtual void emit(const Cfg *Func) const; | 1374 void emit(const Cfg *Func) const override; |
1375 virtual void emitIAS(const Cfg *Func) const; | 1375 void emitIAS(const Cfg *Func) const override; |
1376 virtual void dump(const Cfg *Func) const; | 1376 void dump(const Cfg *Func) const override; |
1377 static bool classof(const Inst *Inst) { return isClassof(Inst, Xchg); } | 1377 static bool classof(const Inst *Inst) { return isClassof(Inst, Xchg); } |
1378 | 1378 |
1379 private: | 1379 private: |
1380 InstX8632Xchg(Cfg *Func, Operand *Dest, Variable *Source); | 1380 InstX8632Xchg(Cfg *Func, Operand *Dest, Variable *Source); |
1381 InstX8632Xchg(const InstX8632Xchg &) LLVM_DELETED_FUNCTION; | 1381 InstX8632Xchg(const InstX8632Xchg &) LLVM_DELETED_FUNCTION; |
1382 InstX8632Xchg &operator=(const InstX8632Xchg &) LLVM_DELETED_FUNCTION; | 1382 InstX8632Xchg &operator=(const InstX8632Xchg &) LLVM_DELETED_FUNCTION; |
1383 virtual ~InstX8632Xchg() {} | 1383 ~InstX8632Xchg() override {} |
1384 }; | 1384 }; |
1385 | 1385 |
1386 // Declare partial template specializations of emit() methods that | 1386 // Declare partial template specializations of emit() methods that |
1387 // already have default implementations. Without this, there is the | 1387 // already have default implementations. Without this, there is the |
1388 // possibility of ODR violations and link errors. | 1388 // possibility of ODR violations and link errors. |
1389 template <> void InstX8632Addss::emit(const Cfg *Func) const; | 1389 template <> void InstX8632Addss::emit(const Cfg *Func) const; |
1390 template <> void InstX8632Blendvps::emit(const Cfg *Func) const; | 1390 template <> void InstX8632Blendvps::emit(const Cfg *Func) const; |
1391 template <> void InstX8632Cbwdq::emit(const Cfg *Func) const; | 1391 template <> void InstX8632Cbwdq::emit(const Cfg *Func) const; |
1392 template <> void InstX8632Div::emit(const Cfg *Func) const; | 1392 template <> void InstX8632Div::emit(const Cfg *Func) const; |
1393 template <> void InstX8632Divss::emit(const Cfg *Func) const; | 1393 template <> void InstX8632Divss::emit(const Cfg *Func) const; |
(...skipping 14 matching lines...) Expand all Loading... |
1408 template <> void InstX8632Psub::emit(const Cfg *Func) const; | 1408 template <> void InstX8632Psub::emit(const Cfg *Func) const; |
1409 template <> void InstX8632Sqrtss::emit(const Cfg *Func) const; | 1409 template <> void InstX8632Sqrtss::emit(const Cfg *Func) const; |
1410 template <> void InstX8632Subss::emit(const Cfg *Func) const; | 1410 template <> void InstX8632Subss::emit(const Cfg *Func) const; |
1411 | 1411 |
1412 template <> void InstX8632Cbwdq::emitIAS(const Cfg *Func) const; | 1412 template <> void InstX8632Cbwdq::emitIAS(const Cfg *Func) const; |
1413 template <> void InstX8632Movd::emitIAS(const Cfg *Func) const; | 1413 template <> void InstX8632Movd::emitIAS(const Cfg *Func) const; |
1414 | 1414 |
1415 } // end of namespace Ice | 1415 } // end of namespace Ice |
1416 | 1416 |
1417 #endif // SUBZERO_SRC_ICEINSTX8632_H | 1417 #endif // SUBZERO_SRC_ICEINSTX8632_H |
OLD | NEW |