1 /* assemble.c code generation for the Netwide Assembler
3 * The Netwide Assembler is copyright (C) 1996 Simon Tatham and
4 * Julian Hall. All rights reserved. The software is
5 * redistributable under the license given in the file "LICENSE"
6 * distributed in the NASM archive.
8 * the actual codes (C syntax, i.e. octal):
9 * \0 - terminates the code. (Unless it's a literal of course.)
10 * \1, \2, \3 - that many literal bytes follow in the code stream
11 * \4, \6 - the POP/PUSH (respectively) codes for CS, DS, ES, SS
12 * (POP is never used for CS) depending on operand 0
13 * \5, \7 - the second byte of POP/PUSH codes for FS, GS, depending
15 * \10..\13 - a literal byte follows in the code stream, to be added
16 * to the register value of operand 0..3
17 * \14..\17 - a signed byte immediate operand, from operand 0..3
18 * \20..\23 - a byte immediate operand, from operand 0..3
19 * \24..\27 - an unsigned byte immediate operand, from operand 0..3
20 * \30..\33 - a word immediate operand, from operand 0..3
21 * \34..\37 - select between \3[0-3] and \4[0-3] depending on 16/32 bit
22 * assembly mode or the operand-size override on the operand
23 * \40..\43 - a long immediate operand, from operand 0..3
24 * \44..\47 - select between \3[0-3], \4[0-3] and \5[4-7]
25 * depending on the address size of the instruction.
26 * \50..\53 - a byte relative operand, from operand 0..3
27 * \54..\57 - a qword immediate operand, from operand 0..3
28 * \60..\63 - a word relative operand, from operand 0..3
29 * \64..\67 - select between \6[0-3] and \7[0-3] depending on 16/32 bit
30 * assembly mode or the operand-size override on the operand
31 * \70..\73 - a long relative operand, from operand 0..3
32 * \74..\77 - a word constant, from the _segment_ part of operand 0..3
33 * \1ab - a ModRM, calculated on EA in operand a, with the spare
34 * field the register value of operand b.
35 * \140..\143 - an immediate word or signed byte for operand 0..3
36 * \144..\147 - or 2 (s-field) into opcode byte if operand 0..3
37 * is a signed byte rather than a word. Opcode byte follows.
38 * \150..\153 - an immediate dword or signed byte for operand 0..3
39 * \154..\157 - or 2 (s-field) into opcode byte if operand 0..3
40 * is a signed byte rather than a dword. Opcode byte follows.
41 * \160..\163 - this instruction uses DREX rather than REX, with the
42 * OC0 field set to 0, and the dest field taken from
44 * \164..\167 - this instruction uses DREX rather than REX, with the
45 * OC0 field set to 1, and the dest field taken from
47 * \171 - placement of DREX suffix in the absence of an EA
48 * \172\ab - the register number from operand a in bits 7..4, with
49 * the 4-bit immediate from operand b in bits 3..0.
50 * \173\xab - the register number from operand a in bits 7..4, with
51 * the value b in bits 3..0.
52 * \174\a - the register number from operand a in bits 7..4, and
53 * an arbitrary value in bits 3..0 (assembled as zero.)
54 * \2ab - a ModRM, calculated on EA in operand a, with the spare
55 * field equal to digit b.
56 * \250..\253 - same as \150..\153, except warn if the 64-bit operand
57 * is not equal to the truncated and sign-extended 32-bit
58 * operand; used for 32-bit immediates in 64-bit mode.
59 * \260..\263 - this instruction uses VEX rather than REX, with the
60 * V field taken from operand 0..3.
61 * \270 - this instruction uses VEX rather than REX, with the
62 * V field set to 1111b.
64 * VEX prefixes are followed by the sequence:
65 * \mm\wlp where mm is the M field; and wlp is:
67 * [w0] ww = 0 for W = 0
68 * [w1] ww = 1 for W = 1
69 * [wx] ww = 2 for W don't care (always assembled as 0)
70 * [ww] ww = 3 for W used as REX.W
73 * \310 - indicates fixed 16-bit address size, i.e. optional 0x67.
74 * \311 - indicates fixed 32-bit address size, i.e. optional 0x67.
75 * \312 - (disassembler only) marker on LOOP, LOOPxx instructions.
76 * \313 - indicates fixed 64-bit address size, 0x67 invalid.
77 * \314 - (disassembler only) invalid with REX.B
78 * \315 - (disassembler only) invalid with REX.X
79 * \316 - (disassembler only) invalid with REX.R
80 * \317 - (disassembler only) invalid with REX.W
81 * \320 - indicates fixed 16-bit operand size, i.e. optional 0x66.
82 * \321 - indicates fixed 32-bit operand size, i.e. optional 0x66.
83 * \322 - indicates that this instruction is only valid when the
84 * operand size is the default (instruction to disassembler,
85 * generates no code in the assembler)
86 * \323 - indicates fixed 64-bit operand size, REX on extensions only.
87 * \324 - indicates 64-bit operand size requiring REX prefix.
88 * \330 - a literal byte follows in the code stream, to be added
89 * to the condition code value of the instruction.
90 * \331 - instruction not valid with REP prefix. Hint for
91 * disassembler only; for SSE instructions.
92 * \332 - REP prefix (0xF2 byte) used as opcode extension.
93 * \333 - REP prefix (0xF3 byte) used as opcode extension.
94 * \334 - LOCK prefix used instead of REX.R
95 * \335 - disassemble a rep (0xF3 byte) prefix as repe not rep.
96 * \340 - reserve <operand 0> bytes of uninitialized storage.
97 * Operand 0 had better be a segmentless constant.
98 * \360 - no SSE prefix (== \364\331)
99 * \361 - 66 SSE prefix (== \366\331)
100 * \362 - F2 SSE prefix (== \364\332)
101 * \363 - F3 SSE prefix (== \364\333)
102 * \364 - operand-size prefix (0x66) not permitted
103 * \365 - address-size prefix (0x67) not permitted
104 * \366 - operand-size prefix (0x66) used as opcode extension
105 * \367 - address-size prefix (0x67) used as opcode extension
106 * \370,\371,\372 - match only if operand 0 meets byte jump criteria.
107 * 370 is used for Jcc, 371 is used for JMP.
108 * \373 - assemble 0x03 if bits==16, 0x05 if bits==32;
109 * used for conditional jump over longer jump
112 #include "compiler.h"
116 #include <inttypes.h>
120 #include "assemble.h"
124 /* Initialized to zero by the C standard */
125 static const uint8_t const_zero_buf
[256];
128 int sib_present
; /* is a SIB byte necessary? */
129 int bytes
; /* # of bytes of offset needed */
130 int size
; /* lazy - this is sib+bytes+1 */
131 uint8_t modrm
, sib
, rex
, rip
; /* the bytes themselves */
134 static uint32_t cpu
; /* cpu level received from nasm.c */
135 static efunc errfunc
;
136 static struct ofmt
*outfmt
;
137 static ListGen
*list
;
139 static int64_t calcsize(int32_t, int64_t, int, insn
*, const uint8_t *);
140 static void gencode(int32_t, int64_t, int, insn
*, const uint8_t *, int64_t);
141 static int matches(const struct itemplate
*, insn
*, int bits
);
142 static int32_t regflag(const operand
*);
143 static int32_t regval(const operand
*);
144 static int rexflags(int, int32_t, int);
145 static int op_rexflags(const operand
*, int);
146 static ea
*process_ea(operand
*, ea
*, int, int, int, int32_t);
147 static void add_asp(insn
*, int);
149 static int has_prefix(insn
* ins
, enum prefix_pos pos
, enum prefixes prefix
)
151 return ins
->prefixes
[pos
] == prefix
;
154 static void assert_no_prefix(insn
* ins
, enum prefix_pos pos
)
156 if (ins
->prefixes
[pos
])
157 errfunc(ERR_NONFATAL
, "invalid %s prefix",
158 prefix_name(ins
->prefixes
[pos
]));
161 static const char *size_name(int size
)
183 static void warn_overflow(int size
, int64_t data
)
186 int64_t lim
= ((int64_t)1 << (size
*8))-1;
188 if (data
< ~lim
|| data
> lim
)
189 errfunc(ERR_WARNING
| ERR_WARN_NOV
,
190 "%s data exceeds bounds", size_name(size
));
194 * This routine wrappers the real output format's output routine,
195 * in order to pass a copy of the data off to the listing file
196 * generator at the same time.
198 static void out(int64_t offset
, int32_t segto
, const void *data
,
199 enum out_type type
, uint64_t size
,
200 int32_t segment
, int32_t wrt
)
202 static int32_t lineno
= 0; /* static!!! */
203 static char *lnfname
= NULL
;
206 if (type
== OUT_ADDRESS
&& segment
== NO_SEG
&& wrt
== NO_SEG
) {
208 * This is a non-relocated address, and we're going to
209 * convert it into RAWDATA format.
214 errfunc(ERR_PANIC
, "OUT_ADDRESS with size > 8");
218 WRITEADDR(q
, *(int64_t *)data
, size
);
223 list
->output(offset
, data
, type
, size
);
226 * this call to src_get determines when we call the
227 * debug-format-specific "linenum" function
228 * it updates lineno and lnfname to the current values
229 * returning 0 if "same as last time", -2 if lnfname
230 * changed, and the amount by which lineno changed,
231 * if it did. thus, these variables must be static
234 if (src_get(&lineno
, &lnfname
)) {
235 outfmt
->current_dfmt
->linenum(lnfname
, lineno
, segto
);
238 outfmt
->output(segto
, data
, type
, size
, segment
, wrt
);
241 static int jmp_match(int32_t segment
, int64_t offset
, int bits
,
242 insn
* ins
, const uint8_t *code
)
247 if (c
!= 0370 && c
!= 0371)
249 if (ins
->oprs
[0].opflags
& OPFLAG_FORWARD
) {
250 if ((optimizing
< 0 || (ins
->oprs
[0].type
& STRICT
))
254 return (pass0
== 0); /* match a forward reference */
256 isize
= calcsize(segment
, offset
, bits
, ins
, code
);
257 if (ins
->oprs
[0].segment
!= segment
)
259 isize
= ins
->oprs
[0].offset
- offset
- isize
; /* isize is now the delta */
260 if (isize
>= -128L && isize
<= 127L)
261 return 1; /* it is byte size */
266 int64_t assemble(int32_t segment
, int64_t offset
, int bits
, uint32_t cp
,
267 insn
* instruction
, struct ofmt
*output
, efunc error
,
270 const struct itemplate
*temp
;
275 int64_t start
= offset
;
276 int64_t wsize
= 0; /* size for DB etc. */
278 errfunc
= error
; /* to pass to other functions */
280 outfmt
= output
; /* likewise */
281 list
= listgen
; /* and again */
283 switch (instruction
->opcode
) {
313 int32_t t
= instruction
->times
;
316 "instruction->times < 0 (%ld) in assemble()", t
);
318 while (t
--) { /* repeat TIMES times */
319 for (e
= instruction
->eops
; e
; e
= e
->next
) {
320 if (e
->type
== EOT_DB_NUMBER
) {
322 if (e
->segment
!= NO_SEG
)
323 errfunc(ERR_NONFATAL
,
324 "one-byte relocation attempted");
326 uint8_t out_byte
= e
->offset
;
327 out(offset
, segment
, &out_byte
,
328 OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
330 } else if (wsize
> 8) {
331 errfunc(ERR_NONFATAL
,
332 "integer supplied to a DT, DO or DY"
335 out(offset
, segment
, &e
->offset
,
336 OUT_ADDRESS
, wsize
, e
->segment
, e
->wrt
);
338 } else if (e
->type
== EOT_DB_STRING
||
339 e
->type
== EOT_DB_STRING_FREE
) {
342 out(offset
, segment
, e
->stringval
,
343 OUT_RAWDATA
, e
->stringlen
, NO_SEG
, NO_SEG
);
344 align
= e
->stringlen
% wsize
;
347 align
= wsize
- align
;
348 out(offset
, segment
, const_zero_buf
,
349 OUT_RAWDATA
, align
, NO_SEG
, NO_SEG
);
351 offset
+= e
->stringlen
+ align
;
354 if (t
> 0 && t
== instruction
->times
- 1) {
356 * Dummy call to list->output to give the offset to the
359 list
->output(offset
, NULL
, OUT_RAWDATA
, 0);
360 list
->uplevel(LIST_TIMES
);
363 if (instruction
->times
> 1)
364 list
->downlevel(LIST_TIMES
);
365 return offset
- start
;
368 if (instruction
->opcode
== I_INCBIN
) {
369 const char *fname
= instruction
->eops
->stringval
;
372 fp
= fopen(fname
, "rb");
374 error(ERR_NONFATAL
, "`incbin': unable to open file `%s'",
376 } else if (fseek(fp
, 0L, SEEK_END
) < 0) {
377 error(ERR_NONFATAL
, "`incbin': unable to seek on file `%s'",
380 static char buf
[4096];
381 size_t t
= instruction
->times
;
386 if (instruction
->eops
->next
) {
387 base
= instruction
->eops
->next
->offset
;
389 if (instruction
->eops
->next
->next
&&
390 len
> (size_t)instruction
->eops
->next
->next
->offset
)
391 len
= (size_t)instruction
->eops
->next
->next
->offset
;
394 * Dummy call to list->output to give the offset to the
397 list
->output(offset
, NULL
, OUT_RAWDATA
, 0);
398 list
->uplevel(LIST_INCBIN
);
402 fseek(fp
, base
, SEEK_SET
);
406 fread(buf
, 1, (l
> (int32_t) sizeof(buf
) ? (int32_t) sizeof(buf
) : l
),
410 * This shouldn't happen unless the file
411 * actually changes while we are reading
415 "`incbin': unexpected EOF while"
416 " reading file `%s'", fname
);
417 t
= 0; /* Try to exit cleanly */
420 out(offset
, segment
, buf
, OUT_RAWDATA
, m
,
425 list
->downlevel(LIST_INCBIN
);
426 if (instruction
->times
> 1) {
428 * Dummy call to list->output to give the offset to the
431 list
->output(offset
, NULL
, OUT_RAWDATA
, 0);
432 list
->uplevel(LIST_TIMES
);
433 list
->downlevel(LIST_TIMES
);
436 return instruction
->times
* len
;
438 return 0; /* if we're here, there's an error */
441 /* Check to see if we need an address-size prefix */
442 add_asp(instruction
, bits
);
446 for (temp
= nasm_instructions
[instruction
->opcode
]; temp
->opcode
!= -1; temp
++){
447 int m
= matches(temp
, instruction
, bits
);
450 m
+= jmp_match(segment
, offset
, bits
, instruction
, temp
->code
);
452 if (m
== 100) { /* matches! */
453 const uint8_t *codes
= temp
->code
;
454 int64_t insn_size
= calcsize(segment
, offset
, bits
,
456 itimes
= instruction
->times
;
457 if (insn_size
< 0) /* shouldn't be, on pass two */
458 error(ERR_PANIC
, "errors made it through from pass one");
461 for (j
= 0; j
< MAXPREFIX
; j
++) {
463 switch (instruction
->prefixes
[j
]) {
479 "cs segment base generated, but will be ignored in 64-bit mode");
486 "ds segment base generated, but will be ignored in 64-bit mode");
493 "es segment base generated, but will be ignored in 64-bit mode");
506 "ss segment base generated, but will be ignored in 64-bit mode");
513 "segr6 and segr7 cannot be used as prefixes");
518 "16-bit addressing is not supported "
520 } else if (bits
!= 16)
530 "64-bit addressing is only supported "
554 error(ERR_PANIC
, "invalid instruction prefix");
557 out(offset
, segment
, &c
, OUT_RAWDATA
, 1,
562 insn_end
= offset
+ insn_size
;
563 gencode(segment
, offset
, bits
, instruction
, codes
,
566 if (itimes
> 0 && itimes
== instruction
->times
- 1) {
568 * Dummy call to list->output to give the offset to the
571 list
->output(offset
, NULL
, OUT_RAWDATA
, 0);
572 list
->uplevel(LIST_TIMES
);
575 if (instruction
->times
> 1)
576 list
->downlevel(LIST_TIMES
);
577 return offset
- start
;
578 } else if (m
> 0 && m
> size_prob
) {
584 if (temp
->opcode
== -1) { /* didn't match any instruction */
587 error(ERR_NONFATAL
, "operation size not specified");
590 error(ERR_NONFATAL
, "mismatch in operand sizes");
593 error(ERR_NONFATAL
, "no instruction for this cpu level");
596 error(ERR_NONFATAL
, "instruction not supported in 64-bit mode");
600 "invalid combination of opcode and operands");
607 int64_t insn_size(int32_t segment
, int64_t offset
, int bits
, uint32_t cp
,
608 insn
* instruction
, efunc error
)
610 const struct itemplate
*temp
;
612 errfunc
= error
; /* to pass to other functions */
615 if (instruction
->opcode
== -1)
618 if (instruction
->opcode
== I_DB
|| instruction
->opcode
== I_DW
||
619 instruction
->opcode
== I_DD
|| instruction
->opcode
== I_DQ
||
620 instruction
->opcode
== I_DT
|| instruction
->opcode
== I_DO
||
621 instruction
->opcode
== I_DY
) {
623 int32_t isize
, osize
, wsize
= 0; /* placate gcc */
626 switch (instruction
->opcode
) {
652 for (e
= instruction
->eops
; e
; e
= e
->next
) {
656 if (e
->type
== EOT_DB_NUMBER
)
658 else if (e
->type
== EOT_DB_STRING
||
659 e
->type
== EOT_DB_STRING_FREE
)
660 osize
= e
->stringlen
;
662 align
= (-osize
) % wsize
;
665 isize
+= osize
+ align
;
667 return isize
* instruction
->times
;
670 if (instruction
->opcode
== I_INCBIN
) {
671 const char *fname
= instruction
->eops
->stringval
;
675 fp
= fopen(fname
, "rb");
677 error(ERR_NONFATAL
, "`incbin': unable to open file `%s'",
679 else if (fseek(fp
, 0L, SEEK_END
) < 0)
680 error(ERR_NONFATAL
, "`incbin': unable to seek on file `%s'",
685 if (instruction
->eops
->next
) {
686 len
-= instruction
->eops
->next
->offset
;
687 if (instruction
->eops
->next
->next
&&
688 len
> (size_t)instruction
->eops
->next
->next
->offset
) {
689 len
= (size_t)instruction
->eops
->next
->next
->offset
;
692 return instruction
->times
* len
;
694 return 0; /* if we're here, there's an error */
697 /* Check to see if we need an address-size prefix */
698 add_asp(instruction
, bits
);
700 for (temp
= nasm_instructions
[instruction
->opcode
]; temp
->opcode
!= -1; temp
++) {
701 int m
= matches(temp
, instruction
, bits
);
703 m
+= jmp_match(segment
, offset
, bits
, instruction
, temp
->code
);
706 /* we've matched an instruction. */
708 const uint8_t *codes
= temp
->code
;
711 isize
= calcsize(segment
, offset
, bits
, instruction
, codes
);
714 for (j
= 0; j
< MAXPREFIX
; j
++) {
715 switch (instruction
->prefixes
[j
]) {
741 return isize
* instruction
->times
;
744 return -1; /* didn't match any instruction */
747 static bool possible_sbyte(operand
*o
)
749 return !(o
->opflags
& OPFLAG_FORWARD
) &&
750 optimizing
>= 0 && !(o
->type
& STRICT
) &&
751 o
->wrt
== NO_SEG
&& o
->segment
== NO_SEG
;
754 /* check that opn[op] is a signed byte of size 16 or 32 */
755 static bool is_sbyte16(operand
*o
)
759 if (!possible_sbyte(o
))
763 return v
>= -128 && v
<= 127;
766 static bool is_sbyte32(operand
*o
)
770 if (!possible_sbyte(o
))
774 return v
>= -128 && v
<= 127;
777 /* check that opn[op] is a signed byte of size 32; warn if this is not
778 the original value when extended to 64 bits */
779 static bool is_sbyte64(operand
*o
)
784 /* dead in the water on forward reference or External */
785 if (!possible_sbyte(o
))
791 warn_overflow(32, v64
);
793 return v32
>= -128 && v32
<= 127;
795 static int64_t calcsize(int32_t segment
, int64_t offset
, int bits
,
796 insn
* ins
, const uint8_t *codes
)
803 ins
->rex
= 0; /* Ensure REX is reset */
805 if (ins
->prefixes
[PPS_OSIZE
] == P_O64
)
808 (void)segment
; /* Don't warn that this parameter is unused */
809 (void)offset
; /* Don't warn that this parameter is unused */
813 opx
= &ins
->oprs
[c
& 3];
818 codes
+= c
, length
+= c
;
831 op_rexflags(opx
, REX_B
|REX_H
|REX_P
|REX_W
);
862 if (opx
->type
& (BITS16
| BITS32
| BITS64
))
863 length
+= (opx
->type
& BITS16
) ? 2 : 4;
865 length
+= (bits
== 16) ? 2 : 4;
877 length
+= ins
->addr_size
>> 3;
889 length
+= 8; /* MOV reg64/imm */
901 if (opx
->type
& (BITS16
| BITS32
| BITS64
))
902 length
+= (opx
->type
& BITS16
) ? 2 : 4;
904 length
+= (bits
== 16) ? 2 : 4;
922 length
+= is_sbyte16(opx
) ? 1 : 2;
935 length
+= is_sbyte32(opx
) ? 1 : 4;
950 ins
->drexdst
= regval(opx
);
957 ins
->rex
|= REX_D
|REX_OC
;
958 ins
->drexdst
= regval(opx
);
972 length
+= is_sbyte64(opx
) ? 1 : 4;
979 ins
->drexdst
= regval(opx
);
980 ins
->vex_m
= *codes
++;
981 ins
->vex_wlp
= *codes
++;
986 ins
->vex_m
= *codes
++;
987 ins
->vex_wlp
= *codes
++;
997 length
+= (bits
!= 16) && !has_prefix(ins
, PPS_ASIZE
, P_A16
);
1000 length
+= (bits
!= 32) && !has_prefix(ins
, PPS_ASIZE
, P_A32
);
1005 if (bits
!= 64 || has_prefix(ins
, PPS_ASIZE
, P_A16
) ||
1006 has_prefix(ins
, PPS_ASIZE
, P_A32
))
1015 length
+= (bits
!= 16);
1018 length
+= (bits
== 16);
1043 if (ins
->oprs
[0].segment
!= NO_SEG
)
1044 errfunc(ERR_NONFATAL
, "attempt to reserve non-constant"
1045 " quantity of BSS space");
1047 length
+= ins
->oprs
[0].offset
;
1070 default: /* can't do it by 'case' statements */
1071 if (c
>= 0100 && c
<= 0277) { /* it's an EA */
1075 ea_data
.rex
= 0; /* Ensure ea.REX is initially 0 */
1078 /* pick rfield from operand b */
1079 rflags
= regflag(&ins
->oprs
[c
& 7]);
1080 rfield
= nasm_regvals
[ins
->oprs
[c
& 7].basereg
];
1087 (&ins
->oprs
[(c
>> 3) & 7], &ea_data
, bits
,
1088 ins
->addr_size
, rfield
, rflags
)) {
1089 errfunc(ERR_NONFATAL
, "invalid effective address");
1092 ins
->rex
|= ea_data
.rex
;
1093 length
+= ea_data
.size
;
1096 errfunc(ERR_PANIC
, "internal instruction table corrupt"
1097 ": instruction code 0x%02X given", c
);
1102 ins
->rex
&= rex_mask
;
1104 if (ins
->rex
& REX_V
) {
1105 int bad32
= REX_R
|REX_W
|REX_X
|REX_B
;
1107 if (ins
->rex
& REX_H
) {
1108 errfunc(ERR_NONFATAL
, "cannot use high register in vex instruction");
1111 switch (ins
->vex_wlp
& 030) {
1125 if (bits
!= 64 && ((ins
->rex
& bad32
) || ins
->drexdst
> 7)) {
1126 errfunc(ERR_NONFATAL
, "invalid operands in non-64-bit mode");
1129 if (ins
->vex_m
!= 1 || (ins
->rex
& (REX_W
|REX_R
|REX_B
)))
1133 } else if (ins
->rex
& REX_D
) {
1134 if (ins
->rex
& REX_H
) {
1135 errfunc(ERR_NONFATAL
, "cannot use high register in drex instruction");
1138 if (bits
!= 64 && ((ins
->rex
& (REX_R
|REX_W
|REX_X
|REX_B
)) ||
1139 ins
->drexdst
> 7)) {
1140 errfunc(ERR_NONFATAL
, "invalid operands in non-64-bit mode");
1144 } else if (ins
->rex
& REX_REAL
) {
1145 if (ins
->rex
& REX_H
) {
1146 errfunc(ERR_NONFATAL
, "cannot use high register in rex instruction");
1148 } else if (bits
== 64) {
1150 } else if ((ins
->rex
& REX_L
) &&
1151 !(ins
->rex
& (REX_P
|REX_W
|REX_X
|REX_B
)) &&
1154 assert_no_prefix(ins
, PPS_LREP
);
1157 errfunc(ERR_NONFATAL
, "invalid operands in non-64-bit mode");
1165 #define EMIT_REX() \
1166 if (!(ins->rex & (REX_D|REX_V)) && (ins->rex & REX_REAL) && (bits == 64)) { \
1167 ins->rex = (ins->rex & REX_REAL)|REX_P; \
1168 out(offset, segment, &ins->rex, OUT_RAWDATA, 1, NO_SEG, NO_SEG); \
1173 static void gencode(int32_t segment
, int64_t offset
, int bits
,
1174 insn
* ins
, const uint8_t *codes
, int64_t insn_end
)
1176 static char condval
[] = { /* conditional opcodes */
1177 0x7, 0x3, 0x2, 0x6, 0x2, 0x4, 0xF, 0xD, 0xC, 0xE, 0x6, 0x2,
1178 0x3, 0x7, 0x3, 0x5, 0xE, 0xC, 0xD, 0xF, 0x1, 0xB, 0x9, 0x5,
1179 0x0, 0xA, 0xA, 0xB, 0x8, 0x4
1185 struct operand
*opx
;
1189 opx
= &ins
->oprs
[c
& 3];
1195 out(offset
, segment
, codes
, OUT_RAWDATA
, c
, NO_SEG
, NO_SEG
);
1202 switch (ins
->oprs
[0].basereg
) {
1204 bytes
[0] = 0x0E + (c
== 0x04 ? 1 : 0);
1207 bytes
[0] = 0x1E + (c
== 0x04 ? 1 : 0);
1210 bytes
[0] = 0x06 + (c
== 0x04 ? 1 : 0);
1213 bytes
[0] = 0x16 + (c
== 0x04 ? 1 : 0);
1217 "bizarre 8086 segment register received");
1219 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1225 switch (ins
->oprs
[0].basereg
) {
1227 bytes
[0] = 0xA0 + (c
== 0x05 ? 1 : 0);
1230 bytes
[0] = 0xA8 + (c
== 0x05 ? 1 : 0);
1234 "bizarre 386 segment register received");
1236 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1245 bytes
[0] = *codes
++ + ((regval(opx
)) & 7);
1246 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1254 /* XXX: warns for legitimate optimizer actions */
1255 if (opx
->offset
< -128 || opx
->offset
> 127) {
1256 errfunc(ERR_WARNING
| ERR_WARN_NOV
,
1257 "signed byte value exceeds bounds");
1260 if (opx
->segment
!= NO_SEG
) {
1262 out(offset
, segment
, &data
, OUT_ADDRESS
, 1,
1263 opx
->segment
, opx
->wrt
);
1265 bytes
[0] = opx
->offset
;
1266 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
,
1276 if (opx
->offset
< -256 || opx
->offset
> 255) {
1277 errfunc(ERR_WARNING
| ERR_WARN_NOV
,
1278 "byte value exceeds bounds");
1280 if (opx
->segment
!= NO_SEG
) {
1282 out(offset
, segment
, &data
, OUT_ADDRESS
, 1,
1283 opx
->segment
, opx
->wrt
);
1285 bytes
[0] = opx
->offset
;
1286 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
,
1296 if (opx
->offset
< 0 || opx
->offset
> 255)
1297 errfunc(ERR_WARNING
| ERR_WARN_NOV
,
1298 "unsigned byte value exceeds bounds");
1299 if (opx
->segment
!= NO_SEG
) {
1301 out(offset
, segment
, &data
, OUT_ADDRESS
, 1,
1302 opx
->segment
, opx
->wrt
);
1304 bytes
[0] = opx
->offset
;
1305 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
,
1316 if (opx
->segment
== NO_SEG
&& opx
->wrt
== NO_SEG
)
1317 warn_overflow(2, data
);
1318 out(offset
, segment
, &data
, OUT_ADDRESS
, 2,
1319 opx
->segment
, opx
->wrt
);
1327 if (opx
->type
& (BITS16
| BITS32
))
1328 size
= (opx
->type
& BITS16
) ? 2 : 4;
1330 size
= (bits
== 16) ? 2 : 4;
1332 if (opx
->segment
== NO_SEG
&& opx
->wrt
== NO_SEG
)
1333 warn_overflow(size
, data
);
1334 out(offset
, segment
, &data
, OUT_ADDRESS
, size
,
1335 opx
->segment
, opx
->wrt
);
1344 if (opx
->segment
== NO_SEG
&& opx
->wrt
== NO_SEG
)
1345 warn_overflow(4, data
);
1346 out(offset
, segment
, &data
, OUT_ADDRESS
, 4,
1347 opx
->segment
, opx
->wrt
);
1356 size
= ins
->addr_size
>> 3;
1357 if (opx
->segment
== NO_SEG
&&
1359 warn_overflow(size
, data
);
1360 out(offset
, segment
, &data
, OUT_ADDRESS
, size
,
1361 opx
->segment
, opx
->wrt
);
1369 if (opx
->segment
!= segment
)
1370 errfunc(ERR_NONFATAL
,
1371 "short relative jump outside segment");
1372 data
= opx
->offset
- insn_end
;
1373 if (data
> 127 || data
< -128)
1374 errfunc(ERR_NONFATAL
, "short jump is out of range");
1376 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1384 data
= (int64_t)opx
->offset
;
1385 out(offset
, segment
, &data
, OUT_ADDRESS
, 8,
1386 opx
->segment
, opx
->wrt
);
1394 if (opx
->segment
!= segment
) {
1396 out(offset
, segment
, &data
,
1397 OUT_REL2ADR
, insn_end
- offset
,
1398 opx
->segment
, opx
->wrt
);
1400 data
= opx
->offset
- insn_end
;
1401 out(offset
, segment
, &data
,
1402 OUT_ADDRESS
, 2, NO_SEG
, NO_SEG
);
1411 if (opx
->type
& (BITS16
| BITS32
| BITS64
))
1412 size
= (opx
->type
& BITS16
) ? 2 : 4;
1414 size
= (bits
== 16) ? 2 : 4;
1415 if (opx
->segment
!= segment
) {
1417 out(offset
, segment
, &data
,
1418 size
== 2 ? OUT_REL2ADR
: OUT_REL4ADR
,
1419 insn_end
- offset
, opx
->segment
, opx
->wrt
);
1421 data
= opx
->offset
- insn_end
;
1422 out(offset
, segment
, &data
,
1423 OUT_ADDRESS
, size
, NO_SEG
, NO_SEG
);
1432 if (opx
->segment
!= segment
) {
1434 out(offset
, segment
, &data
,
1435 OUT_REL4ADR
, insn_end
- offset
,
1436 opx
->segment
, opx
->wrt
);
1438 data
= opx
->offset
- insn_end
;
1439 out(offset
, segment
, &data
,
1440 OUT_ADDRESS
, 4, NO_SEG
, NO_SEG
);
1449 if (opx
->segment
== NO_SEG
)
1450 errfunc(ERR_NONFATAL
, "value referenced by FAR is not"
1453 out(offset
, segment
, &data
, OUT_ADDRESS
, 2,
1454 outfmt
->segbase(1 + opx
->segment
),
1464 if (is_sbyte16(opx
)) {
1466 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
,
1470 if (opx
->segment
== NO_SEG
&&
1472 warn_overflow(2, data
);
1473 out(offset
, segment
, &data
, OUT_ADDRESS
, 2,
1474 opx
->segment
, opx
->wrt
);
1484 bytes
[0] = *codes
++;
1485 if (is_sbyte16(opx
))
1486 bytes
[0] |= 2; /* s-bit */
1487 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1496 if (is_sbyte32(opx
)) {
1498 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
,
1502 out(offset
, segment
, &data
, OUT_ADDRESS
, 4,
1503 opx
->segment
, opx
->wrt
);
1513 bytes
[0] = *codes
++;
1514 if (is_sbyte32(opx
))
1515 bytes
[0] |= 2; /* s-bit */
1516 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1532 (ins
->drexdst
<< 4) |
1533 (ins
->rex
& REX_OC
? 0x08 : 0) |
1534 (ins
->rex
& (REX_R
|REX_X
|REX_B
));
1536 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1542 opx
= &ins
->oprs
[c
>> 3];
1543 bytes
[0] = nasm_regvals
[opx
->basereg
] << 4;
1544 opx
= &ins
->oprs
[c
& 7];
1545 if (opx
->segment
!= NO_SEG
|| opx
->wrt
!= NO_SEG
) {
1546 errfunc(ERR_NONFATAL
,
1547 "non-absolute expression not permitted as argument %d",
1550 if (opx
->offset
& ~15) {
1551 errfunc(ERR_WARNING
| ERR_WARN_NOV
,
1552 "four-bit argument exceeds bounds");
1554 bytes
[0] |= opx
->offset
& 15;
1556 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1562 opx
= &ins
->oprs
[c
>> 4];
1563 bytes
[0] = nasm_regvals
[opx
->basereg
] << 4;
1565 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1571 opx
= &ins
->oprs
[c
];
1572 bytes
[0] = nasm_regvals
[opx
->basereg
] << 4;
1573 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1582 /* is_sbyte32() is right here, we have already warned */
1583 if (is_sbyte32(opx
)) {
1585 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
,
1589 out(offset
, segment
, &data
, OUT_ADDRESS
, 4,
1590 opx
->segment
, opx
->wrt
);
1601 if (ins
->vex_m
!= 1 || (ins
->rex
& (REX_W
|REX_X
|REX_B
))) {
1603 bytes
[1] = ins
->vex_m
| ((~ins
->rex
& 7) << 5);
1604 bytes
[2] = ((ins
->rex
& REX_W
) << (7-3)) |
1605 ((~ins
->drexdst
& 15)<< 3) | (ins
->vex_wlp
& 07);
1606 out(offset
, segment
, &bytes
, OUT_RAWDATA
, 3, NO_SEG
, NO_SEG
);
1610 bytes
[1] = ((~ins
->rex
& REX_R
) << (7-2)) |
1611 ((~ins
->drexdst
& 15) << 3) | (ins
->vex_wlp
& 07);
1612 out(offset
, segment
, &bytes
, OUT_RAWDATA
, 2, NO_SEG
, NO_SEG
);
1624 if (bits
== 32 && !has_prefix(ins
, PPS_ASIZE
, P_A16
)) {
1626 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1633 if (bits
!= 32 && !has_prefix(ins
, PPS_ASIZE
, P_A32
)) {
1635 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1657 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1666 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1681 *bytes
= *codes
++ ^ condval
[ins
->condition
];
1682 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1691 *bytes
= c
- 0332 + 0xF2;
1692 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1697 if (ins
->rex
& REX_R
) {
1699 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1702 ins
->rex
&= ~(REX_L
|REX_R
);
1709 if (ins
->oprs
[0].segment
!= NO_SEG
)
1710 errfunc(ERR_PANIC
, "non-constant BSS size in pass two");
1712 int64_t size
= ins
->oprs
[0].offset
;
1714 out(offset
, segment
, NULL
,
1715 OUT_RESERVE
, size
, NO_SEG
, NO_SEG
);
1725 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1731 bytes
[0] = c
- 0362 + 0xf2;
1732 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1742 *bytes
= c
- 0366 + 0x66;
1743 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1753 *bytes
= bits
== 16 ? 3 : 5;
1754 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1, NO_SEG
, NO_SEG
);
1758 default: /* can't do it by 'case' statements */
1759 if (c
>= 0100 && c
<= 0277) { /* it's an EA */
1767 /* pick rfield from operand b */
1768 rflags
= regflag(&ins
->oprs
[c
& 7]);
1769 rfield
= nasm_regvals
[ins
->oprs
[c
& 7].basereg
];
1771 /* rfield is constant */
1777 (&ins
->oprs
[(c
>> 3) & 7], &ea_data
, bits
,
1778 ins
->addr_size
, rfield
, rflags
)) {
1779 errfunc(ERR_NONFATAL
, "invalid effective address");
1784 *p
++ = ea_data
.modrm
;
1785 if (ea_data
.sib_present
)
1788 /* DREX suffixes come between the SIB and the displacement */
1789 if (ins
->rex
& REX_D
) {
1791 (ins
->drexdst
<< 4) |
1792 (ins
->rex
& REX_OC
? 0x08 : 0) |
1793 (ins
->rex
& (REX_R
|REX_X
|REX_B
));
1798 out(offset
, segment
, bytes
, OUT_RAWDATA
, s
, NO_SEG
, NO_SEG
);
1800 switch (ea_data
.bytes
) {
1804 if (ins
->oprs
[(c
>> 3) & 7].segment
!= NO_SEG
) {
1805 data
= ins
->oprs
[(c
>> 3) & 7].offset
;
1806 out(offset
, segment
, &data
, OUT_ADDRESS
, 1,
1807 ins
->oprs
[(c
>> 3) & 7].segment
,
1808 ins
->oprs
[(c
>> 3) & 7].wrt
);
1810 *bytes
= ins
->oprs
[(c
>> 3) & 7].offset
;
1811 out(offset
, segment
, bytes
, OUT_RAWDATA
, 1,
1819 data
= ins
->oprs
[(c
>> 3) & 7].offset
;
1820 warn_overflow(ea_data
.bytes
, data
);
1821 out(offset
, segment
, &data
,
1822 ea_data
.rip
? OUT_REL4ADR
: OUT_ADDRESS
,
1824 ins
->oprs
[(c
>> 3) & 7].segment
,
1825 ins
->oprs
[(c
>> 3) & 7].wrt
);
1831 errfunc(ERR_PANIC
, "internal instruction table corrupt"
1832 ": instruction code 0x%02X given", c
);
1838 static int32_t regflag(const operand
* o
)
1840 if (o
->basereg
< EXPR_REG_START
|| o
->basereg
>= REG_ENUM_LIMIT
) {
1841 errfunc(ERR_PANIC
, "invalid operand passed to regflag()");
1843 return nasm_reg_flags
[o
->basereg
];
1846 static int32_t regval(const operand
* o
)
1848 if (o
->basereg
< EXPR_REG_START
|| o
->basereg
>= REG_ENUM_LIMIT
) {
1849 errfunc(ERR_PANIC
, "invalid operand passed to regval()");
1851 return nasm_regvals
[o
->basereg
];
1854 static int op_rexflags(const operand
* o
, int mask
)
1859 if (o
->basereg
< EXPR_REG_START
|| o
->basereg
>= REG_ENUM_LIMIT
) {
1860 errfunc(ERR_PANIC
, "invalid operand passed to op_rexflags()");
1863 flags
= nasm_reg_flags
[o
->basereg
];
1864 val
= nasm_regvals
[o
->basereg
];
1866 return rexflags(val
, flags
, mask
);
1869 static int rexflags(int val
, int32_t flags
, int mask
)
1874 rex
|= REX_B
|REX_X
|REX_R
;
1877 if (!(REG_HIGH
& ~flags
)) /* AH, CH, DH, BH */
1879 else if (!(REG8
& ~flags
) && val
>= 4) /* SPL, BPL, SIL, DIL */
1885 static int matches(const struct itemplate
*itemp
, insn
* instruction
, int bits
)
1887 int i
, size
[MAX_OPERANDS
], asize
, oprs
, ret
;
1894 if (itemp
->opcode
!= instruction
->opcode
)
1898 * Count the operands
1900 if (itemp
->operands
!= instruction
->operands
)
1904 * Check that no spurious colons or TOs are present
1906 for (i
= 0; i
< itemp
->operands
; i
++)
1907 if (instruction
->oprs
[i
].type
& ~itemp
->opd
[i
] & (COLON
| TO
))
1911 * Process size flags
1913 if (itemp
->flags
& IF_ARMASK
) {
1914 memset(size
, 0, sizeof size
);
1916 i
= ((itemp
->flags
& IF_ARMASK
) >> IF_ARSHFT
) - 1;
1918 switch (itemp
->flags
& IF_SMASK
) {
1955 switch (itemp
->flags
& IF_SMASK
) {
1990 for (i
= 0; i
< MAX_OPERANDS
; i
++)
1995 * Check that the operand flags all match up
1997 for (i
= 0; i
< itemp
->operands
; i
++) {
1998 int32_t type
= instruction
->oprs
[i
].type
;
1999 if (!(type
& SIZE_MASK
))
2002 if (itemp
->opd
[i
] & SAME_AS
) {
2003 int j
= itemp
->opd
[i
] & ~SAME_AS
;
2004 if (type
!= instruction
->oprs
[j
].type
||
2005 instruction
->oprs
[i
].basereg
!= instruction
->oprs
[j
].basereg
)
2007 } else if (itemp
->opd
[i
] & ~type
||
2008 ((itemp
->opd
[i
] & SIZE_MASK
) &&
2009 ((itemp
->opd
[i
] ^ type
) & SIZE_MASK
))) {
2010 if ((itemp
->opd
[i
] & ~type
& ~SIZE_MASK
) ||
2019 * Check operand sizes
2021 if (itemp
->flags
& (IF_SM
| IF_SM2
)) {
2022 oprs
= (itemp
->flags
& IF_SM2
? 2 : itemp
->operands
);
2024 for (i
= 0; i
< oprs
; i
++) {
2025 if ((asize
= itemp
->opd
[i
] & SIZE_MASK
) != 0) {
2027 for (j
= 0; j
< oprs
; j
++)
2033 oprs
= itemp
->operands
;
2036 for (i
= 0; i
< itemp
->operands
; i
++) {
2037 if (!(itemp
->opd
[i
] & SIZE_MASK
) &&
2038 (instruction
->oprs
[i
].type
& SIZE_MASK
& ~size
[i
]))
2043 * Check template is okay at the set cpu level
2045 if (((itemp
->flags
& IF_PLEVEL
) > cpu
))
2049 * Check if instruction is available in long mode
2051 if ((itemp
->flags
& IF_NOLONG
) && (bits
== 64))
2055 * Check if special handling needed for Jumps
2057 if ((uint8_t)(itemp
->code
[0]) >= 0370)
2063 static ea
*process_ea(operand
* input
, ea
* output
, int bits
,
2064 int addrbits
, int rfield
, int32_t rflags
)
2066 bool forw_ref
= !!(input
->opflags
& OPFLAG_FORWARD
);
2068 output
->rip
= false;
2070 /* REX flags for the rfield operand */
2071 output
->rex
|= rexflags(rfield
, rflags
, REX_R
|REX_P
|REX_W
|REX_H
);
2073 if (!(REGISTER
& ~input
->type
)) { /* register direct */
2077 if (input
->basereg
< EXPR_REG_START
/* Verify as Register */
2078 || input
->basereg
>= REG_ENUM_LIMIT
)
2081 i
= nasm_regvals
[input
->basereg
];
2084 return NULL
; /* Invalid EA register */
2086 output
->rex
|= op_rexflags(input
, REX_B
|REX_P
|REX_W
|REX_H
);
2088 output
->sib_present
= false; /* no SIB necessary */
2089 output
->bytes
= 0; /* no offset necessary either */
2090 output
->modrm
= 0xC0 | ((rfield
& 7) << 3) | (i
& 7);
2091 } else { /* it's a memory reference */
2092 if (input
->basereg
== -1
2093 && (input
->indexreg
== -1 || input
->scale
== 0)) {
2094 /* it's a pure offset */
2095 if (bits
== 64 && (~input
->type
& IP_REL
)) {
2096 int scale
, index
, base
;
2097 output
->sib_present
= true;
2101 output
->sib
= (scale
<< 6) | (index
<< 3) | base
;
2103 output
->modrm
= 4 | ((rfield
& 7) << 3);
2104 output
->rip
= false;
2106 output
->sib_present
= false;
2107 output
->bytes
= (addrbits
!= 16 ? 4 : 2);
2108 output
->modrm
= (addrbits
!= 16 ? 5 : 6) | ((rfield
& 7) << 3);
2109 output
->rip
= bits
== 64;
2111 } else { /* it's an indirection */
2112 int i
= input
->indexreg
, b
= input
->basereg
, s
= input
->scale
;
2113 int32_t o
= input
->offset
, seg
= input
->segment
;
2114 int hb
= input
->hintbase
, ht
= input
->hinttype
;
2117 int32_t ix
, bx
; /* register flags */
2120 i
= -1; /* make this easy, at least */
2122 if (i
>= EXPR_REG_START
&& i
< REG_ENUM_LIMIT
) {
2123 it
= nasm_regvals
[i
];
2124 ix
= nasm_reg_flags
[i
];
2130 if (b
>= EXPR_REG_START
&& b
< REG_ENUM_LIMIT
) {
2131 bt
= nasm_regvals
[b
];
2132 bx
= nasm_reg_flags
[b
];
2138 /* check for a 32/64-bit memory reference... */
2139 if ((ix
|bx
) & (BITS32
|BITS64
)) {
2140 /* it must be a 32/64-bit memory reference. Firstly we have
2141 * to check that all registers involved are type E/Rxx. */
2142 int32_t sok
= BITS32
|BITS64
;
2145 if (!(REG64
& ~ix
) || !(REG32
& ~ix
))
2153 return NULL
; /* Invalid register */
2154 if (~sok
& bx
& SIZE_MASK
)
2155 return NULL
; /* Invalid size */
2159 /* While we're here, ensure the user didn't specify
2161 if (input
->disp_size
== 16 || input
->disp_size
== 64)
2164 if (addrbits
== 16 ||
2165 (addrbits
== 32 && !(sok
& BITS32
)) ||
2166 (addrbits
== 64 && !(sok
& BITS64
)))
2169 /* now reorganize base/index */
2170 if (s
== 1 && bt
!= it
&& bt
!= -1 && it
!= -1 &&
2171 ((hb
== b
&& ht
== EAH_NOTBASE
)
2172 || (hb
== i
&& ht
== EAH_MAKEBASE
))) {
2173 /* swap if hints say so */
2174 t
= bt
, bt
= it
, it
= t
;
2175 t
= bx
, bx
= ix
, ix
= t
;
2177 if (bt
== it
) /* convert EAX+2*EAX to 3*EAX */
2178 bt
= -1, bx
= 0, s
++;
2179 if (bt
== -1 && s
== 1 && !(hb
== it
&& ht
== EAH_NOTBASE
)) {
2180 /* make single reg base, unless hint */
2181 bt
= it
, bx
= ix
, it
= -1, ix
= 0;
2183 if (((s
== 2 && it
!= REG_NUM_ESP
2184 && !(input
->eaflags
& EAF_TIMESTWO
)) || s
== 3
2185 || s
== 5 || s
== 9) && bt
== -1)
2186 bt
= it
, bx
= ix
, s
--; /* convert 3*EAX to EAX+2*EAX */
2187 if (it
== -1 && (bt
& 7) != REG_NUM_ESP
2188 && (input
->eaflags
& EAF_TIMESTWO
))
2189 it
= bt
, ix
= bx
, bt
= -1, bx
= 0, s
= 1;
2190 /* convert [NOSPLIT EAX] to sib format with 0x0 displacement */
2191 if (s
== 1 && it
== REG_NUM_ESP
) {
2192 /* swap ESP into base if scale is 1 */
2193 t
= it
, it
= bt
, bt
= t
;
2194 t
= ix
, ix
= bx
, bx
= t
;
2196 if (it
== REG_NUM_ESP
2197 || (s
!= 1 && s
!= 2 && s
!= 4 && s
!= 8 && it
!= -1))
2198 return NULL
; /* wrong, for various reasons */
2200 output
->rex
|= rexflags(it
, ix
, REX_X
);
2201 output
->rex
|= rexflags(bt
, bx
, REX_B
);
2203 if (it
== -1 && (bt
& 7) != REG_NUM_ESP
) {
2212 if (rm
!= REG_NUM_EBP
&& o
== 0 &&
2213 seg
== NO_SEG
&& !forw_ref
&&
2215 (EAF_BYTEOFFS
| EAF_WORDOFFS
)))
2217 else if (input
->eaflags
& EAF_BYTEOFFS
||
2218 (o
>= -128 && o
<= 127 && seg
== NO_SEG
2220 && !(input
->eaflags
& EAF_WORDOFFS
)))
2226 output
->sib_present
= false;
2227 output
->bytes
= (bt
== -1 || mod
== 2 ? 4 : mod
);
2228 output
->modrm
= (mod
<< 6) | ((rfield
& 7) << 3) | rm
;
2231 int mod
, scale
, index
, base
;
2251 default: /* then what the smeg is it? */
2252 return NULL
; /* panic */
2260 if (base
!= REG_NUM_EBP
&& o
== 0 &&
2261 seg
== NO_SEG
&& !forw_ref
&&
2263 (EAF_BYTEOFFS
| EAF_WORDOFFS
)))
2265 else if (input
->eaflags
& EAF_BYTEOFFS
||
2266 (o
>= -128 && o
<= 127 && seg
== NO_SEG
2268 && !(input
->eaflags
& EAF_WORDOFFS
)))
2274 output
->sib_present
= true;
2275 output
->bytes
= (bt
== -1 || mod
== 2 ? 4 : mod
);
2276 output
->modrm
= (mod
<< 6) | ((rfield
& 7) << 3) | 4;
2277 output
->sib
= (scale
<< 6) | (index
<< 3) | base
;
2279 } else { /* it's 16-bit */
2282 /* check for 64-bit long mode */
2286 /* check all registers are BX, BP, SI or DI */
2287 if ((b
!= -1 && b
!= R_BP
&& b
!= R_BX
&& b
!= R_SI
2288 && b
!= R_DI
) || (i
!= -1 && i
!= R_BP
&& i
!= R_BX
2289 && i
!= R_SI
&& i
!= R_DI
))
2292 /* ensure the user didn't specify DWORD/QWORD */
2293 if (input
->disp_size
== 32 || input
->disp_size
== 64)
2296 if (s
!= 1 && i
!= -1)
2297 return NULL
; /* no can do, in 16-bit EA */
2298 if (b
== -1 && i
!= -1) {
2303 if ((b
== R_SI
|| b
== R_DI
) && i
!= -1) {
2308 /* have BX/BP as base, SI/DI index */
2310 return NULL
; /* shouldn't ever happen, in theory */
2311 if (i
!= -1 && b
!= -1 &&
2312 (i
== R_BP
|| i
== R_BX
|| b
== R_SI
|| b
== R_DI
))
2313 return NULL
; /* invalid combinations */
2314 if (b
== -1) /* pure offset: handled above */
2315 return NULL
; /* so if it gets to here, panic! */
2319 switch (i
* 256 + b
) {
2320 case R_SI
* 256 + R_BX
:
2323 case R_DI
* 256 + R_BX
:
2326 case R_SI
* 256 + R_BP
:
2329 case R_DI
* 256 + R_BP
:
2347 if (rm
== -1) /* can't happen, in theory */
2348 return NULL
; /* so panic if it does */
2350 if (o
== 0 && seg
== NO_SEG
&& !forw_ref
&& rm
!= 6 &&
2351 !(input
->eaflags
& (EAF_BYTEOFFS
| EAF_WORDOFFS
)))
2353 else if (input
->eaflags
& EAF_BYTEOFFS
||
2354 (o
>= -128 && o
<= 127 && seg
== NO_SEG
2356 && !(input
->eaflags
& EAF_WORDOFFS
)))
2361 output
->sib_present
= false; /* no SIB - it's 16-bit */
2362 output
->bytes
= mod
; /* bytes of offset needed */
2363 output
->modrm
= (mod
<< 6) | ((rfield
& 7) << 3) | rm
;
2368 output
->size
= 1 + output
->sib_present
+ output
->bytes
;
2372 static void add_asp(insn
*ins
, int addrbits
)
2377 valid
= (addrbits
== 64) ? 64|32 : 32|16;
2379 switch (ins
->prefixes
[PPS_ASIZE
]) {
2390 valid
&= (addrbits
== 32) ? 16 : 32;
2396 for (j
= 0; j
< ins
->operands
; j
++) {
2397 if (!(MEMORY
& ~ins
->oprs
[j
].type
)) {
2400 /* Verify as Register */
2401 if (ins
->oprs
[j
].indexreg
< EXPR_REG_START
2402 || ins
->oprs
[j
].indexreg
>= REG_ENUM_LIMIT
)
2405 i
= nasm_reg_flags
[ins
->oprs
[j
].indexreg
];
2407 /* Verify as Register */
2408 if (ins
->oprs
[j
].basereg
< EXPR_REG_START
2409 || ins
->oprs
[j
].basereg
>= REG_ENUM_LIMIT
)
2412 b
= nasm_reg_flags
[ins
->oprs
[j
].basereg
];
2414 if (ins
->oprs
[j
].scale
== 0)
2418 int ds
= ins
->oprs
[j
].disp_size
;
2419 if ((addrbits
!= 64 && ds
> 8) ||
2420 (addrbits
== 64 && ds
== 16))
2440 if (valid
& addrbits
) {
2441 ins
->addr_size
= addrbits
;
2442 } else if (valid
& ((addrbits
== 32) ? 16 : 32)) {
2443 /* Add an address size prefix */
2444 enum prefixes pref
= (addrbits
== 32) ? P_A16
: P_A32
;
2445 ins
->prefixes
[PPS_ASIZE
] = pref
;
2446 ins
->addr_size
= (addrbits
== 32) ? 16 : 32;
2449 errfunc(ERR_NONFATAL
, "impossible combination of address sizes");
2450 ins
->addr_size
= addrbits
; /* Error recovery */
2453 defdisp
= ins
->addr_size
== 16 ? 16 : 32;
2455 for (j
= 0; j
< ins
->operands
; j
++) {
2456 if (!(MEM_OFFS
& ~ins
->oprs
[j
].type
) &&
2457 (ins
->oprs
[j
].disp_size
? ins
->oprs
[j
].disp_size
: defdisp
)
2458 != ins
->addr_size
) {
2459 /* mem_offs sizes must match the address size; if not,
2460 strip the MEM_OFFS bit and match only EA instructions */
2461 ins
->oprs
[j
].type
&= ~(MEM_OFFS
& ~MEMORY
);