|
|
1.1 ! root 1: ////////// ! 2: / n1/i386/tables/leaves.t ! 3: ////////// ! 4: ! 5: ///////// ! 6: / ! 7: / Leaf nodes, fixups, type conversions and casts, ! 8: / all performed by a single table. ! 9: / Table of contents: ! 10: / 1. Loads. ! 11: / 2. Widens. ! 12: / 3. Shrinks. ! 13: / 4. Tests. ! 14: / 5. Function arguments. ! 15: / 6. Cleanups ! 16: / These tables MUST be correct and complete, since they get used ! 17: / to fix up any missing entries in the other tables. ! 18: / Work on them carefully! ! 19: / The compiler is not very good at detecting errors or omissions here. ! 20: / A missing fixup entry usually makes the compiler run out of stack ! 21: / as the code generator calls itself again and again. ! 22: / ! 23: ///////// ! 24: ! 25: CONVERT: ! 26: CAST: ! 27: FIXUP: ! 28: LEAF: ! 29: ! 30: ///////// ! 31: / ! 32: / 1. Loads. ! 33: / ! 34: ///////// ! 35: ! 36: / Load a constant 0 (long, word or byte) or NULL (pointer). ! 37: / The subtract instruction is the shortest and fastest way to zero a register. ! 38: % PVALUE ! 39: NFLT ANYR * * TEMP ! 40: 0|MMX * ! 41: * * ! 42: [ZSUB] [R],[R] ! 43: ! 44: / Load an effective address. ! 45: % PVALUE ! 46: DWORD ANYR * * TEMP ! 47: LEA|MMX DWORD ! 48: * * ! 49: [ZLEA] [R],[NSE AL] ! 50: ! 51: / For the word and byte patterns below, ! 52: / if [AL] is register, e.g. EAX (meaning word AX or byte AL), ! 53: / the generated ZMOV looks wrong (using EAX rather than AX or AL), ! 54: / but it gets cleaned up ex post facto by n2/i386/asm.c/asm(). ! 55: / This is a kludge but at the moment I see no way around it. ! 56: / Load a dword. ! 57: % PVALUE ! 58: DWORD ANYR * * TEMP ! 59: ADR|IMM DWORD ! 60: * * ! 61: / Load a word. ! 62: % PVALUE ! 63: WORD ANYR * * TEMP ! 64: ADR|IMM WORD ! 65: * * ! 66: / Load a byte. ! 67: % PVALUE|PBYTE ! 68: BYTE ANYR * * TEMP ! 69: ADR|IMM BYTE ! 70: * * ! 71: [TN ZMOV] [TN R],[AL] ! 72: ! 73: / DECVAX or IEEE software floating point loads. ! 74: / Double immediate load. ! 75: % PVALUE|PIEEE|PDECVAX ! 76: FF64 EDXEAX * * TEMP ! 77: IMM|MMX FF64 ! 78: * * ! 79: [ZMOV] [HI R],[HI AL] ! 80: [ZMOV] [LO R],[LO AL] ! 81: ! 82: / Double load. ! 83: / The bogus left arg spec EDX prevents EDX from being used ! 84: / for addressing the left arg, which would make the second fetch invalid. ! 85: % PVALUE|PIEEE|PDECVAX ! 86: FF64 EDXEAX EDX * TEMP ! 87: ADR FF64 ! 88: * * ! 89: [ZMOV] [HI R],[HI AL] ! 90: [ZMOV] [LO R],[LO AL] ! 91: ! 92: / The float load actually loads 64 bits. ! 93: / It exists for much the same reasons as the byte and word loads. ! 94: / DECVAX format: 0-extend the float to double. ! 95: % PVALUE|PDECVAX ! 96: FLOAT EDXEAX * * TEMP ! 97: ADR|IMM FF32 ! 98: * * ! 99: [ZMOV] [HI R],[AL] ! 100: [ZMOV] [LO R],[CONST 0] ! 101: ! 102: / IEEE format: convert float to double. ! 103: % PVALUE|PIEEE ! 104: FLOAT EDXEAX * * TEMP ! 105: ADR|IMM FF32 ! 106: * * ! 107: [ZMOV] [LO R],[AL] ! 108: [ZCALL] [GID _dfcvt] ! 109: ! 110: / Floating point loads using the numeric data coprocessor (80x87). ! 111: / Load floating 0. ! 112: % PVALUE|PNDP ! 113: FF64 FPAC * * FPAC ! 114: 0|MMX * ! 115: * * ! 116: [ZFLDZ] ! 117: ! 118: / Load floating 1. ! 119: % PVALUE|PNDP ! 120: FF64 FPAC * * FPAC ! 121: 1|MMX * ! 122: * * ! 123: [ZFLD1] ! 124: ! 125: / General floating point load. ! 126: % PVALUE|PNDP ! 127: FF64 FPAC * * FPAC ! 128: ADR FF64 ! 129: * * ! 130: [ZFLDD] [AL] ! 131: ! 132: ///////// ! 133: / ! 134: / 2. Widens. ! 135: / ! 136: ///////// ! 137: ! 138: / Widen short to dword. ! 139: / If [AL] is register, e.g. EAX (meaning word AX or byte AL), ! 140: / the generated ZMOVSX looks wrong (using EAX rather than AX or AL), ! 141: / but it gets cleaned up ex post facto by n2/i386/asm.c/asm(). ! 142: / This is a kludge but at the moment I see no way around it. ! 143: % PVALUE|PEFFECT ! 144: DWORD ANYR * * TEMP ! 145: ADR SHORT ! 146: * * ! 147: / Widen byte to word. ! 148: % PVALUE|PEFFECT ! 149: WORD ANYR * * TEMP ! 150: ADR BYTE ! 151: * * ! 152: [TL ZMOVSX] [R],[AL] ! 153: ! 154: / DECVAX or IEEE software floating point. ! 155: / Widen signed immediate dword to double. ! 156: % PVALUE|PEFFECT|PDECVAX|PIEEE ! 157: FF64 EDXEAX * * TEMP ! 158: IMM|MMX FS32 ! 159: * * ! 160: [ZMOV] [LO R],[AL] ! 161: [ZCALL] [GID _dicvt] ! 162: ! 163: / Widen signed integer to double. ! 164: % PVALUE|PEFFECT|PDECVAX|PIEEE ! 165: FF64 EDXEAX * * TEMP ! 166: ADR FS8|FS16|FS32 ! 167: * * ! 168: [TL ZMOVSX] [LO R],[AL] ! 169: [ZCALL] [GID _dicvt] ! 170: ! 171: / Widen unsigned immediate dword to double. ! 172: % PVALUE|PEFFECT|PDECVAX|PIEEE ! 173: FF64 EDXEAX * * TEMP ! 174: IMM|MMX FU32|PTX ! 175: * * ! 176: [ZMOV] [LO R],[AL] ! 177: [ZCALL] [GID _ducvt] ! 178: ! 179: / Widen unsigned integer to double. ! 180: % PVALUE|PEFFECT|PDECVAX|PIEEE ! 181: FF64 EDXEAX * * TEMP ! 182: ADR FU8|FU16|FU32|PTX ! 183: * * ! 184: [TL ZMOVZX] [LO R],[AL] ! 185: [ZCALL] [GID _ducvt] ! 186: ! 187: / Widen float to double. ! 188: % PVALUE|PEFFECT|PDECVAX|PIEEE ! 189: FF64 EDXEAX * * TEMP ! 190: ADR|IMM FF32 ! 191: * * ! 192: [ZMOV] [LO R],[AL] ! 193: [ZCALL] [GID _dfcvt] ! 194: ! 195: / Widen to NDP float or double. ! 196: % PVALUE|PNDP ! 197: FLOAT FPAC * * FPAC ! 198: ADR FS16|FS32|FF32 ! 199: * * ! 200: [TL ZFLDD] [AL] ! 201: ! 202: ///////// ! 203: / ! 204: / 3. Shrinks. ! 205: / The word or byte value is simply the LO or LO LO part of the register. ! 206: / ! 207: ///////// ! 208: ! 209: / To word. ! 210: / Immediate to word. ! 211: % PVALUE|PEFFECT ! 212: WORD ANYR * * TEMP ! 213: IMM|MMX DWORD ! 214: * * ! 215: [ZMOVW] [LO R],[LO AL] ! 216: ! 217: / Dword to word. ! 218: % PVALUE|PEFFECT|P_SLT ! 219: WORD ANYR ANYR * TEMP ! 220: TREG DWORD ! 221: * * ! 222: ; ! 223: ! 224: / Direct dword to word. ! 225: % PVALUE|PEFFECT ! 226: WORD ANYR * * TEMP ! 227: DIR|MMX DWORD ! 228: * * ! 229: [ZMOVW] [LO R],[AL] ! 230: ! 231: / Addressible dword to word. ! 232: / Since directs are handled above, the arg must be register. ! 233: % PVALUE|PEFFECT ! 234: WORD ANYR * * TEMP ! 235: ADR DWORD ! 236: * * ! 237: [ZMOV] [R],[AL] ! 238: ! 239: / To byte. ! 240: / Immediate to byte. ! 241: % PVALUE|PEFFECT ! 242: BYTE ANYR * * TEMP ! 243: IMM|MMX DWORD ! 244: * * ! 245: [ZMOVB] [LO LO R],[LO LO AL] ! 246: ! 247: / Dword or word to byte. ! 248: % PVALUE|PEFFECT|P_SLT ! 249: BYTE ANYR ANYR * TEMP ! 250: TREG WORD|DWORD ! 251: * * ! 252: ; ! 253: ! 254: / Direct word or dword to byte. ! 255: % PVALUE|PEFFECT ! 256: BYTE ANYR * * TEMP ! 257: DIR|MMX WORD|DWORD ! 258: * * ! 259: [ZMOVB] [LO LO R],[AL] ! 260: ! 261: / Addressible word or dword to byte. ! 262: / Since directs are handled above, the arg must be register. ! 263: % PVALUE|PEFFECT ! 264: BYTE ANYR * * TEMP ! 265: ADR WORD|DWORD ! 266: * * ! 267: [ZMOV] [R],[AL] ! 268: ! 269: / IEEE or DECVAX software floating point. ! 270: / The bogus left arg spec EDX prevents EDX from being used ! 271: / for addressing the left arg, which would make the second fetch invalid. ! 272: / Shrink double to signed long integer. ! 273: % PVALUE|PEFFECT|PDECVAX|PIEEE ! 274: FS32 EDXEAX EDX * EAX ! 275: ADR|IMM FF64 ! 276: * * ! 277: [ZMOV] [REGNO EDX], [HI AL] ! 278: [ZMOV] [REGNO EAX], [LO AL] ! 279: [ZCALL] [GID _idcvt] ! 280: ! 281: / Shrink double to signed word or byte. ! 282: / Cf. comment above re EDX. ! 283: % PVALUE|PEFFECT|PDECVAX|PIEEE ! 284: FS16|FS8 EDXEAX EDX * EAX ! 285: ADR|IMM FF64 ! 286: * * ! 287: [ZMOV] [REGNO EDX], [HI AL] ! 288: [ZMOV] [REGNO EAX], [LO AL] ! 289: [ZCALL] [GID _idcvt] ! 290: [TN ZMOVSX] [REGNO EAX], [TN REGNO EAX] ! 291: ! 292: / Shrink double to unsigned long integer or pointer. ! 293: / Cf. comment above re EDX. ! 294: % PVALUE|PEFFECT|PDECVAX|PIEEE ! 295: FU32|PTX EDXEAX EDX * EAX ! 296: ADR|IMM FF64 ! 297: * * ! 298: [ZMOV] [REGNO EDX], [HI AL] ! 299: [ZMOV] [REGNO EAX], [LO AL] ! 300: [ZCALL] [GID _udcvt] ! 301: ! 302: / Shrink double to unsigned long word or byte. ! 303: / Cf. comment above re EDX. ! 304: % PVALUE|PEFFECT|PDECVAX|PIEEE ! 305: FU16|FU8 EDXEAX EDX * EAX ! 306: ADR|IMM FF64 ! 307: * * ! 308: [ZMOV] [REGNO EDX], [HI AL] ! 309: [ZMOV] [REGNO EAX], [LO AL] ! 310: [ZCALL] [GID _udcvt] ! 311: [TN ZMOVZX] [REGNO EAX], [TN REGNO EAX] ! 312: ! 313: / Shrink float to signed long integer. ! 314: % PVALUE|PEFFECT|PDECVAX|PIEEE ! 315: FS32 EAX * * TEMP ! 316: ADR|IMM FF32 ! 317: * * ! 318: [ZMOV] [R], [AL] ! 319: [ZCALL] [GID _ifcvt] ! 320: ! 321: / Shrink float to signed word or byte. ! 322: % PVALUE|PEFFECT|PDECVAX|PIEEE ! 323: FS16|FS8 EAX * * TEMP ! 324: ADR|IMM FF32 ! 325: * * ! 326: [ZMOV] [R], [AL] ! 327: [ZCALL] [GID _ifcvt] ! 328: [TN ZMOVSX] [R], [TN R] ! 329: ! 330: / Shrink float to unsigned long integer or pointer. ! 331: % PVALUE|PEFFECT|PDECVAX|PIEEE ! 332: FU32|PTX EAX * * TEMP ! 333: ADR|IMM FF32 ! 334: * * ! 335: [ZMOV] [R], [AL] ! 336: [ZCALL] [GID _ufcvt] ! 337: ! 338: / Shrink float to unsigned word or byte. ! 339: % PVALUE|PEFFECT|PDECVAX|PIEEE ! 340: FU16|FU8 EAX * * TEMP ! 341: ADR|IMM FF32 ! 342: * * ! 343: [ZMOV] [R], [AL] ! 344: [ZCALL] [GID _ufcvt] ! 345: [TN ZMOVZX] [R], [TN R] ! 346: ! 347: ///////// ! 348: / ! 349: / 4. Test contexts. ! 350: / These handle checking of leaf nodes and transform the result ! 351: / of a PVALUE match into a match that generates a jump. ! 352: / ! 353: ///////// ! 354: ! 355: / Register. ! 356: / Long. ! 357: % PSREL ! 358: LONG NONE * * NONE ! 359: REG|MMX LONG ! 360: * * ! 361: / Pointer (equality only). ! 362: % PEREL ! 363: PTX * * * NONE ! 364: REG|MMX PTX ! 365: * * ! 366: [ZOR] [AL],[AL] ! 367: [REL0] [LAB] ! 368: ! 369: / Addressible. ! 370: / Long. ! 371: % PSREL ! 372: LONG NONE * * NONE ! 373: ADR LONG ! 374: * * ! 375: / Pointer. ! 376: % PREL ! 377: PTX NONE * * NONE ! 378: ADR PTX ! 379: * * ! 380: [ZCMP] [AL],[CONST 0] ! 381: [REL0] [LAB] ! 382: ! 383: / Short. ! 384: % PSREL ! 385: * NONE * * NONE ! 386: ADR SHORT ! 387: * * ! 388: [TL ZCMP] [AL],[CONST 0] ! 389: [REL0] [LAB] ! 390: ! 391: / Unsigned >= is always true. ! 392: % PUGE ! 393: * NONE * * NONE ! 394: * * ! 395: * * ! 396: [ZJMP] [LAB] ! 397: ! 398: / Unsigned < is always false. ! 399: % PULT ! 400: * NONE * * NONE ! 401: * * ! 402: * * ! 403: ; ! 404: ! 405: / Long. ! 406: % PSREL ! 407: LONG NONE ANYR * NONE ! 408: TREG LONG ! 409: * * ! 410: / Pointer. ! 411: % PREL ! 412: PTX NONE ANYR * NONE ! 413: TREG PTX ! 414: * * ! 415: [ZOR] [RL],[RL] ! 416: [REL0] [LAB] ! 417: ! 418: / Double, IEEE software floating point. ! 419: % PREL|PIEEE ! 420: FF64 NONE * * NONE ! 421: ADR FF64 ! 422: * * ! 423: [ZTEST] [HI AL],[CONST 0x7FF00000] ! 424: [REL0] [LAB] ! 425: ! 426: / Double, DECVAX software floating point. ! 427: % PREL|PDECVAX ! 428: FF64 NONE * * NONE ! 429: ADR FF64 ! 430: * * ! 431: [ZTEST] [HI AL],[CONST 0x7F800000] ! 432: [REL0] [LAB] ! 433: ! 434: / Float, IEEE or DECVAX software floating point. ! 435: % PREL|PIEEE|PDECVAX ! 436: FLOAT NONE * * NONE ! 437: ADR FF32 ! 438: * * ! 439: [ZTEST] [AL],[CONST 0x7F800000] ! 440: [REL0] [LAB] ! 441: ! 442: / NDP floating point. ! 443: % PREL|PNDP ! 444: FF64 * * * NONE ! 445: REG|MMX FF64 ! 446: * * ! 447: [ZCALL] [GID _tstccp] ! 448: [REL0] [LAB] ! 449: ! 450: ///////// ! 451: / ! 452: / 5. Push function arguments onto the stack. ! 453: / ! 454: ///////// ! 455: ! 456: / Effective address. ! 457: % PFNARG ! 458: DWORD ANYR * * NONE ! 459: LEA|MMX DWORD ! 460: * * ! 461: [ZLEA] [R],[NSE AL] ! 462: [ZPUSH] [R] ! 463: ! 464: / Immediate. ! 465: % PFNARG ! 466: DWORD NONE * * NONE ! 467: IMM|MMX DWORD ! 468: * * ! 469: / Addressible. ! 470: % PFNARG ! 471: DWORD NONE * * NONE ! 472: ADR DWORD ! 473: * * ! 474: [ZPUSH] [AL] ! 475: ! 476: ////////// ! 477: / Floating point. ! 478: ////////// ! 479: ! 480: / IEEE or DECVAX software fp. ! 481: / Push FPAC. ! 482: % PFNARG|PIEEE|PDECVAX ! 483: FF64 EDXEAX EDXEAX * NONE ! 484: REG|MMX FF64 ! 485: * * ! 486: [ZPUSH] [HI RL] ! 487: [ZPUSH] [LO RL] ! 488: ! 489: / Push addressible double. ! 490: % PFNARG|PIEEE|PDECVAX ! 491: FF64 NONE * * NONE ! 492: ADR FF64 ! 493: * * ! 494: [ZPUSH] [HI AL] ! 495: [ZPUSH] [LO AL] ! 496: ! 497: / Hardware coprocessor (NDP) floating point. ! 498: / Push direct double. ! 499: / The fwait is required to assure completion of any pending NDP operation, ! 500: / notably a store into the location being pushed. ! 501: % PFNARG|PNDP ! 502: FF64 NONE * * NONE ! 503: DIR|MMX FF64 ! 504: * * ! 505: [ZFWAIT] ! 506: [ZPUSH] [HI AL] ! 507: [ZPUSH] [LO AL] ! 508: ! 509: / Push double from NDP stacktop. ! 510: % PFNARG|PNDP ! 511: FF64 NONE * * NONE ! 512: REG|MMX FF64 ! 513: * * ! 514: [ZCALL] [GID _dp87] ! 515: ! 516: //////// ! 517: / ! 518: / 6. Miscellaneous cleanups. ! 519: / Transform value contexts into effect contexts. ! 520: / The empty entries are needed because a CALL node always produces a value. ! 521: / ! 522: //////// ! 523: ! 524: / Ignore structs used for effect. ! 525: % PEFFECT ! 526: FBLK NONE * * NONE ! 527: ADR|IMM FBLK ! 528: * * ! 529: ; ! 530: ! 531: / Ignore dword, word, byte for effect. ! 532: % PEFFECT ! 533: NFLT NONE * * NONE ! 534: REG|MMX NFLT ! 535: * * ! 536: ; ! 537: ! 538: / Ignore software fp double for effect. ! 539: % PEFFECT|PIEEE|PDECVAX ! 540: FF64 NONE * * NONE ! 541: REG|MMX FF64 ! 542: * * ! 543: ; ! 544: ! 545: / Clean the 80x87 stack. ! 546: % PEFFECT|PNDP ! 547: FF64 NONE * * NONE ! 548: REG|MMX FF64 ! 549: * * ! 550: [ZFDROP] ! 551: ! 552: ////////// ! 553: / end of n1/i386/tables/leaves.t ! 554: //////////
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.