2 * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
4 * MODULE NAME : INDEINS *
6 * 5669-196 (C) COPYRIGHT 1988 Microsoft Corp. *
8 * DESCRIPTIVE NAME: Instructions for the 80386 *
10 * STATUS (LEVEL) : Version (0) Level (1.0) *
12 * FUNCTION : These macros define instructions that are recognized by *
13 * the 80386 but that are not recognized by MASM 3.0. We *
14 * have to create these instructions ourselves because the *
15 * Macro Assembler won't. *
19 * REGISTER USAGE : 80286 Standard *
23 * $MAC(INDEINS) COMP(LOAD) PROD(3270PC) : *
25 * $D0=D0004700 410 870604 D : NEW FOR RELEASE 1.1 *
26 * $P1=P0000311 410 870804 D : RENAME MODULE'S LIBRARY FILE TYPE TO "MAC" *
28 * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
31 ; Some information about creating instructions
33 ; MODIFIER BYTE VALUES
39 ; EAX AX AL 000 DISP0 00
40 ; ECX CX CL 001 DISPB 01
41 ; EDX DX DL 010 DISPW 10
42 ; EBX BX BL 011 DISPR 11
58 ; 00F-000 OPCODE VALUES 00F-001 OPCODE VALUES
59 ; --------------------- ---------------------
73 ; Macros to move to and from the 80386 system registers and to and from the
74 ; new segment registers FS and GS.
77 ; CMOV - Move to and From Control Registers
89 IRP TREG,<CR3,CR2,CR1,CR0>
102 DB 0C0H + _CRCNT*8 + _DREGNUM
104 SYNTAX ERROR - EXTENDED REGISTER EXPECTED
109 IRP TREG,<CR3,CR2,CR1,CR0>
110 IFIDN <®2>,<&TREG>
122 DB 0C0H + _CRCNT*8 + _DREGNUM
124 SYNTAX ERROR - EXTENDED REGISTER EXPECTED
127 SYNTAX ERROR - CONTROL REGISTER EXPECTED
133 ; DMOV - Move to and From Debug Registers
145 IRP TREG,<DR7,DR6,DRX,DRX,DR3,DR2,DR1,DR0>
146 IFIDN <®1>,<&TREG>
158 DB 0C0H + _DRCNT*8 + _DREGNUM
160 SYNTAX ERROR - EXTENDED REGISTER EXPECTED
165 IRP TREG,<DR7,DR6,DRX,DRX,DR3,DR2,DR1,DR0>
166 IFIDN <®2>,<&TREG>
178 DB 0C0H + _DRCNT*8 + _DREGNUM
180 SYNTAX ERROR - EXTENDED REGISTER EXPECTED
183 SYNTAX ERROR - DEBUG REGISTER EXPECTED
188 ; TMOV - Move to and From Test Registers
201 IFIDN <®1>,<&TREG>
214 DB 0C0H + _TRCNT*8 + _DREGNUM
216 SYNTAX ERROR - EXTENDED REGISTER EXPECTED
222 IFIDN <®2>,<&TREG>
235 DB 0C0H + _TRCNT*8 + _DREGNUM
237 SYNTAX ERROR - EXTENDED REGISTER EXPECTED
240 SYNTAX ERROR - TEST REGISTER EXPECTED
245 ; SMOV - Move to/from FS/GS segment registers from/to general registers
292 SYNTAX ERROR - FS OR GS SEGMENT REGISTER EXPECTED
302 SYNTAX ERROR - WORD REGISTER EXPECTED
304 DB 0C0H + _SREGNUM*8 + _WREGNUM
309 F_MOD MACRO TYPE,DISP1,DISP2
312 IRP _TEST_,<DISP32, DISP8>
313 IFIDN <&TYPE>,<&_TEST_>
321 IRP _TEST_,<DISP32, DISP8>
322 IFIDN <&TYPE>,<&_TEST_>
331 SYNTAX ERROR - IMMEDIATE OPERAND EXPECTED
359 MK_IMMD MACRO P2,P3,P4,P5
361 IRP _PARM,<&P2,&P3,&P4,&P5>
379 _IMMDCNT = _IMMDCNT + 1
380 IFIDN <&_PARM>,<IMMD>
388 IRP TREG,<BH,DH,CH,AH,BL,DL,CL,AL>
389 IFIDN <&TBREG>,<&TREG>
392 _BREGNUM = _BREGNUM + 1
396 IRP TREG,<BH,DH,CH,AH,BL,DL,CL,AL>
397 IFIDN <&TDREG>,<&TREG>
400 _BREGNUM = _BREGNUM + 1
408 IRP TREG,<DI,SI,BP,SP,BX,DX,CX,AX>
409 IFIDN <&TWREG>,<&TREG>
412 _WREGNUM = _WREGNUM + 1
416 IRP TREG,<DI,SI,BP,SP,BX,DX,CX,AX>
417 IFIDN <&TWREG>,<&TREG>
420 _WREGNUM = _WREGNUM + 1
428 IRP TREG,<EDI,ESI,EBP,ESP,EBX,EDX,ECX,EAX>
429 IFIDN <&TDREG>,<&TREG>
432 _DREGNUM = _DREGNUM + 1
436 IRP TREG,<EDI,ESI,EBP,ESP,EBX,EDX,ECX,EAX>
437 IFIDN <&TDREG>,<&TREG>
440 _DREGNUM = _DREGNUM + 1
449 IRP TREG,<[EDI],[ESI],[EBP],[ESP],[EBX],[EDX],[ECX],[EAX]>
450 IFIDN <&TBASE>,<&TREG>
458 IRP TREG,<[EDI],[ESI],[EBP],[ESP],[EBX],[EDX],[ECX],[EAX]>
459 IFIDN <&TBASE>,<&TREG>
471 IRP TREG,<[EDI,[ESI,[EBP,_XX_,[EBX,[EDX,[ECX,[EAX>
472 IFIDN <&INDX>,<&TREG>
480 IRP TREG,<[EDI,[ESI,[EBP,_XX_,[EBX,[EDX,[ECX,[EAX>
481 IFIDN <&INDX>,<&TREG>
493 IRP TREG,<*8], *4], *2], *1]>
494 IFIDN <&TSCALE>,<&TREG>
504 ; Macros to PUSH and POP the new segment registers FS and GS
507 ; PUSH_FS - PUSH FS segment register
515 ; PUSH_GS - PUSH GS segment register
523 ; POP_FS - POP FS segment register
531 ; POP_GS - POP GS segment register
540 ; Macros for multiplication instructions
542 ; RIMUL - Uncharacterized Signed Multiply (16-bit)
543 ; Syntax: RIMUL REG,REG/MEM
563 ; ERIMUL - 32 bit Uncharacterized Signed Multiply
564 ; Systax: ERIMUL REG,REG/MEM
566 ERIMUL MACRO REG,OPND
573 ; Macros to load pointers with the segment in FS, GS or SS. That is, these are
574 ; just like the instructions LDS and LES but for the FS, GS and SS registers.
576 NEWLS MACRO OP,REG,OPND
582 LDS ®,DWORD PTR &OPND
596 NEWLS 0B4H,®,<&OPND>
602 NEWLS 0B5H,®,<&OPND>
608 NEWLS 0B2H,®,<&OPND>
611 ; Now we do 32 bit versions of the above
617 NEWLS 0B4H,®,<&OPND>
624 NEWLS 0B5H,®,<&OPND>
631 NEWLS 0B2H,®,<&OPND>
636 ; Macros for some shift instructions
638 ; Shift Left Double R/M, Reg [CL = COUNT] [16-bit Operand]
639 ; SHLD OPND,REG (Double left shift) [CL = COUNT]
642 SHDOP 0A5H,<&OPND>,®
646 ; Shift Right Double R/M, Reg [CL = COUNT] [16-bit Operand]
647 ; SHRD OPND,REG (Double right shift) [CL = COUNT]
650 SHDOP 0ADH,<&OPND>,®
654 ; Shift Left Double R/M, Reg, Immd (8-bit) [16-bit Operand]
655 ; SHLDI OPND,REG,IMMD-8
657 SHLDI MACRO OPND,REG,IMMD
658 SHDOP 0A4H,<&OPND>,®
663 ; Shift Right Double R/M, Reg, Immd (8-bit) [16-bit Operand]
664 ; SHRDI OPND,REG,IMMD-8
666 SHRDI MACRO OPND,REG,IMMD
667 SHDOP 0ACH,<&OPND>,®
671 ; Now 32 bit versions of the above
673 ; Shift Left Double R/M, Reg [CL = COUNT] [32-bit Operand]
674 ; ESHLD OPND,REG (Double left shift) [CL = COUNT]
678 SHDOP 0A5H,<&OPND>,®
682 ; Shift Right Double R/M, Reg [CL = COUNT] [32-bit Operand]
683 ; ESHRD OPND,REG (Double right shift) [CL = COUNT]
687 SHDOP 0ADH,<&OPND>,®
691 ; Shift Left Double R/M, Reg, Immd (8-bit) [32-bit Operand]
692 ; ESHLDI OPND,REG,IMMD-8 (Double left shift)
694 ESHLDI MACRO OPND,REG,IMMD
696 SHDOP 0A4H,<&OPND>,®
701 ; Shift Right Double R/M, Reg, Immd (8-bit) [32-bit Operand]
702 ; ESHRDI OPND,REG,IMMD-8 (Double right shift)
704 ESHRDI MACRO OPND,REG,IMMD
706 SHDOP 0ACH,<&OPND>,®
711 SHDOP MACRO OP,OPND,REG
731 ; The following two instructions, CALLFAR and JUMPFAR, work in the
732 ; MS Macro Assembler, but not for intersegment direct. The assembler
733 ; generates segments based on 8088 values, and we need them based
734 ; on protect-mode selector values. The assembler works just ducky for
735 ; jump and call far indirect, since you go pick up the offset and
736 ; segment at execution time.
738 CALLFAR MACRO DISP,SEGMENT
740 DB 09AH ; Call far direct
741 DW (OFFSET &DISP) ; to this offset
742 DW &SEGMENT ; in this segment
747 JUMPFAR MACRO DISP,SEGMENT
749 DB 0EAH ; Jump far direct
750 DW (OFFSET &DISP) ; to this offset
751 DW &SEGMENT ; in this segment
757 ; Macros for extended jump instructions
759 LJCOND MACRO OP,DISPL
764 DW (OFFSET &DISPL)-(&TEMP)
767 ; LJO DISPL (Long Jump on Overflow)
773 ; LJNO DISPL (Long Jump on NO Overflow)
778 ; LJB DISPL (Long Jump on Below)
783 ; LJC DISPL (Long Jump on Carry)
788 ; LNAE DISPL (Long Jump on Not Above or Equal)
793 ; LJNB DISPL (Long Jump on Not Below)
798 ; LJNC DISPL (Long Jump on No Carry)
803 ; LJAE DISPL (Long Jump on Above or Equal)
808 ; LJE DISPL (Long Jump on Equal)
813 ; LJZ DISPL (Long Jump on Zero)
818 ; LJNE DISPL (Long Jump on Not Equal)
823 ; LJNZ DISPL (Long Jump on Not Zero)
828 ; LJBE DISPL (Long Jump on Below or Equal)
833 ; LJNA DISPL (Long Jump on Not Above)
838 ; LJNBE DISPL (Long Jump on Not Below or Equal)
843 ; LJA DISPL (Long Jump on Above)
848 ; LJS DISPL (Long Jump on Sign)
853 ; LJNS DISPL (Long Jump on No Sign)
858 ; LJP DISPL (Long Jump on Parity)
863 ; LJPE DISPL (Long Jump on Parity Even)
868 ; LJNP DISPL (Long Jump on No Parity)
873 ; LJPO DISPL (Long Jump on Parity Odd)
878 ; LJL DISPL (Long Jump on Less)
883 ; LJNGE DISPL (Long Jump on Not Greater or Equal)
888 ; LJNL DISPL (Long Jump on Not Less)
893 ; LJGE DISPL (Long Jump on Greater than or Equal)
898 ; LJLE DISPL (Long Jump on Less than or Equal)
903 ; LJNG DISPL (Long Jump on Not Greater than)
908 ; LJNLE DISPL (Long Jump on Not Less than or Equal)
913 ; LJG DISPL (Long Jump on Greater than)
918 ; JECXZ DISPL (Jump short on ECX Zero)