1 /* src/vm/jit/allocator/simplereg.c - register allocator
3 Copyright (C) 1996-2005 R. Grafl, A. Krall, C. Kruegel, C. Oates,
4 R. Obermaisser, M. Platter, M. Probst, S. Ring, E. Steiner,
5 C. Thalinger, D. Thuernbeck, P. Tomsich, C. Ullrich, J. Wenninger,
6 Institut f. Computersprachen - TU Wien
8 This file is part of CACAO.
10 This program is free software; you can redistribute it and/or
11 modify it under the terms of the GNU General Public License as
12 published by the Free Software Foundation; either version 2, or (at
13 your option) any later version.
15 This program is distributed in the hope that it will be useful, but
16 WITHOUT ANY WARRANTY; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
18 General Public License for more details.
20 You should have received a copy of the GNU General Public License
21 along with this program; if not, write to the Free Software
22 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
25 Contact: cacao@complang.tuwien.ac.at
27 Authors: Andreas Krall
35 $Id: simplereg.c 5404 2006-09-07 13:29:05Z christian $
48 #include "vm/builtin.h"
49 #include "vm/exceptions.h"
50 #include "mm/memory.h"
51 #include "vm/method.h"
52 #include "vm/options.h"
53 #include "vm/resolve.h"
54 #include "vm/stringlocal.h"
55 #include "vm/jit/reg.h"
56 #include "vm/jit/allocator/simplereg.h"
59 /* function prototypes for this file ******************************************/
61 static void interface_regalloc(jitdata *jd);
62 static void local_regalloc(jitdata *jd);
63 static void new_allocate_scratch_registers(jitdata *jd);
64 static void allocate_scratch_registers(jitdata *jd);
67 /* regalloc ********************************************************************
69 Does a simple register allocation.
71 *******************************************************************************/
73 bool new_regalloc(jitdata *jd)
75 /* There is a problem with the use of unused float argument
76 registers in leafmethods for stackslots on c7 (2 * Dual Core
77 AMD Opteron(tm) Processor 270) - runtime for the jvm98 _mtrt
78 benchmark is heaviliy increased. This could be prevented by
79 setting rd->argfltreguse to FLT_ARG_CNT before calling
80 allocate_scratch_registers and setting it back to the original
81 value before calling local_regalloc. */
83 printf("------- rd->memuse bef %d\n",jd->rd->memuse);
85 interface_regalloc(jd);
86 printf("------- rd->memuse int %d\n",jd->rd->memuse);
87 new_allocate_scratch_registers(jd);
88 printf("------- rd->memuse scr %d\n",jd->rd->memuse);
90 printf("------- rd->memuse loc %d\n",jd->rd->memuse);
98 /* interface_regalloc **********************************************************
100 Allocates registers for all interface variables.
102 *******************************************************************************/
104 static void interface_regalloc(jitdata *jd)
111 int intalloc, fltalloc; /* Remember allocated Register/Memory offset */
112 /* in case more vars are packed into this interface slot */
114 int intregsneeded = 0;
116 /* allocate LNG and DBL Types first to ensure 2 memory slots or registers */
117 /* on HAS_4BYTE_STACKSLOT architectures */
118 int typeloop[] = { TYPE_LNG, TYPE_DBL, TYPE_INT, TYPE_FLT, TYPE_ADR };
120 /* get required compiler data */
126 /* rd->memuse was already set in stack.c to allocate stack space
127 for passing arguments to called methods. */
129 #if defined(__I386__)
130 if (checksync && (m->flags & ACC_SYNCHRONIZED)) {
131 /* reserve 0(%esp) for Monitorenter/exit Argument on i386 */
137 if (jd->isleafmethod) {
138 /* Reserve argument register, which will be used for Locals acting */
140 if (rd->argintreguse < m->parseddesc->argintreguse)
141 rd->argintreguse = m->parseddesc->argintreguse;
142 if (rd->argfltreguse < m->parseddesc->argfltreguse)
143 rd->argfltreguse = m->parseddesc->argfltreguse;
144 #ifdef HAS_ADDRESS_REGISTER_FILE
145 if (rd->argadrreguse < m->parseddesc->argadrreguse)
146 rd->argadrreguse = m->parseddesc->argadrreguse;
151 for (s = 0; s < cd->maxstack; s++) {
152 intalloc = -1; fltalloc = -1;
156 for (tt = 0; tt <=4; tt++) {
157 if ((t = jd->interface_map[s * 5 + TYPE_INT]) != UNUSED) {
158 saved |= (jd->var[t].flags & SAVEDVAR);
162 for (tt = 0; tt <= 4; tt++) {
164 if (jd->interface_map[s * 5 + t] == UNUSED)
167 v = &(jd->var[jd->interface_map[s * 5 + t]]);
168 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
169 intregsneeded = (IS_2_WORD_TYPE(t)) ? 1 : 0;
171 #if defined(HAS_4BYTE_STACKSLOT)
172 memneeded = (IS_2_WORD_TYPE(t)) ? 1 : 0;
175 #if defined(HAS_ADDRESS_REGISTER_FILE)
176 if (IS_ADR_TYPE(t)) {
177 if (!jd->isleafmethod
178 &&(rd->argadrreguse < ADR_ARG_CNT)) {
179 v->regoff = rd->argadrregs[rd->argadrreguse++];
180 } else if (rd->tmpadrreguse > 0) {
181 v->regoff = rd->tmpadrregs[--rd->tmpadrreguse];
182 } else if (rd->savadrreguse > 0) {
183 v->regoff = rd->savadrregs[--rd->savadrreguse];
185 v->flags |= INMEMORY;
186 v->regoff = rd->memuse++;
188 } else /* !IS_ADR_TYPE */
189 #endif /* defined(HAS_ADDRESS_REGISTER_FILE) */
191 if (IS_FLT_DBL_TYPE(t)) {
193 /* Reuse memory slot(s)/register(s) for shared interface slots */
194 v->flags |= jd->var[fltalloc].flags & INMEMORY;
195 v->regoff = jd->var[fltalloc].regoff;
196 } else if (rd->argfltreguse < FLT_ARG_CNT) {
197 v->regoff = rd->argfltregs[rd->argfltreguse++];
198 } else if (rd->tmpfltreguse > 0) {
199 v->regoff = rd->tmpfltregs[--rd->tmpfltreguse];
200 } else if (rd->savfltreguse > 0) {
201 v->regoff = rd->savfltregs[--rd->savfltreguse];
203 v->flags |= INMEMORY;
204 #if defined(ALIGN_DOUBLES_IN_MEMORY)
205 /* Align doubles in Memory */
206 if ( (memneeded) && (rd->memuse & 1))
209 v->regoff = rd->memuse;
210 rd->memuse += memneeded + 1;
212 fltalloc = jd->interface_map[s * 5 + t];
213 } else { /* !IS_FLT_DBL_TYPE(t) */
214 #if defined(HAS_4BYTE_STACKSLOT) && !defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
216 * for i386 put all longs in memory
218 if (IS_2_WORD_TYPE(t)) {
219 v->flags |= INMEMORY;
220 #if defined(ALIGN_LONGS_IN_MEMORY)
221 /* Align longs in Memory */
225 v->regoff = rd->memuse;
226 rd->memuse += memneeded + 1;
228 #endif /* defined(HAS_4BYTE_STACKSLOT) && !defined(SUPPORT_COMBINE...GISTERS) */
230 /* Reuse memory slot(s)/register(s) for shared interface slots */
231 v->flags |= jd->var[intalloc].flags
233 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
234 if (!(v->flags & INMEMORY)
235 && IS_2_WORD_TYPE(jd->var[intalloc].type))
236 v->regoff = GET_LOW_REG(
237 jd->var[intalloc].regoff);
241 jd->var[intalloc].regoff;
243 if (rd->argintreguse + intregsneeded
245 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
248 rd->argintregs[rd->argintreguse],
249 rd->argintregs[rd->argintreguse + 1]);
253 rd->argintregs[rd->argintreguse];
254 rd->argintreguse += intregsneeded + 1;
256 else if (rd->tmpintreguse > intregsneeded) {
257 rd->tmpintreguse -= intregsneeded + 1;
258 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
261 rd->tmpintregs[rd->tmpintreguse],
262 rd->tmpintregs[rd->tmpintreguse + 1]);
266 rd->tmpintregs[rd->tmpintreguse];
268 else if (rd->savintreguse > intregsneeded) {
269 rd->savintreguse -= intregsneeded + 1;
271 rd->savintregs[rd->savintreguse];
272 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
275 rd->savintregs[rd->savintreguse],
276 rd->savintregs[rd->savintreguse + 1]);
280 rd->savintregs[rd->savintreguse];
283 v->flags |= INMEMORY;
284 #if defined(ALIGN_LONGS_IN_MEMORY)
285 /* Align longs in Memory */
286 if ( (memneeded) && (rd->memuse & 1))
289 v->regoff = rd->memuse;
290 rd->memuse += memneeded + 1;
293 intalloc = jd->interface_map[s * 5 + t];
294 } /* if (IS_FLT_DBL_TYPE(t)) */
296 } else { /* (saved) */
297 /* now the same like above, but without a chance to take a temporary register */
298 #ifdef HAS_ADDRESS_REGISTER_FILE
299 if (IS_ADR_TYPE(t)) {
300 if (rd->savadrreguse > 0) {
301 v->regoff = rd->savadrregs[--rd->savadrreguse];
304 v->flags |= INMEMORY;
305 v->regoff = rd->memuse++;
310 if (IS_FLT_DBL_TYPE(t)) {
312 v->flags |= jd->var[fltalloc].flags & INMEMORY;
313 v->regoff = jd->var[fltalloc].regoff;
315 if (rd->savfltreguse > 0) {
317 rd->savfltregs[--rd->savfltreguse];
320 v->flags |= INMEMORY;
321 #if defined(ALIGN_DOUBLES_IN_MEMORY)
322 /* Align doubles in Memory */
323 if ( (memneeded) && (rd->memuse & 1))
326 v->regoff = rd->memuse;
327 rd->memuse += memneeded + 1;
329 fltalloc = jd->interface_map[s * 5 + t];
331 else { /* IS_INT_LNG */
332 #if defined(HAS_4BYTE_STACKSLOT) && !defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
334 * for i386 put all longs in memory
336 if (IS_2_WORD_TYPE(t)) {
337 v->flags |= INMEMORY;
338 #if defined(ALIGN_LONGS_IN_MEMORY)
339 /* Align longs in Memory */
343 v->regoff = rd->memuse;
344 rd->memuse += memneeded + 1;
349 v->flags |= jd->var[intalloc].flags
351 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
352 if (!(v->flags & INMEMORY)
353 && IS_2_WORD_TYPE(jd->var[intalloc].type))
356 jd->var[intalloc].regoff);
360 jd->var[intalloc].regoff;
362 if (rd->savintreguse > intregsneeded) {
363 rd->savintreguse -= intregsneeded + 1;
364 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
366 v->regoff = PACK_REGS(
367 rd->savintregs[rd->savintreguse],
368 rd->savintregs[rd->savintreguse + 1]);
372 rd->savintregs[rd->savintreguse];
374 v->flags |= INMEMORY;
375 #if defined(ALIGN_LONGS_IN_MEMORY)
376 /* Align longs in Memory */
377 if ( (memneeded) && (rd->memuse & 1))
380 v->regoff = rd->memuse;
381 rd->memuse += memneeded + 1;
386 } /* if (IS_FLT_DBL_TYPE(t) else */
387 } /* if (IS_ADR_TYPE(t)) else */
388 } /* if (saved) else */
394 /* interface_regalloc **********************************************************
396 Allocates registers for all interface variables.
398 *******************************************************************************/
400 static void interface_regalloc(jitdata *jd)
407 int intalloc, fltalloc; /* Remember allocated Register/Memory offset */
408 /* in case a more vars are packed into this interface slot */
410 int intregsneeded = 0;
412 /* allocate LNG and DBL Types first to ensure 2 memory slots or registers */
413 /* on HAS_4BYTE_STACKSLOT architectures */
414 int typeloop[] = { TYPE_LNG, TYPE_DBL, TYPE_INT, TYPE_FLT, TYPE_ADR };
416 /* get required compiler data */
422 /* rd->memuse was already set in stack.c to allocate stack space
423 for passing arguments to called methods. */
425 #if defined(__I386__)
426 if (checksync && (m->flags & ACC_SYNCHRONIZED)) {
427 /* reserve 0(%esp) for Monitorenter/exit Argument on i386 */
433 if (jd->isleafmethod) {
434 /* Reserve argument register, which will be used for Locals acting */
436 if (rd->argintreguse < m->parseddesc->argintreguse)
437 rd->argintreguse = m->parseddesc->argintreguse;
438 if (rd->argfltreguse < m->parseddesc->argfltreguse)
439 rd->argfltreguse = m->parseddesc->argfltreguse;
440 #ifdef HAS_ADDRESS_REGISTER_FILE
441 if (rd->argadrreguse < m->parseddesc->argadrreguse)
442 rd->argadrreguse = m->parseddesc->argadrreguse;
447 for (s = 0; s < cd->maxstack; s++) {
448 intalloc = -1; fltalloc = -1;
449 saved = (rd->interfaces[s][TYPE_INT].flags |
450 rd->interfaces[s][TYPE_LNG].flags |
451 rd->interfaces[s][TYPE_FLT].flags |
452 rd->interfaces[s][TYPE_DBL].flags |
453 rd->interfaces[s][TYPE_ADR].flags) & SAVEDVAR;
455 for (tt = 0; tt <= 4; tt++) {
457 v = &rd->interfaces[s][t];
459 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
460 intregsneeded = (IS_2_WORD_TYPE(t)) ? 1 : 0;
462 #if defined(HAS_4BYTE_STACKSLOT)
463 memneeded = (IS_2_WORD_TYPE(t)) ? 1 : 0;
466 #if defined(HAS_ADDRESS_REGISTER_FILE)
467 if (IS_ADR_TYPE(t)) {
468 if (!jd->isleafmethod
469 &&(rd->argadrreguse < ADR_ARG_CNT)) {
470 v->regoff = rd->argadrregs[rd->argadrreguse++];
471 } else if (rd->tmpadrreguse > 0) {
472 v->regoff = rd->tmpadrregs[--rd->tmpadrreguse];
473 } else if (rd->savadrreguse > 0) {
474 v->regoff = rd->savadrregs[--rd->savadrreguse];
476 v->flags |= INMEMORY;
477 v->regoff = rd->memuse++;
479 } else /* !IS_ADR_TYPE */
480 #endif /* defined(HAS_ADDRESS_REGISTER_FILE) */
482 if (IS_FLT_DBL_TYPE(t)) {
484 /* Reuse memory slot(s)/register(s) for shared interface slots */
485 v->flags |= rd->interfaces[s][fltalloc].flags
487 v->regoff = rd->interfaces[s][fltalloc].regoff;
488 } else if (rd->argfltreguse < FLT_ARG_CNT) {
489 v->regoff = rd->argfltregs[rd->argfltreguse++];
490 } else if (rd->tmpfltreguse > 0) {
491 v->regoff = rd->tmpfltregs[--rd->tmpfltreguse];
492 } else if (rd->savfltreguse > 0) {
493 v->regoff = rd->savfltregs[--rd->savfltreguse];
495 v->flags |= INMEMORY;
496 #if defined(ALIGN_DOUBLES_IN_MEMORY)
497 /* Align doubles in Memory */
498 if ( (memneeded) && (rd->memuse & 1))
501 v->regoff = rd->memuse;
502 rd->memuse += memneeded + 1;
505 } else { /* !IS_FLT_DBL_TYPE(t) */
506 #if defined(HAS_4BYTE_STACKSLOT) && !defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
508 * for i386 put all longs in memory
510 if (IS_2_WORD_TYPE(t)) {
511 v->flags |= INMEMORY;
512 #if defined(ALIGN_LONGS_IN_MEMORY)
513 /* Align longs in Memory */
517 v->regoff = rd->memuse;
518 rd->memuse += memneeded + 1;
520 #endif /* defined(HAS_4BYTE_STACKSLOT) && !defined(SUPPORT_COMBINE...GISTERS) */
522 /* Reuse memory slot(s)/register(s) for shared interface slots */
524 rd->interfaces[s][intalloc].flags
526 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
527 if (!(v->flags & INMEMORY)
528 && IS_2_WORD_TYPE(intalloc))
529 v->regoff = GET_LOW_REG(
530 rd->interfaces[s][intalloc].regoff);
534 rd->interfaces[s][intalloc].regoff;
536 if (rd->argintreguse + intregsneeded
538 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
541 rd->argintregs[rd->argintreguse],
542 rd->argintregs[rd->argintreguse + 1]);
546 rd->argintregs[rd->argintreguse];
547 rd->argintreguse += intregsneeded + 1;
549 else if (rd->tmpintreguse > intregsneeded) {
550 rd->tmpintreguse -= intregsneeded + 1;
551 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
554 rd->tmpintregs[rd->tmpintreguse],
555 rd->tmpintregs[rd->tmpintreguse + 1]);
559 rd->tmpintregs[rd->tmpintreguse];
561 else if (rd->savintreguse > intregsneeded) {
562 rd->savintreguse -= intregsneeded + 1;
564 rd->savintregs[rd->savintreguse];
565 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
568 rd->savintregs[rd->savintreguse],
569 rd->savintregs[rd->savintreguse + 1]);
573 rd->savintregs[rd->savintreguse];
576 v->flags |= INMEMORY;
577 #if defined(ALIGN_LONGS_IN_MEMORY)
578 /* Align longs in Memory */
579 if ( (memneeded) && (rd->memuse & 1))
582 v->regoff = rd->memuse;
583 rd->memuse += memneeded + 1;
587 } /* if (IS_FLT_DBL_TYPE(t)) */
589 } else { /* (saved) */
590 /* now the same like above, but without a chance to take a temporary register */
591 #ifdef HAS_ADDRESS_REGISTER_FILE
592 if (IS_ADR_TYPE(t)) {
593 if (rd->savadrreguse > 0) {
594 v->regoff = rd->savadrregs[--rd->savadrreguse];
597 v->flags |= INMEMORY;
598 v->regoff = rd->memuse++;
603 if (IS_FLT_DBL_TYPE(t)) {
605 v->flags |= rd->interfaces[s][fltalloc].flags
607 v->regoff = rd->interfaces[s][fltalloc].regoff;
609 if (rd->savfltreguse > 0) {
610 v->regoff = rd->savfltregs[--rd->savfltreguse];
613 v->flags |= INMEMORY;
614 #if defined(ALIGN_DOUBLES_IN_MEMORY)
615 /* Align doubles in Memory */
616 if ( (memneeded) && (rd->memuse & 1))
619 v->regoff = rd->memuse;
620 rd->memuse += memneeded + 1;
624 else { /* IS_INT_LNG */
625 #if defined(HAS_4BYTE_STACKSLOT) && !defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
627 * for i386 put all longs in memory
629 if (IS_2_WORD_TYPE(t)) {
630 v->flags |= INMEMORY;
631 #if defined(ALIGN_LONGS_IN_MEMORY)
632 /* Align longs in Memory */
636 v->regoff = rd->memuse;
637 rd->memuse += memneeded + 1;
643 rd->interfaces[s][intalloc].flags & INMEMORY;
644 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
645 if (!(v->flags & INMEMORY)
646 && IS_2_WORD_TYPE(intalloc))
649 rd->interfaces[s][intalloc].regoff);
653 rd->interfaces[s][intalloc].regoff;
655 if (rd->savintreguse > intregsneeded) {
656 rd->savintreguse -= intregsneeded + 1;
657 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
659 v->regoff = PACK_REGS(
660 rd->savintregs[rd->savintreguse],
661 rd->savintregs[rd->savintreguse + 1]);
665 rd->savintregs[rd->savintreguse];
667 v->flags |= INMEMORY;
668 #if defined(ALIGN_LONGS_IN_MEMORY)
669 /* Align longs in Memory */
670 if ( (memneeded) && (rd->memuse & 1))
673 v->regoff = rd->memuse;
674 rd->memuse += memneeded + 1;
679 } /* if (IS_FLT_DBL_TYPE(t) else */
680 } /* if (IS_ADR_TYPE(t)) else */
681 } /* if (saved) else */
682 } /* if (type >= 0) */
686 #endif /* defined(NEW_VAR) */
690 /* local_regalloc **************************************************************
692 Allocates registers for all local variables.
694 *******************************************************************************/
696 static void local_regalloc(jitdata *jd)
703 int intalloc, fltalloc;
705 int intregsneeded = 0;
707 int typeloop[] = { TYPE_LNG, TYPE_DBL, TYPE_INT, TYPE_FLT, TYPE_ADR };
708 int fargcnt, iargcnt;
709 #ifdef HAS_ADDRESS_REGISTER_FILE
713 /* get required compiler data */
719 if (jd->isleafmethod) {
720 methoddesc *md = m->parseddesc;
722 iargcnt = rd->argintreguse;
723 fargcnt = rd->argfltreguse;
724 #ifdef HAS_ADDRESS_REGISTER_FILE
725 aargcnt = rd->argadrreguse;
727 for (p = 0, s = 0; s < cd->maxlocals; s++, p++) {
728 intalloc = -1; fltalloc = -1;
729 for (tt = 0; tt <= 4; tt++) {
731 lm = jd->local_map[s * 5 + t];
737 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
738 intregsneeded = (IS_2_WORD_TYPE(t)) ? 1 : 0;
740 #if defined(HAS_4BYTE_STACKSLOT)
741 memneeded = (IS_2_WORD_TYPE(t)) ? 1 : 0;
747 * #ifdef HAS_ADDRESS_REGISTER_FILE
754 * } else { / int & lng
758 * must not to be changed!
761 #ifdef HAS_ADDRESS_REGISTER_FILE
762 if (IS_ADR_TYPE(t)) {
763 if ((p < md->paramcount) && !md->params[p].inmemory) {
765 v->regoff = rd->argadrregs[md->params[p].regoff];
767 else if (rd->tmpadrreguse > 0) {
769 v->regoff = rd->tmpadrregs[--rd->tmpadrreguse];
771 /* use unused argument registers as local registers */
772 else if ((p >= md->paramcount) &&
773 (aargcnt < ADR_ARG_CNT)) {
775 v->regoff = rd->argadrregs[aargcnt++];
777 else if (rd->savadrreguse > 0) {
779 v->regoff = rd->savadrregs[--rd->savadrreguse];
782 v->flags |= INMEMORY;
783 v->regoff = rd->memuse++;
787 if (IS_FLT_DBL_TYPE(t)) {
789 v->flags = jd->var[fltalloc].flags;
790 v->regoff = jd->var[fltalloc].regoff;
792 #if !defined(SUPPORT_PASS_FLOATARGS_IN_INTREGS)
793 /* We can only use float arguments as local variables,
794 * if we do not pass them in integer registers. */
795 else if ((p < md->paramcount) &&
796 !md->params[p].inmemory) {
798 v->regoff = rd->argfltregs[md->params[p].regoff];
801 else if (rd->tmpfltreguse > 0) {
803 v->regoff = rd->tmpfltregs[--rd->tmpfltreguse];
805 /* use unused argument registers as local registers */
806 else if ((p >= md->paramcount) &&
807 (fargcnt < FLT_ARG_CNT)) {
809 v->regoff = rd->argfltregs[fargcnt];
812 else if (rd->savfltreguse > 0) {
814 v->regoff = rd->savfltregs[--rd->savfltreguse];
818 #if defined(ALIGN_DOUBLES_IN_MEMORY)
819 /* Align doubles in Memory */
820 if ( (memneeded) && (rd->memuse & 1))
823 v->regoff = rd->memuse;
824 rd->memuse += memneeded + 1;
826 fltalloc = jd->local_map[s * 5 + t];
829 #if defined(HAS_4BYTE_STACKSLOT) && !defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
831 * for i386 put all longs in memory
833 if (IS_2_WORD_TYPE(t)) {
835 #if defined(ALIGN_LONGS_IN_MEMORY)
836 /* Align longs in Memory */
840 v->regoff = rd->memuse;
841 rd->memuse += memneeded + 1;
846 v->flags = jd->var[intalloc].flags;
847 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
848 if (!(v->flags & INMEMORY)
849 && IS_2_WORD_TYPE(jd->var[intalloc].type))
850 v->regoff = GET_LOW_REG(
851 jd->var[intalloc].regoff);
854 v->regoff = jd->var[intalloc].regoff;
856 else if ((p < md->paramcount) &&
857 !md->params[p].inmemory) {
859 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
860 if (IS_2_WORD_TYPE(t))
861 v->regoff = PACK_REGS(
862 rd->argintregs[GET_LOW_REG(md->params[p].regoff)],
863 rd->argintregs[GET_HIGH_REG(md->params[p].regoff)]);
867 rd->argintregs[md->params[p].regoff];
869 else if (rd->tmpintreguse > intregsneeded) {
870 rd->tmpintreguse -= intregsneeded + 1;
872 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
874 v->regoff = PACK_REGS(
875 rd->tmpintregs[rd->tmpintreguse],
876 rd->tmpintregs[rd->tmpintreguse + 1]);
880 rd->tmpintregs[rd->tmpintreguse];
883 * use unused argument registers as local registers
885 else if ((p >= m->parseddesc->paramcount) &&
886 (iargcnt + intregsneeded < INT_ARG_CNT)) {
888 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
891 rd->argintregs[iargcnt],
892 rd->argintregs[iargcnt + 1]);
895 v->regoff = rd->argintregs[iargcnt];
896 iargcnt += intregsneeded + 1;
898 else if (rd->savintreguse > intregsneeded) {
899 rd->savintreguse -= intregsneeded + 1;
901 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
903 v->regoff = PACK_REGS(
904 rd->savintregs[rd->savintreguse],
905 rd->savintregs[rd->savintreguse + 1]);
908 v->regoff =rd->savintregs[rd->savintreguse];
912 #if defined(ALIGN_LONGS_IN_MEMORY)
913 /* Align longs in Memory */
914 if ( (memneeded) && (rd->memuse & 1))
917 v->regoff = rd->memuse;
918 rd->memuse += memneeded + 1;
921 intalloc = jd->local_map[s * 5 + t];
923 #ifdef HAS_ADDRESS_REGISTER_FILE
926 } /* for (tt=0;...) */
928 /* If the current parameter is a 2-word type, the next local slot */
931 if (p < md->paramcount)
932 if (IS_2_WORD_TYPE(md->paramtypes[p].type))
938 for (s = 0; s < cd->maxlocals; s++) {
939 intalloc = -1; fltalloc = -1;
940 for (tt=0; tt<=4; tt++) {
943 lm = jd->local_map[s * 5 + t];
949 #ifdef SUPPORT_COMBINE_INTEGER_REGISTERS
950 intregsneeded = (IS_2_WORD_TYPE(t)) ? 1 : 0;
952 #if defined(HAS_4BYTE_STACKSLOT)
953 memneeded = (IS_2_WORD_TYPE(t)) ? 1 : 0;
955 #ifdef HAS_ADDRESS_REGISTER_FILE
956 if ( IS_ADR_TYPE(t) ) {
957 if (rd->savadrreguse > 0) {
959 v->regoff = rd->savadrregs[--rd->savadrreguse];
963 v->regoff = rd->memuse++;
967 if (IS_FLT_DBL_TYPE(t)) {
969 v->flags = jd->var[fltalloc].flags;
970 v->regoff = jd->var[fltalloc].regoff;
972 else if (rd->savfltreguse > 0) {
974 v->regoff = rd->savfltregs[--rd->savfltreguse];
978 #if defined(ALIGN_DOUBLES_IN_MEMORY)
979 /* Align doubles in Memory */
980 if ( (memneeded) && (rd->memuse & 1))
983 v->regoff = rd->memuse;
984 rd->memuse += memneeded + 1;
986 fltalloc = jd->local_map[s * 5 + t];
989 #if defined(HAS_4BYTE_STACKSLOT) && !defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
991 * for i386 put all longs in memory
993 if (IS_2_WORD_TYPE(t)) {
995 #if defined(ALIGN_LONGS_IN_MEMORY)
996 /* Align longs in Memory */
1000 v->regoff = rd->memuse;
1001 rd->memuse += memneeded + 1;
1004 if (intalloc >= 0) {
1005 v->flags = jd->var[intalloc].flags;
1006 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1007 if (!(v->flags & INMEMORY)
1008 && IS_2_WORD_TYPE(jd->var[intalloc].type))
1009 v->regoff = GET_LOW_REG(
1010 jd->var[intalloc].regoff);
1013 v->regoff = jd->var[intalloc].regoff;
1015 else if (rd->savintreguse > intregsneeded) {
1016 rd->savintreguse -= intregsneeded+1;
1018 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1020 v->regoff = PACK_REGS(
1021 rd->savintregs[rd->savintreguse],
1022 rd->savintregs[rd->savintreguse + 1]);
1025 v->regoff =rd->savintregs[rd->savintreguse];
1028 v->flags = INMEMORY;
1029 #if defined(ALIGN_LONGS_IN_MEMORY)
1030 /* Align longs in Memory */
1031 if ( (memneeded) && (rd->memuse & 1))
1034 v->regoff = rd->memuse;
1035 rd->memuse += memneeded + 1;
1037 #if defined(HAS_4BYTE_STACKSLOT) && !defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1040 intalloc = jd->local_map[s * 5 + t];
1042 #ifdef HAS_ADDRESS_REGISTER_FILE
1050 /* local_regalloc **************************************************************
1052 Allocates registers for all local variables.
1054 *******************************************************************************/
1056 static void local_regalloc(jitdata *jd)
1063 int intalloc, fltalloc;
1065 int intregsneeded = 0;
1067 int typeloop[] = { TYPE_LNG, TYPE_DBL, TYPE_INT, TYPE_FLT, TYPE_ADR };
1068 int fargcnt, iargcnt;
1069 #ifdef HAS_ADDRESS_REGISTER_FILE
1073 /* get required compiler data */
1079 if (jd->isleafmethod) {
1080 methoddesc *md = m->parseddesc;
1082 iargcnt = rd->argintreguse;
1083 fargcnt = rd->argfltreguse;
1084 #ifdef HAS_ADDRESS_REGISTER_FILE
1085 aargcnt = rd->argadrreguse;
1087 for (p = 0, s = 0; s < cd->maxlocals; s++, p++) {
1088 intalloc = -1; fltalloc = -1;
1089 for (tt = 0; tt <= 4; tt++) {
1091 v = &rd->locals[s][t];
1096 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1097 intregsneeded = (IS_2_WORD_TYPE(t)) ? 1 : 0;
1099 #if defined(HAS_4BYTE_STACKSLOT)
1100 memneeded = (IS_2_WORD_TYPE(t)) ? 1 : 0;
1106 * #ifdef HAS_ADDRESS_REGISTER_FILE
1107 * if (IS_ADR_TYPE) {
1113 * } else { / int & lng
1117 * must not to be changed!
1120 #ifdef HAS_ADDRESS_REGISTER_FILE
1121 if (IS_ADR_TYPE(t)) {
1122 if ((p < md->paramcount) && !md->params[p].inmemory) {
1124 v->regoff = rd->argadrregs[md->params[p].regoff];
1126 else if (rd->tmpadrreguse > 0) {
1128 v->regoff = rd->tmpadrregs[--rd->tmpadrreguse];
1130 /* use unused argument registers as local registers */
1131 else if ((p >= md->paramcount) &&
1132 (aargcnt < ADR_ARG_CNT)) {
1134 v->regoff = rd->argadrregs[aargcnt++];
1136 else if (rd->savadrreguse > 0) {
1138 v->regoff = rd->savadrregs[--rd->savadrreguse];
1141 v->flags |= INMEMORY;
1142 v->regoff = rd->memuse++;
1146 if (IS_FLT_DBL_TYPE(t)) {
1147 if (fltalloc >= 0) {
1148 v->flags = rd->locals[s][fltalloc].flags;
1149 v->regoff = rd->locals[s][fltalloc].regoff;
1151 #if !defined(SUPPORT_PASS_FLOATARGS_IN_INTREGS)
1152 /* We can only use float arguments as local variables,
1153 * if we do not pass them in integer registers. */
1154 else if ((p < md->paramcount) &&
1155 !md->params[p].inmemory) {
1157 v->regoff = rd->argfltregs[md->params[p].regoff];
1160 else if (rd->tmpfltreguse > 0) {
1162 v->regoff = rd->tmpfltregs[--rd->tmpfltreguse];
1164 /* use unused argument registers as local registers */
1165 else if ((p >= md->paramcount) &&
1166 (fargcnt < FLT_ARG_CNT)) {
1168 v->regoff = rd->argfltregs[fargcnt];
1171 else if (rd->savfltreguse > 0) {
1173 v->regoff = rd->savfltregs[--rd->savfltreguse];
1176 v->flags = INMEMORY;
1177 #if defined(ALIGN_DOUBLES_IN_MEMORY)
1178 /* Align doubles in Memory */
1179 if ( (memneeded) && (rd->memuse & 1))
1182 v->regoff = rd->memuse;
1183 rd->memuse += memneeded + 1;
1188 #if defined(HAS_4BYTE_STACKSLOT) && !defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1190 * for i386 put all longs in memory
1192 if (IS_2_WORD_TYPE(t)) {
1193 v->flags = INMEMORY;
1194 #if defined(ALIGN_LONGS_IN_MEMORY)
1195 /* Align longs in Memory */
1199 v->regoff = rd->memuse;
1200 rd->memuse += memneeded + 1;
1204 if (intalloc >= 0) {
1205 v->flags = rd->locals[s][intalloc].flags;
1206 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1207 if (!(v->flags & INMEMORY)
1208 && IS_2_WORD_TYPE(intalloc))
1209 v->regoff = GET_LOW_REG(
1210 rd->locals[s][intalloc].regoff);
1213 v->regoff = rd->locals[s][intalloc].regoff;
1215 else if ((p < md->paramcount) &&
1216 !md->params[p].inmemory) {
1218 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1219 if (IS_2_WORD_TYPE(t))
1220 v->regoff = PACK_REGS(
1221 rd->argintregs[GET_LOW_REG(md->params[p].regoff)],
1222 rd->argintregs[GET_HIGH_REG(md->params[p].regoff)]);
1226 rd->argintregs[md->params[p].regoff];
1228 else if (rd->tmpintreguse > intregsneeded) {
1229 rd->tmpintreguse -= intregsneeded + 1;
1231 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1233 v->regoff = PACK_REGS(
1234 rd->tmpintregs[rd->tmpintreguse],
1235 rd->tmpintregs[rd->tmpintreguse + 1]);
1239 rd->tmpintregs[rd->tmpintreguse];
1242 * use unused argument registers as local registers
1244 else if ((p >= m->parseddesc->paramcount) &&
1245 (iargcnt + intregsneeded < INT_ARG_CNT)) {
1247 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1249 v->regoff=PACK_REGS(
1250 rd->argintregs[iargcnt],
1251 rd->argintregs[iargcnt + 1]);
1254 v->regoff = rd->argintregs[iargcnt];
1255 iargcnt += intregsneeded + 1;
1257 else if (rd->savintreguse > intregsneeded) {
1258 rd->savintreguse -= intregsneeded + 1;
1260 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1262 v->regoff = PACK_REGS(
1263 rd->savintregs[rd->savintreguse],
1264 rd->savintregs[rd->savintreguse + 1]);
1267 v->regoff =rd->savintregs[rd->savintreguse];
1270 v->flags = INMEMORY;
1271 #if defined(ALIGN_LONGS_IN_MEMORY)
1272 /* Align longs in Memory */
1273 if ( (memneeded) && (rd->memuse & 1))
1276 v->regoff = rd->memuse;
1277 rd->memuse += memneeded + 1;
1282 #ifdef HAS_ADDRESS_REGISTER_FILE
1285 } /* for (tt=0;...) */
1287 /* If the current parameter is a 2-word type, the next local slot */
1290 if (p < md->paramcount)
1291 if (IS_2_WORD_TYPE(md->paramtypes[p].type))
1297 for (s = 0; s < cd->maxlocals; s++) {
1298 intalloc = -1; fltalloc = -1;
1299 for (tt=0; tt<=4; tt++) {
1301 v = &rd->locals[s][t];
1304 #ifdef SUPPORT_COMBINE_INTEGER_REGISTERS
1305 intregsneeded = (IS_2_WORD_TYPE(t)) ? 1 : 0;
1307 #if defined(HAS_4BYTE_STACKSLOT)
1308 memneeded = (IS_2_WORD_TYPE(t)) ? 1 : 0;
1310 #ifdef HAS_ADDRESS_REGISTER_FILE
1311 if ( IS_ADR_TYPE(t) ) {
1312 if (rd->savadrreguse > 0) {
1314 v->regoff = rd->savadrregs[--rd->savadrreguse];
1317 v->flags = INMEMORY;
1318 v->regoff = rd->memuse++;
1322 if (IS_FLT_DBL_TYPE(t)) {
1323 if (fltalloc >= 0) {
1324 v->flags = rd->locals[s][fltalloc].flags;
1325 v->regoff = rd->locals[s][fltalloc].regoff;
1327 else if (rd->savfltreguse > 0) {
1329 v->regoff = rd->savfltregs[--rd->savfltreguse];
1332 v->flags = INMEMORY;
1333 #if defined(ALIGN_DOUBLES_IN_MEMORY)
1334 /* Align doubles in Memory */
1335 if ( (memneeded) && (rd->memuse & 1))
1338 v->regoff = rd->memuse;
1339 rd->memuse += memneeded + 1;
1344 #if defined(HAS_4BYTE_STACKSLOT) && !defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1346 * for i386 put all longs in memory
1348 if (IS_2_WORD_TYPE(t)) {
1349 v->flags = INMEMORY;
1350 #if defined(ALIGN_LONGS_IN_MEMORY)
1351 /* Align longs in Memory */
1355 v->regoff = rd->memuse;
1356 rd->memuse += memneeded + 1;
1359 if (intalloc >= 0) {
1360 v->flags = rd->locals[s][intalloc].flags;
1361 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1362 if (!(v->flags & INMEMORY)
1363 && IS_2_WORD_TYPE(intalloc))
1364 v->regoff = GET_LOW_REG(
1365 rd->locals[s][intalloc].regoff);
1368 v->regoff = rd->locals[s][intalloc].regoff;
1370 else if (rd->savintreguse > intregsneeded) {
1371 rd->savintreguse -= intregsneeded+1;
1373 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1375 v->regoff = PACK_REGS(
1376 rd->savintregs[rd->savintreguse],
1377 rd->savintregs[rd->savintreguse + 1]);
1380 v->regoff =rd->savintregs[rd->savintreguse];
1383 v->flags = INMEMORY;
1384 #if defined(ALIGN_LONGS_IN_MEMORY)
1385 /* Align longs in Memory */
1386 if ( (memneeded) && (rd->memuse & 1))
1389 v->regoff = rd->memuse;
1390 rd->memuse += memneeded + 1;
1392 #if defined(HAS_4BYTE_STACKSLOT) && !defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1397 #ifdef HAS_ADDRESS_REGISTER_FILE
1405 #endif /* defined(NEW_VAR) */
1407 static void reg_init_temp(methodinfo *m, registerdata *rd)
1410 #if defined(HAS_4BYTE_STACKSLOT)
1411 rd->freememtop_2 = 0;
1414 rd->freetmpinttop = 0;
1415 rd->freesavinttop = 0;
1416 rd->freetmpflttop = 0;
1417 rd->freesavflttop = 0;
1418 #ifdef HAS_ADDRESS_REGISTER_FILE
1419 rd->freetmpadrtop = 0;
1420 rd->freesavadrtop = 0;
1423 rd->freearginttop = 0;
1424 rd->freeargflttop = 0;
1425 #ifdef HAS_ADDRESS_REGISTER_FILE
1426 rd->freeargadrtop = 0;
1430 #if defined(NEW_VAR)
1432 #define reg_new_temp(jd,index) \
1433 if ( (index >= jd->localcount) \
1434 && (!(jd->var[index].flags & OUTVAR)) \
1435 && (!(jd->var[index].flags & PREALLOC)) ) \
1436 reg_new_temp_func(jd, index)
1438 static void reg_new_temp_func(jitdata *jd, s4 index)
1447 v = &(jd->var[index]);
1449 /* Try to allocate a saved register if there is no temporary one */
1450 /* available. This is what happens during the second run. */
1451 tryagain = (v->flags & SAVEDVAR) ? 1 : 2;
1453 #ifdef SUPPORT_COMBINE_INTEGER_REGISTERS
1454 intregsneeded = (IS_2_WORD_TYPE(v->type)) ? 1 : 0;
1458 #if defined(HAS_4BYTE_STACKSLOT)
1459 memneeded = (IS_2_WORD_TYPE(v->type)) ? 1 : 0;
1464 for(; tryagain; --tryagain) {
1465 if (tryagain == 1) {
1466 if (!(v->flags & SAVEDVAR))
1467 v->flags |= SAVEDTMP;
1468 #ifdef HAS_ADDRESS_REGISTER_FILE
1469 if (IS_ADR_TYPE(v->type)) {
1470 if (rd->freesavadrtop > 0) {
1471 v->regoff = rd->freesavadrregs[--rd->freesavadrtop];
1473 } else if (rd->savadrreguse > 0) {
1474 v->regoff = rd->savadrregs[--rd->savadrreguse];
1480 if (IS_FLT_DBL_TYPE(v->type)) {
1481 if (rd->freesavflttop > 0) {
1482 v->regoff = rd->freesavfltregs[--rd->freesavflttop];
1484 } else if (rd->savfltreguse > 0) {
1485 v->regoff = rd->savfltregs[--rd->savfltreguse];
1489 #if defined(HAS_4BYTE_STACKSLOT) && !defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1491 * for i386 put all longs in memory
1493 if (!IS_2_WORD_TYPE(v->type))
1496 if (rd->freesavinttop > intregsneeded) {
1497 rd->freesavinttop -= intregsneeded + 1;
1498 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1500 v->regoff = PACK_REGS(
1501 rd->freesavintregs[rd->freesavinttop],
1502 rd->freesavintregs[rd->freesavinttop + 1]);
1506 rd->freesavintregs[rd->freesavinttop];
1508 } else if (rd->savintreguse > intregsneeded) {
1509 rd->savintreguse -= intregsneeded + 1;
1510 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1512 v->regoff = PACK_REGS(
1513 rd->savintregs[rd->savintreguse],
1514 rd->savintregs[rd->savintreguse + 1]);
1517 v->regoff = rd->savintregs[rd->savintreguse];
1523 } else { /* tryagain == 2 */
1524 #ifdef HAS_ADDRESS_REGISTER_FILE
1525 if (IS_ADR_TYPE(v->type)) {
1526 if (rd->freetmpadrtop > 0) {
1527 v->regoff = rd->freetmpadrregs[--rd->freetmpadrtop];
1529 } else if (rd->tmpadrreguse > 0) {
1530 v->regoff = rd->tmpadrregs[--rd->tmpadrreguse];
1536 if (IS_FLT_DBL_TYPE(v->type)) {
1537 if (rd->freeargflttop > 0) {
1538 v->regoff = rd->freeargfltregs[--rd->freeargflttop];
1541 } else if (rd->argfltreguse < FLT_ARG_CNT) {
1542 v->regoff = rd->argfltregs[rd->argfltreguse++];
1545 } else if (rd->freetmpflttop > 0) {
1546 v->regoff = rd->freetmpfltregs[--rd->freetmpflttop];
1548 } else if (rd->tmpfltreguse > 0) {
1549 v->regoff = rd->tmpfltregs[--rd->tmpfltreguse];
1554 #if defined(HAS_4BYTE_STACKSLOT) && !defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1556 * for i386 put all longs in memory
1558 if (!IS_2_WORD_TYPE(v->type))
1561 if (rd->freearginttop > intregsneeded) {
1562 rd->freearginttop -= intregsneeded + 1;
1564 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1566 v->regoff = PACK_REGS(
1567 rd->freeargintregs[rd->freearginttop],
1568 rd->freeargintregs[rd->freearginttop + 1]);
1572 rd->freeargintregs[rd->freearginttop];
1574 } else if (rd->argintreguse
1575 < INT_ARG_CNT - intregsneeded) {
1576 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1578 v->regoff = PACK_REGS(
1579 rd->argintregs[rd->argintreguse],
1580 rd->argintregs[rd->argintreguse + 1]);
1583 v->regoff = rd->argintregs[rd->argintreguse];
1585 rd->argintreguse += intregsneeded + 1;
1587 } else if (rd->freetmpinttop > intregsneeded) {
1588 rd->freetmpinttop -= intregsneeded + 1;
1589 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1591 v->regoff = PACK_REGS(
1592 rd->freetmpintregs[rd->freetmpinttop],
1593 rd->freetmpintregs[rd->freetmpinttop + 1]);
1596 v->regoff = rd->freetmpintregs[rd->freetmpinttop];
1598 } else if (rd->tmpintreguse > intregsneeded) {
1599 rd->tmpintreguse -= intregsneeded + 1;
1600 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1602 v->regoff = PACK_REGS(
1603 rd->tmpintregs[rd->tmpintreguse],
1604 rd->tmpintregs[rd->tmpintreguse + 1]);
1607 v->regoff = rd->tmpintregs[rd->tmpintreguse];
1610 } /* if (!IS_2_WORD_TYPE(s->type)) */
1611 } /* if (IS_FLT_DBL_TYPE(s->type)) */
1612 } /* if (IS_ADR_TYPE(s->type)) */
1613 } /* if (tryagain == 1) else */
1614 } /* for(; tryagain; --tryagain) */
1616 #if defined(HAS_4BYTE_STACKSLOT)
1617 if ((memneeded == 1) && (rd->freememtop_2 > 0)) {
1619 v->regoff = rd->freemem_2[rd->freememtop_2];
1621 #endif /*defined(HAS_4BYTE_STACKSLOT) */
1622 if ((memneeded == 0) && (rd->freememtop > 0)) {
1624 v->regoff = rd->freemem[rd->freememtop];
1626 #if defined(ALIGN_LONGS_IN_MEMORY) || defined(ALIGN_DOUBLES_IN_MEMORY)
1627 /* align 2 Word Types */
1628 if ((memneeded) && ((rd->memuse & 1) == 1)) {
1629 /* Put patched memory slot on freemem */
1630 rd->freemem[rd->freememtop++] = rd->memuse;
1633 #endif /* defined(ALIGN_LONGS_IN_MEMORY) || defined(ALIGN_DOUBLES_IN_MEMORY) */
1634 v->regoff = rd->memuse;
1635 rd->memuse += memneeded + 1;
1637 v->flags |= INMEMORY;
1640 #define reg_new_temp(rd,s) if (s->varkind == TEMPVAR) reg_new_temp_func(rd, s)
1642 static void reg_new_temp_func(registerdata *rd, stackptr s)
1648 /* Try to allocate a saved register if there is no temporary one */
1649 /* available. This is what happens during the second run. */
1650 tryagain = (s->flags & SAVEDVAR) ? 1 : 2;
1652 #ifdef SUPPORT_COMBINE_INTEGER_REGISTERS
1653 intregsneeded = (IS_2_WORD_TYPE(s->type)) ? 1 : 0;
1657 #if defined(HAS_4BYTE_STACKSLOT)
1658 memneeded = (IS_2_WORD_TYPE(s->type)) ? 1 : 0;
1663 for(; tryagain; --tryagain) {
1664 if (tryagain == 1) {
1665 if (!(s->flags & SAVEDVAR))
1666 s->flags |= SAVEDTMP;
1667 #ifdef HAS_ADDRESS_REGISTER_FILE
1668 if (IS_ADR_TYPE(s->type)) {
1669 if (rd->freesavadrtop > 0) {
1670 s->regoff = rd->freesavadrregs[--rd->freesavadrtop];
1672 } else if (rd->savadrreguse > 0) {
1673 s->regoff = rd->savadrregs[--rd->savadrreguse];
1679 if (IS_FLT_DBL_TYPE(s->type)) {
1680 if (rd->freesavflttop > 0) {
1681 s->regoff = rd->freesavfltregs[--rd->freesavflttop];
1683 } else if (rd->savfltreguse > 0) {
1684 s->regoff = rd->savfltregs[--rd->savfltreguse];
1688 #if defined(HAS_4BYTE_STACKSLOT) && !defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1690 * for i386 put all longs in memory
1692 if (!IS_2_WORD_TYPE(s->type))
1695 if (rd->freesavinttop > intregsneeded) {
1696 rd->freesavinttop -= intregsneeded + 1;
1697 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1699 s->regoff = PACK_REGS(
1700 rd->freesavintregs[rd->freesavinttop],
1701 rd->freesavintregs[rd->freesavinttop + 1]);
1705 rd->freesavintregs[rd->freesavinttop];
1707 } else if (rd->savintreguse > intregsneeded) {
1708 rd->savintreguse -= intregsneeded + 1;
1709 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1711 s->regoff = PACK_REGS(
1712 rd->savintregs[rd->savintreguse],
1713 rd->savintregs[rd->savintreguse + 1]);
1716 s->regoff = rd->savintregs[rd->savintreguse];
1722 } else { /* tryagain == 2 */
1723 #ifdef HAS_ADDRESS_REGISTER_FILE
1724 if (IS_ADR_TYPE(s->type)) {
1725 if (rd->freetmpadrtop > 0) {
1726 s->regoff = rd->freetmpadrregs[--rd->freetmpadrtop];
1728 } else if (rd->tmpadrreguse > 0) {
1729 s->regoff = rd->tmpadrregs[--rd->tmpadrreguse];
1735 if (IS_FLT_DBL_TYPE(s->type)) {
1736 if (rd->freeargflttop > 0) {
1737 s->regoff = rd->freeargfltregs[--rd->freeargflttop];
1740 } else if (rd->argfltreguse < FLT_ARG_CNT) {
1741 s->regoff = rd->argfltregs[rd->argfltreguse++];
1744 } else if (rd->freetmpflttop > 0) {
1745 s->regoff = rd->freetmpfltregs[--rd->freetmpflttop];
1747 } else if (rd->tmpfltreguse > 0) {
1748 s->regoff = rd->tmpfltregs[--rd->tmpfltreguse];
1753 #if defined(HAS_4BYTE_STACKSLOT) && !defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1755 * for i386 put all longs in memory
1757 if (!IS_2_WORD_TYPE(s->type))
1760 if (rd->freearginttop > intregsneeded) {
1761 rd->freearginttop -= intregsneeded + 1;
1763 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1765 s->regoff = PACK_REGS(
1766 rd->freeargintregs[rd->freearginttop],
1767 rd->freeargintregs[rd->freearginttop + 1]);
1771 rd->freeargintregs[rd->freearginttop];
1773 } else if (rd->argintreguse
1774 < INT_ARG_CNT - intregsneeded) {
1775 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1777 s->regoff = PACK_REGS(
1778 rd->argintregs[rd->argintreguse],
1779 rd->argintregs[rd->argintreguse + 1]);
1782 s->regoff = rd->argintregs[rd->argintreguse];
1784 rd->argintreguse += intregsneeded + 1;
1786 } else if (rd->freetmpinttop > intregsneeded) {
1787 rd->freetmpinttop -= intregsneeded + 1;
1788 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1790 s->regoff = PACK_REGS(
1791 rd->freetmpintregs[rd->freetmpinttop],
1792 rd->freetmpintregs[rd->freetmpinttop + 1]);
1795 s->regoff = rd->freetmpintregs[rd->freetmpinttop];
1797 } else if (rd->tmpintreguse > intregsneeded) {
1798 rd->tmpintreguse -= intregsneeded + 1;
1799 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1801 s->regoff = PACK_REGS(
1802 rd->tmpintregs[rd->tmpintreguse],
1803 rd->tmpintregs[rd->tmpintreguse + 1]);
1806 s->regoff = rd->tmpintregs[rd->tmpintreguse];
1809 } /* if (!IS_2_WORD_TYPE(s->type)) */
1810 } /* if (IS_FLT_DBL_TYPE(s->type)) */
1811 } /* if (IS_ADR_TYPE(s->type)) */
1812 } /* if (tryagain == 1) else */
1813 } /* for(; tryagain; --tryagain) */
1815 #if defined(HAS_4BYTE_STACKSLOT)
1816 if ((memneeded == 1) && (rd->freememtop_2 > 0)) {
1818 s->regoff = rd->freemem_2[rd->freememtop_2];
1820 #endif /*defined(HAS_4BYTE_STACKSLOT) */
1821 if ((memneeded == 0) && (rd->freememtop > 0)) {
1823 s->regoff = rd->freemem[rd->freememtop];
1825 #if defined(ALIGN_LONGS_IN_MEMORY) || defined(ALIGN_DOUBLES_IN_MEMORY)
1826 /* align 2 Word Types */
1827 if ((memneeded) && ((rd->memuse & 1) == 1)) {
1828 /* Put patched memory slot on freemem */
1829 rd->freemem[rd->freememtop++] = rd->memuse;
1832 #endif /* defined(ALIGN_LONGS_IN_MEMORY) || defined(ALIGN_DOUBLES_IN_MEMORY) */
1833 s->regoff = rd->memuse;
1834 rd->memuse += memneeded + 1;
1836 s->flags |= INMEMORY;
1840 #if defined(NEW_VAR)
1841 #define reg_free_temp(jd,index) \
1842 if ((index > jd->localcount) \
1843 && (!(jd->var[index].flags & OUTVAR)) \
1844 && (!(jd->var[index].flags & STCOPY)) \
1845 && (!(jd->var[index].flags & PREALLOC)) ) \
1846 reg_free_temp_func(jd, index)
1848 /* Do not free regs/memory locations used by Stackslots flagged STCOPY! There is still another Stackslot */
1849 /* alive using this reg/memory location */
1851 static void reg_free_temp_func(jitdata *jd, s4 index)
1859 v = &(jd->var[index]);
1862 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1863 intregsneeded = (IS_2_WORD_TYPE(v->type)) ? 1 : 0;
1868 #if defined(HAS_4BYTE_STACKSLOT)
1869 memneeded = (IS_2_WORD_TYPE(v->type)) ? 1 : 0;
1874 if (v->flags & INMEMORY) {
1875 #if defined(HAS_4BYTE_STACKSLOT)
1876 if (memneeded > 0) {
1877 rd->freemem_2[rd->freememtop_2] = v->regoff;
1882 rd->freemem[rd->freememtop] = v->regoff;
1886 #ifdef HAS_ADDRESS_REGISTER_FILE
1887 } else if (IS_ADR_TYPE(v->type)) {
1888 if (v->flags & (SAVEDVAR | SAVEDTMP)) {
1889 /* v->flags &= ~SAVEDTMP; */
1890 rd->freesavadrregs[rd->freesavadrtop++] = v->regoff;
1892 rd->freetmpadrregs[rd->freetmpadrtop++] = v->regoff;
1894 } else if (IS_FLT_DBL_TYPE(v->type)) {
1895 if (v->flags & (SAVEDVAR | SAVEDTMP)) {
1896 /* v->flags &= ~SAVEDTMP; */
1897 rd->freesavfltregs[rd->freesavflttop++] = v->regoff;
1898 } else if (v->flags & TMPARG) {
1899 /* v->flags &= ~TMPARG; */
1900 rd->freeargfltregs[rd->freeargflttop++] = v->regoff;
1902 rd->freetmpfltregs[rd->freetmpflttop++] = v->regoff;
1903 } else { /* IS_INT_LNG_TYPE */
1904 if (v->flags & (SAVEDVAR | SAVEDTMP)) {
1905 /* v->flags &= ~SAVEDTMP; */
1906 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1907 if (intregsneeded) {
1908 rd->freesavintregs[rd->freesavinttop] =
1909 GET_LOW_REG(v->regoff);
1910 rd->freesavintregs[rd->freesavinttop + 1] =
1911 GET_HIGH_REG(v->regoff);
1914 rd->freesavintregs[rd->freesavinttop] = v->regoff;
1915 rd->freesavinttop += intregsneeded + 1;
1917 } else if (v->flags & TMPARG) {
1918 /* s->flags &= ~TMPARG; */
1919 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1920 if (intregsneeded) {
1921 rd->freeargintregs[rd->freearginttop] =
1922 GET_LOW_REG(v->regoff);
1923 rd->freeargintregs[rd->freearginttop + 1] =
1924 GET_HIGH_REG(v->regoff);
1927 rd->freeargintregs[rd->freearginttop] = v->regoff;
1928 rd->freearginttop += intregsneeded + 1;
1930 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1931 if (intregsneeded) {
1932 rd->freetmpintregs[rd->freetmpinttop] =
1933 GET_LOW_REG(s->regoff);
1934 rd->freetmpintregs[rd->freetmpinttop + 1] =
1935 GET_HIGH_REG(s->regoff);
1938 rd->freetmpintregs[rd->freetmpinttop] = v->regoff;
1939 rd->freetmpinttop += intregsneeded + 1;
1945 #define reg_free_temp(rd,s) if (((s)->varkind == TEMPVAR) && (!((s)->flags & STCOPY))) reg_free_temp_func(rd, (s))
1947 /* Do not free regs/memory locations used by Stackslots flagged STCOPY! There is still another Stackslot */
1948 /* alive using this reg/memory location */
1950 static void reg_free_temp_func(registerdata *rd, stackptr s)
1955 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
1956 intregsneeded = (IS_2_WORD_TYPE(s->type)) ? 1 : 0;
1961 #if defined(HAS_4BYTE_STACKSLOT)
1962 memneeded = (IS_2_WORD_TYPE(s->type)) ? 1 : 0;
1967 if (s->flags & INMEMORY) {
1968 #if defined(HAS_4BYTE_STACKSLOT)
1969 if (memneeded > 0) {
1970 rd->freemem_2[rd->freememtop_2] = s->regoff;
1975 rd->freemem[rd->freememtop] = s->regoff;
1979 #ifdef HAS_ADDRESS_REGISTER_FILE
1980 } else if (IS_ADR_TYPE(s->type)) {
1981 if (s->flags & (SAVEDVAR | SAVEDTMP)) {
1982 /* s->flags &= ~SAVEDTMP; */
1983 rd->freesavadrregs[rd->freesavadrtop++] = s->regoff;
1985 rd->freetmpadrregs[rd->freetmpadrtop++] = s->regoff;
1987 } else if (IS_FLT_DBL_TYPE(s->type)) {
1988 if (s->flags & (SAVEDVAR | SAVEDTMP)) {
1989 /* s->flags &= ~SAVEDTMP; */
1990 rd->freesavfltregs[rd->freesavflttop++] = s->regoff;
1991 } else if (s->flags & TMPARG) {
1992 /* s->flags &= ~TMPARG; */
1993 rd->freeargfltregs[rd->freeargflttop++] = s->regoff;
1995 rd->freetmpfltregs[rd->freetmpflttop++] = s->regoff;
1996 } else { /* IS_INT_LNG_TYPE */
1997 if (s->flags & (SAVEDVAR | SAVEDTMP)) {
1998 /* s->flags &= ~SAVEDTMP; */
1999 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
2000 if (intregsneeded) {
2001 rd->freesavintregs[rd->freesavinttop] =
2002 GET_LOW_REG(s->regoff);
2003 rd->freesavintregs[rd->freesavinttop + 1] =
2004 GET_HIGH_REG(s->regoff);
2007 rd->freesavintregs[rd->freesavinttop] = s->regoff;
2008 rd->freesavinttop += intregsneeded + 1;
2010 } else if (s->flags & TMPARG) {
2011 /* s->flags &= ~TMPARG; */
2012 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
2013 if (intregsneeded) {
2014 rd->freeargintregs[rd->freearginttop] =
2015 GET_LOW_REG(s->regoff);
2016 rd->freeargintregs[rd->freearginttop + 1] =
2017 GET_HIGH_REG(s->regoff);
2020 rd->freeargintregs[rd->freearginttop] = s->regoff;
2021 rd->freearginttop += intregsneeded + 1;
2023 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
2024 if (intregsneeded) {
2025 rd->freetmpintregs[rd->freetmpinttop] =
2026 GET_LOW_REG(s->regoff);
2027 rd->freetmpintregs[rd->freetmpinttop + 1] =
2028 GET_HIGH_REG(s->regoff);
2031 rd->freetmpintregs[rd->freetmpinttop] = s->regoff;
2032 rd->freetmpinttop += intregsneeded + 1;
2039 #if !defined(NEW_VAR)
2040 static bool reg_alloc_dup(stackptr src, stackptr dst) {
2041 /* only copy TEMPVARS, do not mess with STACKVAR, */
2042 /* LOCALVAR, or ARGVAR */
2043 if ((src->varkind == TEMPVAR) && (dst->varkind == TEMPVAR)) {
2044 /* can not allocate a REG_TMP to a REG_SAV Slot */
2045 if (src->flags & INMEMORY) {
2046 dst->regoff = src->regoff;
2047 dst->flags |= INMEMORY;
2049 } else if ((src->flags & SAVEDVAR) == (dst->flags & SAVEDVAR)) {
2050 dst->regoff = src->regoff;
2051 dst->flags |= src->flags & SAVEDTMP;
2052 dst->flags |= src->flags & TMPARG;
2055 } else if ((dst->flags & SAVEDVAR) == 0) {
2056 /* can only use a REG_SAV as REG_TMP! */
2057 dst->regoff = src->regoff;
2058 dst->flags |= src->flags & TMPARG;
2059 dst->flags |= SAVEDTMP;
2064 /* no copy possible - allocate a new reg/memory location*/
2069 /* Mark the copies (STCOPY) at the dst stack right for DUPx and SWAP */
2070 static void new_reg_mark_copy(registerdata *rd, stackptr *dupslots,
2071 int nin, int nout, int nthrough)
2075 stackptr dst_stackslots[6];
2076 int s_bottom, d_bottom, i, j, slots;
2084 assert(nin <= 4 && (nout + nthrough) <= 6);
2086 /* remember all different Registers/Memory Location of used TEMPVAR */
2087 /* instacks in src_varnum[] and src_flags[] _uniquely_. Take the STCOPY */
2088 /* flag of the last (deepest) occurence */
2090 argp = dupslots + slots;
2091 for (s_bottom = 4; slots--; ) {
2093 if (sp->varkind == TEMPVAR) {
2095 for (i = 3; i >= s_bottom; i--) {
2096 if ((src_regoff[i] == sp->regoff) &&
2097 ((src_flags[i] & INMEMORY) == (sp->flags & INMEMORY)) )
2099 src_flags[i] &= (~STCOPY | (sp->flags & STCOPY));
2105 src_regoff[s_bottom] = sp->regoff;
2106 src_flags[s_bottom] = sp->flags;
2111 /* Remember used TEMPVAR dst Stackslots in dst_stackslots[], since they */
2112 /* have to be from the "lowest" upwards, and the stackelements list is */
2113 /* linked from only top downwards */
2115 slots = nthrough + nout;
2116 argp = dupslots + nin + nout;
2117 for (d_bottom = 6; slots--; ) {
2119 if (sp->varkind == TEMPVAR) {
2121 dst_stackslots[d_bottom] = sp;
2125 /* Mark all reused reg/mem in dst stacklots with STCOPY, if the */
2126 /* corresponding src stackslot was marked STCOPY*/
2127 /* if the correspondig STCOPY from the src stackslot was not set, do not */
2128 /* mark the lowest occurence at dst stackslots */
2129 /* mark in src_flag reg/mem with STKEEP, if they where reused in the dst */
2130 /* stacklots, so they are not freed afterwards */
2131 for (i = d_bottom; i < 6; i++) {
2132 for (j = s_bottom; j < 4; j++) {
2133 if ( (src_regoff[j] == dst_stackslots[i]->regoff) &&
2134 ((src_flags[j] & INMEMORY) == (dst_stackslots[i]->flags & INMEMORY)) )
2136 if (src_flags[j] & STCOPY) {
2137 dst_stackslots[i]->flags |= STCOPY;
2140 src_flags[j] |= STCOPY;
2141 dst_stackslots[i]->flags &= ~STCOPY;
2143 /* do not free reg/mem of src Stackslot */
2144 src_flags[j] |= STKEEP;
2149 /* free all reg/mem of src stack, which where not marked with STKEEP */
2150 for (j=s_bottom; j < 4; j++) {
2151 if ((src_flags[j] & STKEEP)==0) {
2152 /* free, if STCOPY of src stackslot is not set */
2153 /* STCOPY is already checked in reg_free_temp macro! */
2155 argp = dupslots + slots;
2158 if ((src_regoff[j] == sp->regoff) &&
2159 ((src_flags[j] & INMEMORY) == (sp->flags & INMEMORY)) )
2161 reg_free_temp(rd, sp);
2169 #if defined(NEW_VAR)
2170 /* allocate_scratch_registers **************************************************
2172 Allocate temporary (non-interface, non-local) registers.
2174 *******************************************************************************/
2176 static void new_allocate_scratch_registers(jitdata *jd)
2184 builtintable_entry *bte;
2188 /* get required compiler data */
2193 /* initialize temp registers */
2195 reg_init_temp(m, rd);
2197 bptr = jd->new_basicblocks;
2199 while (bptr != NULL) {
2200 if (bptr->flags >= BBREACHED) {
2201 iptr = bptr->iinstr;
2204 while (--len >= 0) {
2205 switch (iptr->opc) {
2210 case ICMD_CHECKNULL:
2216 case ICMD_PUTSTATICCONST:
2217 case ICMD_INLINE_START:
2218 case ICMD_INLINE_END:
2219 case ICMD_INLINE_GOTO:
2222 /* pop 0 push 1 const */
2230 /* pop 0 push 1 load */
2237 reg_new_temp(jd, iptr->dst.varindex);
2251 reg_free_temp(jd, iptr->sx.s23.s2.varindex);
2252 reg_free_temp(jd, iptr->s1.varindex);
2253 reg_new_temp(jd, iptr->dst.varindex);
2267 reg_free_temp(jd, iptr->sx.s23.s3.varindex);
2268 reg_free_temp(jd, iptr->sx.s23.s2.varindex);
2269 reg_free_temp(jd, iptr->s1.varindex);
2272 /* pop 1 push 0 store */
2292 case ICMD_PUTSTATIC:
2293 case ICMD_PUTFIELDCONST:
2295 /* pop 1 push 0 branch */
2298 case ICMD_IFNONNULL:
2314 /* pop 1 push 0 table branch */
2316 case ICMD_TABLESWITCH:
2317 case ICMD_LOOKUPSWITCH:
2319 case ICMD_MONITORENTER:
2320 case ICMD_MONITOREXIT:
2321 reg_free_temp(jd, iptr->s1.varindex);
2324 /* pop 2 push 0 branch */
2326 case ICMD_IF_ICMPEQ:
2327 case ICMD_IF_ICMPNE:
2328 case ICMD_IF_ICMPLT:
2329 case ICMD_IF_ICMPGE:
2330 case ICMD_IF_ICMPGT:
2331 case ICMD_IF_ICMPLE:
2333 case ICMD_IF_LCMPEQ:
2334 case ICMD_IF_LCMPNE:
2335 case ICMD_IF_LCMPLT:
2336 case ICMD_IF_LCMPGE:
2337 case ICMD_IF_LCMPGT:
2338 case ICMD_IF_LCMPLE:
2340 case ICMD_IF_FCMPEQ:
2341 case ICMD_IF_FCMPNE:
2343 case ICMD_IF_FCMPL_LT:
2344 case ICMD_IF_FCMPL_GE:
2345 case ICMD_IF_FCMPL_GT:
2346 case ICMD_IF_FCMPL_LE:
2348 case ICMD_IF_FCMPG_LT:
2349 case ICMD_IF_FCMPG_GE:
2350 case ICMD_IF_FCMPG_GT:
2351 case ICMD_IF_FCMPG_LE:
2353 case ICMD_IF_DCMPEQ:
2354 case ICMD_IF_DCMPNE:
2356 case ICMD_IF_DCMPL_LT:
2357 case ICMD_IF_DCMPL_GE:
2358 case ICMD_IF_DCMPL_GT:
2359 case ICMD_IF_DCMPL_LE:
2361 case ICMD_IF_DCMPG_LT:
2362 case ICMD_IF_DCMPG_GE:
2363 case ICMD_IF_DCMPG_GT:
2364 case ICMD_IF_DCMPG_LE:
2366 case ICMD_IF_ACMPEQ:
2367 case ICMD_IF_ACMPNE:
2375 case ICMD_IASTORECONST:
2376 case ICMD_LASTORECONST:
2377 case ICMD_AASTORECONST:
2378 case ICMD_BASTORECONST:
2379 case ICMD_CASTORECONST:
2380 case ICMD_SASTORECONST:
2381 reg_free_temp(jd, iptr->sx.s23.s2.varindex);
2382 reg_free_temp(jd, iptr->s1.varindex);
2385 /* pop 0 push 1 dup */
2388 /* src === dst->prev (identical Stackslot Element) */
2389 /* src --> dst (copied value, take same reg/mem) */
2391 /* if (!reg_alloc_dup(iptr->s1.varindex, iptr->dst.varindex)) { */
2392 reg_new_temp(jd, iptr->dst.varindex);
2394 /* iptr->dst.varindex->flags |= STCOPY; */
2398 /* pop 0 push 2 dup */
2401 /* src->prev === dst->prev->prev->prev (identical Stackslot Element) */
2402 /* src === dst->prev->prev (identical Stackslot Element) */
2403 /* src->prev --> dst->prev (copied value, take same reg/mem) */
2404 /* src --> dst (copied value, take same reg/mem) */
2406 /* if (!reg_alloc_dup(iptr->dst.dupslots[0], iptr->dst.dupslots[2+0])) */
2407 reg_new_temp(jd, iptr->dst.dupslots[2+0]);
2408 /* if (!reg_alloc_dup(iptr->dst.dupslots[1], iptr->dst.dupslots[2+1])) */
2409 reg_new_temp(jd, iptr->dst.dupslots[2+1]);
2410 /* new_reg_mark_copy(rd, iptr->dst.dupslots, 2, 2, 2); */
2413 /* pop 2 push 3 dup */
2416 /* src->prev --> dst->prev (copied value, take same reg/mem) */
2417 /* src --> dst (copied value, take same reg/mem) */
2418 /* src --> dst->prev->prev (copied value, take same reg/mem) */
2420 /* if (!reg_alloc_dup(iptr->dst.dupslots[1], iptr->dst.dupslots[2+0])) */
2421 reg_new_temp(jd, iptr->dst.dupslots[2+0]);
2422 /* if (!reg_alloc_dup(iptr->dst.dupslots[1], iptr->dst.dupslots[2+2])) */
2423 reg_new_temp(jd, iptr->dst.dupslots[2+2]);
2424 /* if (!reg_alloc_dup(iptr->dst.dupslots[0], iptr->dst.dupslots[2+1])) */
2425 reg_new_temp(jd, iptr->dst.dupslots[2+1]);
2426 /* new_reg_mark_copy(rd, iptr->dst.dupslots, 2, 3, 0); */
2429 /* pop 3 push 4 dup */
2432 /* src->prev->prev --> dst->prev->prev */
2433 /* src->prev --> dst->prev */
2435 /* src --> dst->prev->prev->prev */
2437 /* if (!reg_alloc_dup(iptr->dst.dupslots[2], iptr->dst.dupslots[3+0])) */
2438 reg_new_temp(jd, iptr->dst.dupslots[3+0]);
2439 /* if (!reg_alloc_dup(iptr->dst.dupslots[2], iptr->dst.dupslots[3+3])) */
2440 reg_new_temp(jd, iptr->dst.dupslots[3+3]);
2441 /* if (!reg_alloc_dup(iptr->dst.dupslots[1], iptr->dst.dupslots[3+2])) */
2442 reg_new_temp(jd, iptr->dst.dupslots[3+2]);
2443 /* if (!reg_alloc_dup(iptr->dst.dupslots[0], iptr->dst.dupslots[3+1])) */
2444 reg_new_temp(jd, iptr->dst.dupslots[3+1]);
2445 /* new_reg_mark_copy(rd, iptr->dst.dupslots, 3, 4, 0); */
2448 /* pop 3 push 5 dup */
2451 /* src->prev->prev --> dst->prev->prev */
2452 /* src->prev --> dst->prev */
2454 /* src->prev --> dst->prev->prev->prev->prev */
2455 /* src --> dst->prev->prev->prev */
2457 /* if (!reg_alloc_dup(iptr->dst.dupslots[2], iptr->dst.dupslots[3+1])) */
2458 reg_new_temp(jd, iptr->dst.dupslots[3+1]);
2459 /* if (!reg_alloc_dup(iptr->dst.dupslots[2], iptr->dst.dupslots[3+4])) */
2460 reg_new_temp(jd, iptr->dst.dupslots[3+4]);
2461 /* if (!reg_alloc_dup(iptr->dst.dupslots[1], iptr->dst.dupslots[3+0])) */
2462 reg_new_temp(jd, iptr->dst.dupslots[3+0]);
2463 /* if (!reg_alloc_dup(iptr->dst.dupslots[1], iptr->dst.dupslots[3+3])) */
2464 reg_new_temp(jd, iptr->dst.dupslots[3+3]);
2465 /* if (!reg_alloc_dup(iptr->dst.dupslots[0], iptr->dst.dupslots[3+2])) */
2466 reg_new_temp(jd, iptr->dst.dupslots[3+2]);
2467 /* new_reg_mark_copy(rd, iptr->dst.dupslots, 3, 5, 0); */
2470 /* pop 4 push 6 dup */
2473 /* src->prev->prev->prev --> dst->prev->prev->prev */
2474 /* src->prev->prev --> dst->prev->prev */
2475 /* src->prev --> dst->prev */
2477 /* src->prev --> dst->prev->prev->prev->prev->prev */
2478 /* src --> dst->prev->prev->prev->prev */
2480 /* if (!reg_alloc_dup(iptr->dst.dupslots[3], iptr->dst.dupslots[4+1])) */
2481 reg_new_temp(jd, iptr->dst.dupslots[4+1]);
2482 /* if (!reg_alloc_dup(iptr->dst.dupslots[3], iptr->dst.dupslots[4+5])) */
2483 reg_new_temp(jd, iptr->dst.dupslots[4+5]);
2484 /* if (!reg_alloc_dup(iptr->dst.dupslots[2], iptr->dst.dupslots[4+0])) */
2485 reg_new_temp(jd, iptr->dst.dupslots[4+0]);
2486 /* if (!reg_alloc_dup(iptr->dst.dupslots[2], iptr->dst.dupslots[4+4])) */
2487 reg_new_temp(jd, iptr->dst.dupslots[4+4]);
2488 /* if (!reg_alloc_dup(iptr->dst.dupslots[1], iptr->dst.dupslots[4+3])) */
2489 reg_new_temp(jd, iptr->dst.dupslots[4+3]);
2490 /* if (!reg_alloc_dup(iptr->dst.dupslots[0], iptr->dst.dupslots[4+2])) */
2491 reg_new_temp(jd, iptr->dst.dupslots[4+2]);
2492 /* new_reg_mark_copy(rd, iptr->dst.dupslots, 4, 6, 0); */
2495 /* pop 2 push 2 swap */
2498 /* src --> dst->prev (copy) */
2499 /* src->prev --> dst (copy) */
2501 /* if (!reg_alloc_dup(iptr->dst.dupslots[1], iptr->dst.dupslots[2+0])) */
2502 reg_new_temp(jd, iptr->dst.dupslots[2+0]);
2503 /* if (!reg_alloc_dup(iptr->dst.dupslots[0], iptr->dst.dupslots[2+1])) */
2504 reg_new_temp(jd, iptr->dst.dupslots[2+1]);
2505 /* new_reg_mark_copy(rd, iptr->dst.dupslots, 2, 2, 0); */
2554 reg_free_temp(jd, iptr->sx.s23.s2.varindex);
2555 reg_free_temp(jd, iptr->s1.varindex);
2556 reg_new_temp(jd, iptr->dst.varindex);
2561 case ICMD_IADDCONST:
2562 case ICMD_ISUBCONST:
2563 case ICMD_IMULCONST:
2567 case ICMD_IANDCONST:
2569 case ICMD_IXORCONST:
2570 case ICMD_ISHLCONST:
2571 case ICMD_ISHRCONST:
2572 case ICMD_IUSHRCONST:
2574 case ICMD_LADDCONST:
2575 case ICMD_LSUBCONST:
2576 case ICMD_LMULCONST:
2580 case ICMD_LANDCONST:
2582 case ICMD_LXORCONST:
2583 case ICMD_LSHLCONST:
2584 case ICMD_LSHRCONST:
2585 case ICMD_LUSHRCONST:
2590 case ICMD_INT2SHORT:
2608 case ICMD_CHECKCAST:
2610 case ICMD_ARRAYLENGTH:
2611 case ICMD_INSTANCEOF:
2614 case ICMD_ANEWARRAY:
2617 reg_free_temp(jd, iptr->s1.varindex);
2618 reg_new_temp(jd, iptr->dst.varindex);
2623 case ICMD_GETSTATIC:
2626 reg_new_temp(jd, iptr->dst.varindex);
2629 /* pop many push any */
2631 case ICMD_INVOKESTATIC:
2632 case ICMD_INVOKESPECIAL:
2633 case ICMD_INVOKEVIRTUAL:
2634 case ICMD_INVOKEINTERFACE:
2635 INSTRUCTION_GET_METHODDESC(iptr,md);
2637 argp = iptr->sx.s23.s2.args;
2639 reg_free_temp(jd, *argp);
2642 if (md->returntype.type != TYPE_VOID)
2643 reg_new_temp(jd, iptr->dst.varindex);
2647 bte = iptr->sx.s23.s3.bte;
2650 argp = iptr->sx.s23.s2.args;
2652 reg_free_temp(jd, *argp);
2655 if (md->returntype.type != TYPE_VOID)
2656 reg_new_temp(jd, iptr->dst.varindex);
2659 case ICMD_MULTIANEWARRAY:
2660 i = iptr->s1.argcount;
2661 argp = iptr->sx.s23.s2.args;
2663 reg_free_temp(jd, *argp);
2666 reg_new_temp(jd, iptr->dst.varindex);
2671 new_internalerror("Unknown ICMD %d during register allocation",
2676 } /* while instructions */
2679 } /* while blocks */
2683 /* allocate_scratch_registers **************************************************
2685 Allocate temporary (non-interface, non-local) registers.
2687 *******************************************************************************/
2689 static void new_allocate_scratch_registers(jitdata *jd)
2697 builtintable_entry *bte;
2701 /* get required compiler data */
2706 /* initialize temp registers */
2708 reg_init_temp(m, rd);
2710 bptr = jd->new_basicblocks;
2712 while (bptr != NULL) {
2713 if (bptr->flags >= BBREACHED) {
2714 iptr = bptr->iinstr;
2717 while (--len >= 0) {
2718 switch (iptr->opc) {
2723 case ICMD_CHECKNULL:
2729 case ICMD_PUTSTATICCONST:
2730 case ICMD_INLINE_START:
2731 case ICMD_INLINE_END:
2732 case ICMD_INLINE_GOTO:
2735 /* pop 0 push 1 const */
2743 /* pop 0 push 1 load */
2750 reg_new_temp(rd, iptr->dst.var);
2764 reg_free_temp(rd, iptr->sx.s23.s2.var);
2765 reg_free_temp(rd, iptr->s1.var);
2766 reg_new_temp(rd, iptr->dst.var);
2780 reg_free_temp(rd, iptr->sx.s23.s3.var);
2781 reg_free_temp(rd, iptr->sx.s23.s2.var);
2782 reg_free_temp(rd, iptr->s1.var);
2785 /* pop 1 push 0 store */
2805 case ICMD_PUTSTATIC:
2806 case ICMD_PUTFIELDCONST:
2808 /* pop 1 push 0 branch */
2811 case ICMD_IFNONNULL:
2827 /* pop 1 push 0 table branch */
2829 case ICMD_TABLESWITCH:
2830 case ICMD_LOOKUPSWITCH:
2832 case ICMD_MONITORENTER:
2833 case ICMD_MONITOREXIT:
2834 reg_free_temp(rd, iptr->s1.var);
2837 /* pop 2 push 0 branch */
2839 case ICMD_IF_ICMPEQ:
2840 case ICMD_IF_ICMPNE:
2841 case ICMD_IF_ICMPLT:
2842 case ICMD_IF_ICMPGE:
2843 case ICMD_IF_ICMPGT:
2844 case ICMD_IF_ICMPLE:
2846 case ICMD_IF_LCMPEQ:
2847 case ICMD_IF_LCMPNE:
2848 case ICMD_IF_LCMPLT:
2849 case ICMD_IF_LCMPGE:
2850 case ICMD_IF_LCMPGT:
2851 case ICMD_IF_LCMPLE:
2853 case ICMD_IF_FCMPEQ:
2854 case ICMD_IF_FCMPNE:
2856 case ICMD_IF_FCMPL_LT:
2857 case ICMD_IF_FCMPL_GE:
2858 case ICMD_IF_FCMPL_GT:
2859 case ICMD_IF_FCMPL_LE:
2861 case ICMD_IF_FCMPG_LT:
2862 case ICMD_IF_FCMPG_GE:
2863 case ICMD_IF_FCMPG_GT:
2864 case ICMD_IF_FCMPG_LE:
2866 case ICMD_IF_DCMPEQ:
2867 case ICMD_IF_DCMPNE:
2869 case ICMD_IF_DCMPL_LT:
2870 case ICMD_IF_DCMPL_GE:
2871 case ICMD_IF_DCMPL_GT:
2872 case ICMD_IF_DCMPL_LE:
2874 case ICMD_IF_DCMPG_LT:
2875 case ICMD_IF_DCMPG_GE:
2876 case ICMD_IF_DCMPG_GT:
2877 case ICMD_IF_DCMPG_LE:
2879 case ICMD_IF_ACMPEQ:
2880 case ICMD_IF_ACMPNE:
2888 case ICMD_IASTORECONST:
2889 case ICMD_LASTORECONST:
2890 case ICMD_AASTORECONST:
2891 case ICMD_BASTORECONST:
2892 case ICMD_CASTORECONST:
2893 case ICMD_SASTORECONST:
2894 reg_free_temp(rd, iptr->sx.s23.s2.var);
2895 reg_free_temp(rd, iptr->s1.var);
2898 /* pop 0 push 1 dup */
2901 /* src === dst->prev (identical Stackslot Element) */
2902 /* src --> dst (copied value, take same reg/mem) */
2904 if (!reg_alloc_dup(iptr->s1.var, iptr->dst.var)) {
2905 reg_new_temp(rd, iptr->dst.var);
2907 iptr->dst.var->flags |= STCOPY;
2911 /* pop 0 push 2 dup */
2914 /* src->prev === dst->prev->prev->prev (identical Stackslot Element) */
2915 /* src === dst->prev->prev (identical Stackslot Element) */
2916 /* src->prev --> dst->prev (copied value, take same reg/mem) */
2917 /* src --> dst (copied value, take same reg/mem) */
2919 if (!reg_alloc_dup(iptr->dst.dupslots[0], iptr->dst.dupslots[2+0]))
2920 reg_new_temp(rd, iptr->dst.dupslots[2+0]);
2921 if (!reg_alloc_dup(iptr->dst.dupslots[1], iptr->dst.dupslots[2+1]))
2922 reg_new_temp(rd, iptr->dst.dupslots[2+1]);
2923 new_reg_mark_copy(rd, iptr->dst.dupslots, 2, 2, 2);
2926 /* pop 2 push 3 dup */
2929 /* src->prev --> dst->prev (copied value, take same reg/mem) */
2930 /* src --> dst (copied value, take same reg/mem) */
2931 /* src --> dst->prev->prev (copied value, take same reg/mem) */
2933 if (!reg_alloc_dup(iptr->dst.dupslots[1], iptr->dst.dupslots[2+0]))
2934 reg_new_temp(rd, iptr->dst.dupslots[2+0]);
2935 if (!reg_alloc_dup(iptr->dst.dupslots[1], iptr->dst.dupslots[2+2]))
2936 reg_new_temp(rd, iptr->dst.dupslots[2+2]);
2937 if (!reg_alloc_dup(iptr->dst.dupslots[0], iptr->dst.dupslots[2+1]))
2938 reg_new_temp(rd, iptr->dst.dupslots[2+1]);
2939 new_reg_mark_copy(rd, iptr->dst.dupslots, 2, 3, 0);
2942 /* pop 3 push 4 dup */
2945 /* src->prev->prev --> dst->prev->prev */
2946 /* src->prev --> dst->prev */
2948 /* src --> dst->prev->prev->prev */
2950 if (!reg_alloc_dup(iptr->dst.dupslots[2], iptr->dst.dupslots[3+0]))
2951 reg_new_temp(rd, iptr->dst.dupslots[3+0]);
2952 if (!reg_alloc_dup(iptr->dst.dupslots[2], iptr->dst.dupslots[3+3]))
2953 reg_new_temp(rd, iptr->dst.dupslots[3+3]);
2954 if (!reg_alloc_dup(iptr->dst.dupslots[1], iptr->dst.dupslots[3+2]))
2955 reg_new_temp(rd, iptr->dst.dupslots[3+2]);
2956 if (!reg_alloc_dup(iptr->dst.dupslots[0], iptr->dst.dupslots[3+1]))
2957 reg_new_temp(rd, iptr->dst.dupslots[3+1]);
2958 new_reg_mark_copy(rd, iptr->dst.dupslots, 3, 4, 0);
2961 /* pop 3 push 5 dup */
2964 /* src->prev->prev --> dst->prev->prev */
2965 /* src->prev --> dst->prev */
2967 /* src->prev --> dst->prev->prev->prev->prev */
2968 /* src --> dst->prev->prev->prev */
2970 if (!reg_alloc_dup(iptr->dst.dupslots[2], iptr->dst.dupslots[3+1]))
2971 reg_new_temp(rd, iptr->dst.dupslots[3+1]);
2972 if (!reg_alloc_dup(iptr->dst.dupslots[2], iptr->dst.dupslots[3+4]))
2973 reg_new_temp(rd, iptr->dst.dupslots[3+4]);
2974 if (!reg_alloc_dup(iptr->dst.dupslots[1], iptr->dst.dupslots[3+0]))
2975 reg_new_temp(rd, iptr->dst.dupslots[3+0]);
2976 if (!reg_alloc_dup(iptr->dst.dupslots[1], iptr->dst.dupslots[3+3]))
2977 reg_new_temp(rd, iptr->dst.dupslots[3+3]);
2978 if (!reg_alloc_dup(iptr->dst.dupslots[0], iptr->dst.dupslots[3+2]))
2979 reg_new_temp(rd, iptr->dst.dupslots[3+2]);
2980 new_reg_mark_copy(rd, iptr->dst.dupslots, 3, 5, 0);
2983 /* pop 4 push 6 dup */
2986 /* src->prev->prev->prev --> dst->prev->prev->prev */
2987 /* src->prev->prev --> dst->prev->prev */
2988 /* src->prev --> dst->prev */
2990 /* src->prev --> dst->prev->prev->prev->prev->prev */
2991 /* src --> dst->prev->prev->prev->prev */
2993 if (!reg_alloc_dup(iptr->dst.dupslots[3], iptr->dst.dupslots[4+1]))
2994 reg_new_temp(rd, iptr->dst.dupslots[4+1]);
2995 if (!reg_alloc_dup(iptr->dst.dupslots[3], iptr->dst.dupslots[4+5]))
2996 reg_new_temp(rd, iptr->dst.dupslots[4+5]);
2997 if (!reg_alloc_dup(iptr->dst.dupslots[2], iptr->dst.dupslots[4+0]))
2998 reg_new_temp(rd, iptr->dst.dupslots[4+0]);
2999 if (!reg_alloc_dup(iptr->dst.dupslots[2], iptr->dst.dupslots[4+4]))
3000 reg_new_temp(rd, iptr->dst.dupslots[4+4]);
3001 if (!reg_alloc_dup(iptr->dst.dupslots[1], iptr->dst.dupslots[4+3]))
3002 reg_new_temp(rd, iptr->dst.dupslots[4+3]);
3003 if (!reg_alloc_dup(iptr->dst.dupslots[0], iptr->dst.dupslots[4+2]))
3004 reg_new_temp(rd, iptr->dst.dupslots[4+2]);
3005 new_reg_mark_copy(rd, iptr->dst.dupslots, 4, 6, 0);
3008 /* pop 2 push 2 swap */
3011 /* src --> dst->prev (copy) */
3012 /* src->prev --> dst (copy) */
3014 if (!reg_alloc_dup(iptr->dst.dupslots[1], iptr->dst.dupslots[2+0]))
3015 reg_new_temp(rd, iptr->dst.dupslots[2+0]);
3016 if (!reg_alloc_dup(iptr->dst.dupslots[0], iptr->dst.dupslots[2+1]))
3017 reg_new_temp(rd, iptr->dst.dupslots[2+1]);
3018 new_reg_mark_copy(rd, iptr->dst.dupslots, 2, 2, 0);
3067 reg_free_temp(rd, iptr->sx.s23.s2.var);
3068 reg_free_temp(rd, iptr->s1.var);
3069 reg_new_temp(rd, iptr->dst.var);
3074 case ICMD_IADDCONST:
3075 case ICMD_ISUBCONST:
3076 case ICMD_IMULCONST:
3080 case ICMD_IANDCONST:
3082 case ICMD_IXORCONST:
3083 case ICMD_ISHLCONST:
3084 case ICMD_ISHRCONST:
3085 case ICMD_IUSHRCONST:
3087 case ICMD_LADDCONST:
3088 case ICMD_LSUBCONST:
3089 case ICMD_LMULCONST:
3093 case ICMD_LANDCONST:
3095 case ICMD_LXORCONST:
3096 case ICMD_LSHLCONST:
3097 case ICMD_LSHRCONST:
3098 case ICMD_LUSHRCONST:
3103 case ICMD_INT2SHORT:
3121 case ICMD_CHECKCAST:
3123 case ICMD_ARRAYLENGTH:
3124 case ICMD_INSTANCEOF:
3127 case ICMD_ANEWARRAY:
3130 reg_free_temp(rd, iptr->s1.var);
3131 reg_new_temp(rd, iptr->dst.var);
3136 case ICMD_GETSTATIC:
3139 reg_new_temp(rd, iptr->dst.var);
3142 /* pop many push any */
3144 case ICMD_INVOKESTATIC:
3145 case ICMD_INVOKESPECIAL:
3146 case ICMD_INVOKEVIRTUAL:
3147 case ICMD_INVOKEINTERFACE:
3148 INSTRUCTION_GET_METHODDESC(iptr,md);
3150 argp = iptr->sx.s23.s2.args;
3152 reg_free_temp(rd, *argp);
3155 if (md->returntype.type != TYPE_VOID)
3156 reg_new_temp(rd, iptr->dst.var);
3160 bte = iptr->sx.s23.s3.bte;
3163 argp = iptr->sx.s23.s2.args;
3165 reg_free_temp(rd, *argp);
3168 if (md->returntype.type != TYPE_VOID)
3169 reg_new_temp(rd, iptr->dst.var);
3172 case ICMD_MULTIANEWARRAY:
3173 i = iptr->s1.argcount;
3174 argp = iptr->sx.s23.s2.args;
3176 reg_free_temp(rd, *argp);
3179 reg_new_temp(rd, iptr->dst.var);
3184 new_internalerror("Unknown ICMD %d during register allocation",
3189 } /* while instructions */
3192 } /* while blocks */
3196 #if defined(ENABLE_STATISTICS)
3197 void reg_make_statistics(jitdata *jd)
3204 stackptr src, src_old;
3208 int size_interface; /* == maximum size of in/out stack at basic block boundaries */
3211 /* get required compiler data */
3221 /* count how many local variables are held in memory or register */
3222 for(i=0; i < cd->maxlocals; i++)
3223 for (type=0; type <=4; type++)
3224 if (rd->locals[i][type].type != -1) { /* valid local */
3225 if (rd->locals[i][type].flags & INMEMORY) {
3226 count_locals_spilled++;
3230 count_locals_register++;
3233 /* count how many stack slots are held in memory or register */
3235 bptr = jd->new_basicblocks;
3237 while (bptr != NULL) {
3238 if (bptr->flags >= BBREACHED) {
3240 #if defined(ENABLE_LSRA) || defined(ENABLE_SSA)
3243 /* check for memory moves from interface to BB instack */
3244 dst = bptr->instack;
3245 len = bptr->indepth;
3247 if (len > size_interface) size_interface = len;
3249 while (dst != NULL) {
3251 if (dst->varkind != STACKVAR) {
3252 if ( (dst->flags & INMEMORY) ||
3253 (rd->interfaces[len][dst->type].flags & INMEMORY) ||
3254 ( (dst->flags & INMEMORY) &&
3255 (rd->interfaces[len][dst->type].flags & INMEMORY) &&
3256 (dst->regoff != rd->interfaces[len][dst->type].regoff) ))
3258 /* one in memory or both inmemory at different offsets */
3259 count_mem_move_bb++;
3267 /* check for memory moves from BB outstack to interface */
3268 dst = bptr->outstack;
3269 len = bptr->outdepth;
3270 if (len > size_interface) size_interface = len;
3274 if (dst->varkind != STACKVAR) {
3275 if ( (dst->flags & INMEMORY) || \
3276 (rd->interfaces[len][dst->type].flags & INMEMORY) || \
3277 ( (dst->flags & INMEMORY) && \
3278 (rd->interfaces[len][dst->type].flags & INMEMORY) && \
3279 (dst->regoff != rd->interfaces[len][dst->type].regoff) ))
3281 /* one in memory or both inmemory at different offsets */
3282 count_mem_move_bb++;
3289 #if defined(ENABLE_LSRA) || defined(ENABLE_SSA)
3294 dst = bptr->instack;
3295 iptr = bptr->iinstr;
3299 while (--len >= 0) {
3301 dst = iptr->dst.var;
3303 if ((src!= NULL) && (src != src_old)) { /* new stackslot */
3304 switch (src->varkind) {
3307 if (!(src->flags & INMEMORY))
3308 count_ss_register++;
3314 /* case LOCALVAR: */
3315 /* if (!(rd->locals[src->varnum][src->type].flags & INMEMORY)) */
3316 /* count_ss_register++; */
3318 /* count_ss_spilled++; */
3321 if (!(src->flags & INMEMORY))
3322 count_argument_mem_ss++;
3324 count_argument_reg_ss++;
3328 /* if (IS_FLT_DBL_TYPE(src->type)) { */
3329 /* if (src->varnum < FLT_ARG_CNT) { */
3330 /* count_ss_register++; */
3334 /* #if defined(__POWERPC__) */
3335 /* if (src->varnum < INT_ARG_CNT - (IS_2_WORD_TYPE(src->type) != 0)) { */
3337 /* if (src->varnum < INT_ARG_CNT) { */
3339 /* count_ss_register++; */
3343 /* count_ss_spilled++; */
3350 } /* while instructions */
3353 } /* while blocks */
3354 count_interface_size += size_interface; /* accummulate the size of the interface (between bb boundaries) */
3355 if (in_register) count_method_in_register++;
3357 printf("INREGISTER: %s%s%s\n",m->class->name->text, m->name->text, m->descriptor->text);
3360 #endif /* defined(ENABLE_STATISTICS) */
3364 * These are local overrides for various environment variables in Emacs.
3365 * Please do not remove this and leave it at the end of the file, where
3366 * Emacs will automagically detect them.
3367 * ---------------------------------------------------------------------
3370 * indent-tabs-mode: t
3374 * vim:noexpandtab:sw=4:ts=4: