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 18 /*! \file lower.h 19 \brief A header file to define interface between lowering and register allocator 20 */ 21 22 #ifndef _DALVIK_LOWER 23 #define _DALVIK_LOWER 24 25 #define CODE_CACHE_PADDING 1024 //code space for a single bytecode 26 // comment out for phase 1 porting 27 #define PREDICTED_CHAINING 28 #define JIT_CHAIN 29 30 #define NUM_DEPENDENCIES 24 /* max number of dependencies from a LowOp */ 31 //compilaton flags used by NCG O1 32 #define DUMP_EXCEPTION //to measure performance, required to have correct exception handling 33 /*! multiple versions for hardcoded registers */ 34 #define HARDREG_OPT 35 #define CFG_OPT 36 /*! remove redundant move ops when accessing virtual registers */ 37 #define MOVE_OPT 38 /*! remove redundant spill of virtual registers */ 39 #define SPILL_OPT 40 #define XFER_OPT 41 //#define DSE_OPT //no perf improvement for cme 42 /*! use live range analysis to allocate registers */ 43 #define LIVERANGE_OPT 44 /*! remove redundant null check */ 45 #define NULLCHECK_OPT 46 //#define BOUNDCHECK_OPT 47 /*! optimize the access to glue structure */ 48 #define GLUE_OPT 49 #define CALL_FIX 50 #define NATIVE_FIX 51 #define INVOKE_FIX //optimization 52 #define GETVR_FIX //optimization 53 54 #include "Dalvik.h" 55 #include "enc_wrapper.h" 56 #include "AnalysisO1.h" 57 #include "compiler/CompilerIR.h" 58 59 //compilation flags for debugging 60 //#define DEBUG_INFO 61 //#define DEBUG_CALL_STACK 62 //#define DEBUG_IGET_OBJ 63 //#define DEBUG_NCG_CODE_SIZE 64 //#define DEBUG_NCG 65 //#define DEBUG_NCG_1 66 //#define DEBUG_LOADING 67 //#define USE_INTERPRETER 68 //#define DEBUG_EACH_BYTECODE 69 70 /*! registers for functions are hardcoded */ 71 #define HARDCODE_REG_CALL 72 #define HARDCODE_REG_SHARE 73 #define HARDCODE_REG_HELPER 74 75 #define PhysicalReg_FP PhysicalReg_EDI 76 #define PhysicalReg_Glue PhysicalReg_EBP 77 78 //COPIED from interp/InterpDefs.h 79 #define FETCH(_offset) (rPC[(_offset)]) 80 #define INST_INST(_inst) ((_inst) & 0xff) 81 #define INST_A(_inst) (((_inst) >> 8) & 0x0f) 82 #define INST_B(_inst) ((_inst) >> 12) 83 #define INST_AA(_inst) ((_inst) >> 8) 84 85 //#include "vm/mterp/common/asm-constants.h" 86 #define offEBP_self 8 87 #define offEBP_spill -56 88 #define offThread_exception 68 89 #define offClassObject_descriptor 24 90 #define offArrayObject_length 8 91 #ifdef PROFILE_FIELD_ACCESS 92 #define offStaticField_value 24 93 #define offInstField_byteOffset 24 94 #else 95 #define offStaticField_value 16 96 #define offInstField_byteOffset 16 97 #endif 98 99 #ifdef EASY_GDB 100 #define offStackSaveArea_prevFrame 4 101 #define offStackSaveArea_savedPc 8 102 #define offStackSaveArea_method 12 103 #define offStackSaveArea_localRefTop 16 // -> StackSaveArea.xtra.locakRefCookie 104 #define offStackSaveArea_returnAddr 20 105 #define offStackSaveArea_isDebugInterpreted 24 106 #define sizeofStackSaveArea 24 107 #else 108 #define offStackSaveArea_prevFrame 0 109 #define offStackSaveArea_savedPc 4 110 #define offStackSaveArea_method 8 111 #define offStackSaveArea_localRefTop 12 // -> StackSaveArea.xtra.locakRefCookie 112 #define offStackSaveArea_returnAddr 16 113 #define offStackSaveArea_isDebugInterpreted 20 114 #define sizeofStackSaveArea 20 115 #endif 116 117 #define offClassObject_status 44 118 #define offClassObject_accessFlags 32 119 #ifdef MTERP_NO_UNALIGN_64 120 #define offArrayObject_contents 16 121 #else 122 #define offArrayObject_contents 12 123 #endif 124 125 #define offField_clazz 0 126 #define offObject_clazz 0 127 #define offClassObject_vtable 116 128 #define offClassObject_pDvmDex 40 129 #define offClassObject_super 72 130 #define offClassObject_vtableCount 112 131 #define offMethod_name 16 132 #define offMethod_accessFlags 4 133 #define offMethod_methodIndex 8 134 #define offMethod_registersSize 10 135 #define offMethod_outsSize 12 136 #define offGlue_interpStackEnd 32 137 #define offThread_inJitCodeCache 124 138 #define offThread_jniLocal_nextEntry 168 139 #define offMethod_insns 32 140 #ifdef ENABLE_TRACING 141 #define offMethod_insns_bytecode 44 142 #define offMethod_insns_ncg 48 143 #endif 144 145 #define offGlue_pc 0 146 #define offGlue_fp 4 147 #define offGlue_retval 8 148 149 #define offThread_curFrame 4 150 #define offGlue_method 16 151 #define offGlue_methodClassDex 20 152 #define offGlue_self 24 153 #define offGlue_pSelfSuspendCount 36 154 #define offGlue_cardTable 40 155 #define offGlue_pDebuggerActive 44 156 #define offGlue_pActiveProfilers 48 157 #define offGlue_entryPoint 52 158 #define offGlue_icRechainCount 84 159 #define offGlue_espEntry 88 160 #define offGlue_spillRegion 92 161 #define offDvmDex_pResStrings 8 162 #define offDvmDex_pResClasses 12 163 #define offDvmDex_pResMethods 16 164 #define offDvmDex_pResFields 20 165 #define offMethod_clazz 0 166 167 // Definitions must be consistent with vm/mterp/x86/header.S 168 #define FRAME_SIZE 124 169 170 typedef enum ArgsDoneType { 171 ArgsDone_Normal = 0, 172 ArgsDone_Native, 173 ArgsDone_Full 174 } ArgsDoneType; 175 176 /*! An enum type 177 to list bytecodes for AGET, APUT 178 */ 179 typedef enum ArrayAccess { 180 AGET, AGET_WIDE, AGET_CHAR, AGET_SHORT, AGET_BOOLEAN, AGET_BYTE, 181 APUT, APUT_WIDE, APUT_CHAR, APUT_SHORT, APUT_BOOLEAN, APUT_BYTE 182 } ArrayAccess; 183 /*! An enum type 184 to list bytecodes for IGET, IPUT 185 */ 186 typedef enum InstanceAccess { 187 IGET, IGET_WIDE, IPUT, IPUT_WIDE 188 } InstanceAccess; 189 /*! An enum type 190 to list bytecodes for SGET, SPUT 191 */ 192 typedef enum StaticAccess { 193 SGET, SGET_WIDE, SPUT, SPUT_WIDE 194 } StaticAccess; 195 196 typedef enum JmpCall_type { 197 JmpCall_uncond = 1, 198 JmpCall_cond, 199 JmpCall_reg, //jump reg32 200 JmpCall_call 201 } JmpCall_type; 202 203 //////////////////////////////////////////////////////////////// 204 /* data structure for native codes */ 205 /* Due to space considation, a lowered op (LowOp) has two operands (LowOpnd), depending on 206 the type of the operand, LowOpndReg or LowOpndImm or LowOpndMem will follow */ 207 /*! type of an operand can be immediate, register or memory */ 208 typedef enum LowOpndType { 209 LowOpndType_Imm = 0, 210 LowOpndType_Reg, 211 LowOpndType_Mem, 212 LowOpndType_Label, 213 LowOpndType_NCG, 214 LowOpndType_Chain 215 } LowOpndType; 216 typedef enum LowOpndDefUse { 217 LowOpndDefUse_Def = 0, 218 LowOpndDefUse_Use, 219 LowOpndDefUse_UseDef 220 } LowOpndDefUse; 221 222 /*! 223 \brief base data structure for an operand */ 224 typedef struct LowOpnd { 225 LowOpndType type; 226 OpndSize size; 227 LowOpndDefUse defuse; 228 } LowOpnd; 229 /*! 230 \brief data structure for a register operand */ 231 typedef struct LowOpndReg { 232 LowOpndRegType regType; 233 int logicalReg; 234 int physicalReg; 235 } LowOpndReg; 236 /*! 237 \brief data structure for an immediate operand */ 238 typedef struct LowOpndImm { 239 union { 240 s4 value; 241 unsigned char bytes[4]; 242 }; 243 } LowOpndImm; 244 245 typedef struct LowOpndNCG { 246 union { 247 s4 value; 248 unsigned char bytes[4]; 249 }; 250 } LowOpndNCG; 251 252 #define LABEL_SIZE 256 253 typedef struct LowOpndLabel { 254 char label[LABEL_SIZE]; 255 bool isLocal; 256 } LowOpndLabel; 257 258 /* get ready for optimizations at LIR 259 add MemoryAccessType & virtualRegNum to memory operands */ 260 typedef enum MemoryAccessType { 261 MemoryAccess_GLUE, 262 MemoryAccess_VR, 263 MemoryAccess_SPILL, 264 MemoryAccess_Unknown 265 } MemoryAccessType; 266 typedef enum UseDefEntryType { 267 UseDefType_Ctrl = 0, 268 UseDefType_Float, 269 UseDefType_MemVR, 270 UseDefType_MemSpill, 271 UseDefType_MemUnknown, 272 UseDefType_Reg 273 } UseDefEntryType; 274 typedef struct UseDefProducerEntry { 275 UseDefEntryType type; 276 int index; //enum PhysicalReg for "Reg" type 277 int producerSlot; 278 } UseDefProducerEntry; 279 #define MAX_USE_PER_ENTRY 50 /* at most 10 uses for each entry */ 280 typedef struct UseDefUserEntry { 281 UseDefEntryType type; 282 int index; 283 int useSlots[MAX_USE_PER_ENTRY]; 284 int num_uses_per_entry; 285 } UseDefUserEntry; 286 287 /*! 288 \brief data structure for a memory operand */ 289 typedef struct LowOpndMem { 290 LowOpndImm m_disp; 291 LowOpndImm m_scale; 292 LowOpndReg m_index; 293 LowOpndReg m_base; 294 bool hasScale; 295 MemoryAccessType mType; 296 int index; 297 } LowOpndMem; 298 299 typedef enum AtomOpCode { 300 ATOM_PSEUDO_CHAINING_CELL_BACKWARD_BRANCH = -15, 301 ATOM_NORMAL_ALU = -14, 302 ATOM_PSEUDO_ENTRY_BLOCK = -13, 303 ATOM_PSEUDO_EXIT_BLOCK = -12, 304 ATOM_PSEUDO_TARGET_LABEL = -11, 305 ATOM_PSEUDO_CHAINING_CELL_HOT = -10, 306 ATOM_PSEUDO_CHAINING_CELL_INVOKE_PREDICTED = -9, 307 ATOM_PSEUDO_CHAINING_CELL_INVOKE_SINGLETON = -8, 308 ATOM_PSEUDO_CHAINING_CELL_NORMAL = -7, 309 ATOM_PSEUDO_DALVIK_BYTECODE_BOUNDARY = -6, 310 ATOM_PSEUDO_ALIGN4 = -5, 311 ATOM_PSEUDO_PC_RECONSTRUCTION_CELL = -4, 312 ATOM_PSEUDO_PC_RECONSTRUCTION_BLOCK_LABEL = -3, 313 ATOM_PSEUDO_EH_BLOCK_LABEL = -2, 314 ATOM_PSEUDO_NORMAL_BLOCK_LABEL = -1, 315 ATOM_NORMAL, 316 } AtomOpCode; 317 318 typedef enum DependencyType { 319 Dependency_RAW, 320 Dependency_WAW, 321 Dependency_WAR, 322 Dependency_FLAG 323 } DependencyType; 324 typedef struct DependencyStruct { 325 DependencyType dType; 326 int nodeId; 327 int latency; 328 } DependencyStruct; 329 330 typedef struct LowOpBlock { 331 LIR generic; 332 Mnemonic opCode; 333 AtomOpCode opCode2; 334 } LowOpBlock; 335 336 /*! 337 \brief data structure for a lowered operation */ 338 typedef struct LowOp { 339 LIR generic; 340 Mnemonic opCode; 341 AtomOpCode opCode2; 342 LowOpnd opnd1; 343 LowOpnd opnd2; 344 int numOperands; 345 } LowOp; 346 347 typedef struct LowOpLabel { 348 LowOp lop; 349 LowOpndLabel labelOpnd; 350 }LowOpLabel; 351 352 typedef struct LowOpNCG { 353 LowOp lop; 354 LowOpndNCG ncgOpnd; 355 }LowOpNCG; 356 357 typedef struct LowOpBlockLabel { 358 LowOpBlock lop; 359 LowOpndImm immOpnd; 360 } LowOpBlockLabel; 361 362 typedef struct LowOpImm { 363 LowOp lop; 364 LowOpndImm immOpnd; 365 } LowOpImm; 366 367 typedef struct LowOpMem { 368 LowOp lop; 369 LowOpndMem memOpnd; 370 } LowOpMem; 371 372 typedef struct LowOpReg { 373 LowOp lop; 374 LowOpndReg regOpnd; 375 } LowOpReg; 376 377 typedef struct LowOpImmImm { 378 LowOp lop; 379 LowOpndImm immOpnd1; 380 LowOpndImm immOpnd2; 381 } LowOpImmImm; 382 383 typedef struct LowOpImmReg { 384 LowOp lop; 385 LowOpndImm immOpnd1; 386 LowOpndReg regOpnd2; 387 } LowOpImmReg; 388 389 typedef struct LowOpImmMem { 390 LowOp lop; 391 LowOpndImm immOpnd1; 392 LowOpndMem memOpnd2; 393 } LowOpImmMem; 394 395 typedef struct LowOpRegImm { 396 LowOp lop; 397 LowOpndReg regOpnd1; 398 LowOpndImm immOpnd2; 399 } LowOpRegImm; 400 401 typedef struct LowOpRegReg { 402 LowOp lop; 403 LowOpndReg regOpnd1; 404 LowOpndReg regOpnd2; 405 } LowOpRegReg; 406 407 typedef struct LowOpRegMem { 408 LowOp lop; 409 LowOpndReg regOpnd1; 410 LowOpndMem memOpnd2; 411 } LowOpRegMem; 412 413 typedef struct LowOpMemImm { 414 LowOp lop; 415 LowOpndMem memOpnd1; 416 LowOpndImm immOpnd2; 417 } LowOpMemImm; 418 419 typedef struct LowOpMemReg { 420 LowOp lop; 421 LowOpndMem memOpnd1; 422 LowOpndReg regOpnd2; 423 } LowOpMemReg; 424 425 typedef struct LowOpMemMem { 426 LowOp lop; 427 LowOpndMem memOpnd1; 428 LowOpndMem memOpnd2; 429 } LowOpMemMem; 430 431 /*! 432 \brief data structure for labels used when lowering a method 433 434 four label maps are defined: globalMap globalShortMap globalWorklist globalShortWorklist 435 globalMap: global labels where codePtr points to the label 436 freeLabelMap called in clearNCG 437 globalWorklist: global labels where codePtr points to an instruciton using the label 438 standalone NCG ------- 439 accessed by insertLabelWorklist & performLabelWorklist 440 code cache ------ 441 inserted by performLabelWorklist(false), 442 handled & cleared by generateRelocation in NcgFile.c 443 globalShortMap: local labels where codePtr points to the label 444 freeShortMap called after generation of one bytecode 445 globalShortWorklist: local labels where codePtr points to an instruction using the label 446 accessed by insertShortWorklist & insertLabel 447 definition of local label: life time of the label is within a bytecode or within a helper function 448 extra label maps are used by code cache: 449 globalDataWorklist VMAPIWorklist 450 */ 451 typedef struct LabelMap { 452 char label[LABEL_SIZE]; 453 char* codePtr; //code corresponding to the label or code that uses the label 454 struct LabelMap* nextItem; 455 OpndSize size; 456 uint addend; 457 } LabelMap; 458 /*! 459 \brief data structure to handle forward jump (GOTO, IF) 460 461 accessed by insertNCGWorklist & performNCGWorklist 462 */ 463 typedef struct NCGWorklist { 464 //when WITH_JIT, relativePC stores the target basic block id 465 s4 relativePC; //relative offset in bytecode 466 int offsetPC; //PC in bytecode 467 int offsetNCG; //PC in native code 468 char* codePtr; //code for native jump instruction 469 struct NCGWorklist* nextItem; 470 OpndSize size; 471 }NCGWorklist; 472 /*! 473 \brief data structure to handle SWITCH & FILL_ARRAY_DATA 474 475 two data worklist are defined: globalDataWorklist (used by code cache) & methodDataWorklist 476 methodDataWorklist is accessed by insertDataWorklist & performDataWorklist 477 */ 478 typedef struct DataWorklist { 479 s4 relativePC; //relative offset in bytecode to access the data 480 int offsetPC; //PC in bytecode 481 int offsetNCG; //PC in native code 482 char* codePtr; //code for native instruction add_imm_reg imm, %edx 483 char* codePtr2;//code for native instruction add_reg_reg %eax, %edx for SWITCH 484 // add_imm_reg imm, %edx for FILL_ARRAY_DATA 485 struct DataWorklist* nextItem; 486 }DataWorklist; 487 #ifdef ENABLE_TRACING 488 typedef struct MapWorklist { 489 u4 offsetPC; 490 u4 offsetNCG; 491 int isStartOfPC; //1 --> true 0 --> false 492 struct MapWorklist* nextItem; 493 } MapWorklist; 494 #endif 495 496 #define BUFFER_SIZE 1024 //# of Low Ops buffered 497 //the following three numbers are hardcoded, please CHECK 498 #define BYTECODE_SIZE_PER_METHOD 81920 499 #define NATIVE_SIZE_PER_DEX 19000000 //FIXME for core.jar: 16M --> 18M for O1 500 #define NATIVE_SIZE_FOR_VM_STUBS 100000 501 #define MAX_HANDLER_OFFSET 1024 //maximal number of handler offsets 502 503 extern int LstrClassCastExceptionPtr, LstrInstantiationErrorPtr, LstrInternalError, LstrFilledNewArrayNotImpl; 504 extern int LstrArithmeticException, LstrArrayIndexException, LstrArrayStoreException, LstrStringIndexOutOfBoundsException; 505 extern int LstrDivideByZero, LstrNegativeArraySizeException, LstrNoSuchMethodError, LstrNullPointerException; 506 extern int LdoubNeg, LvaluePosInfLong, LvalueNegInfLong, LvalueNanLong, LshiftMask, Lvalue64, L64bits, LintMax, LintMin; 507 508 extern LabelMap* globalMap; 509 extern LabelMap* globalShortMap; 510 extern LabelMap* globalWorklist; 511 extern LabelMap* globalShortWorklist; 512 extern NCGWorklist* globalNCGWorklist; 513 extern DataWorklist* methodDataWorklist; 514 #ifdef ENABLE_TRACING 515 extern MapWorklist* methodMapWorklist; 516 #endif 517 extern PhysicalReg scratchRegs[4]; 518 519 #define C_SCRATCH_1 scratchRegs[0] 520 #define C_SCRATCH_2 scratchRegs[1] 521 #define C_SCRATCH_3 scratchRegs[2] //scratch reg inside callee 522 523 extern LowOp* ops[BUFFER_SIZE]; 524 extern bool isScratchPhysical; 525 extern u2* rPC; 526 extern u2 inst; 527 extern int offsetPC; 528 extern int offsetNCG; 529 extern int mapFromBCtoNCG[BYTECODE_SIZE_PER_METHOD]; 530 extern char* streamStart; 531 532 extern char* streamCode; 533 534 extern char* streamMethodStart; //start of the method 535 extern char* stream; //current stream pointer 536 extern char* streamMisPred; 537 extern int lowOpTimeStamp; 538 extern Method* currentMethod; 539 extern int currentExceptionBlockIdx; 540 541 extern int globalMapNum; 542 extern int globalWorklistNum; 543 extern int globalDataWorklistNum; 544 extern int globalPCWorklistNum; 545 extern int chainingWorklistNum; 546 extern int VMAPIWorklistNum; 547 548 extern LabelMap* globalDataWorklist; 549 extern LabelMap* globalPCWorklist; 550 extern LabelMap* chainingWorklist; 551 extern LabelMap* VMAPIWorklist; 552 553 extern int ncgClassNum; 554 extern int ncgMethodNum; 555 556 extern LowOp* lirTable[200]; //Number of LIRs for all bytecodes do not exceed 200 557 extern int num_lirs_in_table; 558 559 bool existATryBlock(Method* method, int startPC, int endPC); 560 // interface between register allocator & lowering 561 extern int num_removed_nullCheck; 562 563 int registerAlloc(int type, int reg, bool isPhysical, bool updateRef); 564 int registerAllocMove(int reg, int type, bool isPhysical, int srcReg); 565 int checkVirtualReg(int reg, LowOpndRegType type, int updateRef); //returns the physical register 566 int updateRefCount(int reg, LowOpndRegType type); 567 int updateRefCount2(int reg, int type, bool isPhysical); 568 int spillVirtualReg(int vrNum, LowOpndRegType type, bool updateTable); 569 int isVirtualRegConstant(int regNum, LowOpndRegType type, int* valuePtr, bool updateRef); 570 int checkTempReg(int reg, int type, bool isPhysical, int vA); 571 bool checkTempReg2(int reg, int type, bool isPhysical, int physicalRegForVR); 572 int freeReg(bool spillGL); 573 int nextVersionOfHardReg(PhysicalReg pReg, int refCount); 574 int updateVirtualReg(int reg, LowOpndRegType type); 575 void setVRNullCheck(int regNum, OpndSize size); 576 bool isVRNullCheck(int regNum, OpndSize size); 577 void setVRBoundCheck(int vr_array, int vr_index); 578 bool isVRBoundCheck(int vr_array, int vr_index); 579 int requestVRFreeDelay(int regNum, u4 reason); 580 void cancelVRFreeDelayRequest(int regNum, u4 reason); 581 bool getVRFreeDelayRequested(int regNum); 582 bool isGlueHandled(int glue_reg); 583 void resetGlue(int glue_reg); 584 void updateGlue(int reg, bool isPhysical, int glue_reg); 585 int updateVRAtUse(int reg, LowOpndRegType pType, int regAll); 586 int touchEcx(); 587 int touchEax(); 588 int touchEdx(); 589 int beforeCall(const char* target); 590 int afterCall(const char* target); 591 void startBranch(); 592 void endBranch(); 593 void rememberState(int); 594 void goToState(int); 595 void transferToState(int); 596 void globalVREndOfBB(const Method*); 597 void constVREndOfBB(); 598 void startNativeCode(int num, int type); 599 void endNativeCode(); 600 void donotSpillReg(int physicalReg); 601 void doSpillReg(int physicalReg); 602 603 #define XMM_1 PhysicalReg_XMM0 604 #define XMM_2 PhysicalReg_XMM1 605 #define XMM_3 PhysicalReg_XMM2 606 #define XMM_4 PhysicalReg_XMM3 607 608 ///////////////////////////////////////////////////////////////////////////////// 609 //LR[reg] = disp + PR[base_reg] or disp + LR[base_reg] 610 void load_effective_addr(int disp, int base_reg, bool isBasePhysical, 611 int reg, bool isPhysical); 612 void load_effective_addr_scale(int base_reg, bool isBasePhysical, 613 int index_reg, bool isIndexPhysical, int scale, 614 int reg, bool isPhysical); 615 void load_fpu_cw(int disp, int base_reg, bool isBasePhysical); 616 void store_fpu_cw(bool checkException, int disp, int base_reg, bool isBasePhysical); 617 void convert_integer(OpndSize srcSize, OpndSize dstSize); 618 void load_fp_stack(LowOp* op, OpndSize size, int disp, int base_reg, bool isBasePhysical); 619 void load_int_fp_stack(OpndSize size, int disp, int base_reg, bool isBasePhysical); 620 void load_int_fp_stack_imm(OpndSize size, int imm); 621 void store_fp_stack(LowOp* op, bool pop, OpndSize size, int disp, int base_reg, bool isBasePhysical); 622 void store_int_fp_stack(LowOp* op, bool pop, OpndSize size, int disp, int base_reg, bool isBasePhysical); 623 624 void load_fp_stack_VR(OpndSize size, int vA); 625 void load_int_fp_stack_VR(OpndSize size, int vA); 626 void store_fp_stack_VR(bool pop, OpndSize size, int vA); 627 void store_int_fp_stack_VR(bool pop, OpndSize size, int vA); 628 void compare_VR_ss_reg(int vA, int reg, bool isPhysical); 629 void compare_VR_sd_reg(int vA, int reg, bool isPhysical); 630 void fpu_VR(ALU_Opcode opc, OpndSize size, int vA); 631 void compare_reg_mem(LowOp* op, OpndSize size, int reg, bool isPhysical, 632 int disp, int base_reg, bool isBasePhysical); 633 void compare_mem_reg(OpndSize size, 634 int disp, int base_reg, bool isBasePhysical, 635 int reg, bool isPhysical); 636 void compare_VR_reg(OpndSize size, 637 int vA, 638 int reg, bool isPhysical); 639 void compare_imm_reg(OpndSize size, int imm, 640 int reg, bool isPhysical); 641 void compare_imm_mem(OpndSize size, int imm, 642 int disp, int base_reg, bool isBasePhysical); 643 void compare_imm_VR(OpndSize size, int imm, 644 int vA); 645 void compare_reg_reg(int reg1, bool isPhysical1, 646 int reg2, bool isPhysical2); 647 void compare_reg_reg_16(int reg1, bool isPhysical1, 648 int reg2, bool isPhysical2); 649 void compare_ss_mem_reg(LowOp* op, int disp, int base_reg, bool isBasePhysical, 650 int reg, bool isPhysical); 651 void compare_ss_reg_with_reg(LowOp* op, int reg1, bool isPhysical1, 652 int reg2, bool isPhysical2); 653 void compare_sd_mem_with_reg(LowOp* op, int disp, int base_reg, bool isBasePhysical, 654 int reg, bool isPhysical); 655 void compare_sd_reg_with_reg(LowOp* op, int reg1, bool isPhysical1, 656 int reg2, bool isPhysical2); 657 void compare_fp_stack(bool pop, int reg, bool isDouble); 658 void test_imm_reg(OpndSize size, int imm, int reg, bool isPhysical); 659 void test_imm_mem(OpndSize size, int imm, int disp, int reg, bool isPhysical); 660 661 void conditional_move_reg_to_reg(OpndSize size, ConditionCode cc, int reg1, bool isPhysical1, int reg, bool isPhysical); 662 void move_ss_mem_to_reg(LowOp* op, int disp, int base_reg, bool isBasePhysical, 663 int reg, bool isPhysical); 664 void move_ss_reg_to_mem(LowOp* op, int reg, bool isPhysical, 665 int disp, int base_reg, bool isBasePhysical); 666 LowOpRegMem* move_ss_mem_to_reg_noalloc(int disp, int base_reg, bool isBasePhysical, 667 MemoryAccessType mType, int mIndex, 668 int reg, bool isPhysical); 669 LowOpMemReg* move_ss_reg_to_mem_noalloc(int reg, bool isPhysical, 670 int disp, int base_reg, bool isBasePhysical, 671 MemoryAccessType mType, int mIndex); 672 void move_sd_mem_to_reg(int disp, int base_reg, bool isBasePhysical, 673 int reg, bool isPhysical); 674 void move_sd_reg_to_mem(LowOp* op, int reg, bool isPhysical, 675 int disp, int base_reg, bool isBasePhysical); 676 677 void conditional_jump(ConditionCode cc, const char* target, bool isShortTerm); 678 void unconditional_jump(const char* target, bool isShortTerm); 679 void conditional_jump_int(ConditionCode cc, int target, OpndSize size); 680 void unconditional_jump_int(int target, OpndSize size); 681 void unconditional_jump_reg(int reg, bool isPhysical); 682 void call(const char* target); 683 void call_reg(int reg, bool isPhysical); 684 void call_reg_noalloc(int reg, bool isPhysical); 685 void call_mem(int disp, int reg, bool isPhysical); 686 void x86_return(); 687 688 void alu_unary_reg(OpndSize size, ALU_Opcode opc, int reg, bool isPhysical); 689 void alu_unary_mem(LowOp* op, OpndSize size, ALU_Opcode opc, int disp, int base_reg, bool isBasePhysical); 690 691 void alu_binary_imm_mem(OpndSize size, ALU_Opcode opc, 692 int imm, int disp, int base_reg, bool isBasePhysical); 693 void alu_binary_imm_reg(OpndSize size, ALU_Opcode opc, int imm, int reg, bool isPhysical); 694 void alu_binary_mem_reg(OpndSize size, ALU_Opcode opc, 695 int disp, int base_reg, bool isBasePhysical, 696 int reg, bool isPhysical); 697 void alu_binary_VR_reg(OpndSize size, ALU_Opcode opc, int vA, int reg, bool isPhysical); 698 void alu_sd_binary_VR_reg(ALU_Opcode opc, int vA, int reg, bool isPhysical, bool isSD); 699 void alu_binary_reg_reg(OpndSize size, ALU_Opcode opc, 700 int reg1, bool isPhysical1, 701 int reg2, bool isPhysical2); 702 void alu_binary_reg_mem(OpndSize size, ALU_Opcode opc, 703 int reg, bool isPhysical, 704 int disp, int base_reg, bool isBasePhysical); 705 706 void fpu_mem(LowOp* op, ALU_Opcode opc, OpndSize size, int disp, int base_reg, bool isBasePhysical); 707 void alu_ss_binary_reg_reg(ALU_Opcode opc, int reg, bool isPhysical, 708 int reg2, bool isPhysical2); 709 void alu_sd_binary_reg_reg(ALU_Opcode opc, int reg, bool isPhysical, 710 int reg2, bool isPhysical2); 711 712 void push_mem_to_stack(OpndSize size, int disp, int base_reg, bool isBasePhysical); 713 void push_reg_to_stack(OpndSize size, int reg, bool isPhysical); 714 715 //returns the pointer to end of the native code 716 void move_reg_to_mem(OpndSize size, 717 int reg, bool isPhysical, 718 int disp, int base_reg, bool isBasePhysical); 719 LowOpRegMem* move_mem_to_reg(OpndSize size, 720 int disp, int base_reg, bool isBasePhysical, 721 int reg, bool isPhysical); 722 void movez_mem_to_reg(OpndSize size, 723 int disp, int base_reg, bool isBasePhysical, 724 int reg, bool isPhysical); 725 void movez_reg_to_reg(OpndSize size, 726 int reg, bool isPhysical, 727 int reg2, bool isPhysical2); 728 void moves_mem_to_reg(LowOp* op, OpndSize size, 729 int disp, int base_reg, bool isBasePhysical, 730 int reg, bool isPhysical); 731 void movez_mem_disp_scale_to_reg(OpndSize size, 732 int base_reg, bool isBasePhysical, 733 int disp, int index_reg, bool isIndexPhysical, int scale, 734 int reg, bool isPhysical); 735 void moves_mem_disp_scale_to_reg(OpndSize size, 736 int base_reg, bool isBasePhysical, 737 int disp, int index_reg, bool isIndexPhysical, int scale, 738 int reg, bool isPhysical); 739 void move_reg_to_reg(OpndSize size, 740 int reg, bool isPhysical, 741 int reg2, bool isPhysical2); 742 void move_reg_to_reg_noalloc(OpndSize size, 743 int reg, bool isPhysical, 744 int reg2, bool isPhysical2); 745 void move_mem_scale_to_reg(OpndSize size, 746 int base_reg, bool isBasePhysical, int index_reg, bool isIndexPhysical, int scale, 747 int reg, bool isPhysical); 748 void move_mem_disp_scale_to_reg(OpndSize size, 749 int base_reg, bool isBasePhysical, int disp, int index_reg, bool isIndexPhysical, int scale, 750 int reg, bool isPhysical); 751 void move_reg_to_mem_scale(OpndSize size, 752 int reg, bool isPhysical, 753 int base_reg, bool isBasePhysical, int index_reg, bool isIndexPhysical, int scale); 754 void move_reg_to_mem_disp_scale(OpndSize size, 755 int reg, bool isPhysical, 756 int base_reg, bool isBasePhysical, int disp, int index_reg, bool isIndexPhysical, int scale); 757 void move_imm_to_mem(OpndSize size, int imm, 758 int disp, int base_reg, bool isBasePhysical); 759 void set_VR_to_imm(u2 vA, OpndSize size, int imm); 760 void set_VR_to_imm_noalloc(u2 vA, OpndSize size, int imm); 761 void set_VR_to_imm_noupdateref(LowOp* op, u2 vA, OpndSize size, int imm); 762 void move_imm_to_reg(OpndSize size, int imm, int reg, bool isPhysical); 763 void move_imm_to_reg_noalloc(OpndSize size, int imm, int reg, bool isPhysical); 764 765 //LR[reg] = VR[vB] 766 //or 767 //PR[reg] = VR[vB] 768 void get_virtual_reg(u2 vB, OpndSize size, int reg, bool isPhysical); 769 void get_virtual_reg_noalloc(u2 vB, OpndSize size, int reg, bool isPhysical); 770 //VR[v] = LR[reg] 771 //or 772 //VR[v] = PR[reg] 773 void set_virtual_reg(u2 vA, OpndSize size, int reg, bool isPhysical); 774 void set_virtual_reg_noalloc(u2 vA, OpndSize size, int reg, bool isPhysical); 775 void get_VR_ss(int vB, int reg, bool isPhysical); 776 void set_VR_ss(int vA, int reg, bool isPhysical); 777 void get_VR_sd(int vB, int reg, bool isPhysical); 778 void set_VR_sd(int vA, int reg, bool isPhysical); 779 780 int spill_reg(int reg, bool isPhysical); 781 int unspill_reg(int reg, bool isPhysical); 782 783 void move_reg_to_mem_noalloc(OpndSize size, 784 int reg, bool isPhysical, 785 int disp, int base_reg, bool isBasePhysical, 786 MemoryAccessType mType, int mIndex); 787 LowOpRegMem* move_mem_to_reg_noalloc(OpndSize size, 788 int disp, int base_reg, bool isBasePhysical, 789 MemoryAccessType mType, int mIndex, 790 int reg, bool isPhysical); 791 792 ////////////////////////////////////////////////////////////// 793 int insertLabel(const char* label, bool checkDup); 794 int export_pc(); 795 int simpleNullCheck(int reg, bool isPhysical, int vr); 796 int nullCheck(int reg, bool isPhysical, int exceptionNum, int vr); 797 int handlePotentialException( 798 ConditionCode code_excep, ConditionCode code_okay, 799 int exceptionNum, const char* errName); 800 int get_currentpc(int reg, bool isPhysical); 801 int get_self_pointer(int reg, bool isPhysical); 802 int get_res_strings(int reg, bool isPhysical); 803 int get_res_classes(int reg, bool isPhysical); 804 int get_res_fields(int reg, bool isPhysical); 805 int get_res_methods(int reg, bool isPhysical); 806 int get_glue_method_class(int reg, bool isPhysical); 807 int get_glue_method(int reg, bool isPhysical); 808 int set_glue_method(int reg, bool isPhysical); 809 int get_glue_dvmdex(int reg, bool isPhysical); 810 int set_glue_dvmdex(int reg, bool isPhysical); 811 int get_suspendCount(int reg, bool isPhysical); 812 int get_return_value(OpndSize size, int reg, bool isPhysical); 813 int set_return_value(OpndSize size, int reg, bool isPhysical); 814 int clear_exception(); 815 int get_exception(int reg, bool isPhysical); 816 int set_exception(int reg, bool isPhysical); 817 int save_pc_fp_to_glue(); 818 int savearea_from_fp(int reg, bool isPhysical); 819 820 int call_moddi3(); 821 int call_divdi3(); 822 int call_fmod(); 823 int call_fmodf(); 824 int call_dvmFindCatchBlock(); 825 int call_dvmThrowVerificationError(); 826 int call_dvmAllocObject(); 827 int call_dvmAllocArrayByClass(); 828 int call_dvmResolveMethod(); 829 int call_dvmResolveClass(); 830 int call_dvmInstanceofNonTrivial(); 831 int call_dvmThrow(); 832 int call_dvmThrowWithMessage(); 833 int call_dvmCheckSuspendPending(); 834 int call_dvmLockObject(); 835 int call_dvmUnlockObject(); 836 int call_dvmInitClass(); 837 int call_dvmAllocPrimitiveArray(); 838 int call_dvmInterpHandleFillArrayData(); 839 int call_dvmNcgHandlePackedSwitch(); 840 int call_dvmNcgHandleSparseSwitch(); 841 int call_dvmJitHandlePackedSwitch(); 842 int call_dvmJitHandleSparseSwitch(); 843 int call_dvmJitToInterpTraceSelectNoChain(); 844 int call_dvmJitToPatchPredictedChain(); 845 int call_dvmJitToInterpNormal(); 846 int call_dvmJitToInterpTraceSelect(); 847 int call_dvmQuasiAtomicSwap64(); 848 int call_dvmQuasiAtomicRead64(); 849 int call_dvmCanPutArrayElement(); 850 int call_dvmFindInterfaceMethodInCache(); 851 int call_dvmHandleStackOverflow(); 852 int call_dvmResolveString(); 853 int call_dvmResolveInstField(); 854 int call_dvmResolveStaticField(); 855 856 //labels and branches 857 //shared branch to resolve class: 2 specialized versions 858 //OPTION 1: call & ret 859 //OPTION 2: store jump back label in a fixed register or memory 860 //jump to .class_resolve, then jump back 861 //OPTION 3: share translator code 862 /* global variables: ncg_rPC */ 863 int resolve_class( 864 int startLR/*logical register index*/, bool isPhysical, int tmp/*const pool index*/, 865 int thirdArg); 866 /* EXPORT_PC; movl exceptionPtr, -8(%esp); movl descriptor, -4(%esp); lea; call; lea; jmp */ 867 int throw_exception_message(int exceptionPtr, int obj_reg, bool isPhysical, 868 int startLR/*logical register index*/, bool startPhysical); 869 /* EXPORT_PC; movl exceptionPtr, -8(%esp); movl imm, -4(%esp); lea; call; lea; jmp */ 870 int throw_exception(int exceptionPtr, int imm, 871 int startLR/*logical register index*/, bool startPhysical); 872 873 void freeShortMap(); 874 int insertDataWorklist(s4 relativePC, char* codePtr1); 875 #ifdef ENABLE_TRACING 876 int insertMapWorklist(s4 BCOffset, s4 NCGOffset, int isStartOfPC); 877 #endif 878 int performNCGWorklist(); 879 int performDataWorklist(); 880 void performLabelWorklist(); 881 void performMethodLabelWorklist(); 882 void freeLabelMap(); 883 void performSharedWorklist(); 884 void performChainingWorklist(); 885 void freeNCGWorklist(); 886 void freeDataWorklist(); 887 void freeLabelWorklist(); 888 void freeChainingWorklist(); 889 890 int common_invokeArgsDone(ArgsDoneType form, bool isJitFull); 891 int common_backwardBranch(); 892 int common_exceptionThrown(); 893 int common_errNullObject(); 894 int common_errArrayIndex(); 895 int common_errArrayStore(); 896 int common_errNegArraySize(); 897 int common_errNoSuchMethod(); 898 int common_errDivideByZero(); 899 int common_periodicChecks_entry(); 900 int common_periodicChecks4(); 901 int common_gotoBail(); 902 int common_gotoBail_0(); 903 int common_StringIndexOutOfBounds(); 904 void goto_invokeArgsDone(); 905 906 //lower a bytecode 907 int lowerByteCode(const Method* method); 908 909 int op_nop(); 910 int op_move(); 911 int op_move_from16(); 912 int op_move_16(); 913 int op_move_wide(); 914 int op_move_wide_from16(); 915 int op_move_wide_16(); 916 int op_move_result(); 917 int op_move_result_wide(); 918 int op_move_exception(); 919 920 int op_return_void(); 921 int op_return(); 922 int op_return_wide(); 923 int op_const_4(); 924 int op_const_16(); 925 int op_const(); 926 int op_const_high16(); 927 int op_const_wide_16(); 928 int op_const_wide_32(); 929 int op_const_wide(); 930 int op_const_wide_high16(); 931 int op_const_string(); 932 int op_const_string_jumbo(); 933 int op_const_class(); 934 int op_monitor_enter(); 935 int op_monitor_exit(); 936 int op_check_cast(); 937 int op_instance_of(); 938 939 int op_array_length(); 940 int op_new_instance(); 941 int op_new_array(); 942 int op_filled_new_array(); 943 int op_filled_new_array_range(); 944 int op_fill_array_data(); 945 int op_throw(); 946 int op_throw_verification_error(); 947 int op_goto(); 948 int op_goto_16(); 949 int op_goto_32(); 950 int op_packed_switch(); 951 int op_sparse_switch(); 952 int op_if_ge(); 953 int op_aget(); 954 int op_aget_wide(); 955 int op_aget_object(); 956 int op_aget_boolean(); 957 int op_aget_byte(); 958 int op_aget_char(); 959 int op_aget_short(); 960 int op_aput(); 961 int op_aput_wide(); 962 int op_aput_object(); 963 int op_aput_boolean(); 964 int op_aput_byte(); 965 int op_aput_char(); 966 int op_aput_short(); 967 int op_iget(); 968 int op_iget_wide(bool isVolatile); 969 int op_iget_object(); 970 int op_iget_boolean(); 971 int op_iget_byte(); 972 int op_iget_char(); 973 int op_iget_short(); 974 int op_iput(); 975 int op_iput_wide(bool isVolatile); 976 int op_iput_object(); 977 int op_iput_boolean(); 978 int op_iput_byte(); 979 int op_iput_char(); 980 int op_iput_short(); 981 int op_sget(); 982 int op_sget_wide(bool isVolatile); 983 int op_sget_object(); 984 int op_sget_boolean(); 985 int op_sget_byte(); 986 int op_sget_char(); 987 int op_sget_short(); 988 int op_sput(bool isObj); 989 int op_sput_wide(bool isVolatile); 990 int op_sput_object(); 991 int op_sput_boolean(); 992 int op_sput_byte(); 993 int op_sput_char(); 994 int op_sput_short(); 995 int op_invoke_virtual(); 996 int op_invoke_super(); 997 int op_invoke_direct(); 998 int op_invoke_static(); 999 int op_invoke_interface(); 1000 int op_invoke_virtual_range(); 1001 int op_invoke_super_range(); 1002 int op_invoke_direct_range(); 1003 int op_invoke_static_range(); 1004 int op_invoke_interface_range(); 1005 int op_int_to_long(); 1006 int op_add_long_2addr(); 1007 int op_add_int_lit8(); 1008 int op_cmpl_float(); 1009 int op_cmpg_float(); 1010 int op_cmpl_double(); 1011 int op_cmpg_double(); 1012 int op_cmp_long(); 1013 int op_if_eq(); 1014 int op_if_ne(); 1015 int op_if_lt(); 1016 int op_if_gt(); 1017 int op_if_le(); 1018 int op_if_eqz(); 1019 int op_if_nez(); 1020 int op_if_ltz(); 1021 int op_if_gez(); 1022 int op_if_gtz(); 1023 int op_if_lez(); 1024 int op_neg_int(); 1025 int op_not_int(); 1026 int op_neg_long(); 1027 int op_not_long(); 1028 int op_neg_float(); 1029 int op_neg_double(); 1030 int op_int_to_float(); 1031 int op_int_to_double(); 1032 int op_long_to_int(); 1033 int op_long_to_float(); 1034 int op_long_to_double(); 1035 int op_float_to_int(); 1036 int op_float_to_long(); 1037 int op_float_to_double(); 1038 int op_double_to_int(); 1039 int op_double_to_long(); 1040 int op_double_to_float(); 1041 int op_int_to_byte(); 1042 int op_int_to_char(); 1043 int op_int_to_short(); 1044 int op_add_int(); 1045 int op_sub_int(); 1046 int op_mul_int(); 1047 int op_div_int(); 1048 int op_rem_int(); 1049 int op_and_int(); 1050 int op_or_int(); 1051 int op_xor_int(); 1052 int op_shl_int(); 1053 int op_shr_int(); 1054 int op_ushr_int(); 1055 int op_add_long(); 1056 int op_sub_long(); 1057 int op_mul_long(); 1058 int op_div_long(); 1059 int op_rem_long(); 1060 int op_and_long(); 1061 int op_or_long(); 1062 int op_xor_long(); 1063 int op_shl_long(); 1064 int op_shr_long(); 1065 int op_ushr_long(); 1066 int op_add_float(); 1067 int op_sub_float(); 1068 int op_mul_float(); 1069 int op_div_float(); 1070 int op_rem_float(); 1071 int op_add_double(); 1072 int op_sub_double(); 1073 int op_mul_double(); 1074 int op_div_double(); 1075 int op_rem_double(); 1076 int op_add_int_2addr(); 1077 int op_sub_int_2addr(); 1078 int op_mul_int_2addr(); 1079 int op_div_int_2addr(); 1080 int op_rem_int_2addr(); 1081 int op_and_int_2addr(); 1082 int op_or_int_2addr(); 1083 int op_xor_int_2addr(); 1084 int op_shl_int_2addr(); 1085 int op_shr_int_2addr(); 1086 int op_ushr_int_2addr(); 1087 int op_sub_long_2addr(); 1088 int op_mul_long_2addr(); 1089 int op_div_long_2addr(); 1090 int op_rem_long_2addr(); 1091 int op_and_long_2addr(); 1092 int op_or_long_2addr(); 1093 int op_xor_long_2addr(); 1094 int op_shl_long_2addr(); 1095 int op_shr_long_2addr(); 1096 int op_ushr_long_2addr(); 1097 int op_add_float_2addr(); 1098 int op_sub_float_2addr(); 1099 int op_mul_float_2addr(); 1100 int op_div_float_2addr(); 1101 int op_rem_float_2addr(); 1102 int op_add_double_2addr(); 1103 int op_sub_double_2addr(); 1104 int op_mul_double_2addr(); 1105 int op_div_double_2addr(); 1106 int op_rem_double_2addr(); 1107 int op_add_int_lit16(); 1108 int op_rsub_int(); 1109 int op_mul_int_lit16(); 1110 int op_div_int_lit16(); 1111 int op_rem_int_lit16(); 1112 int op_and_int_lit16(); 1113 int op_or_int_lit16(); 1114 int op_xor_int_lit16(); 1115 int op_rsub_int_lit8(); 1116 int op_mul_int_lit8(); 1117 int op_div_int_lit8(); 1118 int op_rem_int_lit8(); 1119 int op_and_int_lit8(); 1120 int op_or_int_lit8(); 1121 int op_xor_int_lit8(); 1122 int op_shl_int_lit8(); 1123 int op_shr_int_lit8(); 1124 int op_ushr_int_lit8(); 1125 int op_execute_inline(bool isRange); 1126 int op_invoke_object_init_range(); 1127 int op_iget_quick(); 1128 int op_iget_wide_quick(); 1129 int op_iget_object_quick(); 1130 int op_iput_quick(); 1131 int op_iput_wide_quick(); 1132 int op_iput_object_quick(); 1133 int op_invoke_virtual_quick(); 1134 int op_invoke_virtual_quick_range(); 1135 int op_invoke_super_quick(); 1136 int op_invoke_super_quick_range(); 1137 1138 /////////////////////////////////////////////// 1139 void set_reg_opnd(LowOpndReg* op_reg, int reg, bool isPhysical, LowOpndRegType type); 1140 void set_mem_opnd(LowOpndMem* mem, int disp, int base, bool isPhysical); 1141 void set_mem_opnd_scale(LowOpndMem* mem, int base, bool isPhysical, int disp, int index, bool indexPhysical, int scale); 1142 LowOpImm* dump_imm(Mnemonic m, OpndSize size, 1143 int imm); 1144 LowOpNCG* dump_ncg(Mnemonic m, OpndSize size, int imm); 1145 LowOpImm* dump_imm_with_codeaddr(Mnemonic m, OpndSize size, 1146 int imm, char* codePtr); 1147 LowOpImm* dump_special(AtomOpCode cc, int imm); 1148 LowOpMem* dump_mem(Mnemonic m, AtomOpCode m2, OpndSize size, 1149 int disp, int base_reg, bool isBasePhysical); 1150 LowOpReg* dump_reg(Mnemonic m, AtomOpCode m2, OpndSize size, 1151 int reg, bool isPhysical, LowOpndRegType type); 1152 LowOpReg* dump_reg_noalloc(Mnemonic m, OpndSize size, 1153 int reg, bool isPhysical, LowOpndRegType type); 1154 LowOpMemImm* dump_imm_mem_noalloc(Mnemonic m, OpndSize size, 1155 int imm, 1156 int disp, int base_reg, bool isBasePhysical, 1157 MemoryAccessType mType, int mIndex); 1158 LowOpRegReg* dump_reg_reg(Mnemonic m, AtomOpCode m2, OpndSize size, 1159 int reg, bool isPhysical, 1160 int reg2, bool isPhysical2, LowOpndRegType type); 1161 LowOpRegReg* dump_movez_reg_reg(Mnemonic m, OpndSize size, 1162 int reg, bool isPhysical, 1163 int reg2, bool isPhysical2); 1164 LowOpRegMem* dump_mem_reg(Mnemonic m, AtomOpCode m2, OpndSize size, 1165 int disp, int base_reg, bool isBasePhysical, 1166 MemoryAccessType mType, int mIndex, 1167 int reg, bool isPhysical, LowOpndRegType type); 1168 LowOpRegMem* dump_mem_reg_noalloc(Mnemonic m, OpndSize size, 1169 int disp, int base_reg, bool isBasePhysical, 1170 MemoryAccessType mType, int mIndex, 1171 int reg, bool isPhysical, LowOpndRegType type); 1172 LowOpRegMem* dump_mem_scale_reg(Mnemonic m, OpndSize size, 1173 int base_reg, bool isBasePhysical, int disp, int index_reg, bool isIndexPhysical, int scale, 1174 int reg, bool isPhysical, LowOpndRegType type); 1175 LowOpMemReg* dump_reg_mem_scale(Mnemonic m, OpndSize size, 1176 int reg, bool isPhysical, 1177 int base_reg, bool isBasePhysical, int disp, int index_reg, bool isIndexPhysical, int scale, 1178 LowOpndRegType type); 1179 LowOpMemReg* dump_reg_mem(Mnemonic m, AtomOpCode m2, OpndSize size, 1180 int reg, bool isPhysical, 1181 int disp, int base_reg, bool isBasePhysical, 1182 MemoryAccessType mType, int mIndex, LowOpndRegType type); 1183 LowOpMemReg* dump_reg_mem_noalloc(Mnemonic m, OpndSize size, 1184 int reg, bool isPhysical, 1185 int disp, int base_reg, bool isBasePhysical, 1186 MemoryAccessType mType, int mIndex, LowOpndRegType type); 1187 LowOpRegImm* dump_imm_reg(Mnemonic m, AtomOpCode m2, OpndSize size, 1188 int imm, int reg, bool isPhysical, LowOpndRegType type, bool chaining); 1189 LowOpMemImm* dump_imm_mem(Mnemonic m, AtomOpCode m2, OpndSize size, 1190 int imm, 1191 int disp, int base_reg, bool isBasePhysical, 1192 MemoryAccessType mType, int mIndex, bool chaining); 1193 LowOpMemReg* dump_fp_mem(Mnemonic m, OpndSize size, int reg, 1194 int disp, int base_reg, bool isBasePhysical, 1195 MemoryAccessType mType, int mIndex); 1196 LowOpRegMem* dump_mem_fp(Mnemonic m, OpndSize size, 1197 int disp, int base_reg, bool isBasePhysical, 1198 MemoryAccessType mType, int mIndex, 1199 int reg); 1200 LowOpLabel* dump_label(Mnemonic m, OpndSize size, int imm, 1201 const char* label, bool isLocal); 1202 1203 unsigned getJmpCallInstSize(OpndSize size, JmpCall_type type); 1204 bool lowerByteCodeJit(const Method* method, const u2* codePtr, MIR* mir); 1205 void startOfBasicBlock(struct BasicBlock* bb); 1206 extern LowOpBlockLabel* traceLabelList; 1207 extern struct BasicBlock* traceCurrentBB; 1208 extern struct MIR* traceCurrentMIR; 1209 void startOfTrace(const Method* method, LowOpBlockLabel* labelList, int, CompilationUnit*); 1210 void endOfTrace(bool freeOnly); 1211 LowOp* jumpToBasicBlock(char* instAddr, int targetId); 1212 LowOp* condJumpToBasicBlock(char* instAddr, ConditionCode cc, int targetId); 1213 bool jumpToException(const char* target); 1214 int codeGenBasicBlockJit(const Method* method, BasicBlock* bb); 1215 void endOfBasicBlock(struct BasicBlock* bb); 1216 void handleExtendedMIR(CompilationUnit *cUnit, MIR *mir); 1217 int insertChainingWorklist(int bbId, char * codeStart); 1218 void startOfTraceO1(const Method* method, LowOpBlockLabel* labelList, int exceptionBlockId, CompilationUnit *cUnit); 1219 void endOfTraceO1(); 1220 int isPowerOfTwo(int imm); 1221 void move_chain_to_mem(OpndSize size, int imm, 1222 int disp, int base_reg, bool isBasePhysical); 1223 void move_chain_to_reg(OpndSize size, int imm, int reg, bool isPhysical); 1224 1225 void dumpImmToMem(int vrNum, OpndSize size, int value); 1226 bool isInMemory(int regNum, OpndSize size); 1227 int touchEbx(); 1228 int boundCheck(int vr_array, int reg_array, bool isPhysical_array, 1229 int vr_index, int reg_index, bool isPhysical_index, 1230 int exceptionNum); 1231 int getRelativeOffset(const char* target, bool isShortTerm, JmpCall_type type, bool* unknown, 1232 OpndSize* immSize); 1233 int getRelativeNCG(s4 tmp, JmpCall_type type, bool* unknown, OpndSize* size); 1234 void freeAtomMem(); 1235 OpndSize estOpndSizeFromImm(int target); 1236 1237 void preprocessingBB(BasicBlock* bb); 1238 void preprocessingTrace(); 1239 void dump_nop(int size); 1240 #endif 1241