Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1063)

Side by Side Diff: src/IceInstX8632.h

Issue 265703002: Add Om1 lowering with no optimizations (Closed) Base URL: https://gerrit.chromium.org/gerrit/p/native_client/pnacl-subzero.git@master
Patch Set: Merge changed from Karl's committed CL Created 6 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/IceInst.def ('k') | src/IceInstX8632.cpp » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 //===- subzero/src/IceInstX8632.h - Low-level x86 instructions --*- C++ -*-===//
2 //
3 // The Subzero Code Generator
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // This file declares the InstX8632 and OperandX8632 classes and
11 // their subclasses. This represents the machine instructions and
12 // operands used for x86-32 code selection.
13 //
14 //===----------------------------------------------------------------------===//
15
16 #ifndef SUBZERO_SRC_ICEINSTX8632_H
17 #define SUBZERO_SRC_ICEINSTX8632_H
18
19 #include "IceDefs.h"
20 #include "IceInst.h"
21 #include "IceInstX8632.def"
22 #include "IceOperand.h"
23
24 namespace Ice {
25
26 class TargetX8632;
27
28 // OperandX8632 extends the Operand hierarchy. Its subclasses are
29 // OperandX8632Mem and VariableSplit.
30 class OperandX8632 : public Operand {
31 public:
32 enum OperandKindX8632 {
33 k__Start = Operand::kTarget,
34 kMem,
35 kSplit
36 };
37 virtual void emit(const Cfg *Func) const = 0;
38 void dump(const Cfg *Func) const;
39
40 protected:
41 OperandX8632(OperandKindX8632 Kind, Type Ty)
42 : Operand(static_cast<OperandKind>(Kind), Ty) {}
43 virtual ~OperandX8632() {}
44
45 private:
46 OperandX8632(const OperandX8632 &) LLVM_DELETED_FUNCTION;
47 OperandX8632 &operator=(const OperandX8632 &) LLVM_DELETED_FUNCTION;
48 };
49
50 // OperandX8632Mem represents the m32 addressing mode, with optional
51 // base and index registers, a constant offset, and a fixed shift
52 // value for the index register.
53 class OperandX8632Mem : public OperandX8632 {
54 public:
55 static OperandX8632Mem *create(Cfg *Func, Type Ty, Variable *Base,
56 Constant *Offset, Variable *Index = NULL,
57 uint32_t Shift = 0) {
58 return new (Func->allocate<OperandX8632Mem>())
59 OperandX8632Mem(Func, Ty, Base, Offset, Index, Shift);
60 }
61 Variable *getBase() const { return Base; }
62 Constant *getOffset() const { return Offset; }
63 Variable *getIndex() const { return Index; }
64 uint32_t getShift() const { return Shift; }
65 virtual void emit(const Cfg *Func) const;
66 virtual void dump(const Cfg *Func) const;
67
68 static bool classof(const Operand *Operand) {
69 return Operand->getKind() == static_cast<OperandKind>(kMem);
70 }
71
72 private:
73 OperandX8632Mem(Cfg *Func, Type Ty, Variable *Base, Constant *Offset,
74 Variable *Index, uint32_t Shift);
75 OperandX8632Mem(const OperandX8632Mem &) LLVM_DELETED_FUNCTION;
76 OperandX8632Mem &operator=(const OperandX8632Mem &) LLVM_DELETED_FUNCTION;
77 virtual ~OperandX8632Mem() {}
78 Variable *Base;
79 Constant *Offset;
80 Variable *Index;
81 uint32_t Shift;
82 };
83
84 // VariableSplit is a way to treat an f64 memory location as a pair
85 // of i32 locations (Low and High). This is needed for some cases
86 // of the Bitcast instruction. Since it's not possible for integer
87 // registers to access the XMM registers and vice versa, the
88 // lowering forces the f64 to be spilled to the stack and then
89 // accesses through the VariableSplit.
90 class VariableSplit : public OperandX8632 {
91 public:
92 enum Portion {
93 Low,
94 High
95 };
96 static VariableSplit *create(Cfg *Func, Variable *Var, Portion Part) {
97 return new (Func->allocate<VariableSplit>()) VariableSplit(Func, Var, Part);
98 }
99 virtual void emit(const Cfg *Func) const;
100 virtual void dump(const Cfg *Func) const;
101
102 static bool classof(const Operand *Operand) {
103 return Operand->getKind() == static_cast<OperandKind>(kSplit);
104 }
105
106 private:
107 VariableSplit(Cfg *Func, Variable *Var, Portion Part)
108 : OperandX8632(kSplit, IceType_i32), Func(Func), Var(Var), Part(Part) {
109 assert(Var->getType() == IceType_f64);
110 Vars = Func->allocateArrayOf<Variable *>(1);
111 Vars[0] = Var;
112 NumVars = 1;
113 }
114 VariableSplit(const VariableSplit &) LLVM_DELETED_FUNCTION;
115 VariableSplit &operator=(const VariableSplit &) LLVM_DELETED_FUNCTION;
116 virtual ~VariableSplit() { Func->deallocateArrayOf<Variable *>(Vars); }
117 Cfg *Func; // Held only for the destructor.
118 Variable *Var;
119 Portion Part;
120 };
121
122 class InstX8632 : public InstTarget {
123 public:
124 enum InstKindX8632 {
125 k__Start = Inst::Target,
126 Adc,
127 Add,
128 Addss,
129 And,
130 Br,
131 Call,
132 Cdq,
133 Cvt,
134 Div,
135 Divss,
136 Fld,
137 Fstp,
138 Icmp,
139 Idiv,
140 Imul,
141 Label,
142 Load,
143 Mov,
144 Movsx,
145 Movzx,
146 Mul,
147 Mulss,
148 Or,
149 Pop,
150 Push,
151 Ret,
152 Sar,
153 Sbb,
154 Shl,
155 Shld,
156 Shr,
157 Shrd,
158 Store,
159 Sub,
160 Subss,
161 Test,
162 Ucomiss,
163 Xor
164 };
165 static const char *getWidthString(Type Ty);
166 virtual void emit(const Cfg *Func) const = 0;
167 virtual void dump(const Cfg *Func) const;
168
169 protected:
170 InstX8632(Cfg *Func, InstKindX8632 Kind, SizeT Maxsrcs, Variable *Dest)
171 : InstTarget(Func, static_cast<InstKind>(Kind), Maxsrcs, Dest) {}
172 virtual ~InstX8632() {}
173 static bool isClassof(const Inst *Inst, InstKindX8632 MyKind) {
174 return Inst->getKind() == static_cast<InstKind>(MyKind);
175 }
176
177 private:
178 InstX8632(const InstX8632 &) LLVM_DELETED_FUNCTION;
179 InstX8632 &operator=(const InstX8632 &) LLVM_DELETED_FUNCTION;
180 };
181
182 // InstX8632Label represents an intra-block label that is the
183 // target of an intra-block branch. These are used for lowering i1
184 // calculations, Select instructions, and 64-bit compares on a 32-bit
185 // architecture, without basic block splitting. Basic block splitting
186 // is not so desirable for several reasons, one of which is the impact
187 // on decisions based on whether a variable's live range spans
188 // multiple basic blocks.
189 //
190 // Intra-block control flow must be used with caution. Consider the
191 // sequence for "c = (a >= b ? x : y)".
192 // cmp a, b
193 // br lt, L1
194 // mov c, x
195 // jmp L2
196 // L1:
197 // mov c, y
198 // L2:
199 //
200 // Labels L1 and L2 are intra-block labels. Without knowledge of the
201 // intra-block control flow, liveness analysis will determine the "mov
202 // c, x" instruction to be dead. One way to prevent this is to insert
203 // a "FakeUse(c)" instruction anywhere between the two "mov c, ..."
204 // instructions, e.g.:
205 //
206 // cmp a, b
207 // br lt, L1
208 // mov c, x
209 // jmp L2
210 // FakeUse(c)
211 // L1:
212 // mov c, y
213 // L2:
214 //
215 // The down-side is that "mov c, x" can never be dead-code eliminated
216 // even if there are no uses of c. As unlikely as this situation is,
217 // it may be prevented by running dead code elimination before
218 // lowering.
219 class InstX8632Label : public InstX8632 {
220 public:
221 static InstX8632Label *create(Cfg *Func, TargetX8632 *Target) {
222 return new (Func->allocate<InstX8632Label>()) InstX8632Label(Func, Target);
223 }
224 IceString getName(const Cfg *Func) const;
225 virtual void emit(const Cfg *Func) const;
226 virtual void dump(const Cfg *Func) const;
227
228 private:
229 InstX8632Label(Cfg *Func, TargetX8632 *Target);
230 InstX8632Label(const InstX8632Label &) LLVM_DELETED_FUNCTION;
231 InstX8632Label &operator=(const InstX8632Label &) LLVM_DELETED_FUNCTION;
232 virtual ~InstX8632Label() {}
233 SizeT Number; // used only for unique label string generation
234 };
235
236 // Conditional and unconditional branch instruction.
237 class InstX8632Br : public InstX8632 {
238 public:
239 enum BrCond {
240 #define X(tag, dump, emit) tag,
241 ICEINSTX8632BR_TABLE
242 #undef X
243 Br_None
244 };
245
246 // Create a conditional branch to a node.
247 static InstX8632Br *create(Cfg *Func, CfgNode *TargetTrue,
248 CfgNode *TargetFalse, BrCond Condition) {
249 return new (Func->allocate<InstX8632Br>())
250 InstX8632Br(Func, TargetTrue, TargetFalse, NULL, Condition);
251 }
252 // Create an unconditional branch to a node.
253 static InstX8632Br *create(Cfg *Func, CfgNode *Target) {
254 return new (Func->allocate<InstX8632Br>())
255 InstX8632Br(Func, NULL, Target, NULL, Br_None);
256 }
257 // Create a non-terminator conditional branch to a node, with a
258 // fallthrough to the next instruction in the current node. This is
259 // used for switch lowering.
260 static InstX8632Br *create(Cfg *Func, CfgNode *Target, BrCond Condition) {
261 return new (Func->allocate<InstX8632Br>())
262 InstX8632Br(Func, Target, NULL, NULL, Condition);
263 }
264 // Create a conditional intra-block branch (or unconditional, if
265 // Condition==None) to a label in the current block.
266 static InstX8632Br *create(Cfg *Func, InstX8632Label *Label,
267 BrCond Condition) {
268 return new (Func->allocate<InstX8632Br>())
269 InstX8632Br(Func, NULL, NULL, Label, Condition);
270 }
271 CfgNode *getTargetTrue() const { return TargetTrue; }
272 CfgNode *getTargetFalse() const { return TargetFalse; }
273 virtual void emit(const Cfg *Func) const;
274 virtual void dump(const Cfg *Func) const;
275 static bool classof(const Inst *Inst) { return isClassof(Inst, Br); }
276
277 private:
278 InstX8632Br(Cfg *Func, CfgNode *TargetTrue, CfgNode *TargetFalse,
279 InstX8632Label *Label, BrCond Condition);
280 InstX8632Br(const InstX8632Br &) LLVM_DELETED_FUNCTION;
281 InstX8632Br &operator=(const InstX8632Br &) LLVM_DELETED_FUNCTION;
282 virtual ~InstX8632Br() {}
283 BrCond Condition;
284 CfgNode *TargetTrue;
285 CfgNode *TargetFalse;
286 InstX8632Label *Label; // Intra-block branch target
287 };
288
289 // Call instruction. Arguments should have already been pushed.
290 class InstX8632Call : public InstX8632 {
291 public:
292 static InstX8632Call *create(Cfg *Func, Variable *Dest, Operand *CallTarget) {
293 return new (Func->allocate<InstX8632Call>())
294 InstX8632Call(Func, Dest, CallTarget);
295 }
296 Operand *getCallTarget() const { return getSrc(0); }
297 virtual void emit(const Cfg *Func) const;
298 virtual void dump(const Cfg *Func) const;
299 static bool classof(const Inst *Inst) { return isClassof(Inst, Call); }
300
301 private:
302 InstX8632Call(Cfg *Func, Variable *Dest, Operand *CallTarget);
303 InstX8632Call(const InstX8632Call &) LLVM_DELETED_FUNCTION;
304 InstX8632Call &operator=(const InstX8632Call &) LLVM_DELETED_FUNCTION;
305 virtual ~InstX8632Call() {}
306 };
307
308 // See the definition of emitTwoAddress() for a description of
309 // ShiftHack.
310 void emitTwoAddress(const char *Opcode, const Inst *Inst, const Cfg *Func,
311 bool ShiftHack = false);
312
313 template <InstX8632::InstKindX8632 K, bool ShiftHack = false>
314 class InstX8632Binop : public InstX8632 {
315 public:
316 // Create an ordinary binary-op instruction like add or sub.
317 static InstX8632Binop *create(Cfg *Func, Variable *Dest, Operand *Source) {
318 return new (Func->allocate<InstX8632Binop>())
319 InstX8632Binop(Func, Dest, Source);
320 }
321 virtual void emit(const Cfg *Func) const {
322 emitTwoAddress(Opcode, this, Func, ShiftHack);
323 }
324 virtual void dump(const Cfg *Func) const {
325 Ostream &Str = Func->getContext()->getStrDump();
326 dumpDest(Func);
327 Str << " = " << Opcode << "." << getDest()->getType() << " ";
328 dumpSources(Func);
329 }
330 static bool classof(const Inst *Inst) { return isClassof(Inst, K); }
331
332 private:
333 InstX8632Binop(Cfg *Func, Variable *Dest, Operand *Source)
334 : InstX8632(Func, K, 2, Dest) {
335 addSource(Dest);
336 addSource(Source);
337 }
338 InstX8632Binop(const InstX8632Binop &) LLVM_DELETED_FUNCTION;
339 InstX8632Binop &operator=(const InstX8632Binop &) LLVM_DELETED_FUNCTION;
340 virtual ~InstX8632Binop() {}
341 static const char *Opcode;
342 };
343
344 template <InstX8632::InstKindX8632 K> class InstX8632Ternop : public InstX8632 {
345 public:
346 // Create a ternary-op instruction like div or idiv.
347 static InstX8632Ternop *create(Cfg *Func, Variable *Dest, Operand *Source1,
348 Operand *Source2) {
349 return new (Func->allocate<InstX8632Ternop>())
350 InstX8632Ternop(Func, Dest, Source1, Source2);
351 }
352 virtual void emit(const Cfg *Func) const {
353 Ostream &Str = Func->getContext()->getStrEmit();
354 assert(getSrcSize() == 3);
355 Str << "\t" << Opcode << "\t";
356 getSrc(1)->emit(Func);
357 Str << "\n";
358 }
359 virtual void dump(const Cfg *Func) const {
360 Ostream &Str = Func->getContext()->getStrDump();
361 dumpDest(Func);
362 Str << " = " << Opcode << "." << getDest()->getType() << " ";
363 dumpSources(Func);
364 }
365 static bool classof(const Inst *Inst) { return isClassof(Inst, K); }
366
367 private:
368 InstX8632Ternop(Cfg *Func, Variable *Dest, Operand *Source1, Operand *Source2)
369 : InstX8632(Func, K, 3, Dest) {
370 addSource(Dest);
371 addSource(Source1);
372 addSource(Source2);
373 }
374 InstX8632Ternop(const InstX8632Ternop &) LLVM_DELETED_FUNCTION;
375 InstX8632Ternop &operator=(const InstX8632Ternop &) LLVM_DELETED_FUNCTION;
376 virtual ~InstX8632Ternop() {}
377 static const char *Opcode;
378 };
379
380 typedef InstX8632Binop<InstX8632::Add> InstX8632Add;
381 typedef InstX8632Binop<InstX8632::Adc> InstX8632Adc;
382 typedef InstX8632Binop<InstX8632::Addss> InstX8632Addss;
383 typedef InstX8632Binop<InstX8632::Sub> InstX8632Sub;
384 typedef InstX8632Binop<InstX8632::Subss> InstX8632Subss;
385 typedef InstX8632Binop<InstX8632::Sbb> InstX8632Sbb;
386 typedef InstX8632Binop<InstX8632::And> InstX8632And;
387 typedef InstX8632Binop<InstX8632::Or> InstX8632Or;
388 typedef InstX8632Binop<InstX8632::Xor> InstX8632Xor;
389 typedef InstX8632Binop<InstX8632::Imul> InstX8632Imul;
390 typedef InstX8632Binop<InstX8632::Mulss> InstX8632Mulss;
391 typedef InstX8632Binop<InstX8632::Divss> InstX8632Divss;
392 typedef InstX8632Binop<InstX8632::Shl, true> InstX8632Shl;
393 typedef InstX8632Binop<InstX8632::Shr, true> InstX8632Shr;
394 typedef InstX8632Binop<InstX8632::Sar, true> InstX8632Sar;
395 typedef InstX8632Ternop<InstX8632::Idiv> InstX8632Idiv;
396 typedef InstX8632Ternop<InstX8632::Div> InstX8632Div;
397
398 // Mul instruction - unsigned multiply.
399 class InstX8632Mul : public InstX8632 {
400 public:
401 static InstX8632Mul *create(Cfg *Func, Variable *Dest, Variable *Source1,
402 Operand *Source2) {
403 return new (Func->allocate<InstX8632Mul>())
404 InstX8632Mul(Func, Dest, Source1, Source2);
405 }
406 virtual void emit(const Cfg *Func) const;
407 virtual void dump(const Cfg *Func) const;
408 static bool classof(const Inst *Inst) { return isClassof(Inst, Mul); }
409
410 private:
411 InstX8632Mul(Cfg *Func, Variable *Dest, Variable *Source1, Operand *Source2);
412 InstX8632Mul(const InstX8632Mul &) LLVM_DELETED_FUNCTION;
413 InstX8632Mul &operator=(const InstX8632Mul &) LLVM_DELETED_FUNCTION;
414 virtual ~InstX8632Mul() {}
415 };
416
417 // Shld instruction - shift across a pair of operands. TODO: Verify
418 // that the validator accepts the shld instruction.
419 class InstX8632Shld : public InstX8632 {
420 public:
421 static InstX8632Shld *create(Cfg *Func, Variable *Dest, Variable *Source1,
422 Variable *Source2) {
423 return new (Func->allocate<InstX8632Shld>())
424 InstX8632Shld(Func, Dest, Source1, Source2);
425 }
426 virtual void emit(const Cfg *Func) const;
427 virtual void dump(const Cfg *Func) const;
428 static bool classof(const Inst *Inst) { return isClassof(Inst, Shld); }
429
430 private:
431 InstX8632Shld(Cfg *Func, Variable *Dest, Variable *Source1,
432 Variable *Source2);
433 InstX8632Shld(const InstX8632Shld &) LLVM_DELETED_FUNCTION;
434 InstX8632Shld &operator=(const InstX8632Shld &) LLVM_DELETED_FUNCTION;
435 virtual ~InstX8632Shld() {}
436 };
437
438 // Shrd instruction - shift across a pair of operands. TODO: Verify
439 // that the validator accepts the shrd instruction.
440 class InstX8632Shrd : public InstX8632 {
441 public:
442 static InstX8632Shrd *create(Cfg *Func, Variable *Dest, Variable *Source1,
443 Variable *Source2) {
444 return new (Func->allocate<InstX8632Shrd>())
445 InstX8632Shrd(Func, Dest, Source1, Source2);
446 }
447 virtual void emit(const Cfg *Func) const;
448 virtual void dump(const Cfg *Func) const;
449 static bool classof(const Inst *Inst) { return isClassof(Inst, Shrd); }
450
451 private:
452 InstX8632Shrd(Cfg *Func, Variable *Dest, Variable *Source1,
453 Variable *Source2);
454 InstX8632Shrd(const InstX8632Shrd &) LLVM_DELETED_FUNCTION;
455 InstX8632Shrd &operator=(const InstX8632Shrd &) LLVM_DELETED_FUNCTION;
456 virtual ~InstX8632Shrd() {}
457 };
458
459 // Cdq instruction - sign-extend eax into edx
460 class InstX8632Cdq : public InstX8632 {
461 public:
462 static InstX8632Cdq *create(Cfg *Func, Variable *Dest, Operand *Source) {
463 return new (Func->allocate<InstX8632Cdq>())
464 InstX8632Cdq(Func, Dest, Source);
465 }
466 virtual void emit(const Cfg *Func) const;
467 virtual void dump(const Cfg *Func) const;
468 static bool classof(const Inst *Inst) { return isClassof(Inst, Cdq); }
469
470 private:
471 InstX8632Cdq(Cfg *Func, Variable *Dest, Operand *Source);
472 InstX8632Cdq(const InstX8632Cdq &) LLVM_DELETED_FUNCTION;
473 InstX8632Cdq &operator=(const InstX8632Cdq &) LLVM_DELETED_FUNCTION;
474 virtual ~InstX8632Cdq() {}
475 };
476
477 // Cvt instruction - wrapper for cvtsX2sY where X and Y are in {s,d,i}
478 // as appropriate. s=float, d=double, i=int. X and Y are determined
479 // from dest/src types. Sign and zero extension on the integer
480 // operand needs to be done separately.
481 class InstX8632Cvt : public InstX8632 {
482 public:
483 static InstX8632Cvt *create(Cfg *Func, Variable *Dest, Operand *Source) {
484 return new (Func->allocate<InstX8632Cvt>())
485 InstX8632Cvt(Func, Dest, Source);
486 }
487 virtual void emit(const Cfg *Func) const;
488 virtual void dump(const Cfg *Func) const;
489 static bool classof(const Inst *Inst) { return isClassof(Inst, Cvt); }
490
491 private:
492 InstX8632Cvt(Cfg *Func, Variable *Dest, Operand *Source);
493 InstX8632Cvt(const InstX8632Cvt &) LLVM_DELETED_FUNCTION;
494 InstX8632Cvt &operator=(const InstX8632Cvt &) LLVM_DELETED_FUNCTION;
495 virtual ~InstX8632Cvt() {}
496 };
497
498 // cmp - Integer compare instruction.
499 class InstX8632Icmp : public InstX8632 {
500 public:
501 static InstX8632Icmp *create(Cfg *Func, Operand *Src1, Operand *Src2) {
502 return new (Func->allocate<InstX8632Icmp>())
503 InstX8632Icmp(Func, Src1, Src2);
504 }
505 virtual void emit(const Cfg *Func) const;
506 virtual void dump(const Cfg *Func) const;
507 static bool classof(const Inst *Inst) { return isClassof(Inst, Icmp); }
508
509 private:
510 InstX8632Icmp(Cfg *Func, Operand *Src1, Operand *Src2);
511 InstX8632Icmp(const InstX8632Icmp &) LLVM_DELETED_FUNCTION;
512 InstX8632Icmp &operator=(const InstX8632Icmp &) LLVM_DELETED_FUNCTION;
513 virtual ~InstX8632Icmp() {}
514 };
515
516 // ucomiss/ucomisd - floating-point compare instruction.
517 class InstX8632Ucomiss : public InstX8632 {
518 public:
519 static InstX8632Ucomiss *create(Cfg *Func, Operand *Src1, Operand *Src2) {
520 return new (Func->allocate<InstX8632Ucomiss>())
521 InstX8632Ucomiss(Func, Src1, Src2);
522 }
523 virtual void emit(const Cfg *Func) const;
524 virtual void dump(const Cfg *Func) const;
525 static bool classof(const Inst *Inst) { return isClassof(Inst, Ucomiss); }
526
527 private:
528 InstX8632Ucomiss(Cfg *Func, Operand *Src1, Operand *Src2);
529 InstX8632Ucomiss(const InstX8632Ucomiss &) LLVM_DELETED_FUNCTION;
530 InstX8632Ucomiss &operator=(const InstX8632Ucomiss &) LLVM_DELETED_FUNCTION;
531 virtual ~InstX8632Ucomiss() {}
532 };
533
534 // Test instruction.
535 class InstX8632Test : public InstX8632 {
536 public:
537 static InstX8632Test *create(Cfg *Func, Operand *Source1, Operand *Source2) {
538 return new (Func->allocate<InstX8632Test>())
539 InstX8632Test(Func, Source1, Source2);
540 }
541 virtual void emit(const Cfg *Func) const;
542 virtual void dump(const Cfg *Func) const;
543 static bool classof(const Inst *Inst) { return isClassof(Inst, Test); }
544
545 private:
546 InstX8632Test(Cfg *Func, Operand *Source1, Operand *Source2);
547 InstX8632Test(const InstX8632Test &) LLVM_DELETED_FUNCTION;
548 InstX8632Test &operator=(const InstX8632Test &) LLVM_DELETED_FUNCTION;
549 virtual ~InstX8632Test() {}
550 };
551
552 // This is essentially a "mov" instruction with an OperandX8632Mem
553 // operand instead of Variable as the destination. It's important
554 // for liveness that there is no Dest operand.
555 class InstX8632Store : public InstX8632 {
556 public:
557 static InstX8632Store *create(Cfg *Func, Operand *Value, OperandX8632 *Mem) {
558 return new (Func->allocate<InstX8632Store>())
559 InstX8632Store(Func, Value, Mem);
560 }
561 virtual void emit(const Cfg *Func) const;
562 virtual void dump(const Cfg *Func) const;
563 static bool classof(const Inst *Inst) { return isClassof(Inst, Store); }
564
565 private:
566 InstX8632Store(Cfg *Func, Operand *Value, OperandX8632 *Mem);
567 InstX8632Store(const InstX8632Store &) LLVM_DELETED_FUNCTION;
568 InstX8632Store &operator=(const InstX8632Store &) LLVM_DELETED_FUNCTION;
569 virtual ~InstX8632Store() {}
570 };
571
572 // Move/assignment instruction - wrapper for mov/movss/movsd.
573 class InstX8632Mov : public InstX8632 {
574 public:
575 static InstX8632Mov *create(Cfg *Func, Variable *Dest, Operand *Source) {
576 return new (Func->allocate<InstX8632Mov>())
577 InstX8632Mov(Func, Dest, Source);
578 }
579 virtual bool isRedundantAssign() const;
580 virtual void emit(const Cfg *Func) const;
581 virtual void dump(const Cfg *Func) const;
582 static bool classof(const Inst *Inst) { return isClassof(Inst, Mov); }
583
584 private:
585 InstX8632Mov(Cfg *Func, Variable *Dest, Operand *Source);
586 InstX8632Mov(const InstX8632Mov &) LLVM_DELETED_FUNCTION;
587 InstX8632Mov &operator=(const InstX8632Mov &) LLVM_DELETED_FUNCTION;
588 virtual ~InstX8632Mov() {}
589 };
590
591 // Movsx - copy from a narrower integer type to a wider integer
592 // type, with sign extension.
593 class InstX8632Movsx : public InstX8632 {
594 public:
595 static InstX8632Movsx *create(Cfg *Func, Variable *Dest, Operand *Source) {
596 return new (Func->allocate<InstX8632Movsx>())
597 InstX8632Movsx(Func, Dest, Source);
598 }
599 virtual void emit(const Cfg *Func) const;
600 virtual void dump(const Cfg *Func) const;
601 static bool classof(const Inst *Inst) { return isClassof(Inst, Movsx); }
602
603 private:
604 InstX8632Movsx(Cfg *Func, Variable *Dest, Operand *Source);
605 InstX8632Movsx(const InstX8632Movsx &) LLVM_DELETED_FUNCTION;
606 InstX8632Movsx &operator=(const InstX8632Movsx &) LLVM_DELETED_FUNCTION;
607 virtual ~InstX8632Movsx() {}
608 };
609
610 // Movsx - copy from a narrower integer type to a wider integer
611 // type, with zero extension.
612 class InstX8632Movzx : public InstX8632 {
613 public:
614 static InstX8632Movzx *create(Cfg *Func, Variable *Dest, Operand *Source) {
615 return new (Func->allocate<InstX8632Movzx>())
616 InstX8632Movzx(Func, Dest, Source);
617 }
618 virtual void emit(const Cfg *Func) const;
619 virtual void dump(const Cfg *Func) const;
620 static bool classof(const Inst *Inst) { return isClassof(Inst, Movzx); }
621
622 private:
623 InstX8632Movzx(Cfg *Func, Variable *Dest, Operand *Source);
624 InstX8632Movzx(const InstX8632Movzx &) LLVM_DELETED_FUNCTION;
625 InstX8632Movzx &operator=(const InstX8632Movzx &) LLVM_DELETED_FUNCTION;
626 virtual ~InstX8632Movzx() {}
627 };
628
629 // Fld - load a value onto the x87 FP stack.
630 class InstX8632Fld : public InstX8632 {
631 public:
632 static InstX8632Fld *create(Cfg *Func, Operand *Src) {
633 return new (Func->allocate<InstX8632Fld>()) InstX8632Fld(Func, Src);
634 }
635 virtual void emit(const Cfg *Func) const;
636 virtual void dump(const Cfg *Func) const;
637 static bool classof(const Inst *Inst) { return isClassof(Inst, Fld); }
638
639 private:
640 InstX8632Fld(Cfg *Func, Operand *Src);
641 InstX8632Fld(const InstX8632Fld &) LLVM_DELETED_FUNCTION;
642 InstX8632Fld &operator=(const InstX8632Fld &) LLVM_DELETED_FUNCTION;
643 virtual ~InstX8632Fld() {}
644 };
645
646 // Fstp - store x87 st(0) into memory and pop st(0).
647 class InstX8632Fstp : public InstX8632 {
648 public:
649 static InstX8632Fstp *create(Cfg *Func, Variable *Dest) {
650 return new (Func->allocate<InstX8632Fstp>()) InstX8632Fstp(Func, Dest);
651 }
652 virtual void emit(const Cfg *Func) const;
653 virtual void dump(const Cfg *Func) const;
654 static bool classof(const Inst *Inst) { return isClassof(Inst, Fstp); }
655
656 private:
657 InstX8632Fstp(Cfg *Func, Variable *Dest);
658 InstX8632Fstp(const InstX8632Fstp &) LLVM_DELETED_FUNCTION;
659 InstX8632Fstp &operator=(const InstX8632Fstp &) LLVM_DELETED_FUNCTION;
660 virtual ~InstX8632Fstp() {}
661 };
662
663 class InstX8632Pop : public InstX8632 {
664 public:
665 static InstX8632Pop *create(Cfg *Func, Variable *Dest) {
666 return new (Func->allocate<InstX8632Pop>()) InstX8632Pop(Func, Dest);
667 }
668 virtual void emit(const Cfg *Func) const;
669 virtual void dump(const Cfg *Func) const;
670 static bool classof(const Inst *Inst) { return isClassof(Inst, Pop); }
671
672 private:
673 InstX8632Pop(Cfg *Func, Variable *Dest);
674 InstX8632Pop(const InstX8632Pop &) LLVM_DELETED_FUNCTION;
675 InstX8632Pop &operator=(const InstX8632Pop &) LLVM_DELETED_FUNCTION;
676 virtual ~InstX8632Pop() {}
677 };
678
679 class InstX8632Push : public InstX8632 {
680 public:
681 static InstX8632Push *create(Cfg *Func, Operand *Source,
682 bool SuppressStackAdjustment) {
683 return new (Func->allocate<InstX8632Push>())
684 InstX8632Push(Func, Source, SuppressStackAdjustment);
685 }
686 virtual void emit(const Cfg *Func) const;
687 virtual void dump(const Cfg *Func) const;
688 static bool classof(const Inst *Inst) { return isClassof(Inst, Push); }
689
690 private:
691 InstX8632Push(Cfg *Func, Operand *Source, bool SuppressStackAdjustment);
692 InstX8632Push(const InstX8632Push &) LLVM_DELETED_FUNCTION;
693 InstX8632Push &operator=(const InstX8632Push &) LLVM_DELETED_FUNCTION;
694 bool SuppressStackAdjustment;
695 virtual ~InstX8632Push() {}
696 };
697
698 // Ret instruction. Currently only supports the "ret" version that
699 // does not pop arguments. This instruction takes a Source operand
700 // (for non-void returning functions) for liveness analysis, though
701 // a FakeUse before the ret would do just as well.
702 class InstX8632Ret : public InstX8632 {
703 public:
704 static InstX8632Ret *create(Cfg *Func, Variable *Source = NULL) {
705 return new (Func->allocate<InstX8632Ret>()) InstX8632Ret(Func, Source);
706 }
707 virtual void emit(const Cfg *Func) const;
708 virtual void dump(const Cfg *Func) const;
709 static bool classof(const Inst *Inst) { return isClassof(Inst, Ret); }
710
711 private:
712 InstX8632Ret(Cfg *Func, Variable *Source);
713 InstX8632Ret(const InstX8632Ret &) LLVM_DELETED_FUNCTION;
714 InstX8632Ret &operator=(const InstX8632Ret &) LLVM_DELETED_FUNCTION;
715 virtual ~InstX8632Ret() {}
716 };
717
718 } // end of namespace Ice
719
720 #endif // SUBZERO_SRC_ICEINSTX8632_H
OLDNEW
« no previous file with comments | « src/IceInst.def ('k') | src/IceInstX8632.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698