Merged trunk and subtype.
[cacao.git] / src / vm / jit / i386 / emit.c
1 /* src/vm/jit/i386/emit.c - i386 code emitter functions
2
3    Copyright (C) 1996-2005, 2006, 2007, 2008
4    CACAOVM - Verein zur Foerderung der freien virtuellen Maschine CACAO
5
6    This file is part of CACAO.
7
8    This program is free software; you can redistribute it and/or
9    modify it under the terms of the GNU General Public License as
10    published by the Free Software Foundation; either version 2, or (at
11    your option) any later version.
12
13    This program is distributed in the hope that it will be useful, but
14    WITHOUT ANY WARRANTY; without even the implied warranty of
15    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16    General Public License for more details.
17
18    You should have received a copy of the GNU General Public License
19    along with this program; if not, write to the Free Software
20    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
21    02110-1301, USA.
22
23 */
24
25
26 #include "config.h"
27
28 #include <assert.h>
29
30 #include "vm/types.h"
31
32 #include "vm/jit/i386/codegen.h"
33 #include "vm/jit/i386/emit.h"
34 #include "vm/jit/i386/md-abi.h"
35
36 #include "mm/memory.h"
37
38 #include "threads/lock-common.h"
39
40 #include "vm/options.h"
41 #include "vm/statistics.h"
42
43 #include "vm/jit/abi.h"
44 #include "vm/jit/asmpart.h"
45 #include "vm/jit/dseg.h"
46 #include "vm/jit/emit-common.hpp"
47 #include "vm/jit/jit.hpp"
48 #include "vm/jit/patcher-common.hpp"
49 #include "vm/jit/replace.hpp"
50 #include "vm/jit/trace.hpp"
51 #include "vm/jit/trap.h"
52
53
54 /* emit_load ******************************************************************
55
56    Emits a possible load of an operand.
57
58 *******************************************************************************/
59
60 inline s4 emit_load(jitdata *jd, instruction *iptr, varinfo *src, s4 tempreg)
61 {
62         codegendata  *cd;
63         s4            disp;
64         s4            reg;
65
66         /* get required compiler data */
67
68         cd = jd->cd;
69
70         if (IS_INMEMORY(src->flags)) {
71                 COUNT_SPILLS;
72
73                 disp = src->vv.regoff;
74
75                 switch (src->type) {
76                 case TYPE_INT:
77                 case TYPE_ADR:
78                         M_ILD(tempreg, REG_SP, disp);
79                         break;
80                 case TYPE_LNG:
81                         M_LLD(tempreg, REG_SP, disp);
82                         break;
83                 case TYPE_FLT:
84                         M_FLD(tempreg, REG_SP, disp);
85                         break;
86                 case TYPE_DBL:
87                         M_DLD(tempreg, REG_SP, disp);
88                         break;
89                 default:
90                         vm_abort("emit_load: unknown type %d", src->type);
91                 }
92
93                 reg = tempreg;
94         }
95         else
96                 reg = src->vv.regoff;
97
98         return reg;
99 }
100
101
102 /* emit_load_low ************************************************************
103
104    Emits a possible load of the low 32-bits of an operand.
105
106 *******************************************************************************/
107
108 inline s4 emit_load_low(jitdata *jd, instruction *iptr, varinfo *src,s4 tempreg)
109 {
110         codegendata  *cd;
111         s4            disp;
112         s4            reg;
113
114         assert(src->type == TYPE_LNG);
115
116         /* get required compiler data */
117
118         cd = jd->cd;
119
120
121         if (IS_INMEMORY(src->flags)) {
122                 COUNT_SPILLS;
123
124                 disp = src->vv.regoff;
125
126                 M_ILD(tempreg, REG_SP, disp);
127
128                 reg = tempreg;
129         }
130         else
131                 reg = GET_LOW_REG(src->vv.regoff);
132
133         return reg;
134 }
135
136
137 /* emit_load_high ***********************************************************
138
139    Emits a possible load of the high 32-bits of an operand.
140
141 *******************************************************************************/
142
143 inline s4 emit_load_high(jitdata *jd, instruction *iptr,varinfo *src,s4 tempreg)
144 {
145         codegendata  *cd;
146         s4            disp;
147         s4            reg;
148
149         /* get required compiler data */
150
151         assert(src->type == TYPE_LNG);
152
153         cd = jd->cd;
154
155         if (IS_INMEMORY(src->flags)) {
156                 COUNT_SPILLS;
157
158                 disp = src->vv.regoff;
159
160                 M_ILD(tempreg, REG_SP, disp + 4);
161
162                 reg = tempreg;
163         }
164         else
165                 reg = GET_HIGH_REG(src->vv.regoff);
166
167         return reg;
168 }
169
170
171 /* emit_store ******************************************************************
172
173    Emits a possible store of the destination operand.
174
175 *******************************************************************************/
176
177 inline void emit_store(jitdata *jd, instruction *iptr, varinfo *dst, s4 d)
178 {
179         codegendata  *cd;
180         s4            disp;
181
182         /* get required compiler data */
183
184         cd = jd->cd;
185
186         if (IS_INMEMORY(dst->flags)) {
187                 COUNT_SPILLS;
188
189                 disp = dst->vv.regoff;
190
191                 switch (dst->type) {
192                 case TYPE_INT:
193                 case TYPE_ADR:
194                         M_IST(d, REG_SP, disp);
195                         break;
196                 case TYPE_LNG:
197                         M_LST(d, REG_SP, disp);
198                         break;
199                 case TYPE_FLT:
200                         M_FST(d, REG_SP, disp);
201                         break;
202                 case TYPE_DBL:
203                         M_DST(d, REG_SP, disp);
204                         break;
205                 default:
206                         vm_abort("emit_store: unknown type %d", dst->type);
207                 }
208         }
209 }
210
211
212 /* emit_store_low **************************************************************
213
214    Emits a possible store of the low 32-bits of the destination
215    operand.
216
217 *******************************************************************************/
218
219 inline void emit_store_low(jitdata *jd, instruction *iptr, varinfo *dst, s4 d)
220 {
221         codegendata  *cd;
222
223         assert(dst->type == TYPE_LNG);
224
225         /* get required compiler data */
226
227         cd = jd->cd;
228
229         if (IS_INMEMORY(dst->flags)) {
230                 COUNT_SPILLS;
231                 M_IST(GET_LOW_REG(d), REG_SP, dst->vv.regoff);
232         }
233 }
234
235
236 /* emit_store_high *************************************************************
237
238    Emits a possible store of the high 32-bits of the destination
239    operand.
240
241 *******************************************************************************/
242
243 inline void emit_store_high(jitdata *jd, instruction *iptr, varinfo *dst, s4 d)
244 {
245         codegendata  *cd;
246
247         assert(dst->type == TYPE_LNG);
248
249         /* get required compiler data */
250
251         cd = jd->cd;
252
253         if (IS_INMEMORY(dst->flags)) {
254                 COUNT_SPILLS;
255                 M_IST(GET_HIGH_REG(d), REG_SP, dst->vv.regoff + 4);
256         }
257 }
258
259
260 /* emit_copy *******************************************************************
261
262    Generates a register/memory to register/memory copy.
263
264 *******************************************************************************/
265
266 void emit_copy(jitdata *jd, instruction *iptr)
267 {
268         codegendata *cd;
269         varinfo     *src;
270         varinfo     *dst;
271         s4           s1, d;
272
273         /* get required compiler data */
274
275         cd = jd->cd;
276
277         /* get source and destination variables */
278
279         src = VAROP(iptr->s1);
280         dst = VAROP(iptr->dst);
281
282         if ((src->vv.regoff != dst->vv.regoff) ||
283                 ((src->flags ^ dst->flags) & INMEMORY)) {
284
285                 if ((src->type == TYPE_RET) || (dst->type == TYPE_RET)) {
286                         /* emit nothing, as the value won't be used anyway */
287                         return;
288                 }
289
290                 /* If one of the variables resides in memory, we can eliminate
291                    the register move from/to the temporary register with the
292                    order of getting the destination register and the load. */
293
294                 if (IS_INMEMORY(src->flags)) {
295                         if (IS_LNG_TYPE(src->type))
296                                 d = codegen_reg_of_var(iptr->opc, dst, REG_ITMP12_PACKED);
297                         else
298                                 d = codegen_reg_of_var(iptr->opc, dst, REG_ITMP1);
299
300                         s1 = emit_load(jd, iptr, src, d);
301                 }
302                 else {
303                         if (IS_LNG_TYPE(src->type))
304                                 s1 = emit_load(jd, iptr, src, REG_ITMP12_PACKED);
305                         else
306                                 s1 = emit_load(jd, iptr, src, REG_ITMP1);
307
308                         d = codegen_reg_of_var(iptr->opc, dst, s1);
309                 }
310
311                 if (s1 != d) {
312                         switch (src->type) {
313                         case TYPE_INT:
314                         case TYPE_ADR:
315                                 M_MOV(s1, d);
316                                 break;
317                         case TYPE_LNG:
318                                 M_LNGMOVE(s1, d);
319                                 break;
320                         case TYPE_FLT:
321                         case TYPE_DBL:
322 /*                              M_FMOV(s1, d); */
323                                 break;
324                         default:
325                                 vm_abort("emit_copy: unknown type %d", src->type);
326                         }
327                 }
328
329                 emit_store(jd, iptr, dst, d);
330         }
331 }
332
333
334 /* emit_branch *****************************************************************
335
336    Emits the code for conditional and unconditional branchs.
337
338 *******************************************************************************/
339
340 void emit_branch(codegendata *cd, s4 disp, s4 condition, s4 reg, u4 options)
341 {
342         s4 branchdisp;
343
344         /* ATTENTION: a displacement overflow cannot happen */
345
346         /* check which branch to generate */
347
348         if (condition == BRANCH_UNCONDITIONAL) {
349
350                 /* calculate the different displacements */
351
352                 branchdisp = disp - BRANCH_UNCONDITIONAL_SIZE;
353
354                 M_JMP_IMM(branchdisp);
355         }
356         else {
357                 /* calculate the different displacements */
358
359                 branchdisp = disp - BRANCH_CONDITIONAL_SIZE;
360
361                 switch (condition) {
362                 case BRANCH_EQ:
363                         M_BEQ(branchdisp);
364                         break;
365                 case BRANCH_NE:
366                         M_BNE(branchdisp);
367                         break;
368                 case BRANCH_LT:
369                         M_BLT(branchdisp);
370                         break;
371                 case BRANCH_GE:
372                         M_BGE(branchdisp);
373                         break;
374                 case BRANCH_GT:
375                         M_BGT(branchdisp);
376                         break;
377                 case BRANCH_LE:
378                         M_BLE(branchdisp);
379                         break;
380                 case BRANCH_ULT:
381                         M_BB(branchdisp);
382                         break;
383                 case BRANCH_ULE:
384                         M_BBE(branchdisp);
385                         break;
386                 case BRANCH_UGE:
387                         M_BAE(branchdisp);
388                         break;
389                 case BRANCH_UGT:
390                         M_BA(branchdisp);
391                         break;
392                 default:
393                         vm_abort("emit_branch: unknown condition %d", condition);
394                 }
395         }
396 }
397
398
399 /* emit_arithmetic_check *******************************************************
400
401    Emit an ArithmeticException check.
402
403 *******************************************************************************/
404
405 void emit_arithmetic_check(codegendata *cd, instruction *iptr, s4 reg)
406 {
407         if (INSTRUCTION_MUST_CHECK(iptr)) {
408                 M_TEST(reg);
409                 M_BNE(6);
410                 M_ALD_MEM(reg, TRAP_ArithmeticException);
411         }
412 }
413
414
415 /* emit_arrayindexoutofbounds_check ********************************************
416
417    Emit a ArrayIndexOutOfBoundsException check.
418
419 *******************************************************************************/
420
421 void emit_arrayindexoutofbounds_check(codegendata *cd, instruction *iptr, s4 s1, s4 s2)
422 {
423         if (INSTRUCTION_MUST_CHECK(iptr)) {
424         M_ILD(REG_ITMP3, s1, OFFSET(java_array_t, size));
425         M_CMP(REG_ITMP3, s2);
426         M_BB(6);
427                 M_ALD_MEM(s2, TRAP_ArrayIndexOutOfBoundsException);
428         }
429 }
430
431
432 /* emit_arraystore_check *******************************************************
433
434    Emit an ArrayStoreException check.
435
436 *******************************************************************************/
437
438 void emit_arraystore_check(codegendata *cd, instruction *iptr)
439 {
440         if (INSTRUCTION_MUST_CHECK(iptr)) {
441                 M_TEST(REG_RESULT);
442                 M_BNE(6);
443                 M_ALD_MEM(REG_RESULT, TRAP_ArrayStoreException);
444         }
445 }
446
447
448 /* emit_classcast_check ********************************************************
449
450    Emit a ClassCastException check.
451
452 *******************************************************************************/
453
454 void emit_classcast_check(codegendata *cd, instruction *iptr, s4 condition, s4 reg, s4 s1)
455 {
456         if (INSTRUCTION_MUST_CHECK(iptr)) {
457                 switch (condition) {
458                 case BRANCH_LE:
459                         M_BGT(6);
460                         break;
461                 case BRANCH_GE:
462                         M_BLT(6);
463                         break;
464                 case BRANCH_EQ:
465                         M_BNE(6);
466                         break;
467                 case BRANCH_NE:
468                         M_BEQ(6);
469                         break;
470                 case BRANCH_ULE:
471                         M_BBE(6);
472                         break;
473                 default:
474                         vm_abort("emit_classcast_check: unknown condition %d", condition);
475                 }
476                 M_ALD_MEM(s1, TRAP_ClassCastException);
477         }
478 }
479
480
481 /* emit_nullpointer_check ******************************************************
482
483    Emit a NullPointerException check.
484
485 *******************************************************************************/
486
487 void emit_nullpointer_check(codegendata *cd, instruction *iptr, s4 reg)
488 {
489         if (INSTRUCTION_MUST_CHECK(iptr)) {
490                 M_TEST(reg);
491                 M_BNE(6);
492                 M_ALD_MEM(reg, TRAP_NullPointerException);
493         }
494 }
495
496
497 /* emit_exception_check ********************************************************
498
499    Emit an Exception check.
500
501 *******************************************************************************/
502
503 void emit_exception_check(codegendata *cd, instruction *iptr)
504 {
505         if (INSTRUCTION_MUST_CHECK(iptr)) {
506                 M_TEST(REG_RESULT);
507                 M_BNE(6);
508                 M_ALD_MEM(REG_RESULT, TRAP_CHECK_EXCEPTION);
509         }
510 }
511
512
513 /* emit_trap_compiler **********************************************************
514
515    Emit a trap instruction which calls the JIT compiler.
516
517 *******************************************************************************/
518
519 void emit_trap_compiler(codegendata *cd)
520 {
521         M_ALD_MEM(REG_METHODPTR, TRAP_COMPILER);
522 }
523
524 /* emit_trap_countdown *********************************************************
525
526    Emit a countdown trap.
527
528    counter....absolute address of the counter variable
529
530 *******************************************************************************/
531
532 void emit_trap_countdown(codegendata *cd, s4 *counter)
533 {
534         M_ISUB_IMM_MEMABS(1, (s4) counter);
535         M_BNS(6);
536         M_ALD_MEM(REG_METHODPTR, TRAP_COUNTDOWN);
537 }
538
539 /* emit_trap *******************************************************************
540
541    Emit a trap instruction and return the original machine code.
542
543 *******************************************************************************/
544
545 uint32_t emit_trap(codegendata *cd)
546 {
547         uint16_t mcode;
548
549         /* Get machine code which is patched back in later. The
550            trap is 2 bytes long. */
551
552         mcode = *((uint16_t *) cd->mcodeptr);
553
554 #if 0
555         /* XXX this breaks GDB, so we disable it for now */
556         *(cd->mcodeptr++) = 0xcc;
557         M_INT3;
558 #else
559         M_UD2;
560 #endif
561
562         return (uint32_t) mcode;
563 }
564
565
566 /* emit_verbosecall_enter ******************************************************
567
568    Generates the code for the call trace.
569
570 *******************************************************************************/
571
572 #if !defined(NDEBUG)
573 void emit_verbosecall_enter(jitdata *jd)
574 {
575         methodinfo   *m;
576         codeinfo     *code;
577         codegendata  *cd;
578         registerdata *rd;
579         methoddesc   *md;
580         int32_t       stackframesize;
581         int           i;
582         int           align_off;             /* offset for alignment compensation */
583
584         if (!JITDATA_HAS_FLAG_VERBOSECALL(jd))
585                 return;
586
587         /* get required compiler data */
588
589         m    = jd->m;
590         code = jd->code;
591         cd   = jd->cd;
592         rd   = jd->rd;
593
594         md = m->parseddesc;
595
596         /* mark trace code */
597
598         M_NOP;
599
600         /* keep stack 16-byte aligned */
601
602         stackframesize = 2 + TMP_CNT;
603         ALIGN_2(stackframesize);
604
605         M_ASUB_IMM(stackframesize * 8, REG_SP);
606
607         /* save temporary registers for leaf methods */
608
609         if (code_is_leafmethod(code)) {
610                 for (i = 0; i < INT_TMP_CNT; i++)
611                         M_IST(rd->tmpintregs[i], REG_SP, (2 + i) * 8);
612         }
613
614         /* no argument registers to save */
615
616         align_off = cd->stackframesize ? 4 : 0;
617         M_AST_IMM(m, REG_SP, 0 * 4);
618         M_AST_IMM(0, REG_SP, 1 * 4);
619         M_AST(REG_SP, REG_SP, 2 * 4);
620         M_IADD_IMM_MEMBASE(stackframesize * 8 + cd->stackframesize * 8 + 4 + align_off, REG_SP, 2 * 4);
621         M_MOV_IMM(trace_java_call_enter, REG_ITMP1);
622         M_CALL(REG_ITMP1);
623
624         /* no argument registers to restore */
625
626         /* restore temporary registers for leaf methods */
627
628         if (code_is_leafmethod(code)) {
629                 for (i = 0; i < INT_TMP_CNT; i++)
630                         M_ILD(rd->tmpintregs[i], REG_SP, (2 + i) * 8);
631         }
632
633         M_AADD_IMM(stackframesize * 8, REG_SP);
634
635         /* mark trace code */
636
637         M_NOP;
638 }
639 #endif /* !defined(NDEBUG) */
640
641
642 /* emit_verbosecall_exit *******************************************************
643
644    Generates the code for the call trace.
645
646 *******************************************************************************/
647
648 #if !defined(NDEBUG)
649 void emit_verbosecall_exit(jitdata *jd)
650 {
651         methodinfo   *m;
652         codegendata  *cd;
653         registerdata *rd;
654         methoddesc   *md;
655
656         if (!JITDATA_HAS_FLAG_VERBOSECALL(jd))
657                 return;
658
659         /* get required compiler data */
660
661         m  = jd->m;
662         cd = jd->cd;
663         rd = jd->rd;
664
665         md = m->parseddesc;
666
667         /* mark trace code */
668
669         M_NOP;
670
671         /* keep stack 16-byte aligned */
672
673         M_ASUB_IMM(4 + 4 + 8, REG_SP);
674
675         /* save return value */
676
677         switch (md->returntype.type) {
678         case TYPE_ADR:
679         case TYPE_INT:
680                 M_IST(REG_RESULT, REG_SP, 2 * 4);
681                 break;
682         case TYPE_LNG:
683                 M_LST(REG_RESULT_PACKED, REG_SP, 2 * 4);
684                 break;
685         case TYPE_FLT:
686                 M_FSTNP(REG_NULL, REG_SP, 2 * 4);
687                 break;
688         case TYPE_DBL:
689                 M_DSTNP(REG_NULL, REG_SP, 2 * 4);
690                 break;
691         }
692
693         M_AST_IMM(m, REG_SP, 0 * 4);
694         M_AST(REG_SP, REG_SP, 1 * 4);
695         M_IADD_IMM_MEMBASE(2 * 4, REG_SP, 1 * 4);
696         M_MOV_IMM(trace_java_call_exit, REG_ITMP1);
697         M_CALL(REG_ITMP1);
698
699         /* restore return value */
700
701         switch (md->returntype.type) {
702         case TYPE_ADR:
703         case TYPE_INT:
704                 M_ILD(REG_RESULT, REG_SP, 2 * 4);
705                 break;
706         case TYPE_LNG:
707                 M_LLD(REG_RESULT_PACKED, REG_SP, 2 * 4);
708                 break;
709         }
710
711         M_AADD_IMM(4 + 4 + 8, REG_SP);
712
713         /* mark trace code */
714
715         M_NOP;
716 }
717 #endif /* !defined(NDEBUG) */
718
719
720 /* code generation functions **************************************************/
721
722 static void emit_membase(codegendata *cd, s4 basereg, s4 disp, s4 dreg)
723 {
724         if (basereg == ESP) {
725                 if (disp == 0) {
726                         emit_address_byte(0, dreg, ESP);
727                         emit_address_byte(0, ESP, ESP);
728                 }
729                 else if (IS_IMM8(disp)) {
730                         emit_address_byte(1, dreg, ESP);
731                         emit_address_byte(0, ESP, ESP);
732                         emit_imm8(disp);
733                 }
734                 else {
735                         emit_address_byte(2, dreg, ESP);
736                         emit_address_byte(0, ESP, ESP);
737                         emit_imm32(disp);
738                 }
739         }
740         else if ((disp == 0) && (basereg != EBP)) {
741                 emit_address_byte(0, dreg, basereg);
742         }
743         else if (IS_IMM8(disp)) {
744                 emit_address_byte(1, dreg, basereg);
745                 emit_imm8(disp);
746         }
747         else {
748                 emit_address_byte(2, dreg, basereg);
749                 emit_imm32(disp);
750         }
751 }
752
753
754 static void emit_membase32(codegendata *cd, s4 basereg, s4 disp, s4 dreg)
755 {
756         if (basereg == ESP) {
757                 emit_address_byte(2, dreg, ESP);
758                 emit_address_byte(0, ESP, ESP);
759                 emit_imm32(disp);
760         }
761         else {
762                 emit_address_byte(2, dreg, basereg);
763                 emit_imm32(disp);
764         }
765 }
766
767
768 static void emit_memindex(codegendata *cd, s4 reg, s4 disp, s4 basereg, s4 indexreg, s4 scale)
769 {
770         if (basereg == -1) {
771                 emit_address_byte(0, reg, 4);
772                 emit_address_byte(scale, indexreg, 5);
773                 emit_imm32(disp);
774         }
775         else if ((disp == 0) && (basereg != EBP)) {
776                 emit_address_byte(0, reg, 4);
777                 emit_address_byte(scale, indexreg, basereg);
778         }
779         else if (IS_IMM8(disp)) {
780                 emit_address_byte(1, reg, 4);
781                 emit_address_byte(scale, indexreg, basereg);
782                 emit_imm8(disp);
783         }
784         else {
785                 emit_address_byte(2, reg, 4);
786                 emit_address_byte(scale, indexreg, basereg);
787                 emit_imm32(disp);
788         }
789 }
790
791
792 /* low-level code emitter functions *******************************************/
793
794 void emit_mov_reg_reg(codegendata *cd, s4 reg, s4 dreg)
795 {
796         COUNT(count_mov_reg_reg);
797         *(cd->mcodeptr++) = 0x89;
798         emit_reg((reg),(dreg));
799 }
800
801
802 void emit_mov_imm_reg(codegendata *cd, s4 imm, s4 reg)
803 {
804         *(cd->mcodeptr++) = 0xb8 + ((reg) & 0x07);
805         emit_imm32((imm));
806 }
807
808
809 void emit_movb_imm_reg(codegendata *cd, s4 imm, s4 reg)
810 {
811         *(cd->mcodeptr++) = 0xc6;
812         emit_reg(0,(reg));
813         emit_imm8((imm));
814 }
815
816
817 void emit_mov_membase_reg(codegendata *cd, s4 basereg, s4 disp, s4 reg)
818 {
819         COUNT(count_mov_mem_reg);
820         *(cd->mcodeptr++) = 0x8b;
821         emit_membase(cd, (basereg),(disp),(reg));
822 }
823
824
825 /*
826  * this one is for INVOKEVIRTUAL/INVOKEINTERFACE to have a
827  * constant membase immediate length of 32bit
828  */
829 void emit_mov_membase32_reg(codegendata *cd, s4 basereg, s4 disp, s4 reg)
830 {
831         COUNT(count_mov_mem_reg);
832         *(cd->mcodeptr++) = 0x8b;
833         emit_membase32(cd, (basereg),(disp),(reg));
834 }
835
836
837 void emit_mov_reg_membase(codegendata *cd, s4 reg, s4 basereg, s4 disp)
838 {
839         COUNT(count_mov_reg_mem);
840         *(cd->mcodeptr++) = 0x89;
841         emit_membase(cd, (basereg),(disp),(reg));
842 }
843
844
845 void emit_mov_reg_membase32(codegendata *cd, s4 reg, s4 basereg, s4 disp)
846 {
847         COUNT(count_mov_reg_mem);
848         *(cd->mcodeptr++) = 0x89;
849         emit_membase32(cd, (basereg),(disp),(reg));
850 }
851
852
853 void emit_mov_memindex_reg(codegendata *cd, s4 disp, s4 basereg, s4 indexreg, s4 scale, s4 reg)
854 {
855         COUNT(count_mov_mem_reg);
856         *(cd->mcodeptr++) = 0x8b;
857         emit_memindex(cd, (reg),(disp),(basereg),(indexreg),(scale));
858 }
859
860
861 void emit_mov_reg_memindex(codegendata *cd, s4 reg, s4 disp, s4 basereg, s4 indexreg, s4 scale)
862 {
863         COUNT(count_mov_reg_mem);
864         *(cd->mcodeptr++) = 0x89;
865         emit_memindex(cd, (reg),(disp),(basereg),(indexreg),(scale));
866 }
867
868
869 void emit_movw_reg_memindex(codegendata *cd, s4 reg, s4 disp, s4 basereg, s4 indexreg, s4 scale)
870 {
871         COUNT(count_mov_reg_mem);
872         *(cd->mcodeptr++) = 0x66;
873         *(cd->mcodeptr++) = 0x89;
874         emit_memindex(cd, (reg),(disp),(basereg),(indexreg),(scale));
875 }
876
877
878 void emit_movb_reg_memindex(codegendata *cd, s4 reg, s4 disp, s4 basereg, s4 indexreg, s4 scale)
879 {
880         COUNT(count_mov_reg_mem);
881         *(cd->mcodeptr++) = 0x88;
882         emit_memindex(cd, (reg),(disp),(basereg),(indexreg),(scale));
883 }
884
885
886 void emit_mov_reg_mem(codegendata *cd, s4 reg, s4 mem)
887 {
888         COUNT(count_mov_reg_mem);
889         *(cd->mcodeptr++) = 0x89;
890         emit_mem((reg),(mem));
891 }
892
893
894 void emit_mov_mem_reg(codegendata *cd, s4 mem, s4 dreg)
895 {
896         COUNT(count_mov_mem_reg);
897         *(cd->mcodeptr++) = 0x8b;
898         emit_mem((dreg),(mem));
899 }
900
901
902 void emit_mov_imm_mem(codegendata *cd, s4 imm, s4 mem)
903 {
904         *(cd->mcodeptr++) = 0xc7;
905         emit_mem(0, mem);
906         emit_imm32(imm);
907 }
908
909
910 void emit_mov_imm_membase(codegendata *cd, s4 imm, s4 basereg, s4 disp)
911 {
912         *(cd->mcodeptr++) = 0xc7;
913         emit_membase(cd, (basereg),(disp),0);
914         emit_imm32((imm));
915 }
916
917
918 void emit_mov_imm_membase32(codegendata *cd, s4 imm, s4 basereg, s4 disp)
919 {
920         *(cd->mcodeptr++) = 0xc7;
921         emit_membase32(cd, (basereg),(disp),0);
922         emit_imm32((imm));
923 }
924
925
926 void emit_movb_imm_membase(codegendata *cd, s4 imm, s4 basereg, s4 disp)
927 {
928         *(cd->mcodeptr++) = 0xc6;
929         emit_membase(cd, (basereg),(disp),0);
930         emit_imm8((imm));
931 }
932
933
934 void emit_movsbl_reg_reg(codegendata *cd, s4 a, s4 b)
935 {
936         assert(a < 4);                     /* Can only operate on al, bl, cl, dl. */
937         *(cd->mcodeptr++) = 0x0f;
938         *(cd->mcodeptr++) = 0xbe;
939         emit_reg((b),(a));
940 }
941
942
943 void emit_movsbl_memindex_reg(codegendata *cd, s4 disp, s4 basereg, s4 indexreg, s4 scale, s4 reg)
944 {
945         COUNT(count_mov_mem_reg);
946         *(cd->mcodeptr++) = 0x0f;
947         *(cd->mcodeptr++) = 0xbe;
948         emit_memindex(cd, (reg),(disp),(basereg),(indexreg),(scale));
949 }
950
951
952 void emit_movswl_reg_reg(codegendata *cd, s4 a, s4 b)
953 {
954         *(cd->mcodeptr++) = 0x0f;
955         *(cd->mcodeptr++) = 0xbf;
956         emit_reg((b),(a));
957 }
958
959
960 void emit_movswl_memindex_reg(codegendata *cd, s4 disp, s4 basereg, s4 indexreg, s4 scale, s4 reg)
961 {
962         COUNT(count_mov_mem_reg);
963         *(cd->mcodeptr++) = 0x0f;
964         *(cd->mcodeptr++) = 0xbf;
965         emit_memindex(cd, (reg),(disp),(basereg),(indexreg),(scale));
966 }
967
968
969 void emit_movzbl_reg_reg(codegendata *cd, s4 a, s4 b)
970 {
971         assert(a < 4);                     /* Can only operate on al, bl, cl, dl. */
972         *(cd->mcodeptr++) = 0x0f;
973         *(cd->mcodeptr++) = 0xb6;
974         emit_reg((b),(a));
975 }
976
977
978 void emit_movzwl_reg_reg(codegendata *cd, s4 a, s4 b)
979 {
980         *(cd->mcodeptr++) = 0x0f;
981         *(cd->mcodeptr++) = 0xb7;
982         emit_reg((b),(a));
983 }
984
985
986 void emit_movzwl_memindex_reg(codegendata *cd, s4 disp, s4 basereg, s4 indexreg, s4 scale, s4 reg)
987 {
988         COUNT(count_mov_mem_reg);
989         *(cd->mcodeptr++) = 0x0f;
990         *(cd->mcodeptr++) = 0xb7;
991         emit_memindex(cd, (reg),(disp),(basereg),(indexreg),(scale));
992 }
993
994
995 void emit_mov_imm_memindex(codegendata *cd, s4 imm, s4 disp, s4 basereg, s4 indexreg, s4 scale)
996 {
997         *(cd->mcodeptr++) = 0xc7;
998         emit_memindex(cd, 0,(disp),(basereg),(indexreg),(scale));
999         emit_imm32((imm));
1000 }
1001
1002
1003 void emit_movw_imm_memindex(codegendata *cd, s4 imm, s4 disp, s4 basereg, s4 indexreg, s4 scale)
1004 {
1005         *(cd->mcodeptr++) = 0x66;
1006         *(cd->mcodeptr++) = 0xc7;
1007         emit_memindex(cd, 0,(disp),(basereg),(indexreg),(scale));
1008         emit_imm16((imm));
1009 }
1010
1011
1012 void emit_movb_imm_memindex(codegendata *cd, s4 imm, s4 disp, s4 basereg, s4 indexreg, s4 scale)
1013 {
1014         *(cd->mcodeptr++) = 0xc6;
1015         emit_memindex(cd, 0,(disp),(basereg),(indexreg),(scale));
1016         emit_imm8((imm));
1017 }
1018
1019
1020 /*
1021  * alu operations
1022  */
1023 void emit_alu_reg_reg(codegendata *cd, s4 opc, s4 reg, s4 dreg)
1024 {
1025         *(cd->mcodeptr++) = (((u1) (opc)) << 3) + 1;
1026         emit_reg((reg),(dreg));
1027 }
1028
1029
1030 void emit_alu_reg_membase(codegendata *cd, s4 opc, s4 reg, s4 basereg, s4 disp)
1031 {
1032         *(cd->mcodeptr++) = (((u1) (opc)) << 3) + 1;
1033         emit_membase(cd, (basereg),(disp),(reg));
1034 }
1035
1036
1037 void emit_alu_membase_reg(codegendata *cd, s4 opc, s4 basereg, s4 disp, s4 reg)
1038 {
1039         *(cd->mcodeptr++) = (((u1) (opc)) << 3) + 3;
1040         emit_membase(cd, (basereg),(disp),(reg));
1041 }
1042
1043
1044 void emit_alu_imm_reg(codegendata *cd, s4 opc, s4 imm, s4 dreg)
1045 {
1046         if (IS_IMM8(imm)) { 
1047                 *(cd->mcodeptr++) = 0x83;
1048                 emit_reg((opc),(dreg));
1049                 emit_imm8((imm));
1050         } else { 
1051                 *(cd->mcodeptr++) = 0x81;
1052                 emit_reg((opc),(dreg));
1053                 emit_imm32((imm));
1054         } 
1055 }
1056
1057
1058 void emit_alu_imm32_reg(codegendata *cd, s4 opc, s4 imm, s4 dreg)
1059 {
1060         *(cd->mcodeptr++) = 0x81;
1061         emit_reg((opc),(dreg));
1062         emit_imm32((imm));
1063 }
1064
1065
1066 void emit_alu_imm_membase(codegendata *cd, s4 opc, s4 imm, s4 basereg, s4 disp)
1067 {
1068         if (IS_IMM8(imm)) { 
1069                 *(cd->mcodeptr++) = 0x83;
1070                 emit_membase(cd, (basereg),(disp),(opc));
1071                 emit_imm8((imm));
1072         } else { 
1073                 *(cd->mcodeptr++) = 0x81;
1074                 emit_membase(cd, (basereg),(disp),(opc));
1075                 emit_imm32((imm));
1076         } 
1077 }
1078
1079
1080 void emit_alu_imm_memabs(codegendata *cd, s4 opc, s4 imm, s4 disp)
1081 {
1082         if (IS_IMM8(imm)) { 
1083                 *(cd->mcodeptr++) = 0x83;
1084                 emit_mem(opc, disp);
1085                 emit_imm8((imm));
1086         } else { 
1087                 *(cd->mcodeptr++) = 0x81;
1088                 emit_mem(opc, disp);
1089                 emit_imm32((imm));
1090         }
1091 }
1092
1093 void emit_alu_memindex_reg(codegendata *cd, s4 opc, s4 disp, s4 basereg, s4 indexreg, s4 scale, s4 reg)
1094 {
1095         *(cd->mcodeptr++) = (((u1) (opc)) << 3) + 3;
1096         emit_memindex(cd, (reg),(disp),(basereg),(indexreg),(scale));
1097 }
1098
1099 void emit_test_reg_reg(codegendata *cd, s4 reg, s4 dreg)
1100 {
1101         *(cd->mcodeptr++) = 0x85;
1102         emit_reg((reg),(dreg));
1103 }
1104
1105
1106 void emit_test_imm_reg(codegendata *cd, s4 imm, s4 reg)
1107 {
1108         *(cd->mcodeptr++) = 0xf7;
1109         emit_reg(0,(reg));
1110         emit_imm32((imm));
1111 }
1112
1113
1114
1115 /*
1116  * inc, dec operations
1117  */
1118 void emit_inc_reg(codegendata *cd, s4 reg)
1119 {
1120         *(cd->mcodeptr++) = 0xff;
1121         emit_reg(0,(reg));
1122 }
1123
1124 void emit_dec_mem(codegendata *cd, s4 mem)
1125 {
1126         *(cd->mcodeptr++) = 0xff;
1127         emit_mem(1,(mem));
1128 }
1129
1130
1131 void emit_imul_reg_reg(codegendata *cd, s4 reg, s4 dreg)
1132 {
1133         *(cd->mcodeptr++) = 0x0f;
1134         *(cd->mcodeptr++) = 0xaf;
1135         emit_reg((dreg),(reg));
1136 }
1137
1138
1139 void emit_imul_membase_reg(codegendata *cd, s4 basereg, s4 disp, s4 dreg)
1140 {
1141         *(cd->mcodeptr++) = 0x0f;
1142         *(cd->mcodeptr++) = 0xaf;
1143         emit_membase(cd, (basereg),(disp),(dreg));
1144 }
1145
1146
1147 void emit_imul_imm_reg(codegendata *cd, s4 imm, s4 dreg)
1148 {
1149         if (IS_IMM8((imm))) { 
1150                 *(cd->mcodeptr++) = 0x6b;
1151                 emit_reg(0,(dreg));
1152                 emit_imm8((imm));
1153         } else { 
1154                 *(cd->mcodeptr++) = 0x69;
1155                 emit_reg(0,(dreg));
1156                 emit_imm32((imm));
1157         } 
1158 }
1159
1160
1161 void emit_imul_imm_reg_reg(codegendata *cd, s4 imm, s4 reg, s4 dreg)
1162 {
1163         if (IS_IMM8((imm))) { 
1164                 *(cd->mcodeptr++) = 0x6b;
1165                 emit_reg((dreg),(reg));
1166                 emit_imm8((imm));
1167         } else { 
1168                 *(cd->mcodeptr++) = 0x69;
1169                 emit_reg((dreg),(reg));
1170                 emit_imm32((imm));
1171         } 
1172 }
1173
1174
1175 void emit_imul_imm_membase_reg(codegendata *cd, s4 imm, s4 basereg, s4 disp, s4 dreg)
1176 {
1177         if (IS_IMM8((imm))) {
1178                 *(cd->mcodeptr++) = 0x6b;
1179                 emit_membase(cd, (basereg),(disp),(dreg));
1180                 emit_imm8((imm));
1181         } else {
1182                 *(cd->mcodeptr++) = 0x69;
1183                 emit_membase(cd, (basereg),(disp),(dreg));
1184                 emit_imm32((imm));
1185         }
1186 }
1187
1188
1189 void emit_mul_reg(codegendata *cd, s4 reg)
1190 {
1191         *(cd->mcodeptr++) = 0xf7;
1192         emit_reg(4, reg);
1193 }
1194
1195
1196 void emit_mul_membase(codegendata *cd, s4 basereg, s4 disp)
1197 {
1198         *(cd->mcodeptr++) = 0xf7;
1199         emit_membase(cd, (basereg),(disp),4);
1200 }
1201
1202
1203 void emit_idiv_reg(codegendata *cd, s4 reg)
1204 {
1205         *(cd->mcodeptr++) = 0xf7;
1206         emit_reg(7,(reg));
1207 }
1208
1209
1210
1211 /*
1212  * shift ops
1213  */
1214 void emit_shift_reg(codegendata *cd, s4 opc, s4 reg)
1215 {
1216         *(cd->mcodeptr++) = 0xd3;
1217         emit_reg((opc),(reg));
1218 }
1219
1220
1221 void emit_shift_imm_reg(codegendata *cd, s4 opc, s4 imm, s4 dreg)
1222 {
1223         if ((imm) == 1) {
1224                 *(cd->mcodeptr++) = 0xd1;
1225                 emit_reg((opc),(dreg));
1226         } else {
1227                 *(cd->mcodeptr++) = 0xc1;
1228                 emit_reg((opc),(dreg));
1229                 emit_imm8((imm));
1230         }
1231 }
1232
1233
1234 void emit_shld_reg_reg(codegendata *cd, s4 reg, s4 dreg)
1235 {
1236         *(cd->mcodeptr++) = 0x0f;
1237         *(cd->mcodeptr++) = 0xa5;
1238         emit_reg((reg),(dreg));
1239 }
1240
1241
1242 void emit_shld_imm_reg_reg(codegendata *cd, s4 imm, s4 reg, s4 dreg)
1243 {
1244         *(cd->mcodeptr++) = 0x0f;
1245         *(cd->mcodeptr++) = 0xa4;
1246         emit_reg((reg),(dreg));
1247         emit_imm8((imm));
1248 }
1249
1250
1251 void emit_shld_reg_membase(codegendata *cd, s4 reg, s4 basereg, s4 disp)
1252 {
1253         *(cd->mcodeptr++) = 0x0f;
1254         *(cd->mcodeptr++) = 0xa5;
1255         emit_membase(cd, (basereg),(disp),(reg));
1256 }
1257
1258
1259 void emit_shrd_reg_reg(codegendata *cd, s4 reg, s4 dreg)
1260 {
1261         *(cd->mcodeptr++) = 0x0f;
1262         *(cd->mcodeptr++) = 0xad;
1263         emit_reg((reg),(dreg));
1264 }
1265
1266
1267 void emit_shrd_imm_reg_reg(codegendata *cd, s4 imm, s4 reg, s4 dreg)
1268 {
1269         *(cd->mcodeptr++) = 0x0f;
1270         *(cd->mcodeptr++) = 0xac;
1271         emit_reg((reg),(dreg));
1272         emit_imm8((imm));
1273 }
1274
1275
1276 void emit_shrd_reg_membase(codegendata *cd, s4 reg, s4 basereg, s4 disp)
1277 {
1278         *(cd->mcodeptr++) = 0x0f;
1279         *(cd->mcodeptr++) = 0xad;
1280         emit_membase(cd, (basereg),(disp),(reg));
1281 }
1282
1283
1284
1285 /*
1286  * jump operations
1287  */
1288 void emit_jmp_imm(codegendata *cd, s4 imm)
1289 {
1290         *(cd->mcodeptr++) = 0xe9;
1291         emit_imm32((imm));
1292 }
1293
1294
1295 void emit_jmp_reg(codegendata *cd, s4 reg)
1296 {
1297         *(cd->mcodeptr++) = 0xff;
1298         emit_reg(4,(reg));
1299 }
1300
1301
1302 void emit_jcc(codegendata *cd, s4 opc, s4 imm)
1303 {
1304         *(cd->mcodeptr++) = 0x0f;
1305         *(cd->mcodeptr++) =  0x80 + (u1) (opc);
1306         emit_imm32((imm));
1307 }
1308
1309
1310
1311 /*
1312  * conditional set operations
1313  */
1314 void emit_setcc_reg(codegendata *cd, s4 opc, s4 reg)
1315 {
1316         *(cd->mcodeptr++) = 0x0f;
1317         *(cd->mcodeptr++) = 0x90 + (u1) (opc);
1318         emit_reg(0,(reg));
1319 }
1320
1321
1322 void emit_setcc_membase(codegendata *cd, s4 opc, s4 basereg, s4 disp)
1323 {
1324         *(cd->mcodeptr++) = 0x0f;
1325         *(cd->mcodeptr++) =  0x90 + (u1) (opc);
1326         emit_membase(cd, (basereg),(disp),0);
1327 }
1328
1329
1330 void emit_xadd_reg_mem(codegendata *cd, s4 reg, s4 mem)
1331 {
1332         *(cd->mcodeptr++) = 0x0f;
1333         *(cd->mcodeptr++) = 0xc1;
1334         emit_mem((reg),(mem));
1335 }
1336
1337
1338 void emit_neg_reg(codegendata *cd, s4 reg)
1339 {
1340         *(cd->mcodeptr++) = 0xf7;
1341         emit_reg(3,(reg));
1342 }
1343
1344
1345
1346 void emit_push_imm(codegendata *cd, s4 imm)
1347 {
1348         *(cd->mcodeptr++) = 0x68;
1349         emit_imm32((imm));
1350 }
1351
1352
1353 void emit_pop_reg(codegendata *cd, s4 reg)
1354 {
1355         *(cd->mcodeptr++) = 0x58 + (0x07 & (u1) (reg));
1356 }
1357
1358
1359 void emit_push_reg(codegendata *cd, s4 reg)
1360 {
1361         *(cd->mcodeptr++) = 0x50 + (0x07 & (u1) (reg));
1362 }
1363
1364
1365 void emit_lock(codegendata *cd)
1366 {
1367         *(cd->mcodeptr++) = 0xf0;
1368 }
1369
1370
1371 /*
1372  * call instructions
1373  */
1374 void emit_call_reg(codegendata *cd, s4 reg)
1375 {
1376         *(cd->mcodeptr++) = 0xff;
1377         emit_reg(2,(reg));
1378 }
1379
1380
1381 void emit_call_imm(codegendata *cd, s4 imm)
1382 {
1383         *(cd->mcodeptr++) = 0xe8;
1384         emit_imm32((imm));
1385 }
1386
1387
1388
1389 /*
1390  * floating point instructions
1391  */
1392 void emit_fld1(codegendata *cd)
1393 {
1394         *(cd->mcodeptr++) = 0xd9;
1395         *(cd->mcodeptr++) = 0xe8;
1396 }
1397
1398
1399 void emit_fldz(codegendata *cd)
1400 {
1401         *(cd->mcodeptr++) = 0xd9;
1402         *(cd->mcodeptr++) = 0xee;
1403 }
1404
1405
1406 void emit_fld_reg(codegendata *cd, s4 reg)
1407 {
1408         *(cd->mcodeptr++) = 0xd9;
1409         *(cd->mcodeptr++) = 0xc0 + (0x07 & (u1) (reg));
1410 }
1411
1412
1413 void emit_flds_membase(codegendata *cd, s4 basereg, s4 disp)
1414 {
1415         *(cd->mcodeptr++) = 0xd9;
1416         emit_membase(cd, (basereg),(disp),0);
1417 }
1418
1419
1420 void emit_flds_membase32(codegendata *cd, s4 basereg, s4 disp)
1421 {
1422         *(cd->mcodeptr++) = 0xd9;
1423         emit_membase32(cd, (basereg),(disp),0);
1424 }
1425
1426
1427 void emit_fldl_membase(codegendata *cd, s4 basereg, s4 disp)
1428 {
1429         *(cd->mcodeptr++) = 0xdd;
1430         emit_membase(cd, (basereg),(disp),0);
1431 }
1432
1433
1434 void emit_fldl_membase32(codegendata *cd, s4 basereg, s4 disp)
1435 {
1436         *(cd->mcodeptr++) = 0xdd;
1437         emit_membase32(cd, (basereg),(disp),0);
1438 }
1439
1440
1441 void emit_fldt_membase(codegendata *cd, s4 basereg, s4 disp)
1442 {
1443         *(cd->mcodeptr++) = 0xdb;
1444         emit_membase(cd, (basereg),(disp),5);
1445 }
1446
1447
1448 void emit_flds_memindex(codegendata *cd, s4 disp, s4 basereg, s4 indexreg, s4 scale)
1449 {
1450         *(cd->mcodeptr++) = 0xd9;
1451         emit_memindex(cd, 0,(disp),(basereg),(indexreg),(scale));
1452 }
1453
1454
1455 void emit_fldl_memindex(codegendata *cd, s4 disp, s4 basereg, s4 indexreg, s4 scale)
1456 {
1457         *(cd->mcodeptr++) = 0xdd;
1458         emit_memindex(cd, 0,(disp),(basereg),(indexreg),(scale));
1459 }
1460
1461
1462 void emit_flds_mem(codegendata *cd, s4 mem)
1463 {
1464         *(cd->mcodeptr++) = 0xd9;
1465         emit_mem(0,(mem));
1466 }
1467
1468
1469 void emit_fldl_mem(codegendata *cd, s4 mem)
1470 {
1471         *(cd->mcodeptr++) = 0xdd;
1472         emit_mem(0,(mem));
1473 }
1474
1475
1476 void emit_fildl_membase(codegendata *cd, s4 basereg, s4 disp)
1477 {
1478         *(cd->mcodeptr++) = 0xdb;
1479         emit_membase(cd, (basereg),(disp),0);
1480 }
1481
1482
1483 void emit_fildll_membase(codegendata *cd, s4 basereg, s4 disp)
1484 {
1485         *(cd->mcodeptr++) = 0xdf;
1486         emit_membase(cd, (basereg),(disp),5);
1487 }
1488
1489
1490 void emit_fst_reg(codegendata *cd, s4 reg)
1491 {
1492         *(cd->mcodeptr++) = 0xdd;
1493         *(cd->mcodeptr++) = 0xd0 + (0x07 & (u1) (reg));
1494 }
1495
1496
1497 void emit_fsts_membase(codegendata *cd, s4 basereg, s4 disp)
1498 {
1499         *(cd->mcodeptr++) = 0xd9;
1500         emit_membase(cd, (basereg),(disp),2);
1501 }
1502
1503
1504 void emit_fstl_membase(codegendata *cd, s4 basereg, s4 disp)
1505 {
1506         *(cd->mcodeptr++) = 0xdd;
1507         emit_membase(cd, (basereg),(disp),2);
1508 }
1509
1510
1511 void emit_fsts_memindex(codegendata *cd, s4 disp, s4 basereg, s4 indexreg, s4 scale)
1512 {
1513         *(cd->mcodeptr++) = 0xd9;
1514         emit_memindex(cd, 2,(disp),(basereg),(indexreg),(scale));
1515 }
1516
1517
1518 void emit_fstl_memindex(codegendata *cd, s4 disp, s4 basereg, s4 indexreg, s4 scale)
1519 {
1520         *(cd->mcodeptr++) = 0xdd;
1521         emit_memindex(cd, 2,(disp),(basereg),(indexreg),(scale));
1522 }
1523
1524
1525 void emit_fstp_reg(codegendata *cd, s4 reg)
1526 {
1527         *(cd->mcodeptr++) = 0xdd;
1528         *(cd->mcodeptr++) = 0xd8 + (0x07 & (u1) (reg));
1529 }
1530
1531
1532 void emit_fstps_membase(codegendata *cd, s4 basereg, s4 disp)
1533 {
1534         *(cd->mcodeptr++) = 0xd9;
1535         emit_membase(cd, (basereg),(disp),3);
1536 }
1537
1538
1539 void emit_fstps_membase32(codegendata *cd, s4 basereg, s4 disp)
1540 {
1541         *(cd->mcodeptr++) = 0xd9;
1542         emit_membase32(cd, (basereg),(disp),3);
1543 }
1544
1545
1546 void emit_fstpl_membase(codegendata *cd, s4 basereg, s4 disp)
1547 {
1548         *(cd->mcodeptr++) = 0xdd;
1549         emit_membase(cd, (basereg),(disp),3);
1550 }
1551
1552
1553 void emit_fstpl_membase32(codegendata *cd, s4 basereg, s4 disp)
1554 {
1555         *(cd->mcodeptr++) = 0xdd;
1556         emit_membase32(cd, (basereg),(disp),3);
1557 }
1558
1559
1560 void emit_fstpt_membase(codegendata *cd, s4 basereg, s4 disp)
1561 {
1562         *(cd->mcodeptr++) = 0xdb;
1563         emit_membase(cd, (basereg),(disp),7);
1564 }
1565
1566
1567 void emit_fstps_memindex(codegendata *cd, s4 disp, s4 basereg, s4 indexreg, s4 scale)
1568 {
1569         *(cd->mcodeptr++) = 0xd9;
1570         emit_memindex(cd, 3,(disp),(basereg),(indexreg),(scale));
1571 }
1572
1573
1574 void emit_fstpl_memindex(codegendata *cd, s4 disp, s4 basereg, s4 indexreg, s4 scale)
1575 {
1576         *(cd->mcodeptr++) = 0xdd;
1577         emit_memindex(cd, 3,(disp),(basereg),(indexreg),(scale));
1578 }
1579
1580
1581 void emit_fstps_mem(codegendata *cd, s4 mem)
1582 {
1583         *(cd->mcodeptr++) = 0xd9;
1584         emit_mem(3,(mem));
1585 }
1586
1587
1588 void emit_fstpl_mem(codegendata *cd, s4 mem)
1589 {
1590         *(cd->mcodeptr++) = 0xdd;
1591         emit_mem(3,(mem));
1592 }
1593
1594
1595 void emit_fistl_membase(codegendata *cd, s4 basereg, s4 disp)
1596 {
1597         *(cd->mcodeptr++) = 0xdb;
1598         emit_membase(cd, (basereg),(disp),2);
1599 }
1600
1601
1602 void emit_fistpl_membase(codegendata *cd, s4 basereg, s4 disp)
1603 {
1604         *(cd->mcodeptr++) = 0xdb;
1605         emit_membase(cd, (basereg),(disp),3);
1606 }
1607
1608
1609 void emit_fistpll_membase(codegendata *cd, s4 basereg, s4 disp)
1610 {
1611         *(cd->mcodeptr++) = 0xdf;
1612         emit_membase(cd, (basereg),(disp),7);
1613 }
1614
1615
1616 void emit_fchs(codegendata *cd)
1617 {
1618         *(cd->mcodeptr++) = 0xd9;
1619         *(cd->mcodeptr++) = 0xe0;
1620 }
1621
1622
1623 void emit_faddp(codegendata *cd)
1624 {
1625         *(cd->mcodeptr++) = 0xde;
1626         *(cd->mcodeptr++) = 0xc1;
1627 }
1628
1629
1630 void emit_fadd_reg_st(codegendata *cd, s4 reg)
1631 {
1632         *(cd->mcodeptr++) = 0xd8;
1633         *(cd->mcodeptr++) = 0xc0 + (0x0f & (u1) (reg));
1634 }
1635
1636
1637 void emit_fadd_st_reg(codegendata *cd, s4 reg)
1638 {
1639         *(cd->mcodeptr++) = 0xdc;
1640         *(cd->mcodeptr++) = 0xc0 + (0x0f & (u1) (reg));
1641 }
1642
1643
1644 void emit_faddp_st_reg(codegendata *cd, s4 reg)
1645 {
1646         *(cd->mcodeptr++) = 0xde;
1647         *(cd->mcodeptr++) = 0xc0 + (0x0f & (u1) (reg));
1648 }
1649
1650
1651 void emit_fadds_membase(codegendata *cd, s4 basereg, s4 disp)
1652 {
1653         *(cd->mcodeptr++) = 0xd8;
1654         emit_membase(cd, (basereg),(disp),0);
1655 }
1656
1657
1658 void emit_faddl_membase(codegendata *cd, s4 basereg, s4 disp)
1659 {
1660         *(cd->mcodeptr++) = 0xdc;
1661         emit_membase(cd, (basereg),(disp),0);
1662 }
1663
1664
1665 void emit_fsub_reg_st(codegendata *cd, s4 reg)
1666 {
1667         *(cd->mcodeptr++) = 0xd8;
1668         *(cd->mcodeptr++) = 0xe0 + (0x07 & (u1) (reg));
1669 }
1670
1671
1672 void emit_fsub_st_reg(codegendata *cd, s4 reg)
1673 {
1674         *(cd->mcodeptr++) = 0xdc;
1675         *(cd->mcodeptr++) = 0xe8 + (0x07 & (u1) (reg));
1676 }
1677
1678
1679 void emit_fsubp_st_reg(codegendata *cd, s4 reg)
1680 {
1681         *(cd->mcodeptr++) = 0xde;
1682         *(cd->mcodeptr++) = 0xe8 + (0x07 & (u1) (reg));
1683 }
1684
1685
1686 void emit_fsubp(codegendata *cd)
1687 {
1688         *(cd->mcodeptr++) = 0xde;
1689         *(cd->mcodeptr++) = 0xe9;
1690 }
1691
1692
1693 void emit_fsubs_membase(codegendata *cd, s4 basereg, s4 disp)
1694 {
1695         *(cd->mcodeptr++) = 0xd8;
1696         emit_membase(cd, (basereg),(disp),4);
1697 }
1698
1699
1700 void emit_fsubl_membase(codegendata *cd, s4 basereg, s4 disp)
1701 {
1702         *(cd->mcodeptr++) = 0xdc;
1703         emit_membase(cd, (basereg),(disp),4);
1704 }
1705
1706
1707 void emit_fmul_reg_st(codegendata *cd, s4 reg)
1708 {
1709         *(cd->mcodeptr++) = 0xd8;
1710         *(cd->mcodeptr++) = 0xc8 + (0x07 & (u1) (reg));
1711 }
1712
1713
1714 void emit_fmul_st_reg(codegendata *cd, s4 reg)
1715 {
1716         *(cd->mcodeptr++) = 0xdc;
1717         *(cd->mcodeptr++) = 0xc8 + (0x07 & (u1) (reg));
1718 }
1719
1720
1721 void emit_fmulp(codegendata *cd)
1722 {
1723         *(cd->mcodeptr++) = 0xde;
1724         *(cd->mcodeptr++) = 0xc9;
1725 }
1726
1727
1728 void emit_fmulp_st_reg(codegendata *cd, s4 reg)
1729 {
1730         *(cd->mcodeptr++) = 0xde;
1731         *(cd->mcodeptr++) = 0xc8 + (0x07 & (u1) (reg));
1732 }
1733
1734
1735 void emit_fmuls_membase(codegendata *cd, s4 basereg, s4 disp)
1736 {
1737         *(cd->mcodeptr++) = 0xd8;
1738         emit_membase(cd, (basereg),(disp),1);
1739 }
1740
1741
1742 void emit_fmull_membase(codegendata *cd, s4 basereg, s4 disp)
1743 {
1744         *(cd->mcodeptr++) = 0xdc;
1745         emit_membase(cd, (basereg),(disp),1);
1746 }
1747
1748
1749 void emit_fdiv_reg_st(codegendata *cd, s4 reg)
1750 {
1751         *(cd->mcodeptr++) = 0xd8;
1752         *(cd->mcodeptr++) = 0xf0 + (0x07 & (u1) (reg));
1753 }
1754
1755
1756 void emit_fdiv_st_reg(codegendata *cd, s4 reg)
1757 {
1758         *(cd->mcodeptr++) = 0xdc;
1759         *(cd->mcodeptr++) = 0xf8 + (0x07 & (u1) (reg));
1760 }
1761
1762
1763 void emit_fdivp(codegendata *cd)
1764 {
1765         *(cd->mcodeptr++) = 0xde;
1766         *(cd->mcodeptr++) = 0xf9;
1767 }
1768
1769
1770 void emit_fdivp_st_reg(codegendata *cd, s4 reg)
1771 {
1772         *(cd->mcodeptr++) = 0xde;
1773         *(cd->mcodeptr++) = 0xf8 + (0x07 & (u1) (reg));
1774 }
1775
1776
1777 void emit_fxch(codegendata *cd)
1778 {
1779         *(cd->mcodeptr++) = 0xd9;
1780         *(cd->mcodeptr++) = 0xc9;
1781 }
1782
1783
1784 void emit_fxch_reg(codegendata *cd, s4 reg)
1785 {
1786         *(cd->mcodeptr++) = 0xd9;
1787         *(cd->mcodeptr++) = 0xc8 + (0x07 & (reg));
1788 }
1789
1790
1791 void emit_fprem(codegendata *cd)
1792 {
1793         *(cd->mcodeptr++) = 0xd9;
1794         *(cd->mcodeptr++) = 0xf8;
1795 }
1796
1797
1798 void emit_fprem1(codegendata *cd)
1799 {
1800         *(cd->mcodeptr++) = 0xd9;
1801         *(cd->mcodeptr++) = 0xf5;
1802 }
1803
1804
1805 void emit_fucom(codegendata *cd)
1806 {
1807         *(cd->mcodeptr++) = 0xdd;
1808         *(cd->mcodeptr++) = 0xe1;
1809 }
1810
1811
1812 void emit_fucom_reg(codegendata *cd, s4 reg)
1813 {
1814         *(cd->mcodeptr++) = 0xdd;
1815         *(cd->mcodeptr++) = 0xe0 + (0x07 & (u1) (reg));
1816 }
1817
1818
1819 void emit_fucomp_reg(codegendata *cd, s4 reg)
1820 {
1821         *(cd->mcodeptr++) = 0xdd;
1822         *(cd->mcodeptr++) = 0xe8 + (0x07 & (u1) (reg));
1823 }
1824
1825
1826 void emit_fucompp(codegendata *cd)
1827 {
1828         *(cd->mcodeptr++) = 0xda;
1829         *(cd->mcodeptr++) = 0xe9;
1830 }
1831
1832
1833 void emit_fnstsw(codegendata *cd)
1834 {
1835         *(cd->mcodeptr++) = 0xdf;
1836         *(cd->mcodeptr++) = 0xe0;
1837 }
1838
1839
1840 void emit_sahf(codegendata *cd)
1841 {
1842         *(cd->mcodeptr++) = 0x9e;
1843 }
1844
1845
1846 void emit_finit(codegendata *cd)
1847 {
1848         *(cd->mcodeptr++) = 0x9b;
1849         *(cd->mcodeptr++) = 0xdb;
1850         *(cd->mcodeptr++) = 0xe3;
1851 }
1852
1853
1854 void emit_fldcw_mem(codegendata *cd, s4 mem)
1855 {
1856         *(cd->mcodeptr++) = 0xd9;
1857         emit_mem(5,(mem));
1858 }
1859
1860
1861 void emit_fldcw_membase(codegendata *cd, s4 basereg, s4 disp)
1862 {
1863         *(cd->mcodeptr++) = 0xd9;
1864         emit_membase(cd, (basereg),(disp),5);
1865 }
1866
1867
1868 void emit_wait(codegendata *cd)
1869 {
1870         *(cd->mcodeptr++) = 0x9b;
1871 }
1872
1873
1874 void emit_ffree_reg(codegendata *cd, s4 reg)
1875 {
1876         *(cd->mcodeptr++) = 0xdd;
1877         *(cd->mcodeptr++) = 0xc0 + (0x07 & (u1) (reg));
1878 }
1879
1880
1881 void emit_fdecstp(codegendata *cd)
1882 {
1883         *(cd->mcodeptr++) = 0xd9;
1884         *(cd->mcodeptr++) = 0xf6;
1885 }
1886
1887
1888 void emit_fincstp(codegendata *cd)
1889 {
1890         *(cd->mcodeptr++) = 0xd9;
1891         *(cd->mcodeptr++) = 0xf7;
1892 }
1893
1894 #if defined(ENABLE_ESCAPE_CHECK)
1895 void emit_escape_check(codegendata *cd, s4 reg) {
1896         M_PUSH(reg);
1897         M_MOV_IMM(asm_escape_check, REG_ITMP3);
1898         M_CALL(REG_ITMP3);
1899         M_IADD_IMM(4, REG_SP);
1900 }
1901 #endif
1902
1903 /*
1904  * These are local overrides for various environment variables in Emacs.
1905  * Please do not remove this and leave it at the end of the file, where
1906  * Emacs will automagically detect them.
1907  * ---------------------------------------------------------------------
1908  * Local variables:
1909  * mode: c
1910  * indent-tabs-mode: t
1911  * c-basic-offset: 4
1912  * tab-width: 4
1913  * End:
1914  */