7b1c1ace3c5921576192acead6f21095936974d8
[cacao.git] / src / vm / jit / parse.c
1 /* src/vm/jit/parse.c - parser for JavaVM to intermediate code translation
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 #include <string.h>
30
31 #include "vm/types.h"
32
33 #include "mm/memory.h"
34
35 #include "native/native.hpp"
36
37 #include "threads/lock.hpp"
38
39 #include "toolbox/logging.h"
40
41 #include "vm/jit/builtin.hpp"
42 #include "vm/exceptions.hpp"
43 #include "vm/global.h"
44 #include "vm/linker.h"
45 #include "vm/loader.hpp"
46 #include "vm/options.h"
47 #include "vm/resolve.hpp"
48
49 #if defined(ENABLE_STATISTICS)
50 # include "vm/statistics.h"
51 #endif
52
53 #include "vm/string.hpp"
54 #include "vm/suck.hpp"
55
56 #include "vm/jit/asmpart.h"
57 #include "vm/jit/jit.hpp"
58 #include "vm/jit/parse.h"
59 #include "vm/jit/loop/loop.h"
60
61 #include "vm/jit/ir/bytecode.h"
62
63
64 #define INSTRUCTIONS_INCREMENT  5  /* number of additional instructions to    */
65                                    /* allocate if space runs out              */
66
67
68 /* local macros ***************************************************************/
69
70 #define BYTECODEINDEX_TO_BASICBLOCK(dst) \
71     do { \
72         (dst).block = \
73             parse_bytecodeindex_to_basicblock(jd, &pd, (dst).insindex); \
74     } while (0)
75
76
77 /* parserdata_t ***************************************************************/
78
79 typedef struct parsedata_t parsedata_t;
80
81 struct parsedata_t {
82         u1          *bytecodestart;         /* start of bytecode instructions     */
83         u1          *basicblockstart;       /* start of bytecode basic-blocks     */
84
85         s4          *bytecodemap;           /* bytecode to IR mapping             */
86         
87         instruction *instructions;          /* instruction array                  */
88         s4           instructionslength;    /* length of the instruction array    */
89
90         s4          *instructionmap;        /* IR to basic-block mapping          */
91 };
92
93
94 /* parse_setup *****************************************************************
95
96    Fills the passed parsedata_t structure.
97
98 *******************************************************************************/
99
100 static void parse_setup(jitdata *jd, parsedata_t *pd)
101 {
102         methodinfo *m;
103
104         /* get required compiler data */
105
106         m = jd->m;
107
108         /* bytecode start array */
109
110         pd->bytecodestart = DMNEW(u1, m->jcodelength + 1);
111         MZERO(pd->bytecodestart, u1, m->jcodelength + 1);
112
113         /* bytecode basic-block start array */
114
115         pd->basicblockstart = DMNEW(u1, m->jcodelength + 1);
116         MZERO(pd->basicblockstart, u1, m->jcodelength + 1);
117
118         /* bytecode instruction index to IR instruction mapping */
119
120         pd->bytecodemap = DMNEW(s4, m->jcodelength + 1);
121         MSET(pd->bytecodemap, -1, s4, m->jcodelength + 1);
122
123         /* allocate the instruction array */
124
125         pd->instructionslength = m->jcodelength + 1;
126         pd->instructions = DMNEW(instruction, pd->instructionslength);
127
128         /* Zero the intermediate instructions array so we don't have any
129            invalid pointers in it if we cannot finish stack_analyse(). */
130
131         MZERO(pd->instructions, instruction, pd->instructionslength);
132
133         /* The instructionmap is allocated later when we know the count of
134            instructions. */
135
136         pd->instructionmap = NULL;
137 }
138
139
140 /* parse_realloc_instructions **************************************************
141
142    Reallocate the instructions array so there is room for at least N 
143    additional instructions.
144
145    RETURN VALUE:
146        the new value for iptr
147
148 *******************************************************************************/
149
150 static instruction *parse_realloc_instructions(parsedata_t *pd, s4 icount, s4 n)
151 {
152         /* increase the size of the instruction array */
153
154         pd->instructionslength += (n + INSTRUCTIONS_INCREMENT);
155
156         /* reallocate the array */
157
158         pd->instructions = DMREALLOC(pd->instructions, instruction, icount,
159                                                                  pd->instructionslength);
160         MZERO(pd->instructions + icount, instruction,
161                   (pd->instructionslength - icount));
162
163         /* return the iptr */
164
165         return pd->instructions + icount;
166 }
167
168
169 /* parse_bytecodeindex_to_basicblock *******************************************
170
171    Resolves a bytecode index to the corresponding basic block.
172
173 *******************************************************************************/
174
175 static basicblock *parse_bytecodeindex_to_basicblock(jitdata *jd,
176                                                                                                          parsedata_t *pd,
177                                                                                                          s4 bcindex)
178 {
179         s4          irindex;
180         basicblock *bb;
181
182         irindex = pd->bytecodemap[bcindex];
183         bb      = jd->basicblocks + pd->instructionmap[irindex];
184
185         return bb;
186 }
187
188
189 /* parse_mark_exception_boundaries *********************************************
190
191    Mark exception handlers and the boundaries of the handled regions as
192    basic block boundaries.
193
194    IN:
195        jd...............current jitdata
196
197    RETURN VALUE:
198        true.............everything ok
199            false............an exception has been thrown
200
201 *******************************************************************************/
202
203 static bool parse_mark_exception_boundaries(jitdata *jd, parsedata_t *pd)
204 {
205         s4                   bcindex;
206         s4                   i;
207         s4                   len;
208         raw_exception_entry *rex;
209         methodinfo          *m;
210
211         m = jd->m;
212         
213         len = m->rawexceptiontablelength;
214
215         if (len == 0)
216                 return true;
217
218         rex = m->rawexceptiontable;
219
220         for (i = 0; i < len; ++i, ++rex) {
221
222                 /* the start of the handled region becomes a basic block start */
223
224                 bcindex = rex->startpc;
225                 CHECK_BYTECODE_INDEX(bcindex);
226                 MARK_BASICBLOCK(pd, bcindex);
227                 
228                 bcindex = rex->endpc; /* see JVM Spec 4.7.3 */
229                 CHECK_BYTECODE_INDEX_EXCLUSIVE(bcindex);
230
231                 /* check that the range is valid */
232
233 #if defined(ENABLE_VERIFIER)
234                 if (bcindex <= rex->startpc) {
235                         exceptions_throw_verifyerror(m, "Invalid exception handler range");
236                         return false;
237                 }
238 #endif
239                 
240                 /* End of handled region becomes a basic block boundary (if it
241                    is the bytecode end, we'll use the special end block that
242                    is created anyway). */
243
244                 if (bcindex < m->jcodelength)
245                         MARK_BASICBLOCK(pd, bcindex);
246                 else
247                         jd->branchtoend = true;
248
249                 /* the start of the handler becomes a basic block start  */
250
251                 bcindex = rex->handlerpc;
252                 CHECK_BYTECODE_INDEX(bcindex);
253                 MARK_BASICBLOCK(pd, bcindex);
254         }
255
256         /* everything ok */
257
258         return true;
259
260 #if defined(ENABLE_VERIFIER)
261 throw_invalid_bytecode_index:
262         exceptions_throw_verifyerror(m,
263                                                                  "Illegal bytecode index in exception table");
264         return false;
265 #endif
266 }
267
268
269 /* parse_resolve_exception_table ***********************************************
270
271    Enter the exception handlers and their ranges, resolved to basicblock *s,
272    in the jitdata.
273
274    IN:
275        jd...............current jitdata
276
277    RETURN VALUE:
278            true.............everything ok
279            false............an exception has been thrown
280
281 *******************************************************************************/
282
283 static bool parse_resolve_exception_table(jitdata *jd, parsedata_t *pd)
284 {
285         methodinfo          *m;
286         raw_exception_entry *rex;
287         exception_entry     *ex;
288         s4                   i;
289         s4                   len;
290         classinfo           *exclass;
291
292         m = jd->m;
293
294         len = m->rawexceptiontablelength;
295
296         /* common case: no handler entries */
297
298         if (len == 0)
299                 return true;
300
301         /* allocate the exception table */
302
303         jd->exceptiontablelength = len;
304         jd->exceptiontable = DMNEW(exception_entry, len + 1); /* XXX why +1? */
305
306         /* copy and resolve the entries */
307
308         ex = jd->exceptiontable;
309         rex = m->rawexceptiontable;
310
311         for (i = 0; i < len; ++i, ++rex, ++ex) {
312                 /* resolve instruction indices to basic blocks */
313
314                 ex->start   = parse_bytecodeindex_to_basicblock(jd, pd, rex->startpc);
315                 ex->end     = parse_bytecodeindex_to_basicblock(jd, pd, rex->endpc);
316                 ex->handler = parse_bytecodeindex_to_basicblock(jd, pd, rex->handlerpc);
317
318                 /* lazily resolve the catchtype */
319
320                 if (rex->catchtype.any != NULL) {
321                         if (!resolve_classref_or_classinfo(m,
322                                                                                            rex->catchtype,
323                                                                                            resolveLazy, true, false,
324                                                                                            &exclass))
325                                 return false;
326
327                         /* if resolved, enter the result of resolution in the table */
328
329                         if (exclass != NULL)
330                                 rex->catchtype.cls = exclass;
331                 }
332
333                 ex->catchtype = rex->catchtype;
334                 ex->next = NULL;   /* set by loop analysis */
335                 ex->down = ex + 1; /* link to next exception entry */
336         }
337
338         /* terminate the ->down linked list */
339
340         assert(ex != jd->exceptiontable);
341         ex[-1].down = NULL;
342
343         return true;
344 }
345
346
347 /*******************************************************************************
348
349         function 'parse' scans the JavaVM code and generates intermediate code
350
351         During parsing the block index table is used to store at bit pos 0
352         a flag which marks basic block starts and at position 1 to 31 the
353         intermediate instruction index. After parsing the block index table
354         is scanned, for marked positions a block is generated and the block
355         number is stored in the block index table.
356
357 *******************************************************************************/
358
359 /*** macro for checking the length of the bytecode ***/
360
361 #if defined(ENABLE_VERIFIER)
362 #define CHECK_END_OF_BYTECODE(neededlength) \
363         do { \
364                 if ((neededlength) > m->jcodelength) \
365                         goto throw_unexpected_end_of_bytecode; \
366         } while (0)
367 #else /* !ENABLE_VERIFIER */
368 #define CHECK_END_OF_BYTECODE(neededlength)
369 #endif /* ENABLE_VERIFIER */
370
371 bool parse(jitdata *jd)
372 {
373         methodinfo  *m;                     /* method being parsed                */
374         codeinfo    *code;
375         parsedata_t  pd;
376         instruction *iptr;                  /* current ptr into instruction array */
377
378         s4           bcindex;               /* bytecode instruction index         */
379         s4           nextbc;                /* start of next bytecode instruction */
380         s4           opcode;                /* bytecode instruction opcode        */
381
382         s4           irindex;               /* IR instruction index               */
383         s4           ircount;               /* IR instruction count               */
384
385         s4           bbcount;               /* basic block count                  */
386
387         int  s_count = 0;             /* stack element counter                    */
388         bool blockend;                /* true if basic block end has been reached */
389         bool iswide;                  /* true if last instruction was a wide      */
390
391         constant_classref  *cr;
392         constant_classref  *compr;
393         classinfo          *c;
394         builtintable_entry *bte;
395         constant_FMIref    *fmi;
396         methoddesc         *md;
397         unresolved_method  *um;
398         unresolved_field   *uf;
399
400         resolve_result_t    result;
401         u2                  lineindex = 0;
402         u2                  currentline = 0;
403         u2                  linepcchange = 0;
404         u4                  flags;
405         basicblock         *bptr;
406
407         int                *local_map; /* local pointer to renaming map           */
408                                        /* is assigned to rd->local_map at the end */
409         branch_target_t *table;
410         lookup_target_t *lookup;
411         s4               i;
412         s4               j;
413
414         /* get required compiler data */
415
416         m    = jd->m;
417         code = jd->code;
418
419         /* allocate buffers for local variable renaming */
420
421         local_map = DMNEW(int, m->maxlocals * 5);
422
423         for (i = 0; i < m->maxlocals; i++) {
424                 local_map[i * 5 + 0] = 0;
425                 local_map[i * 5 + 1] = 0;
426                 local_map[i * 5 + 2] = 0;
427                 local_map[i * 5 + 3] = 0;
428                 local_map[i * 5 + 4] = 0;
429         }
430
431         /* initialize the parse data structures */
432   
433         parse_setup(jd, &pd);
434   
435         /* initialize local variables */
436   
437         iptr     = pd.instructions;
438         ircount  = 0;
439         bbcount  = 0;
440         blockend = false;
441         iswide   = false;
442
443         /* mark basic block boundaries for exception table */
444
445         if (!parse_mark_exception_boundaries(jd, &pd))
446                 return false;
447
448         /* initialize stack element counter */
449
450         s_count = 1 + m->rawexceptiontablelength;
451
452         /* setup line number info */
453
454         currentline = 0;
455         linepcchange = 0;
456
457         if (m->linenumbercount == 0) {
458                 lineindex = 0;
459         }
460         else {
461                 linepcchange = m->linenumbers[0].start_pc;
462         }
463
464         /*** LOOP OVER ALL BYTECODE INSTRUCTIONS **********************************/
465
466         for (bcindex = 0; bcindex < m->jcodelength; bcindex = nextbc) {
467
468                 /* mark this position as a valid bytecode instruction start */
469
470                 pd.bytecodestart[bcindex] = 1;
471
472                 /* change the current line number, if necessary */
473
474                 /* XXX rewrite this using pointer arithmetic */
475
476                 if (linepcchange == bcindex) {
477                         if (m->linenumbercount > lineindex) {
478 next_linenumber:
479                                 currentline = m->linenumbers[lineindex].line_number;
480                                 lineindex++;
481                                 if (lineindex < m->linenumbercount) {
482                                         linepcchange = m->linenumbers[lineindex].start_pc;
483                                         if (linepcchange == bcindex)
484                                                 goto next_linenumber;
485                                 }
486                         }
487                 }
488
489 fetch_opcode:
490                 /* fetch next opcode  */        
491
492                 opcode = SUCK_BE_U1(m->jcode + bcindex);
493
494                 /* If the previous instruction was a block-end instruction,
495                    mark the current bytecode instruction as basic-block
496                    starting instruction. */
497
498                 /* NOTE: Some compilers put a BC_nop after a blockend
499                    instruction. */
500
501                 if (blockend && (opcode != BC_nop)) {
502                         MARK_BASICBLOCK(&pd, bcindex);
503                         blockend = false;
504                 }
505
506                 /* If the current bytecode instruction was marked as
507                    basic-block starting instruction before (e.g. blockend,
508                    forward-branch target), mark the current IR instruction
509                    too. */
510
511                 if (pd.basicblockstart[bcindex] != 0) {
512                         /* We need a NOP as last instruction in each basic block
513                            for basic block reordering (may be replaced with a GOTO
514                            later). */
515
516                         INSTRUCTIONS_CHECK(1);
517                         OP(ICMD_NOP);
518                 }
519
520                 /* store intermediate instruction count (bit 0 mark block starts) */
521
522                 pd.bytecodemap[bcindex] = ircount;
523
524                 /* compute next instruction start */
525
526                 nextbc = bcindex + bytecode[opcode].length;
527
528                 CHECK_END_OF_BYTECODE(nextbc);
529
530                 /* add stack elements produced by this instruction */
531
532                 s_count += bytecode[opcode].slots;
533
534                 /* We check here for the space of 1 instruction in the
535                    instruction array.  If an opcode is converted to more than
536                    1 instruction, this is checked in the corresponding
537                    case. */
538
539                 INSTRUCTIONS_CHECK(1);
540
541                 /* translate this bytecode instruction */
542                 switch (opcode) {
543
544                 case BC_nop:
545                         break;
546
547                 /* pushing constants onto the stack ***********************************/
548
549                 case BC_bipush:
550                         OP_LOADCONST_I(SUCK_BE_S1(m->jcode + bcindex + 1));
551                         break;
552
553                 case BC_sipush:
554                         OP_LOADCONST_I(SUCK_BE_S2(m->jcode + bcindex + 1));
555                         break;
556
557                 case BC_ldc1:
558                         i = SUCK_BE_U1(m->jcode + bcindex + 1);
559                         goto pushconstantitem;
560
561                 case BC_ldc2:
562                 case BC_ldc2w:
563                         i = SUCK_BE_U2(m->jcode + bcindex + 1);
564
565                 pushconstantitem:
566
567 #if defined(ENABLE_VERIFIER)
568                         if (i >= m->clazz->cpcount) {
569                                 exceptions_throw_verifyerror(m,
570                                         "Attempt to access constant outside range");
571                                 return false;
572                         }
573 #endif
574
575                         switch (m->clazz->cptags[i]) {
576                         case CONSTANT_Integer:
577                                 OP_LOADCONST_I(((constant_integer *) (m->clazz->cpinfos[i]))->value);
578                                 break;
579                         case CONSTANT_Long:
580                                 OP_LOADCONST_L(((constant_long *) (m->clazz->cpinfos[i]))->value);
581                                 break;
582                         case CONSTANT_Float:
583                                 OP_LOADCONST_F(((constant_float *) (m->clazz->cpinfos[i]))->value);
584                                 break;
585                         case CONSTANT_Double:
586                                 OP_LOADCONST_D(((constant_double *) (m->clazz->cpinfos[i]))->value);
587                                 break;
588                         case CONSTANT_String:
589                                 OP_LOADCONST_STRING(literalstring_new((utf *) (m->clazz->cpinfos[i])));
590                                 break;
591                         case CONSTANT_Class:
592                                 cr = (constant_classref *) (m->clazz->cpinfos[i]);
593
594                                 if (!resolve_classref(m, cr, resolveLazy, true, true, &c))
595                                         return false;
596
597                                 /* if not resolved, c == NULL */
598
599                                 OP_LOADCONST_CLASSINFO_OR_CLASSREF_CHECK(c, cr);
600
601                                 break;
602
603 #if defined(ENABLE_VERIFIER)
604                         default:
605                                 exceptions_throw_verifyerror(m,
606                                                 "Invalid constant type to push");
607                                 return false;
608 #endif
609                         }
610                         break;
611
612                 case BC_aconst_null:
613                         OP_LOADCONST_NULL();
614                         break;
615
616                 case BC_iconst_m1:
617                 case BC_iconst_0:
618                 case BC_iconst_1:
619                 case BC_iconst_2:
620                 case BC_iconst_3:
621                 case BC_iconst_4:
622                 case BC_iconst_5:
623                         OP_LOADCONST_I(opcode - BC_iconst_0);
624                         break;
625
626                 case BC_lconst_0:
627                 case BC_lconst_1:
628                         OP_LOADCONST_L(opcode - BC_lconst_0);
629                         break;
630
631                 case BC_fconst_0:
632                 case BC_fconst_1:
633                 case BC_fconst_2:
634                         OP_LOADCONST_F(opcode - BC_fconst_0);
635                         break;
636
637                 case BC_dconst_0:
638                 case BC_dconst_1:
639                         OP_LOADCONST_D(opcode - BC_dconst_0);
640                         break;
641
642                 /* stack operations ***************************************************/
643
644                 /* We need space for additional instruction so we can
645                    translate these instructions to sequences of ICMD_COPY and
646                    ICMD_MOVE instructions. */
647
648                 case BC_dup_x1:
649                         INSTRUCTIONS_CHECK(4);
650                         OP(opcode);
651                         OP(ICMD_NOP);
652                         OP(ICMD_NOP);
653                         OP(ICMD_NOP);
654                         break;
655
656                 case BC_dup_x2:
657                         INSTRUCTIONS_CHECK(6);
658                         OP(opcode);
659                         OP(ICMD_NOP);
660                         OP(ICMD_NOP);
661                         OP(ICMD_NOP);
662                         OP(ICMD_NOP);
663                         OP(ICMD_NOP);
664                         break;
665
666                 case BC_dup2:
667                         INSTRUCTIONS_CHECK(2);
668                         OP(opcode);
669                         OP(ICMD_NOP);
670                         break;
671
672                 case BC_dup2_x1:
673                         INSTRUCTIONS_CHECK(7);
674                         OP(opcode);
675                         OP(ICMD_NOP);
676                         OP(ICMD_NOP);
677                         OP(ICMD_NOP);
678                         OP(ICMD_NOP);
679                         OP(ICMD_NOP);
680                         OP(ICMD_NOP);
681                         break;
682
683                 case BC_dup2_x2:
684                         INSTRUCTIONS_CHECK(9);
685                         OP(opcode);
686                         OP(ICMD_NOP);
687                         OP(ICMD_NOP);
688                         OP(ICMD_NOP);
689                         OP(ICMD_NOP);
690                         OP(ICMD_NOP);
691                         OP(ICMD_NOP);
692                         OP(ICMD_NOP);
693                         OP(ICMD_NOP);
694                         break;
695
696                 case BC_swap:
697                         INSTRUCTIONS_CHECK(3);
698                         OP(opcode);
699                         OP(ICMD_NOP);
700                         OP(ICMD_NOP);
701                         break;
702
703                 /* local variable access instructions *********************************/
704
705                 case BC_iload:
706                 case BC_fload:
707                 case BC_aload:
708                         if (iswide == false) {
709                                 i = SUCK_BE_U1(m->jcode + bcindex + 1);
710                         }
711                         else {
712                                 i = SUCK_BE_U2(m->jcode + bcindex + 1);
713                                 nextbc = bcindex + 3;
714                                 iswide = false;
715                         }
716                         OP_LOAD_ONEWORD(opcode, i, opcode - BC_iload);
717                         break;
718
719                 case BC_lload:
720                 case BC_dload:
721                         if (iswide == false) {
722                                 i = SUCK_BE_U1(m->jcode + bcindex + 1);
723                         }
724                         else {
725                                 i = SUCK_BE_U2(m->jcode + bcindex + 1);
726                                 nextbc = bcindex + 3;
727                                 iswide = false;
728                         }
729                         OP_LOAD_TWOWORD(opcode, i, opcode - BC_iload);
730                         break;
731
732                 case BC_iload_0:
733                 case BC_iload_1:
734                 case BC_iload_2:
735                 case BC_iload_3:
736                         OP_LOAD_ONEWORD(ICMD_ILOAD, opcode - BC_iload_0, TYPE_INT);
737                         break;
738
739                 case BC_lload_0:
740                 case BC_lload_1:
741                 case BC_lload_2:
742                 case BC_lload_3:
743                         OP_LOAD_TWOWORD(ICMD_LLOAD, opcode - BC_lload_0, TYPE_LNG);
744                         break;
745
746                 case BC_fload_0:
747                 case BC_fload_1:
748                 case BC_fload_2:
749                 case BC_fload_3:
750                         OP_LOAD_ONEWORD(ICMD_FLOAD, opcode - BC_fload_0, TYPE_FLT);
751                         break;
752
753                 case BC_dload_0:
754                 case BC_dload_1:
755                 case BC_dload_2:
756                 case BC_dload_3:
757                         OP_LOAD_TWOWORD(ICMD_DLOAD, opcode - BC_dload_0, TYPE_DBL);
758                         break;
759
760                 case BC_aload_0:
761                 case BC_aload_1:
762                 case BC_aload_2:
763                 case BC_aload_3:
764                         OP_LOAD_ONEWORD(ICMD_ALOAD, opcode - BC_aload_0, TYPE_ADR);
765                         break;
766
767                 case BC_istore:
768                 case BC_fstore:
769                 case BC_astore:
770                         if (iswide == false) {
771                                 i = SUCK_BE_U1(m->jcode + bcindex + 1);
772                         }
773                         else {
774                                 i = SUCK_BE_U2(m->jcode + bcindex + 1);
775                                 nextbc = bcindex + 3;
776                                 iswide = false;
777                         }
778                         OP_STORE_ONEWORD(opcode, i, opcode - BC_istore);
779                         break;
780
781                 case BC_lstore:
782                 case BC_dstore:
783                         if (iswide == false) {
784                                 i = SUCK_BE_U1(m->jcode + bcindex + 1);
785                         }
786                         else {
787                                 i = SUCK_BE_U2(m->jcode + bcindex + 1);
788                                 nextbc = bcindex + 3;
789                                 iswide = false;
790                         }
791                         OP_STORE_TWOWORD(opcode, i, opcode - BC_istore);
792                         break;
793
794                 case BC_istore_0:
795                 case BC_istore_1:
796                 case BC_istore_2:
797                 case BC_istore_3:
798                         OP_STORE_ONEWORD(ICMD_ISTORE, opcode - BC_istore_0, TYPE_INT);
799                         break;
800
801                 case BC_lstore_0:
802                 case BC_lstore_1:
803                 case BC_lstore_2:
804                 case BC_lstore_3:
805                         OP_STORE_TWOWORD(ICMD_LSTORE, opcode - BC_lstore_0, TYPE_LNG);
806                         break;
807
808                 case BC_fstore_0:
809                 case BC_fstore_1:
810                 case BC_fstore_2:
811                 case BC_fstore_3:
812                         OP_STORE_ONEWORD(ICMD_FSTORE, opcode - BC_fstore_0, TYPE_FLT);
813                         break;
814
815                 case BC_dstore_0:
816                 case BC_dstore_1:
817                 case BC_dstore_2:
818                 case BC_dstore_3:
819                         OP_STORE_TWOWORD(ICMD_DSTORE, opcode - BC_dstore_0, TYPE_DBL);
820                         break;
821
822                 case BC_astore_0:
823                 case BC_astore_1:
824                 case BC_astore_2:
825                 case BC_astore_3:
826                         OP_STORE_ONEWORD(ICMD_ASTORE, opcode - BC_astore_0, TYPE_ADR);
827                         break;
828
829                 case BC_iinc:
830                         {
831                                 int v;
832
833                                 if (iswide == false) {
834                                         i = SUCK_BE_U1(m->jcode + bcindex + 1);
835                                         v = SUCK_BE_S1(m->jcode + bcindex + 2);
836                                 }
837                                 else {
838                                         i = SUCK_BE_U2(m->jcode + bcindex + 1);
839                                         v = SUCK_BE_S2(m->jcode + bcindex + 3);
840                                         nextbc = bcindex + 5;
841                                         iswide = false;
842                                 }
843                                 INDEX_ONEWORD(i);
844                                 LOCALTYPE_USED(i, TYPE_INT);
845                                 OP_LOCALINDEX_I(opcode, i, v);
846                         }
847                         break;
848
849                 /* wider index for loading, storing and incrementing ******************/
850
851                 case BC_wide:
852                         bcindex++;
853                         iswide = true;
854                         goto fetch_opcode;
855
856                 /* managing arrays ****************************************************/
857
858                 case BC_newarray:
859                         switch (SUCK_BE_S1(m->jcode + bcindex + 1)) {
860                         case 4:
861                                 bte = builtintable_get_internal(BUILTIN_newarray_boolean);
862                                 break;
863                         case 5:
864                                 bte = builtintable_get_internal(BUILTIN_newarray_char);
865                                 break;
866                         case 6:
867                                 bte = builtintable_get_internal(BUILTIN_newarray_float);
868                                 break;
869                         case 7:
870                                 bte = builtintable_get_internal(BUILTIN_newarray_double);
871                                 break;
872                         case 8:
873                                 bte = builtintable_get_internal(BUILTIN_newarray_byte);
874                                 break;
875                         case 9:
876                                 bte = builtintable_get_internal(BUILTIN_newarray_short);
877                                 break;
878                         case 10:
879                                 bte = builtintable_get_internal(BUILTIN_newarray_int);
880                                 break;
881                         case 11:
882                                 bte = builtintable_get_internal(BUILTIN_newarray_long);
883                                 break;
884 #if defined(ENABLE_VERIFIER)
885                         default:
886                                 exceptions_throw_verifyerror(m, "Invalid array-type to create");
887                                 return false;
888 #endif
889                         }
890                         OP_BUILTIN_CHECK_EXCEPTION(bte);
891                         break;
892
893                 case BC_anewarray:
894                         i = SUCK_BE_U2(m->jcode + bcindex + 1);
895                         compr = (constant_classref *) class_getconstant(m->clazz, i, CONSTANT_Class);
896                         if (compr == NULL)
897                                 return false;
898
899                         if (!(cr = class_get_classref_multiarray_of(1, compr)))
900                                 return false;
901
902                         if (!resolve_classref(m, cr, resolveLazy, true, true, &c))
903                                 return false;
904
905                         INSTRUCTIONS_CHECK(2);
906                         OP_LOADCONST_CLASSINFO_OR_CLASSREF_NOCHECK(c, cr);
907                         bte = builtintable_get_internal(BUILTIN_newarray);
908                         OP_BUILTIN_CHECK_EXCEPTION(bte);
909                         s_count++;
910                         break;
911
912                 case BC_multianewarray:
913                         i = SUCK_BE_U2(m->jcode + bcindex + 1);
914                         j = SUCK_BE_U1(m->jcode + bcindex + 3);
915   
916                         cr = (constant_classref *) class_getconstant(m->clazz, i, CONSTANT_Class);
917                         if (cr == NULL)
918                                 return false;
919   
920                         if (!resolve_classref(m, cr, resolveLazy, true, true, &c))
921                                 return false;
922   
923                         /* if unresolved, c == NULL */
924   
925                         iptr->s1.argcount = j;
926                         OP_S3_CLASSINFO_OR_CLASSREF(opcode, c, cr, INS_FLAG_CHECK);
927                         code_unflag_leafmethod(code);
928                         break;
929
930                 /* control flow instructions ******************************************/
931
932                 case BC_ifeq:
933                 case BC_iflt:
934                 case BC_ifle:
935                 case BC_ifne:
936                 case BC_ifgt:
937                 case BC_ifge:
938                 case BC_ifnull:
939                 case BC_ifnonnull:
940                 case BC_if_icmpeq:
941                 case BC_if_icmpne:
942                 case BC_if_icmplt:
943                 case BC_if_icmpgt:
944                 case BC_if_icmple:
945                 case BC_if_icmpge:
946                 case BC_if_acmpeq:
947                 case BC_if_acmpne:
948                 case BC_goto:
949                         i = bcindex + SUCK_BE_S2(m->jcode + bcindex + 1);
950                         CHECK_BYTECODE_INDEX(i);
951                         MARK_BASICBLOCK(&pd, i);
952                         blockend = true;
953                         OP_INSINDEX(opcode, i);
954                         break;
955
956                 case BC_goto_w:
957                         i = bcindex + SUCK_BE_S4(m->jcode + bcindex + 1);
958                         CHECK_BYTECODE_INDEX(i);
959                         MARK_BASICBLOCK(&pd, i);
960                         blockend = true;
961                         OP_INSINDEX(ICMD_GOTO, i);
962                         break;
963
964                 case BC_jsr:
965                         i = bcindex + SUCK_BE_S2(m->jcode + bcindex + 1);
966 jsr_tail:
967                         CHECK_BYTECODE_INDEX(i);
968                         MARK_BASICBLOCK(&pd, i);
969                         blockend = true;
970                         OP_PREPARE_ZEROFLAGS(BC_jsr);
971                         iptr->sx.s23.s3.jsrtarget.insindex = i;
972                         PINC;
973                         break;
974
975                 case BC_jsr_w:
976                         i = bcindex + SUCK_BE_S4(m->jcode + bcindex + 1);
977                         goto jsr_tail;
978
979                 case BC_ret:
980                         if (iswide == false) {
981                                 i = SUCK_BE_U1(m->jcode + bcindex + 1);
982                         }
983                         else {
984                                 i = SUCK_BE_U2(m->jcode + bcindex + 1);
985                                 nextbc = bcindex + 3;
986                                 iswide = false;
987                         }
988                         blockend = true;
989
990                         OP_LOAD_ONEWORD(opcode, i, TYPE_ADR);
991                         break;
992
993                 case BC_ireturn:
994                 case BC_lreturn:
995                 case BC_freturn:
996                 case BC_dreturn:
997                 case BC_areturn:
998                 case BC_return:
999                         blockend = true;
1000                         /* XXX ARETURN will need a flag in the typechecker */
1001                         OP(opcode);
1002                         break;
1003
1004                 case BC_athrow:
1005                         blockend = true;
1006                         /* XXX ATHROW will need a flag in the typechecker */
1007                         OP(opcode);
1008                         break;
1009
1010
1011                 /* table jumps ********************************************************/
1012
1013                 case BC_lookupswitch:
1014                         {
1015                                 s4 num, j;
1016                                 lookup_target_t *lookup;
1017 #if defined(ENABLE_VERIFIER)
1018                                 s4 prevvalue = 0;
1019 #endif
1020                                 blockend = true;
1021                                 nextbc = MEMORY_ALIGN((bcindex + 1), 4);
1022
1023                                 CHECK_END_OF_BYTECODE(nextbc + 8);
1024
1025                                 OP_PREPARE_ZEROFLAGS(opcode);
1026
1027                                 /* default target */
1028
1029                                 j = bcindex + SUCK_BE_S4(m->jcode + nextbc);
1030                                 iptr->sx.s23.s3.lookupdefault.insindex = j;
1031                                 nextbc += 4;
1032                                 CHECK_BYTECODE_INDEX(j);
1033                                 MARK_BASICBLOCK(&pd, j);
1034
1035                                 /* number of pairs */
1036
1037                                 num = SUCK_BE_U4(m->jcode + nextbc);
1038                                 iptr->sx.s23.s2.lookupcount = num;
1039                                 nextbc += 4;
1040
1041                                 /* allocate the intermediate code table */
1042
1043                                 lookup = DMNEW(lookup_target_t, num);
1044                                 iptr->dst.lookup = lookup;
1045
1046                                 /* iterate over the lookup table */
1047
1048                                 CHECK_END_OF_BYTECODE(nextbc + 8 * num);
1049
1050                                 for (i = 0; i < num; i++) {
1051                                         /* value */
1052
1053                                         j = SUCK_BE_S4(m->jcode + nextbc);
1054                                         lookup->value = j;
1055
1056                                         nextbc += 4;
1057
1058 #if defined(ENABLE_VERIFIER)
1059                                         /* check if the lookup table is sorted correctly */
1060
1061                                         if (i && (j <= prevvalue)) {
1062                                                 exceptions_throw_verifyerror(m, "Unsorted lookup switch");
1063                                                 return false;
1064                                         }
1065                                         prevvalue = j;
1066 #endif
1067                                         /* target */
1068
1069                                         j = bcindex + SUCK_BE_S4(m->jcode + nextbc);
1070                                         lookup->target.insindex = j;
1071                                         lookup++;
1072                                         nextbc += 4;
1073                                         CHECK_BYTECODE_INDEX(j);
1074                                         MARK_BASICBLOCK(&pd, j);
1075                                 }
1076
1077                                 PINC;
1078                                 break;
1079                         }
1080
1081                 case BC_tableswitch:
1082                         {
1083                                 s4 num, j;
1084                                 s4 deftarget;
1085                                 branch_target_t *table;
1086
1087                                 blockend = true;
1088                                 nextbc = MEMORY_ALIGN((bcindex + 1), 4);
1089
1090                                 CHECK_END_OF_BYTECODE(nextbc + 12);
1091
1092                                 OP_PREPARE_ZEROFLAGS(opcode);
1093
1094                                 /* default target */
1095
1096                                 deftarget = bcindex + SUCK_BE_S4(m->jcode + nextbc);
1097                                 nextbc += 4;
1098                                 CHECK_BYTECODE_INDEX(deftarget);
1099                                 MARK_BASICBLOCK(&pd, deftarget);
1100
1101                                 /* lower bound */
1102
1103                                 j = SUCK_BE_S4(m->jcode + nextbc);
1104                                 iptr->sx.s23.s2.tablelow = j;
1105                                 nextbc += 4;
1106
1107                                 /* upper bound */
1108
1109                                 num = SUCK_BE_S4(m->jcode + nextbc);
1110                                 iptr->sx.s23.s3.tablehigh = num;
1111                                 nextbc += 4;
1112
1113                                 /* calculate the number of table entries */
1114
1115                                 num = num - j + 1;
1116
1117 #if defined(ENABLE_VERIFIER)
1118                                 if (num < 1) {
1119                                         exceptions_throw_verifyerror(m,
1120                                                         "invalid TABLESWITCH: upper bound < lower bound");
1121                                         return false;
1122                                 }
1123 #endif
1124                                 /* create the intermediate code table */
1125                                 /* the first entry is the default target */
1126
1127                                 table = DMNEW(branch_target_t, 1 + num);
1128                                 iptr->dst.table = table;
1129                                 (table++)->insindex = deftarget;
1130
1131                                 /* iterate over the target table */
1132
1133                                 CHECK_END_OF_BYTECODE(nextbc + 4 * num);
1134
1135                                 for (i = 0; i < num; i++) {
1136                                         j = bcindex + SUCK_BE_S4(m->jcode + nextbc);
1137                                         (table++)->insindex = j;
1138                                         nextbc += 4;
1139                                         CHECK_BYTECODE_INDEX(j);
1140                                         MARK_BASICBLOCK(&pd, j);
1141                                 }
1142
1143                                 PINC;
1144                                 break;
1145                         }
1146
1147
1148                 /* load and store of object fields ************************************/
1149
1150                 case BC_aastore:
1151                         OP(opcode);
1152                         code_unflag_leafmethod(code);
1153                         break;
1154
1155                 case BC_getstatic:
1156                 case BC_putstatic:
1157                 case BC_getfield:
1158                 case BC_putfield:
1159                         i = SUCK_BE_U2(m->jcode + bcindex + 1);
1160                         fmi = class_getconstant(m->clazz, i, CONSTANT_Fieldref);
1161
1162                         if (fmi == NULL)
1163                                 return false;
1164
1165                         OP_PREPARE_ZEROFLAGS(opcode);
1166                         iptr->sx.s23.s3.fmiref = fmi;
1167
1168                         /* only with -noverify, otherwise the typechecker does this */
1169
1170 #if defined(ENABLE_VERIFIER)
1171                         if (!JITDATA_HAS_FLAG_VERIFY(jd)) {
1172 #endif
1173                                 result = resolve_field_lazy(m, fmi);
1174
1175                                 if (result == resolveFailed)
1176                                         return false;
1177
1178                                 if (result != resolveSucceeded) {
1179                                         uf = resolve_create_unresolved_field(m->clazz, m, iptr);
1180
1181                                         if (uf == NULL)
1182                                                 return false;
1183
1184                                         /* store the unresolved_field pointer */
1185
1186                                         iptr->sx.s23.s3.uf = uf;
1187                                         iptr->flags.bits |= INS_FLAG_UNRESOLVED;
1188                                 }
1189 #if defined(ENABLE_VERIFIER)
1190                         }
1191 #endif
1192                         PINC;
1193                         break;
1194
1195
1196                 /* method invocation **************************************************/
1197
1198                 case BC_invokestatic:
1199                         OP_PREPARE_ZEROFLAGS(opcode);
1200
1201                         i = SUCK_BE_U2(m->jcode + bcindex + 1);
1202                         fmi = class_getconstant(m->clazz, i, CONSTANT_Methodref);
1203
1204                         if (fmi == NULL)
1205                                 return false;
1206
1207                         md = fmi->parseddesc.md;
1208
1209                         if (md->params == NULL)
1210                                 if (!descriptor_params_from_paramtypes(md, ACC_STATIC))
1211                                         return false;
1212
1213                         goto invoke_method;
1214
1215                 case BC_invokespecial:
1216                         OP_PREPARE_FLAGS(opcode, INS_FLAG_CHECK);
1217
1218                         i = SUCK_BE_U2(m->jcode + bcindex + 1);
1219                         fmi = class_getconstant(m->clazz, i, CONSTANT_Methodref);
1220
1221                         goto invoke_nonstatic_method;
1222
1223                 case BC_invokeinterface:
1224                         OP_PREPARE_ZEROFLAGS(opcode);
1225
1226                         i = SUCK_BE_U2(m->jcode + bcindex + 1);
1227                         fmi = class_getconstant(m->clazz, i, CONSTANT_InterfaceMethodref);
1228
1229                         goto invoke_nonstatic_method;
1230
1231                 case BC_invokevirtual:
1232                         OP_PREPARE_ZEROFLAGS(opcode);
1233
1234                         i = SUCK_BE_U2(m->jcode + bcindex + 1);
1235                         fmi = class_getconstant(m->clazz, i, CONSTANT_Methodref);
1236
1237 invoke_nonstatic_method:
1238                         if (fmi == NULL)
1239                                 return false;
1240
1241                         md = fmi->parseddesc.md;
1242
1243                         if (md->params == NULL)
1244                                 if (!descriptor_params_from_paramtypes(md, 0))
1245                                         return false;
1246
1247 invoke_method:
1248                         code_unflag_leafmethod(code);
1249
1250                         iptr->sx.s23.s3.fmiref = fmi;
1251
1252                         /* only with -noverify, otherwise the typechecker does this */
1253
1254 #if defined(ENABLE_VERIFIER)
1255                         if (!JITDATA_HAS_FLAG_VERIFY(jd)) {
1256 #endif
1257                                 result = resolve_method_lazy(m, fmi, 
1258                                                                                          (opcode == BC_invokespecial));
1259
1260                                 if (result == resolveFailed)
1261                                         return false;
1262
1263                                 if (result == resolveSucceeded) {
1264                                         methodinfo *mi = iptr->sx.s23.s3.fmiref->p.method;
1265
1266                                         /* if this call is monomorphic, turn it into an
1267                                            INVOKESPECIAL */
1268
1269                                         assert(IS_FMIREF_RESOLVED(iptr->sx.s23.s3.fmiref));
1270
1271                                         if ((iptr->opc == ICMD_INVOKEVIRTUAL)
1272                                                 && (mi->flags & (ACC_FINAL | ACC_PRIVATE)))
1273                                         {
1274                                                 iptr->opc         = ICMD_INVOKESPECIAL;
1275                                                 iptr->flags.bits |= INS_FLAG_CHECK;
1276                                         }
1277                                 }
1278                                 else {
1279                                         um = resolve_create_unresolved_method(m->clazz, m, fmi,
1280                                                         (opcode == BC_invokestatic),
1281                                                         (opcode == BC_invokespecial));
1282
1283                                         if (um == NULL)
1284                                                 return false;
1285
1286                                         /* store the unresolved_method pointer */
1287
1288                                         iptr->sx.s23.s3.um = um;
1289                                         iptr->flags.bits |= INS_FLAG_UNRESOLVED;
1290                                 }
1291 #if defined(ENABLE_VERIFIER)
1292                         }
1293 #endif
1294                         PINC;
1295                         break;
1296
1297                 /* instructions taking class arguments ********************************/
1298
1299                 case BC_new:
1300                         i = SUCK_BE_U2(m->jcode + bcindex + 1);
1301                         cr = class_getconstant(m->clazz, i, CONSTANT_Class);
1302
1303                         if (cr == NULL)
1304                                 return false;
1305
1306                         if (!resolve_classref(m, cr, resolveLazy, true, true, &c))
1307                                 return false;
1308
1309                         INSTRUCTIONS_CHECK(2);
1310                         OP_LOADCONST_CLASSINFO_OR_CLASSREF_NOCHECK(c, cr);
1311                         bte = builtintable_get_internal(BUILTIN_new);
1312                         OP_BUILTIN_CHECK_EXCEPTION(bte);
1313                         s_count++;
1314                         break;
1315
1316                 case BC_checkcast:
1317                         i = SUCK_BE_U2(m->jcode + bcindex + 1);
1318                         cr = class_getconstant(m->clazz, i, CONSTANT_Class);
1319
1320                         if (cr == NULL)
1321                                 return false;
1322
1323                         if (!resolve_classref(m, cr, resolveLazy, true, true, &c))
1324                                 return false;
1325
1326                         if (cr->name->text[0] == '[') {
1327                                 /* array type cast-check */
1328                                 flags = INS_FLAG_CHECK | INS_FLAG_ARRAY;
1329                                 code_unflag_leafmethod(code);
1330                         }
1331                         else {
1332                                 /* object type cast-check */
1333                                 flags = INS_FLAG_CHECK;
1334                         }
1335                         OP_S3_CLASSINFO_OR_CLASSREF(opcode, c, cr, flags);
1336                         break;
1337
1338                 case BC_instanceof:
1339                         i = SUCK_BE_U2(m->jcode + bcindex + 1);
1340                         cr = class_getconstant(m->clazz, i, CONSTANT_Class);
1341
1342                         if (cr == NULL)
1343                                 return false;
1344
1345                         if (!resolve_classref(m, cr, resolveLazy, true, true, &c))
1346                                 return false;
1347
1348                         if (cr->name->text[0] == '[') {
1349                                 /* array type cast-check */
1350                                 INSTRUCTIONS_CHECK(2);
1351                                 OP_LOADCONST_CLASSINFO_OR_CLASSREF_NOCHECK(c, cr);
1352                                 bte = builtintable_get_internal(BUILTIN_arrayinstanceof);
1353                                 OP_BUILTIN_NO_EXCEPTION(bte);
1354                                 s_count++;
1355                         }
1356                         else {
1357                                 /* object type cast-check */
1358                                 OP_S3_CLASSINFO_OR_CLASSREF(opcode, c, cr, 0 /* flags*/);
1359                         }
1360                         break;
1361
1362                 /* synchronization instructions ***************************************/
1363
1364                 case BC_monitorenter:
1365 #if defined(ENABLE_THREADS)
1366                         if (checksync) {
1367                                 bte = builtintable_get_internal(LOCK_monitor_enter);
1368                                 OP_BUILTIN_CHECK_EXCEPTION(bte);
1369                         }
1370                         else
1371 #endif
1372                         {
1373                                 OP_CHECK_EXCEPTION(ICMD_CHECKNULL);
1374                                 OP(ICMD_POP);
1375                         }
1376                         break;
1377
1378                 case BC_monitorexit:
1379 #if defined(ENABLE_THREADS)
1380                         if (checksync) {
1381                                 bte = builtintable_get_internal(LOCK_monitor_exit);
1382                                 OP_BUILTIN_CHECK_EXCEPTION(bte);
1383                         }
1384                         else
1385 #endif
1386                         {
1387                                 OP_CHECK_EXCEPTION(ICMD_CHECKNULL);
1388                                 OP(ICMD_POP);
1389                         }
1390                         break;
1391
1392                 /* arithmetic instructions that may become builtin functions **********/
1393
1394                 case BC_idiv:
1395 #if !SUPPORT_DIVISION
1396                         bte = builtintable_get_internal(BUILTIN_idiv);
1397                         OP_BUILTIN_ARITHMETIC(opcode, bte);
1398 #else
1399 # if SUPPORT_HARDWARE_DIVIDE_BY_ZERO
1400                         OP(opcode);
1401 # else
1402                         OP_CHECK_EXCEPTION(opcode);
1403 # endif
1404 #endif
1405                         break;
1406
1407                 case BC_irem:
1408 #if !SUPPORT_DIVISION
1409                         bte = builtintable_get_internal(BUILTIN_irem);
1410                         OP_BUILTIN_ARITHMETIC(opcode, bte);
1411 #else
1412 # if SUPPORT_HARDWARE_DIVIDE_BY_ZERO
1413                         OP(opcode);
1414 # else
1415                         OP_CHECK_EXCEPTION(opcode);
1416 # endif
1417 #endif
1418                         break;
1419
1420                 case BC_ldiv:
1421 #if !(SUPPORT_DIVISION && SUPPORT_LONG && SUPPORT_LONG_DIV)
1422                         bte = builtintable_get_internal(BUILTIN_ldiv);
1423                         OP_BUILTIN_ARITHMETIC(opcode, bte);
1424 #else
1425 # if SUPPORT_HARDWARE_DIVIDE_BY_ZERO
1426                         OP(opcode);
1427 # else
1428                         OP_CHECK_EXCEPTION(opcode);
1429 # endif
1430 #endif
1431                         break;
1432
1433                 case BC_lrem:
1434 #if !(SUPPORT_DIVISION && SUPPORT_LONG && SUPPORT_LONG_DIV)
1435                         bte = builtintable_get_internal(BUILTIN_lrem);
1436                         OP_BUILTIN_ARITHMETIC(opcode, bte);
1437 #else
1438 # if SUPPORT_HARDWARE_DIVIDE_BY_ZERO
1439                         OP(opcode);
1440 # else
1441                         OP_CHECK_EXCEPTION(opcode);
1442 # endif
1443 #endif
1444                         break;
1445
1446                 case BC_frem:
1447 #if defined(__I386__)
1448                         OP(opcode);
1449 #else
1450                         bte = builtintable_get_internal(BUILTIN_frem);
1451                         OP_BUILTIN_NO_EXCEPTION(bte);
1452 #endif
1453                         break;
1454
1455                 case BC_drem:
1456 #if defined(__I386__)
1457                         OP(opcode);
1458 #else
1459                         bte = builtintable_get_internal(BUILTIN_drem);
1460                         OP_BUILTIN_NO_EXCEPTION(bte);
1461 #endif
1462                         break;
1463
1464                 case BC_f2i:
1465 #if defined(__ALPHA__)
1466                         bte = builtintable_get_internal(BUILTIN_f2i);
1467                         OP_BUILTIN_NO_EXCEPTION(bte);
1468 #else
1469                         OP(opcode);
1470 #endif
1471                         break;
1472
1473                 case BC_f2l:
1474 #if defined(__ALPHA__)
1475                         bte = builtintable_get_internal(BUILTIN_f2l);
1476                         OP_BUILTIN_NO_EXCEPTION(bte);
1477 #else
1478                         OP(opcode);
1479 #endif
1480                         break;
1481
1482                 case BC_d2i:
1483 #if defined(__ALPHA__)
1484                         bte = builtintable_get_internal(BUILTIN_d2i);
1485                         OP_BUILTIN_NO_EXCEPTION(bte);
1486 #else
1487                         OP(opcode);
1488 #endif
1489                         break;
1490
1491                 case BC_d2l:
1492 #if defined(__ALPHA__)
1493                         bte = builtintable_get_internal(BUILTIN_d2l);
1494                         OP_BUILTIN_NO_EXCEPTION(bte);
1495 #else
1496                         OP(opcode);
1497 #endif
1498                         break;
1499
1500
1501                 /* invalid opcodes ****************************************************/
1502
1503                         /* check for invalid opcodes if the verifier is enabled */
1504 #if defined(ENABLE_VERIFIER)
1505                 case BC_breakpoint:
1506                         exceptions_throw_verifyerror(m, "Quick instructions shouldn't appear, yet.");
1507                         return false;
1508
1509
1510                 /* Unused opcodes ************************************************** */
1511
1512                 case 186:
1513                 case 203:
1514                 case 204:
1515                 case 205:
1516                 case 206:
1517                 case 207:
1518                 case 208:
1519                 case 209:
1520                 case 210:
1521                 case 211:
1522                 case 212:
1523                 case 213:
1524                 case 214:
1525                 case 215:
1526                 case 216:
1527                 case 217:
1528                 case 218:
1529                 case 219:
1530                 case 220:
1531                 case 221:
1532                 case 222:
1533                 case 223:
1534                 case 224:
1535                 case 225:
1536                 case 226:
1537                 case 227:
1538                 case 228:
1539                 case 229:
1540                 case 230:
1541                 case 231:
1542                 case 232:
1543                 case 233:
1544                 case 234:
1545                 case 235:
1546                 case 236:
1547                 case 237:
1548                 case 238:
1549                 case 239:
1550                 case 240:
1551                 case 241:
1552                 case 242:
1553                 case 243:
1554                 case 244:
1555                 case 245:
1556                 case 246:
1557                 case 247:
1558                 case 248:
1559                 case 249:
1560                 case 250:
1561                 case 251:
1562                 case 252:
1563                 case 253:
1564                 case 254:
1565                 case 255:
1566                         exceptions_throw_verifyerror(m, "Illegal opcode %d at instr %d\n",
1567                                                                                  opcode, ircount);
1568                         return false;
1569                         break;
1570 #endif /* defined(ENABLE_VERIFIER) */
1571
1572                 /* opcodes that don't require translation *****************************/
1573
1574                 default:
1575                         /* Straight-forward translation to HIR. */
1576                         OP(opcode);
1577                         break;
1578
1579                 } /* end switch */
1580
1581                 /* verifier checks ****************************************************/
1582
1583 #if defined(ENABLE_VERIFIER)
1584                 /* If WIDE was used correctly, iswide should have been reset by now. */
1585                 if (iswide) {
1586                         exceptions_throw_verifyerror(m,
1587                                         "Illegal instruction: WIDE before incompatible opcode");
1588                         return false;
1589                 }
1590 #endif /* defined(ENABLE_VERIFIER) */
1591
1592         } /* end for */
1593
1594         if (JITDATA_HAS_FLAG_REORDER(jd)) {
1595                 /* add a NOP to the last basic block */
1596
1597                 INSTRUCTIONS_CHECK(1);
1598                 OP(ICMD_NOP);
1599         }
1600
1601         /*** END OF LOOP **********************************************************/
1602
1603         /* assert that we did not write more ICMDs than allocated */
1604
1605         assert(ircount <= pd.instructionslength);
1606         assert(ircount == (iptr - pd.instructions));
1607
1608         /*** verifier checks ******************************************************/
1609
1610 #if defined(ENABLE_VERIFIER)
1611         if (bcindex != m->jcodelength) {
1612                 exceptions_throw_verifyerror(m,
1613                                 "Command-sequence crosses code-boundary");
1614                 return false;
1615         }
1616
1617         if (!blockend) {
1618                 exceptions_throw_verifyerror(m, "Falling off the end of the code");
1619                 return false;
1620         }
1621 #endif /* defined(ENABLE_VERIFIER) */
1622
1623         /*** setup the methodinfo, allocate stack and basic blocks ****************/
1624
1625         /* identify basic blocks */
1626
1627         /* check if first instruction is a branch target */
1628
1629         if (pd.basicblockstart[0] == 1) {
1630                 jd->branchtoentry = true;
1631         }
1632         else {
1633                 /* first instruction always starts a basic block */
1634
1635                 iptr = pd.instructions;
1636
1637                 iptr->flags.bits |= INS_FLAG_BASICBLOCK;
1638         }
1639
1640         /* Iterate over all bytecode instructions and set missing
1641            basic-block starts in IR instructions. */
1642
1643         for (bcindex = 0; bcindex < m->jcodelength; bcindex++) {
1644                 /* Does the current bytecode instruction start a basic
1645                    block? */
1646
1647                 if (pd.basicblockstart[bcindex] == 1) {
1648 #if defined(ENABLE_VERIFIER)
1649                         /* Check if this bytecode basic-block start at the
1650                            beginning of a bytecode instruction. */
1651
1652                         if (pd.bytecodestart[bcindex] == 0) {
1653                                 exceptions_throw_verifyerror(m,
1654                                                                                  "Branch into middle of instruction");
1655                                 return false;
1656                         }
1657 #endif
1658
1659                         /* Get the IR instruction mapped to the bytecode
1660                            instruction and set the basic block flag. */
1661
1662                         irindex = pd.bytecodemap[bcindex];
1663                         iptr    = pd.instructions + irindex;
1664
1665                         iptr->flags.bits |= INS_FLAG_BASICBLOCK;
1666                 }
1667         }
1668
1669         /* IR instruction index to basic-block index mapping */
1670
1671         pd.instructionmap = DMNEW(s4, ircount);
1672         MZERO(pd.instructionmap, s4, ircount);
1673
1674         /* Iterate over all IR instructions and count the basic blocks. */
1675
1676         iptr = pd.instructions;
1677
1678         bbcount = 0;
1679
1680         for (i = 0; i < ircount; i++, iptr++) {
1681                 if (INSTRUCTION_STARTS_BASICBLOCK(iptr)) {
1682                         /* store the basic-block number in the IR instruction
1683                            map */
1684
1685                         pd.instructionmap[i] = bbcount;
1686
1687                         /* post-increment the basic-block count */
1688
1689                         bbcount++;
1690                 }
1691         }
1692
1693         /* Allocate basic block array (one more for end ipc). */
1694
1695         jd->basicblocks = DMNEW(basicblock, bbcount + 1);
1696         MZERO(jd->basicblocks, basicblock, bbcount + 1);
1697
1698         /* Now iterate again over all IR instructions and initialize the
1699            basic block structures and, in the same loop, resolve the
1700            branch-target instruction indices to basic blocks. */
1701
1702         iptr = pd.instructions;
1703         bptr = jd->basicblocks;
1704
1705         bbcount = 0;
1706
1707         for (i = 0; i < ircount; i++, iptr++) {
1708                 /* check for basic block */
1709
1710                 if (INSTRUCTION_STARTS_BASICBLOCK(iptr)) {
1711                         /* intialize the basic block */
1712
1713                         BASICBLOCK_INIT(bptr, m);
1714
1715                         bptr->iinstr = iptr;
1716
1717                         if (bbcount > 0) {
1718                                 bptr[-1].icount = bptr->iinstr - bptr[-1].iinstr;
1719                         }
1720
1721                         /* bptr->icount is set when the next block is allocated */
1722
1723                         bptr->nr = bbcount++;
1724                         bptr++;
1725                         bptr[-1].next = bptr;
1726                 }
1727
1728                 /* resolve instruction indices to basic blocks */
1729
1730                 switch (iptr->opc) {
1731                 case ICMD_IFEQ:
1732                 case ICMD_IFLT:
1733                 case ICMD_IFLE:
1734                 case ICMD_IFNE:
1735                 case ICMD_IFGT:
1736                 case ICMD_IFGE:
1737                 case ICMD_IFNULL:
1738                 case ICMD_IFNONNULL:
1739                 case ICMD_IF_ICMPEQ:
1740                 case ICMD_IF_ICMPNE:
1741                 case ICMD_IF_ICMPLT:
1742                 case ICMD_IF_ICMPGT:
1743                 case ICMD_IF_ICMPLE:
1744                 case ICMD_IF_ICMPGE:
1745                 case ICMD_IF_ACMPEQ:
1746                 case ICMD_IF_ACMPNE:
1747                 case ICMD_GOTO:
1748                         BYTECODEINDEX_TO_BASICBLOCK(iptr->dst);
1749                         break;
1750
1751                 case ICMD_JSR:
1752                         BYTECODEINDEX_TO_BASICBLOCK(iptr->sx.s23.s3.jsrtarget);
1753                         break;
1754
1755                 case ICMD_TABLESWITCH:
1756                         table = iptr->dst.table;
1757
1758                         BYTECODEINDEX_TO_BASICBLOCK(*table);
1759                         table++;
1760
1761                         j = iptr->sx.s23.s3.tablehigh - iptr->sx.s23.s2.tablelow + 1;
1762
1763                         while (--j >= 0) {
1764                                 BYTECODEINDEX_TO_BASICBLOCK(*table);
1765                                 table++;
1766                         }
1767                         break;
1768
1769                 case ICMD_LOOKUPSWITCH:
1770                         BYTECODEINDEX_TO_BASICBLOCK(iptr->sx.s23.s3.lookupdefault);
1771
1772                         lookup = iptr->dst.lookup;
1773
1774                         j = iptr->sx.s23.s2.lookupcount;
1775
1776                         while (--j >= 0) {
1777                                 BYTECODEINDEX_TO_BASICBLOCK(lookup->target);
1778                                 lookup++;
1779                         }
1780                         break;
1781                 }
1782         }
1783
1784         /* set instruction count of last real block */
1785
1786         if (bbcount > 0) {
1787                 bptr[-1].icount = (pd.instructions + ircount) - bptr[-1].iinstr;
1788         }
1789
1790         /* allocate additional block at end */
1791
1792         BASICBLOCK_INIT(bptr, m);
1793         bptr->nr = bbcount;
1794
1795         /* set basicblock pointers in exception table */
1796
1797         if (!parse_resolve_exception_table(jd, &pd))
1798                 return false;
1799
1800         /* store the local map */
1801
1802         jd->local_map = local_map;
1803
1804         /* calculate local variable renaming */
1805
1806         {
1807                 s4 nlocals = 0;
1808                 s4 i;
1809                 s4 t;
1810                 s4 varindex;
1811                 s4 *mapptr;
1812                 s4 *reversemap;
1813
1814                 mapptr = local_map;
1815
1816                 /* iterate over local_map[0..m->maxlocals*5-1] and allocate a unique */
1817                 /* variable index for each _used_ (javaindex,type) pair.             */
1818                 /* (local_map[javaindex*5+type] = cacaoindex)                        */
1819                 /* Unused (javaindex,type) pairs are marked with UNUSED.             */
1820
1821                 for (i = 0; i < (m->maxlocals * 5); i++, mapptr++) {
1822                         if (*mapptr)
1823                                 *mapptr = nlocals++;
1824                         else
1825                                 *mapptr = UNUSED;
1826                 }
1827
1828                 jd->localcount = nlocals;
1829
1830                 /* calculate the (maximum) number of variables needed */
1831
1832                 jd->varcount = 
1833                           nlocals                                      /* local variables */
1834                         + bbcount * m->maxstack                                 /* invars */
1835                         + s_count;         /* variables created within blocks (non-invar) */
1836
1837                 /* reserve the first indices for local variables */
1838
1839                 jd->vartop = nlocals;
1840
1841                 /* reserve extra variables needed by stack analyse */
1842
1843                 jd->varcount += STACK_EXTRA_VARS;
1844                 jd->vartop   += STACK_EXTRA_VARS;
1845
1846                 /* The verifier needs space for saving invars in some cases and */
1847                 /* extra variables.                                             */
1848
1849 #if defined(ENABLE_VERIFIER)
1850                 jd->varcount += VERIFIER_EXTRA_LOCALS + VERIFIER_EXTRA_VARS + m->maxstack;
1851                 jd->vartop   += VERIFIER_EXTRA_LOCALS + VERIFIER_EXTRA_VARS + m->maxstack;
1852 #endif
1853                 /* allocate and initialize the variable array */
1854
1855                 jd->var = DMNEW(varinfo, jd->varcount);
1856                 MZERO(jd->var, varinfo, jd->varcount);
1857
1858                 /* set types of all locals in jd->var */
1859                 /* and fill the reverselocalmap       */
1860
1861                 reversemap = DMNEW(s4, nlocals);
1862
1863                 for (i = 0; i < m->maxlocals; i++)
1864                         for (t=0; t<5; t++) {
1865                                 varindex = local_map[5*i + t];
1866                                 if (varindex != UNUSED) {
1867                                         VAR(varindex)->type = t;
1868                                         reversemap[varindex] = i;
1869                                 }
1870                         }
1871
1872                 jd->reverselocalmap = reversemap;
1873         }
1874
1875         /* assign local variables to method variables */
1876
1877         jd->instructions     = pd.instructions;
1878         jd->instructioncount = ircount;
1879         jd->basicblockcount  = bbcount;
1880         jd->stackcount       = s_count + bbcount * m->maxstack; /* in-stacks */
1881
1882         /* allocate stack table */
1883
1884         jd->stack = DMNEW(stackelement_t, jd->stackcount);
1885
1886         /* everything's ok */
1887
1888         return true;
1889
1890         /*** goto labels for throwing verifier exceptions *************************/
1891
1892 #if defined(ENABLE_VERIFIER)
1893
1894 throw_unexpected_end_of_bytecode:
1895         exceptions_throw_verifyerror(m, "Unexpected end of bytecode");
1896         return false;
1897
1898 throw_invalid_bytecode_index:
1899         exceptions_throw_verifyerror(m, "Illegal target of branch instruction");
1900         return false;
1901
1902 throw_illegal_local_variable_number:
1903         exceptions_throw_verifyerror(m, "Illegal local variable number");
1904         return false;
1905
1906 #endif /* ENABLE_VERIFIER */
1907 }
1908
1909
1910 /*
1911  * These are local overrides for various environment variables in Emacs.
1912  * Please do not remove this and leave it at the end of the file, where
1913  * Emacs will automagically detect them.
1914  * ---------------------------------------------------------------------
1915  * Local variables:
1916  * mode: c
1917  * indent-tabs-mode: t
1918  * c-basic-offset: 4
1919  * tab-width: 4
1920  * End:
1921  * vim:noexpandtab:sw=4:ts=4:
1922  */