• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2012 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #ifndef ART_COMPILER_DEX_COMPILER_ENUMS_H_
18 #define ART_COMPILER_DEX_COMPILER_ENUMS_H_
19 
20 #include "dex_instruction.h"
21 
22 namespace art {
23 
24 enum RegisterClass {
25   kInvalidRegClass,
26   kCoreReg,
27   kFPReg,
28   kRefReg,
29   kAnyReg,
30 };
31 
32 enum BitsUsed {
33   kSize32Bits,
34   kSize64Bits,
35   kSize128Bits,
36   kSize256Bits,
37   kSize512Bits,
38   kSize1024Bits,
39 };
40 
41 enum SpecialTargetRegister {
42   kSelf,            // Thread pointer.
43   kSuspend,         // Used to reduce suspend checks for some targets.
44   kLr,
45   kPc,
46   kSp,
47   kArg0,
48   kArg1,
49   kArg2,
50   kArg3,
51   kArg4,
52   kArg5,
53   kArg6,
54   kArg7,
55   kFArg0,
56   kFArg1,
57   kFArg2,
58   kFArg3,
59   kFArg4,
60   kFArg5,
61   kFArg6,
62   kFArg7,
63   kRet0,
64   kRet1,
65   kInvokeTgt,
66   kHiddenArg,
67   kHiddenFpArg,
68   kCount
69 };
70 
71 enum RegLocationType {
72   kLocDalvikFrame = 0,  // Normal Dalvik register
73   kLocPhysReg,
74   kLocCompilerTemp,
75   kLocInvalid
76 };
77 
78 enum BBType {
79   kNullBlock,
80   kEntryBlock,
81   kDalvikByteCode,
82   kExitBlock,
83   kExceptionHandling,
84   kDead,
85 };
86 
87 // Shared pseudo opcodes - must be < 0.
88 enum LIRPseudoOpcode {
89   kPseudoExportedPC = -16,
90   kPseudoSafepointPC = -15,
91   kPseudoIntrinsicRetry = -14,
92   kPseudoSuspendTarget = -13,
93   kPseudoThrowTarget = -12,
94   kPseudoCaseLabel = -11,
95   kPseudoMethodEntry = -10,
96   kPseudoMethodExit = -9,
97   kPseudoBarrier = -8,
98   kPseudoEntryBlock = -7,
99   kPseudoExitBlock = -6,
100   kPseudoTargetLabel = -5,
101   kPseudoDalvikByteCodeBoundary = -4,
102   kPseudoPseudoAlign4 = -3,
103   kPseudoEHBlockLabel = -2,
104   kPseudoNormalBlockLabel = -1,
105 };
106 
107 enum ExtendedMIROpcode {
108   kMirOpFirst = kNumPackedOpcodes,
109   kMirOpPhi = kMirOpFirst,
110   kMirOpCopy,
111   kMirOpFusedCmplFloat,
112   kMirOpFusedCmpgFloat,
113   kMirOpFusedCmplDouble,
114   kMirOpFusedCmpgDouble,
115   kMirOpFusedCmpLong,
116   kMirOpNop,
117   kMirOpNullCheck,
118   kMirOpRangeCheck,
119   kMirOpDivZeroCheck,
120   kMirOpCheck,
121   kMirOpCheckPart2,
122   kMirOpSelect,
123 
124   // Vector opcodes:
125   // TypeSize is an encoded field giving the element type and the vector size.
126   // It is encoded as OpSize << 16 | (number of bits in vector)
127   //
128   // Destination and source are integers that will be interpreted by the
129   // backend that supports Vector operations.  Backends are permitted to support only
130   // certain vector register sizes.
131   //
132   // At this point, only two operand instructions are supported.  Three operand instructions
133   // could be supported by using a bit in TypeSize and arg[0] where needed.
134 
135   // @brief MIR to move constant data to a vector register
136   // vA: destination
137   // vB: number of bits in register
138   // args[0]~args[3]: up to 128 bits of data for initialization
139   kMirOpConstVector,
140 
141   // @brief MIR to move a vectorized register to another
142   // vA: destination
143   // vB: source
144   // vC: TypeSize
145   kMirOpMoveVector,
146 
147   // @brief Packed multiply of units in two vector registers: vB = vB .* vC using vA to know the type of the vector.
148   // vA: destination and source
149   // vB: source
150   // vC: TypeSize
151   kMirOpPackedMultiply,
152 
153   // @brief Packed addition of units in two vector registers: vB = vB .+ vC using vA to know the type of the vector.
154   // vA: destination and source
155   // vB: source
156   // vC: TypeSize
157   kMirOpPackedAddition,
158 
159   // @brief Packed subtraction of units in two vector registers: vB = vB .- vC using vA to know the type of the vector.
160   // vA: destination and source
161   // vB: source
162   // vC: TypeSize
163   kMirOpPackedSubtract,
164 
165   // @brief Packed shift left of units in two vector registers: vB = vB .<< vC using vA to know the type of the vector.
166   // vA: destination and source
167   // vB: amount to shift
168   // vC: TypeSize
169   kMirOpPackedShiftLeft,
170 
171   // @brief Packed signed shift right of units in two vector registers: vB = vB .>> vC using vA to know the type of the vector.
172   // vA: destination and source
173   // vB: amount to shift
174   // vC: TypeSize
175   kMirOpPackedSignedShiftRight,
176 
177   // @brief Packed unsigned shift right of units in two vector registers: vB = vB .>>> vC using vA to know the type of the vector.
178   // vA: destination and source
179   // vB: amount to shift
180   // vC: TypeSize
181   kMirOpPackedUnsignedShiftRight,
182 
183   // @brief Packed bitwise and of units in two vector registers: vB = vB .& vC using vA to know the type of the vector.
184   // vA: destination and source
185   // vB: source
186   // vC: TypeSize
187   kMirOpPackedAnd,
188 
189   // @brief Packed bitwise or of units in two vector registers: vB = vB .| vC using vA to know the type of the vector.
190   // vA: destination and source
191   // vB: source
192   // vC: TypeSize
193   kMirOpPackedOr,
194 
195   // @brief Packed bitwise xor of units in two vector registers: vB = vB .^ vC using vA to know the type of the vector.
196   // vA: destination and source
197   // vB: source
198   // vC: TypeSize
199   kMirOpPackedXor,
200 
201   // @brief Reduce a 128-bit packed element into a single VR by taking lower bits
202   // @details Instruction does a horizontal addition of the packed elements and then adds it to VR
203   // vA: destination and source VR (not vector register)
204   // vB: source (vector register)
205   // vC: TypeSize
206   kMirOpPackedAddReduce,
207 
208   // @brief Extract a packed element into a single VR.
209   // vA: destination VR (not vector register)
210   // vB: source (vector register)
211   // vC: TypeSize
212   // arg[0]: The index to use for extraction from vector register (which packed element)
213   kMirOpPackedReduce,
214 
215   // @brief Create a vector value, with all TypeSize values equal to vC
216   // vA: destination vector register
217   // vB: source VR (not vector register)
218   // vC: TypeSize
219   kMirOpPackedSet,
220 
221   // @brief Reserve N vector registers (named 0..N-1)
222   // vA: Number of registers
223   // @note: The backend may choose to map vector numbers used in vector opcodes.
224   //  Reserved registers are removed from the list of backend temporary pool.
225   kMirOpReserveVectorRegisters,
226 
227   // @brief Free Reserved vector registers
228   // @note: All currently reserved vector registers are returned to the temporary pool.
229   kMirOpReturnVectorRegisters,
230 
231   kMirOpLast,
232 };
233 
234 enum MIROptimizationFlagPositions {
235   kMIRIgnoreNullCheck = 0,
236   kMIRNullCheckOnly,
237   kMIRIgnoreRangeCheck,
238   kMIRRangeCheckOnly,
239   kMIRIgnoreClInitCheck,
240   kMIRInlined,                        // Invoke is inlined (ie dead).
241   kMIRInlinedPred,                    // Invoke is inlined via prediction.
242   kMIRCallee,                         // Instruction is inlined from callee.
243   kMIRIgnoreSuspendCheck,
244   kMIRDup,
245   kMIRMark,                           // Temporary node mark.
246   kMIRLastMIRFlag,
247 };
248 
249 // For successor_block_list.
250 enum BlockListType {
251   kNotUsed = 0,
252   kCatch,
253   kPackedSwitch,
254   kSparseSwitch,
255 };
256 
257 enum AssemblerStatus {
258   kSuccess,
259   kRetryAll,
260 };
261 
262 enum OpSize {
263   kWord,            // Natural word size of target (32/64).
264   k32,
265   k64,
266   kReference,       // Object reference; compressed on 64-bit targets.
267   kSingle,
268   kDouble,
269   kUnsignedHalf,
270   kSignedHalf,
271   kUnsignedByte,
272   kSignedByte,
273 };
274 
275 std::ostream& operator<<(std::ostream& os, const OpSize& kind);
276 
277 enum OpKind {
278   kOpMov,
279   kOpCmov,
280   kOpMvn,
281   kOpCmp,
282   kOpLsl,
283   kOpLsr,
284   kOpAsr,
285   kOpRor,
286   kOpNot,
287   kOpAnd,
288   kOpOr,
289   kOpXor,
290   kOpNeg,
291   kOpAdd,
292   kOpAdc,
293   kOpSub,
294   kOpSbc,
295   kOpRsub,
296   kOpMul,
297   kOpDiv,
298   kOpRem,
299   kOpBic,
300   kOpCmn,
301   kOpTst,
302   kOpRev,
303   kOpRevsh,
304   kOpBkpt,
305   kOpBlx,
306   kOpPush,
307   kOpPop,
308   kOp2Char,
309   kOp2Short,
310   kOp2Byte,
311   kOpCondBr,
312   kOpUncondBr,
313   kOpBx,
314   kOpInvalid,
315 };
316 
317 enum MoveType {
318   kMov8GP,      // Move 8-bit general purpose register.
319   kMov16GP,     // Move 16-bit general purpose register.
320   kMov32GP,     // Move 32-bit general purpose register.
321   kMov64GP,     // Move 64-bit general purpose register.
322   kMov32FP,     // Move 32-bit FP register.
323   kMov64FP,     // Move 64-bit FP register.
324   kMovLo64FP,   // Move low 32-bits of 64-bit FP register.
325   kMovHi64FP,   // Move high 32-bits of 64-bit FP register.
326   kMovU128FP,   // Move 128-bit FP register to/from possibly unaligned region.
327   kMov128FP = kMovU128FP,
328   kMovA128FP,   // Move 128-bit FP register to/from region surely aligned to 16-bytes.
329   kMovLo128FP,  // Move low 64-bits of 128-bit FP register.
330   kMovHi128FP,  // Move high 64-bits of 128-bit FP register.
331 };
332 
333 std::ostream& operator<<(std::ostream& os, const OpKind& kind);
334 
335 enum ConditionCode {
336   kCondEq,  // equal
337   kCondNe,  // not equal
338   kCondCs,  // carry set
339   kCondCc,  // carry clear
340   kCondUlt,  // unsigned less than
341   kCondUge,  // unsigned greater than or same
342   kCondMi,  // minus
343   kCondPl,  // plus, positive or zero
344   kCondVs,  // overflow
345   kCondVc,  // no overflow
346   kCondHi,  // unsigned greater than
347   kCondLs,  // unsigned lower or same
348   kCondGe,  // signed greater than or equal
349   kCondLt,  // signed less than
350   kCondGt,  // signed greater than
351   kCondLe,  // signed less than or equal
352   kCondAl,  // always
353   kCondNv,  // never
354 };
355 
356 std::ostream& operator<<(std::ostream& os, const ConditionCode& kind);
357 
358 // Target specific condition encodings
359 enum ArmConditionCode {
360   kArmCondEq = 0x0,  // 0000
361   kArmCondNe = 0x1,  // 0001
362   kArmCondCs = 0x2,  // 0010
363   kArmCondCc = 0x3,  // 0011
364   kArmCondMi = 0x4,  // 0100
365   kArmCondPl = 0x5,  // 0101
366   kArmCondVs = 0x6,  // 0110
367   kArmCondVc = 0x7,  // 0111
368   kArmCondHi = 0x8,  // 1000
369   kArmCondLs = 0x9,  // 1001
370   kArmCondGe = 0xa,  // 1010
371   kArmCondLt = 0xb,  // 1011
372   kArmCondGt = 0xc,  // 1100
373   kArmCondLe = 0xd,  // 1101
374   kArmCondAl = 0xe,  // 1110
375   kArmCondNv = 0xf,  // 1111
376 };
377 
378 std::ostream& operator<<(std::ostream& os, const ArmConditionCode& kind);
379 
380 enum X86ConditionCode {
381   kX86CondO   = 0x0,    // overflow
382   kX86CondNo  = 0x1,    // not overflow
383 
384   kX86CondB   = 0x2,    // below
385   kX86CondNae = kX86CondB,  // not-above-equal
386   kX86CondC   = kX86CondB,  // carry
387 
388   kX86CondNb  = 0x3,    // not-below
389   kX86CondAe  = kX86CondNb,  // above-equal
390   kX86CondNc  = kX86CondNb,  // not-carry
391 
392   kX86CondZ   = 0x4,    // zero
393   kX86CondEq  = kX86CondZ,  // equal
394 
395   kX86CondNz  = 0x5,    // not-zero
396   kX86CondNe  = kX86CondNz,  // not-equal
397 
398   kX86CondBe  = 0x6,    // below-equal
399   kX86CondNa  = kX86CondBe,  // not-above
400 
401   kX86CondNbe = 0x7,    // not-below-equal
402   kX86CondA   = kX86CondNbe,  // above
403 
404   kX86CondS   = 0x8,    // sign
405   kX86CondNs  = 0x9,    // not-sign
406 
407   kX86CondP   = 0xa,    // 8-bit parity even
408   kX86CondPE  = kX86CondP,
409 
410   kX86CondNp  = 0xb,    // 8-bit parity odd
411   kX86CondPo  = kX86CondNp,
412 
413   kX86CondL   = 0xc,    // less-than
414   kX86CondNge = kX86CondL,  // not-greater-equal
415 
416   kX86CondNl  = 0xd,    // not-less-than
417   kX86CondGe  = kX86CondNl,  // not-greater-equal
418 
419   kX86CondLe  = 0xe,    // less-than-equal
420   kX86CondNg  = kX86CondLe,  // not-greater
421 
422   kX86CondNle = 0xf,    // not-less-than
423   kX86CondG   = kX86CondNle,  // greater
424 };
425 
426 std::ostream& operator<<(std::ostream& os, const X86ConditionCode& kind);
427 
428 enum DividePattern {
429   DivideNone,
430   Divide3,
431   Divide5,
432   Divide7,
433 };
434 
435 std::ostream& operator<<(std::ostream& os, const DividePattern& pattern);
436 
437 /**
438  * @brief Memory barrier types (see "The JSR-133 Cookbook for Compiler Writers").
439  * @details We define the combined barrier types that are actually required
440  * by the Java Memory Model, rather than using exactly the terminology from
441  * the JSR-133 cookbook.  These should, in many cases, be replaced by acquire/release
442  * primitives.  Note that the JSR-133 cookbook generally does not deal with
443  * store atomicity issues, and the recipes there are not always entirely sufficient.
444  * The current recipe is as follows:
445  * -# Use AnyStore ~= (LoadStore | StoreStore) ~= release barrier before volatile store.
446  * -# Use AnyAny barrier after volatile store.  (StoreLoad is as expensive.)
447  * -# Use LoadAny barrier ~= (LoadLoad | LoadStore) ~= acquire barrierafter each volatile load.
448  * -# Use StoreStore barrier after all stores but before return from any constructor whose
449  *    class has final fields.
450  */
451 enum MemBarrierKind {
452   kAnyStore,
453   kLoadAny,
454   kStoreStore,
455   kAnyAny
456 };
457 
458 std::ostream& operator<<(std::ostream& os, const MemBarrierKind& kind);
459 
460 enum OpFeatureFlags {
461   kIsBranch = 0,
462   kNoOperand,
463   kIsUnaryOp,
464   kIsBinaryOp,
465   kIsTertiaryOp,
466   kIsQuadOp,
467   kIsQuinOp,
468   kIsSextupleOp,
469   kIsIT,
470   kIsMoveOp,
471   kMemLoad,
472   kMemStore,
473   kMemVolatile,
474   kMemScaledx0,
475   kMemScaledx2,
476   kMemScaledx4,
477   kPCRelFixup,  // x86 FIXME: add NEEDS_FIXUP to instruction attributes.
478   kRegDef0,
479   kRegDef1,
480   kRegDef2,
481   kRegDefA,
482   kRegDefD,
483   kRegDefFPCSList0,
484   kRegDefFPCSList2,
485   kRegDefList0,
486   kRegDefList1,
487   kRegDefList2,
488   kRegDefLR,
489   kRegDefSP,
490   kRegUse0,
491   kRegUse1,
492   kRegUse2,
493   kRegUse3,
494   kRegUse4,
495   kRegUseA,
496   kRegUseC,
497   kRegUseD,
498   kRegUseB,
499   kRegUseFPCSList0,
500   kRegUseFPCSList2,
501   kRegUseList0,
502   kRegUseList1,
503   kRegUseLR,
504   kRegUsePC,
505   kRegUseSP,
506   kSetsCCodes,
507   kUsesCCodes,
508   kUseFpStack,
509   kUseHi,
510   kUseLo,
511   kDefHi,
512   kDefLo
513 };
514 
515 enum SelectInstructionKind {
516   kSelectNone,
517   kSelectConst,
518   kSelectMove,
519   kSelectGoto
520 };
521 
522 std::ostream& operator<<(std::ostream& os, const SelectInstructionKind& kind);
523 
524 // LIR fixup kinds for Arm
525 enum FixupKind {
526   kFixupNone,
527   kFixupLabel,       // For labels we just adjust the offset.
528   kFixupLoad,        // Mostly for immediates.
529   kFixupVLoad,       // FP load which *may* be pc-relative.
530   kFixupCBxZ,        // Cbz, Cbnz.
531   kFixupPushPop,     // Not really pc relative, but changes size based on args.
532   kFixupCondBranch,  // Conditional branch
533   kFixupT1Branch,    // Thumb1 Unconditional branch
534   kFixupT2Branch,    // Thumb2 Unconditional branch
535   kFixupBlx1,        // Blx1 (start of Blx1/Blx2 pair).
536   kFixupBl1,         // Bl1 (start of Bl1/Bl2 pair).
537   kFixupAdr,         // Adr.
538   kFixupMovImmLST,   // kThumb2MovImm16LST.
539   kFixupMovImmHST,   // kThumb2MovImm16HST.
540   kFixupAlign4,      // Align to 4-byte boundary.
541 };
542 
543 std::ostream& operator<<(std::ostream& os, const FixupKind& kind);
544 
545 enum VolatileKind {
546   kNotVolatile,      // Load/Store is not volatile
547   kVolatile          // Load/Store is volatile
548 };
549 
550 std::ostream& operator<<(std::ostream& os, const VolatileKind& kind);
551 
552 enum WideKind {
553   kNotWide,      // Non-wide view
554   kWide,         // Wide view
555   kRef           // Ref width
556 };
557 
558 std::ostream& operator<<(std::ostream& os, const WideKind& kind);
559 
560 }  // namespace art
561 
562 #endif  // ART_COMPILER_DEX_COMPILER_ENUMS_H_
563