machine_x86.cpp 5.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148
  1. #include "machine_x86.h"
  2. #include "msvc_fixes.h"
  3. #include "icode.h"
  4. #include <cassert>
  5. // Index registers **** temp solution
  6. static const std::string regNames[] = {
  7. "undef",
  8. "ax", "cx", "dx", "bx",
  9. "sp", "bp", "si", "di",
  10. "es", "cs", "ss", "ds",
  11. "al", "cl", "dl", "bl",
  12. "ah", "ch", "dh", "bh",
  13. "tmp","tmp2",
  14. "bx+si", "bx+di", "bp+si", "bp+di",
  15. "si", "di", "bp", "bx"
  16. };
  17. /* uint8_t and uint16_t registers */
  18. Machine_X86::Machine_X86()
  19. {
  20. static_assert((sizeof(regNames)/sizeof(std::string))==LAST_REG,
  21. "Reg count not equal number of strings");
  22. }
  23. const std::string &Machine_X86::regName(eReg r)
  24. {
  25. assert(r<(sizeof(regNames)/sizeof(std::string)));
  26. return regNames[r];
  27. }
  28. static const std::string szOps[] =
  29. {
  30. "CBW", "AAA", "AAD", "AAM", "AAS", "ADC", "ADD", "AND",
  31. "BOUND","CALL", "CALL", "CLC", "CLD", "CLI", "CMC", "CMP",
  32. "CMPS", "REPNE CMPS","REPE CMPS","DAA", "DAS", "DEC", "DIV", "ENTER",
  33. "ESC", "HLT", "IDIV", "IMUL", "IN", "INC", "INS", "REP INS",
  34. "INT", "IRET", "JB", "JBE", "JAE", "JA", "JE", "JNE",
  35. "JL", "JGE", "JLE", "JG", "JS", "JNS", "JO", "JNO",
  36. "JP", "JNP", "JCXZ", "JMP", "JMP", "LAHF", "LDS", "LEA",
  37. "LEAVE","LES", "LOCK", "LODS", "REP LODS", "LOOP", "LOOPE","LOOPNE",
  38. "MOV", "MOVS", "REP MOVS", "MUL", "NEG", "NOT", "OR", "OUT",
  39. "OUTS", "REP OUTS", "POP", "POPA", "POPF", "PUSH", "PUSHA","PUSHF",
  40. "RCL", "RCR", "ROL", "ROR", "RET", "RETF", "SAHF", "SAR",
  41. "SHL", "SHR", "SBB", "SCAS", "REPNE SCAS","REPE SCAS", "CWD", "STC",
  42. "STD", "STI", "STOS", "REP STOS", "SUB", "TEST", "WAIT", "XCHG",
  43. "XLAT", "XOR", "INTO", "NOP", "REPNE", "REPE", "MOD"
  44. };
  45. /* The following opcodes are for mod != 3 */
  46. static std::string szFlops1[] =
  47. {
  48. /* 0 1 2 3 4 5 6 7 */
  49. "FADD", "FMUL", "FCOM", "FCOMP", "FSUB", "FSUBR", "FDIV", "FDIVR", /* 00 */
  50. "FLD", "???", "FST", "???", "FLDENV","FLDCW", "FSTENV","FSTSW", /* 08 */
  51. "FIADD", "FIMUL", "FICOM","FICOMP","FISUB", "FISUBR","FIDIV", "FIDIVR", /* 10 */
  52. "FILD", "???", "FIST", "FISTP", "???", "???", "???", "FSTP", /* 18 */
  53. "FADD", "FMUL", "FCOM", "FCOMP", "FSUB", "FSUBR", "FDIV", "FDIVR", /* 20 */
  54. "FLD", "FLD", "FST", "FSTP", "FRESTOR","???", "FSAVE", "FSTSW", /* 28 */
  55. "FIADD", "FIMUL", "FICOM","FICOMP","FISUB", "FISUBR","FIDIV", "FIDIVR", /* 30 */
  56. "FILD", "???", "FIST", "FISTP", "FBLD", "???", "FBSTP", "FISTP" /* 38 */
  57. };
  58. /* The following opcodes are for mod == 3 */
  59. static std::string szFlops2[] =
  60. {
  61. /* 0 1 2 3 4 5 6 7 */
  62. "FADD", "FMUL", "FCOM", "FCOMP", "FSUB", "FSUBR", "FDIV", "FDIVR", /* 00 */
  63. "FLD", "FXCH", "FNOP", "???", "", "", "", "", /* 08 */
  64. "FIADD", "FIMUL", "FICOM","FICOMP","FISUB", "", "FIDIV", "FIDIVR", /* 10 */
  65. "FILD", "???", "FIST", "FISTP", "???", "???", "???", "FSTP", /* 18 */
  66. "FADD", "FMUL", "FCOM", "FCOMP", "FSUB", "FSUBR", "FDIV", "FDIVR", /* 20 */
  67. "FFREE", "FSTP", "FST", "???", "FUCOM", "FUCOMP","???", "???", /* 28 */
  68. "FADDP", "FMULP", "FICOM","", "FSUBRP","FISUBR","FDIVRP","FDIVP", /* 30 */
  69. "FILD", "???", "FIST", "FISTP", "", "???", "FBSTP", "FISTP" /* 38 */
  70. };
  71. const std::string &Machine_X86::opcodeName(unsigned r)
  72. {
  73. assert(r<(sizeof(szOps)/sizeof(std::string)));
  74. return szOps[r];
  75. }
  76. const std::string &Machine_X86::floatOpName(unsigned r)
  77. {
  78. if(r>=(sizeof(szFlops1)/sizeof(std::string)))
  79. {
  80. r-= (sizeof(szFlops1)/sizeof(std::string));
  81. assert(r<(sizeof(szFlops2)/sizeof(std::string)));
  82. return szFlops2[r];
  83. }
  84. return szFlops1[r];
  85. }
  86. bool Machine_X86::physicalReg(eReg r)
  87. {
  88. return (r>=rAX) and (r<rTMP);
  89. }
  90. bool Machine_X86::isMemOff(eReg r)
  91. {
  92. return r == 0 or r >= INDEX_BX_SI;
  93. }
  94. //TODO: Move these to Machine_X86
  95. eReg Machine_X86::subRegH(eReg reg)
  96. {
  97. return eReg((int)reg + (int)rAH-(int)rAX);
  98. }
  99. eReg Machine_X86::subRegL(eReg reg)
  100. {
  101. return eReg((int)reg + (int)rAL-(int)rAX);
  102. }
  103. bool Machine_X86::isSubRegisterOf(eReg reg,eReg parent)
  104. {
  105. if ((parent < rAX) or (parent > rBX))
  106. return false; // only AX -> BX are coverede by subregisters
  107. return ((reg==subRegH(parent)) or (reg == subRegL(parent)));
  108. }
  109. bool Machine_X86::hasSubregisters(eReg reg)
  110. {
  111. return ((reg >= rAX) and (reg <= rBX));
  112. }
  113. bool Machine_X86::isPartOfComposite(eReg reg)
  114. {
  115. return ((reg >= rAL) and (reg <= rBH));
  116. }
  117. eReg Machine_X86::compositeParent(eReg reg)
  118. {
  119. switch(reg)
  120. {
  121. case rAL: case rAH: return rAX;
  122. case rCL: case rCH: return rCX;
  123. case rDL: case rDH: return rDX;
  124. case rBL: case rBH: return rBX;
  125. default:
  126. return rUNDEF;
  127. }
  128. return rUNDEF;
  129. }
  130. void Machine_X86::writeRegVector (std::ostream &ostr,const LivenessSet &regi)
  131. {
  132. int j;
  133. for (j = rAX; j < INDEX_BX_SI; j++)
  134. {
  135. if (regi.testReg(j))
  136. ostr << regName(eReg(j))<<" ";
  137. }
  138. }