OSDN Git Service

PR rtl-optimization/36006
[pf3gnuchains/gcc-fork.git] / libjava / interpret.cc
1 // interpret.cc - Code for the interpreter
2
3 /* Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007 Free Software Foundation
4
5    This file is part of libgcj.
6
7 This software is copyrighted work licensed under the terms of the
8 Libgcj License.  Please consult the file "LIBGCJ_LICENSE" for
9 details.  */
10
11 /* Author: Kresten Krab Thorup <krab@gnu.org>  */
12
13 #include <config.h>
14 #include <platform.h>
15
16 #pragma implementation "java-interp.h"
17
18 #include <jvm.h>
19 #include <java-cpool.h>
20 #include <java-interp.h>
21 #include <java/lang/System.h>
22 #include <java/lang/String.h>
23 #include <java/lang/Integer.h>
24 #include <java/lang/Long.h>
25 #include <java/lang/StringBuffer.h>
26 #include <java/lang/Class.h>
27 #include <java/lang/reflect/Modifier.h>
28 #include <java/lang/InternalError.h>
29 #include <java/lang/NullPointerException.h>
30 #include <java/lang/ArithmeticException.h>
31 #include <java/lang/IncompatibleClassChangeError.h>
32 #include <java/lang/InstantiationException.h>
33 #include <java/lang/Thread.h>
34 #include <java-insns.h>
35 #include <java-signal.h>
36 #include <java/lang/ClassFormatError.h>
37 #include <execution.h>
38 #include <java/lang/reflect/Modifier.h>
39
40 #include <jvmti.h>
41 #include "jvmti-int.h"
42
43 #include <gnu/gcj/jvmti/Breakpoint.h>
44 #include <gnu/gcj/jvmti/BreakpointManager.h>
45
46 // Execution engine for interpreted code.
47 _Jv_InterpreterEngine _Jv_soleInterpreterEngine;
48
49 #include <stdlib.h>
50
51 using namespace gcj;
52
53 static void throw_internal_error (const char *msg)
54   __attribute__ ((__noreturn__));
55 static void throw_incompatible_class_change_error (jstring msg)
56   __attribute__ ((__noreturn__));
57 static void throw_null_pointer_exception ()
58   __attribute__ ((__noreturn__));
59
60 static void throw_class_format_error (jstring msg)
61         __attribute__ ((__noreturn__));
62 static void throw_class_format_error (const char *msg)
63         __attribute__ ((__noreturn__));
64
65 static void find_catch_location (jthrowable, jthread, jmethodID *, jlong *);
66
67 // A macro to facilitate JVMTI exception reporting
68 #define REPORT_EXCEPTION(Jthrowable)                    \
69   do {                                                  \
70     if (JVMTI_REQUESTED_EVENT (Exception))              \
71       _Jv_ReportJVMTIExceptionThrow (Jthrowable);       \
72   }                                                     \
73   while (0)
74
75 #ifdef DIRECT_THREADED
76 // Lock to ensure that methods are not compiled concurrently.
77 // We could use a finer-grained lock here, however it is not safe to use
78 // the Class monitor as user code in another thread could hold it.
79 static _Jv_Mutex_t compile_mutex;
80
81 void
82 _Jv_InitInterpreter()
83 {
84   _Jv_MutexInit (&compile_mutex);
85 }
86 #else
87 void _Jv_InitInterpreter() {}
88 #endif
89
90 // The breakpoint instruction. For the direct threaded case,
91 // _Jv_InterpMethod::compile will initialize breakpoint_insn
92 // the first time it is called.
93 #ifdef DIRECT_THREADED
94 insn_slot _Jv_InterpMethod::bp_insn_slot;
95 pc_t _Jv_InterpMethod::breakpoint_insn = NULL;
96 #else
97 unsigned char _Jv_InterpMethod::bp_insn_opcode
98   = static_cast<unsigned char> (op_breakpoint);
99 pc_t _Jv_InterpMethod::breakpoint_insn = &_Jv_InterpMethod::bp_insn_opcode;
100 #endif
101
102 extern "C" double __ieee754_fmod (double,double);
103
104 static inline void dupx (_Jv_word *sp, int n, int x)
105 {
106   // first "slide" n+x elements n to the right
107   int top = n-1;
108   for (int i = 0; i < n+x; i++)
109     {
110       sp[(top-i)] = sp[(top-i)-n];
111     }
112   
113   // next, copy the n top elements, n+x down
114   for (int i = 0; i < n; i++)
115     {
116       sp[top-(n+x)-i] = sp[top-i];
117     }
118 }
119
120 // Used to convert from floating types to integral types.
121 template<typename TO, typename FROM>
122 static inline TO
123 convert (FROM val, TO min, TO max)
124 {
125   TO ret;
126   if (val >= (FROM) max)
127     ret = max;
128   else if (val <= (FROM) min)
129     ret = min;
130   else if (val != val)
131     ret = 0;
132   else
133     ret = (TO) val;
134   return ret;
135 }
136
137 #define PUSHA(V)  (sp++)->o = (V)
138 #define PUSHI(V)  (sp++)->i = (V)
139 #define PUSHF(V)  (sp++)->f = (V)
140 #if SIZEOF_VOID_P == 8
141 # define PUSHL(V)   (sp->l = (V), sp += 2)
142 # define PUSHD(V)   (sp->d = (V), sp += 2)
143 #else
144 # define PUSHL(V)  do { _Jv_word2 w2; w2.l=(V); \
145                         (sp++)->ia[0] = w2.ia[0]; \
146                         (sp++)->ia[0] = w2.ia[1]; } while (0)
147 # define PUSHD(V)  do { _Jv_word2 w2; w2.d=(V); \
148                         (sp++)->ia[0] = w2.ia[0]; \
149                         (sp++)->ia[0] = w2.ia[1]; } while (0)
150 #endif
151
152 #define POPA()    ((--sp)->o)
153 #define POPI()    ((jint) (--sp)->i) // cast since it may be promoted
154 #define POPF()    ((jfloat) (--sp)->f)
155 #if SIZEOF_VOID_P == 8
156 # define POPL()   (sp -= 2, (jlong) sp->l)
157 # define POPD()   (sp -= 2, (jdouble) sp->d)
158 #else
159 # define POPL()    ({ _Jv_word2 w2; \
160                      w2.ia[1] = (--sp)->ia[0]; \
161                      w2.ia[0] = (--sp)->ia[0]; w2.l; })
162 # define POPD()    ({ _Jv_word2 w2; \
163                      w2.ia[1] = (--sp)->ia[0]; \
164                      w2.ia[0] = (--sp)->ia[0]; w2.d; })
165 #endif
166
167 #define LOADA(I)  (sp++)->o = locals[I].o
168 #define LOADI(I)  (sp++)->i = locals[I].i
169 #define LOADF(I)  (sp++)->f = locals[I].f
170 #if SIZEOF_VOID_P == 8
171 # define LOADL(I)  (sp->l = locals[I].l, sp += 2)
172 # define LOADD(I)  (sp->d = locals[I].d, sp += 2)
173 #else
174 # define LOADL(I)  do { jint __idx = (I); \
175                         (sp++)->ia[0] = locals[__idx].ia[0]; \
176                         (sp++)->ia[0] = locals[__idx+1].ia[0]; \
177                    } while (0)
178 # define LOADD(I)  LOADL(I)
179 #endif
180
181 #define STOREA(I)                       \
182   do                                    \
183     {                                   \
184       jint __idx = (I);                 \
185       DEBUG_LOCALS_INSN (__idx, 'o');   \
186       locals[__idx].o = (--sp)->o;      \
187     }                                   \
188   while (0)
189 #define STOREI(I)                       \
190   do                                    \
191     {                                   \
192       jint __idx = (I);                 \
193       DEBUG_LOCALS_INSN (__idx, 'i');   \
194       locals[__idx].i = (--sp)->i;      \
195   } while (0)
196 #define STOREF(I)                       \
197   do                                    \
198     {                                   \
199       jint __idx = (I);                 \
200       DEBUG_LOCALS_INSN (__idx, 'f');   \
201       locals[__idx].f = (--sp)->f;      \
202     }                                   \
203   while (0)
204 #if SIZEOF_VOID_P == 8
205 # define STOREL(I) \
206   do                                            \
207     {                                           \
208       jint __idx = (I);                         \
209       DEBUG_LOCALS_INSN (__idx, 'l');           \
210       DEBUG_LOCALS_INSN (__idx + 1, 'x');       \
211       (sp -= 2, locals[__idx].l = sp->l);       \
212     }                                           \
213   while (0)
214 # define STORED(I)                              \
215   do                                            \
216     {                                           \
217       jint __idx = (I);                         \
218       DEBUG_LOCALS_INSN (__idx, 'd');           \
219       DEBUG_LOCALS_INSN (__idx + 1, 'x');       \
220       (sp -= 2, locals[__idx].d = sp->d);       \
221     }                                           \
222   while (0)
223
224 #else
225 # define STOREL(I)                              \
226   do                                            \
227     {                                           \
228       jint __idx = (I);                         \
229       DEBUG_LOCALS_INSN (__idx, 'l');           \
230       DEBUG_LOCALS_INSN (__idx + 1, 'x');       \
231       locals[__idx + 1].ia[0] = (--sp)->ia[0];  \
232       locals[__idx].ia[0] = (--sp)->ia[0];      \
233     }                                           \
234   while (0)
235 # define STORED(I)                              \
236   do {                                          \
237     jint __idx = (I);                           \
238     DEBUG_LOCALS_INSN (__idx, 'd');             \
239     DEBUG_LOCALS_INSN (__idx + 1, 'x');         \
240     locals[__idx + 1].ia[0] = (--sp)->ia[0];    \
241     locals[__idx].ia[0] = (--sp)->ia[0];        \
242   } while (0)
243 #endif
244
245 #define PEEKI(I)  (locals+(I))->i
246 #define PEEKA(I)  (locals+(I))->o
247
248 #define POKEI(I,V)                      \
249   do                                    \
250     {                                   \
251       jint __idx = (I);                 \
252       DEBUG_LOCALS_INSN (__idx, 'i');   \
253       ((locals + __idx)->i = (V));      \
254     }                                   \
255   while (0)
256
257
258 #define BINOPI(OP) { \
259    jint value2 = POPI(); \
260    jint value1 = POPI(); \
261    PUSHI(value1 OP value2); \
262 }
263
264 #define BINOPF(OP) { \
265    jfloat value2 = POPF(); \
266    jfloat value1 = POPF(); \
267    PUSHF(value1 OP value2); \
268 }
269
270 #define BINOPL(OP) { \
271    jlong value2 = POPL(); \
272    jlong value1 = POPL(); \
273    PUSHL(value1 OP value2); \
274 }
275
276 #define BINOPD(OP) { \
277    jdouble value2 = POPD(); \
278    jdouble value1 = POPD(); \
279    PUSHD(value1 OP value2); \
280 }
281
282 static inline jint
283 get1s (unsigned char* loc)
284 {
285   return *(signed char*)loc;
286 }
287
288 static inline jint
289 get1u (unsigned char* loc)
290 {
291   return *loc;
292 }
293
294 static inline jint
295 get2s(unsigned char* loc)
296 {
297   return (((jint)*(signed char*)loc) << 8) | ((jint)*(loc+1));
298 }
299
300 static inline jint
301 get2u (unsigned char* loc)
302 {
303   return (((jint)(*loc)) << 8) | ((jint)*(loc+1));
304 }
305
306 static jint
307 get4 (unsigned char* loc)
308 {
309   return (((jint)(loc[0])) << 24) 
310        | (((jint)(loc[1])) << 16) 
311        | (((jint)(loc[2])) << 8) 
312        | (((jint)(loc[3])) << 0);
313 }
314
315 #define SAVE_PC() frame_desc.pc = pc
316
317 // We used to define this conditionally, depending on HANDLE_SEGV.
318 // However, that runs into a problem if a chunk in low memory is
319 // mapped and we try to look at a field near the end of a large
320 // object.  See PR 26858 for details.  It is, most likely, relatively
321 // inexpensive to simply do this check always.
322 #define NULLCHECK(X) \
323   do { SAVE_PC(); if ((X)==NULL) throw_null_pointer_exception (); } while (0)
324
325 // Note that we can still conditionally define NULLARRAYCHECK, since
326 // we know that all uses of an array will first reference the length
327 // field, which is first -- and thus will trigger a SEGV.
328 #ifdef HANDLE_SEGV
329 #define NULLARRAYCHECK(X) SAVE_PC()
330 #else
331 #define NULLARRAYCHECK(X)                                       \
332   do                                                            \
333     {                                                           \
334       SAVE_PC();                                                \
335       if ((X) == NULL) { throw_null_pointer_exception (); }     \
336     } while (0)
337 #endif
338
339 #define ARRAYBOUNDSCHECK(array, index)                          \
340   do                                                            \
341     {                                                           \
342       if (((unsigned) index) >= (unsigned) (array->length))     \
343         _Jv_ThrowBadArrayIndex (index);                         \
344     } while (0)
345
346 void
347 _Jv_InterpMethod::run_normal (ffi_cif *,
348                               void *ret,
349                               INTERP_FFI_RAW_TYPE *args,
350                               void *__this)
351 {
352   _Jv_InterpMethod *_this = (_Jv_InterpMethod *) __this;
353   run (ret, args, _this);
354 }
355
356 void
357 _Jv_InterpMethod::run_normal_debug (ffi_cif *,
358                                     void *ret,
359                                     INTERP_FFI_RAW_TYPE *args,
360                                     void *__this)
361 {
362   _Jv_InterpMethod *_this = (_Jv_InterpMethod *) __this;
363   run_debug (ret, args, _this);
364 }
365
366 void
367 _Jv_InterpMethod::run_synch_object (ffi_cif *,
368                                     void *ret,
369                                     INTERP_FFI_RAW_TYPE *args,
370                                     void *__this)
371 {
372   _Jv_InterpMethod *_this = (_Jv_InterpMethod *) __this;
373
374   jobject rcv = (jobject) args[0].ptr;
375   JvSynchronize mutex (rcv);
376
377   run (ret, args, _this);
378 }
379
380 void
381 _Jv_InterpMethod::run_synch_object_debug (ffi_cif *,
382                                           void *ret,
383                                           INTERP_FFI_RAW_TYPE *args,
384                                           void *__this)
385 {
386   _Jv_InterpMethod *_this = (_Jv_InterpMethod *) __this;
387
388   jobject rcv = (jobject) args[0].ptr;
389   JvSynchronize mutex (rcv);
390
391   run_debug (ret, args, _this);
392 }
393
394 void
395 _Jv_InterpMethod::run_class (ffi_cif *,
396                              void *ret,
397                              INTERP_FFI_RAW_TYPE *args,
398                              void *__this)
399 {
400   _Jv_InterpMethod *_this = (_Jv_InterpMethod *) __this;
401   _Jv_InitClass (_this->defining_class);
402   run (ret, args, _this);
403 }
404
405 void
406 _Jv_InterpMethod::run_class_debug (ffi_cif *,
407                                    void *ret,
408                                    INTERP_FFI_RAW_TYPE *args,
409                                    void *__this)
410 {
411   _Jv_InterpMethod *_this = (_Jv_InterpMethod *) __this;
412   _Jv_InitClass (_this->defining_class);
413   run_debug (ret, args, _this);
414 }
415
416 void
417 _Jv_InterpMethod::run_synch_class (ffi_cif *,
418                                    void *ret,
419                                    INTERP_FFI_RAW_TYPE *args,
420                                    void *__this)
421 {
422   _Jv_InterpMethod *_this = (_Jv_InterpMethod *) __this;
423
424   jclass sync = _this->defining_class;
425   _Jv_InitClass (sync);
426   JvSynchronize mutex (sync);
427
428   run (ret, args, _this);
429 }
430
431 void
432 _Jv_InterpMethod::run_synch_class_debug (ffi_cif *,
433                                          void *ret,
434                                          INTERP_FFI_RAW_TYPE *args,
435                                          void *__this)
436 {
437   _Jv_InterpMethod *_this = (_Jv_InterpMethod *) __this;
438
439   jclass sync = _this->defining_class;
440   _Jv_InitClass (sync);
441   JvSynchronize mutex (sync);
442
443   run_debug (ret, args, _this);
444 }
445
446 #ifdef DIRECT_THREADED
447 // "Compile" a method by turning it from bytecode to direct-threaded
448 // code.
449 void
450 _Jv_InterpMethod::compile (const void * const *insn_targets)
451 {
452   insn_slot *insns = NULL;
453   int next = 0;
454   unsigned char *codestart = bytecode ();
455   unsigned char *end = codestart + code_length;
456   _Jv_word *pool_data = defining_class->constants.data;
457
458 #define SET_ONE(Field, Value)                                                 \
459   do                                                                          \
460     {                                                                         \
461       if (first_pass)                                                         \
462         ++next;                                                               \
463       else                                                                    \
464         insns[next++].Field = Value;                                          \
465     }                                                                         \
466   while (0)
467
468 #define SET_INSN(Value) SET_ONE (insn, (void *) Value)
469 #define SET_INT(Value) SET_ONE (int_val, Value)
470 #define SET_DATUM(Value) SET_ONE (datum, Value)
471
472   // Map from bytecode PC to slot in INSNS.
473   int *pc_mapping = (int *) __builtin_alloca (sizeof (int) * code_length);
474   for (int i = 0; i < code_length; ++i)
475     pc_mapping[i] = -1;
476
477   for (int i = 0; i < 2; ++i)
478     {
479       jboolean first_pass = i == 0;
480
481       if (! first_pass)
482         {
483           insns = (insn_slot *) _Jv_AllocBytes (sizeof (insn_slot) * next);
484           number_insn_slots = next;
485           next = 0;
486         }
487
488       unsigned char *pc = codestart;
489       while (pc < end)
490         {
491           int base_pc_val = pc - codestart;
492           if (first_pass)
493             pc_mapping[base_pc_val] = next;
494
495           java_opcode opcode = (java_opcode) *pc++;
496           // Just elide NOPs.
497           if (opcode == op_nop)
498             continue;
499           SET_INSN (insn_targets[opcode]);
500
501           switch (opcode)
502             {
503             case op_nop:
504             case op_aconst_null:
505             case op_iconst_m1:
506             case op_iconst_0:
507             case op_iconst_1:
508             case op_iconst_2:
509             case op_iconst_3:
510             case op_iconst_4:
511             case op_iconst_5:
512             case op_lconst_0:
513             case op_lconst_1:
514             case op_fconst_0:
515             case op_fconst_1:
516             case op_fconst_2:
517             case op_dconst_0:
518             case op_dconst_1:
519             case op_iload_0:
520             case op_iload_1:
521             case op_iload_2:
522             case op_iload_3:
523             case op_lload_0:
524             case op_lload_1:
525             case op_lload_2:
526             case op_lload_3:
527             case op_fload_0:
528             case op_fload_1:
529             case op_fload_2:
530             case op_fload_3:
531             case op_dload_0:
532             case op_dload_1:
533             case op_dload_2:
534             case op_dload_3:
535             case op_aload_0:
536             case op_aload_1:
537             case op_aload_2:
538             case op_aload_3:
539             case op_iaload:
540             case op_laload:
541             case op_faload:
542             case op_daload:
543             case op_aaload:
544             case op_baload:
545             case op_caload:
546             case op_saload:
547             case op_istore_0:
548             case op_istore_1:
549             case op_istore_2:
550             case op_istore_3:
551             case op_lstore_0:
552             case op_lstore_1:
553             case op_lstore_2:
554             case op_lstore_3:
555             case op_fstore_0:
556             case op_fstore_1:
557             case op_fstore_2:
558             case op_fstore_3:
559             case op_dstore_0:
560             case op_dstore_1:
561             case op_dstore_2:
562             case op_dstore_3:
563             case op_astore_0:
564             case op_astore_1:
565             case op_astore_2:
566             case op_astore_3:
567             case op_iastore:
568             case op_lastore:
569             case op_fastore:
570             case op_dastore:
571             case op_aastore:
572             case op_bastore:
573             case op_castore:
574             case op_sastore:
575             case op_pop:
576             case op_pop2:
577             case op_dup:
578             case op_dup_x1:
579             case op_dup_x2:
580             case op_dup2:
581             case op_dup2_x1:
582             case op_dup2_x2:
583             case op_swap:
584             case op_iadd:
585             case op_isub:
586             case op_imul:
587             case op_idiv:
588             case op_irem:
589             case op_ishl:
590             case op_ishr:
591             case op_iushr:
592             case op_iand:
593             case op_ior:
594             case op_ixor:
595             case op_ladd:
596             case op_lsub:
597             case op_lmul:
598             case op_ldiv:
599             case op_lrem:
600             case op_lshl:
601             case op_lshr:
602             case op_lushr:
603             case op_land:
604             case op_lor:
605             case op_lxor:
606             case op_fadd:
607             case op_fsub:
608             case op_fmul:
609             case op_fdiv:
610             case op_frem:
611             case op_dadd:
612             case op_dsub:
613             case op_dmul:
614             case op_ddiv:
615             case op_drem:
616             case op_ineg:
617             case op_i2b:
618             case op_i2c:
619             case op_i2s:
620             case op_lneg:
621             case op_fneg:
622             case op_dneg:
623             case op_i2l:
624             case op_i2f:
625             case op_i2d:
626             case op_l2i:
627             case op_l2f:
628             case op_l2d:
629             case op_f2i:
630             case op_f2l:
631             case op_f2d:
632             case op_d2i:
633             case op_d2l:
634             case op_d2f:
635             case op_lcmp:
636             case op_fcmpl:
637             case op_fcmpg:
638             case op_dcmpl:
639             case op_dcmpg:
640             case op_monitorenter:
641             case op_monitorexit:
642             case op_ireturn:
643             case op_lreturn:
644             case op_freturn:
645             case op_dreturn:
646             case op_areturn:
647             case op_return:
648             case op_athrow:
649             case op_arraylength:
650               // No argument, nothing else to do.
651               break;
652
653             case op_bipush:
654               SET_INT (get1s (pc));
655               ++pc;
656               break;
657
658             case op_ldc:
659               {
660                 int index = get1u (pc);
661                 ++pc;
662                 // For an unresolved class we want to delay resolution
663                 // until execution.
664                 if (defining_class->constants.tags[index] == JV_CONSTANT_Class)
665                   {
666                     --next;
667                     SET_INSN (insn_targets[int (op_jsr_w) + 1]);
668                     SET_INT (index);
669                   }
670                 else
671                   SET_DATUM (pool_data[index].o);
672               }
673               break;
674
675             case op_ret:
676             case op_iload:
677             case op_lload:
678             case op_fload:
679             case op_dload:
680             case op_aload:
681             case op_istore:
682             case op_lstore:
683             case op_fstore:
684             case op_dstore:
685             case op_astore:
686             case op_newarray:
687               SET_INT (get1u (pc));
688               ++pc;
689               break;
690
691             case op_iinc:
692               SET_INT (get1u (pc));
693               SET_INT (get1s (pc + 1));
694               pc += 2;
695               break;
696
697             case op_ldc_w:
698               {
699                 int index = get2u (pc);
700                 pc += 2;
701                 // For an unresolved class we want to delay resolution
702                 // until execution.
703                 if (defining_class->constants.tags[index] == JV_CONSTANT_Class)
704                   {
705                     --next;
706                     SET_INSN (insn_targets[int (op_jsr_w) + 1]);
707                     SET_INT (index);
708                   }
709                 else
710                   SET_DATUM (pool_data[index].o);
711               }
712               break;
713
714             case op_ldc2_w:
715               {
716                 int index = get2u (pc);
717                 pc += 2;
718                 SET_DATUM (&pool_data[index]);
719               }
720               break;
721
722             case op_sipush:
723               SET_INT (get2s (pc));
724               pc += 2;
725               break;
726
727             case op_new:
728             case op_getstatic:
729             case op_getfield:
730             case op_putfield:
731             case op_putstatic:
732             case op_anewarray:
733             case op_instanceof:
734             case op_checkcast:
735             case op_invokespecial:
736             case op_invokestatic:
737             case op_invokevirtual:
738               SET_INT (get2u (pc));
739               pc += 2;
740               break;
741
742             case op_multianewarray:
743               SET_INT (get2u (pc));
744               SET_INT (get1u (pc + 2));
745               pc += 3;
746               break;
747
748             case op_jsr:
749             case op_ifeq:
750             case op_ifne:
751             case op_iflt:
752             case op_ifge:
753             case op_ifgt:
754             case op_ifle:
755             case op_if_icmpeq:
756             case op_if_icmpne:
757             case op_if_icmplt:
758             case op_if_icmpge:
759             case op_if_icmpgt:
760             case op_if_icmple:
761             case op_if_acmpeq:
762             case op_if_acmpne:
763             case op_ifnull:
764             case op_ifnonnull:
765             case op_goto:
766               {
767                 int offset = get2s (pc);
768                 pc += 2;
769
770                 int new_pc = base_pc_val + offset;
771
772                 bool orig_was_goto = opcode == op_goto;
773
774                 // Thread jumps.  We limit the loop count; this lets
775                 // us avoid infinite loops if the bytecode contains
776                 // such.  `10' is arbitrary.
777                 int count = 10;
778                 while (codestart[new_pc] == op_goto && count-- > 0)
779                   new_pc += get2s (&codestart[new_pc + 1]);
780
781                 // If the jump takes us to a `return' instruction and
782                 // the original branch was an unconditional goto, then
783                 // we hoist the return.
784                 opcode = (java_opcode) codestart[new_pc];
785                 if (orig_was_goto
786                     && (opcode == op_ireturn || opcode == op_lreturn
787                         || opcode == op_freturn || opcode == op_dreturn
788                         || opcode == op_areturn || opcode == op_return))
789                   {
790                     --next;
791                     SET_INSN (insn_targets[opcode]);
792                   }
793                 else
794                   SET_DATUM (&insns[pc_mapping[new_pc]]);
795               }
796               break;
797
798             case op_tableswitch:
799               {
800                 while ((pc - codestart) % 4 != 0)
801                   ++pc;
802
803                 jint def = get4 (pc);
804                 SET_DATUM (&insns[pc_mapping[base_pc_val + def]]);
805                 pc += 4;
806
807                 int low = get4 (pc);
808                 SET_INT (low);
809                 pc += 4;
810                 int high = get4 (pc);
811                 SET_INT (high);
812                 pc += 4;
813
814                 for (int i = low; i <= high; ++i)
815                   {
816                     SET_DATUM (&insns[pc_mapping[base_pc_val + get4 (pc)]]);
817                     pc += 4;
818                   }
819               }
820               break;
821
822             case op_lookupswitch:
823               {
824                 while ((pc - codestart) % 4 != 0)
825                   ++pc;
826
827                 jint def = get4 (pc);
828                 SET_DATUM (&insns[pc_mapping[base_pc_val + def]]);
829                 pc += 4;
830
831                 jint npairs = get4 (pc);
832                 pc += 4;
833                 SET_INT (npairs);
834
835                 while (npairs-- > 0)
836                   {
837                     jint match = get4 (pc);
838                     jint offset = get4 (pc + 4);
839                     SET_INT (match);
840                     SET_DATUM (&insns[pc_mapping[base_pc_val + offset]]);
841                     pc += 8;
842                   }
843               }
844               break;
845
846             case op_invokeinterface:
847               {
848                 jint index = get2u (pc);
849                 pc += 2;
850                 // We ignore the next two bytes.
851                 pc += 2;
852                 SET_INT (index);
853               }
854               break;
855
856             case op_wide:
857               {
858                 opcode = (java_opcode) get1u (pc);
859                 pc += 1;
860                 jint val = get2u (pc);
861                 pc += 2;
862
863                 // We implement narrow and wide instructions using the
864                 // same code in the interpreter.  So we rewrite the
865                 // instruction slot here.
866                 if (! first_pass)
867                   insns[next - 1].insn = (void *) insn_targets[opcode];
868                 SET_INT (val);
869
870                 if (opcode == op_iinc)
871                   {
872                     SET_INT (get2s (pc));
873                     pc += 2;
874                   }
875               }
876               break;
877
878             case op_jsr_w:
879             case op_goto_w:
880               {
881                 jint offset = get4 (pc);
882                 pc += 4;
883                 SET_DATUM (&insns[pc_mapping[base_pc_val + offset]]);
884               }
885               break;
886
887             // Some "can't happen" cases that we include for
888             // error-checking purposes.
889             case op_putfield_1:
890             case op_putfield_2:
891             case op_putfield_4:
892             case op_putfield_8:
893             case op_putfield_a:
894             case op_putstatic_1:
895             case op_putstatic_2:
896             case op_putstatic_4:
897             case op_putstatic_8:
898             case op_putstatic_a:
899             case op_getfield_1:
900             case op_getfield_2s:
901             case op_getfield_2u:
902             case op_getfield_4:
903             case op_getfield_8:
904             case op_getfield_a:
905             case op_getstatic_1:
906             case op_getstatic_2s:
907             case op_getstatic_2u:
908             case op_getstatic_4:
909             case op_getstatic_8:
910             case op_getstatic_a:
911             case op_breakpoint:
912             default:
913               // Fail somehow.
914               break;
915             }
916         }
917     }
918
919   // Now update exceptions.
920   _Jv_InterpException *exc = exceptions ();
921   for (int i = 0; i < exc_count; ++i)
922     {
923       exc[i].start_pc.p = &insns[pc_mapping[exc[i].start_pc.i]];
924       exc[i].end_pc.p = &insns[pc_mapping[exc[i].end_pc.i]];
925       exc[i].handler_pc.p = &insns[pc_mapping[exc[i].handler_pc.i]];
926       // FIXME: resolve_pool_entry can throw - we shouldn't be doing this
927       // during compilation.
928       jclass handler
929         = (_Jv_Linker::resolve_pool_entry (defining_class,
930                                              exc[i].handler_type.i)).clazz;
931       exc[i].handler_type.p = handler;
932     }
933
934   // Translate entries in the LineNumberTable from bytecode PC's to direct
935   // threaded interpreter instruction values.
936   for (int i = 0; i < line_table_len; i++)
937     {
938       int byte_pc = line_table[i].bytecode_pc;
939       // It isn't worth throwing an exception if this table is
940       // corrupted, but at the same time we don't want a crash.
941       if (byte_pc < 0 || byte_pc >= code_length)
942         byte_pc = 0;
943       line_table[i].pc = &insns[pc_mapping[byte_pc]];
944     }  
945
946   prepared = insns;
947
948   // Now remap the variable table for this method.
949   for (int i = 0; i < local_var_table_len; ++i)
950     {
951       int start_byte = local_var_table[i].bytecode_pc;
952       if (start_byte < 0 || start_byte >= code_length)
953         start_byte = 0;
954       jlocation start =  pc_mapping[start_byte];
955
956       int end_byte = start_byte + local_var_table[i].length;
957       if (end_byte < 0)
958         end_byte = 0;
959       jlocation end = ((end_byte >= code_length)
960                        ? number_insn_slots
961                        : pc_mapping[end_byte]);
962
963       local_var_table[i].pc = &insns[start];
964       local_var_table[i].length = end - start + 1;
965     }
966   
967   if (breakpoint_insn == NULL)
968     {
969       bp_insn_slot.insn = const_cast<void *> (insn_targets[op_breakpoint]);
970       breakpoint_insn = &bp_insn_slot;
971     }
972 }
973 #endif /* DIRECT_THREADED */
974
975 /* Run the given method.
976    When args is NULL, don't run anything -- just compile it. */
977 void
978 _Jv_InterpMethod::run (void *retp, INTERP_FFI_RAW_TYPE *args,
979                        _Jv_InterpMethod *meth)
980 {
981 #undef DEBUG
982 #undef DEBUG_LOCALS_INSN
983 #define DEBUG_LOCALS_INSN(s, t) do {} while (0)
984
985 #include "interpret-run.cc"
986 }
987
988 void
989 _Jv_InterpMethod::run_debug (void *retp, INTERP_FFI_RAW_TYPE *args,
990                              _Jv_InterpMethod *meth)
991 {
992 #define DEBUG
993 #undef DEBUG_LOCALS_INSN
994 #define DEBUG_LOCALS_INSN(s, t)  \
995   do    \
996     {   \
997       frame_desc.locals_type[s] = t;  \
998     }   \
999   while (0)
1000
1001 #include "interpret-run.cc"
1002 }
1003
1004 static void
1005 throw_internal_error (const char *msg)
1006 {
1007   jthrowable t = new java::lang::InternalError (JvNewStringLatin1 (msg));
1008   REPORT_EXCEPTION (t);
1009   throw t;
1010 }
1011
1012 static void 
1013 throw_incompatible_class_change_error (jstring msg)
1014 {
1015   jthrowable t = new java::lang::IncompatibleClassChangeError (msg);
1016   REPORT_EXCEPTION (t);
1017   throw t;
1018 }
1019
1020 static void 
1021 throw_null_pointer_exception ()
1022 {
1023   jthrowable t = new java::lang::NullPointerException;
1024   REPORT_EXCEPTION (t);
1025   throw t;
1026 }
1027
1028 /* Look up source code line number for given bytecode (or direct threaded
1029    interpreter) PC. */
1030 int
1031 _Jv_InterpMethod::get_source_line(pc_t mpc)
1032 {
1033   int line = line_table_len > 0 ? line_table[0].line : -1;
1034   for (int i = 1; i < line_table_len; i++)
1035     if (line_table[i].pc > mpc)
1036       break;
1037     else
1038       line = line_table[i].line;
1039
1040   return line;
1041 }
1042
1043 /** Do static initialization for fields with a constant initializer */
1044 void
1045 _Jv_InitField (jobject obj, jclass klass, int index)
1046 {
1047   using namespace java::lang::reflect;
1048
1049   if (obj != 0 && klass == 0)
1050     klass = obj->getClass ();
1051
1052   if (!_Jv_IsInterpretedClass (klass))
1053     return;
1054
1055   _Jv_InterpClass *iclass = (_Jv_InterpClass*)klass->aux_info;
1056
1057   _Jv_Field * field = (&klass->fields[0]) + index;
1058
1059   if (index > klass->field_count)
1060     throw_internal_error ("field out of range");
1061
1062   int init = iclass->field_initializers[index];
1063   if (init == 0)
1064     return;
1065
1066   _Jv_Constants *pool = &klass->constants;
1067   int tag = pool->tags[init];
1068
1069   if (! field->isResolved ())
1070     throw_internal_error ("initializing unresolved field");
1071
1072   if (obj==0 && ((field->flags & Modifier::STATIC) == 0))
1073     throw_internal_error ("initializing non-static field with no object");
1074
1075   void *addr = 0;
1076
1077   if ((field->flags & Modifier::STATIC) != 0)
1078     addr = (void*) field->u.addr;
1079   else
1080     addr = (void*) (((char*)obj) + field->u.boffset);
1081
1082   switch (tag)
1083     {
1084     case JV_CONSTANT_String:
1085       {
1086         jstring str;
1087         str = _Jv_NewStringUtf8Const (pool->data[init].utf8);
1088         pool->data[init].string = str;
1089         pool->tags[init] = JV_CONSTANT_ResolvedString;
1090       }
1091       /* fall through */
1092
1093     case JV_CONSTANT_ResolvedString:
1094       if (! (field->type == &java::lang::String::class$
1095              || field->type == &java::lang::Class::class$))
1096         throw_class_format_error ("string initialiser to non-string field");
1097
1098       *(jstring*)addr = pool->data[init].string;
1099       break;
1100
1101     case JV_CONSTANT_Integer:
1102       {
1103         int value = pool->data[init].i;
1104
1105         if (field->type == JvPrimClass (boolean))
1106           *(jboolean*)addr = (jboolean)value;
1107         
1108         else if (field->type == JvPrimClass (byte))
1109           *(jbyte*)addr = (jbyte)value;
1110         
1111         else if (field->type == JvPrimClass (char))
1112           *(jchar*)addr = (jchar)value;
1113
1114         else if (field->type == JvPrimClass (short))
1115           *(jshort*)addr = (jshort)value;
1116         
1117         else if (field->type == JvPrimClass (int))
1118           *(jint*)addr = (jint)value;
1119
1120         else
1121           throw_class_format_error ("erroneous field initializer");
1122       }  
1123       break;
1124
1125     case JV_CONSTANT_Long:
1126       if (field->type != JvPrimClass (long))
1127         throw_class_format_error ("erroneous field initializer");
1128
1129       *(jlong*)addr = _Jv_loadLong (&pool->data[init]);
1130       break;
1131
1132     case JV_CONSTANT_Float:
1133       if (field->type != JvPrimClass (float))
1134         throw_class_format_error ("erroneous field initializer");
1135
1136       *(jfloat*)addr = pool->data[init].f;
1137       break;
1138
1139     case JV_CONSTANT_Double:
1140       if (field->type != JvPrimClass (double))
1141         throw_class_format_error ("erroneous field initializer");
1142
1143       *(jdouble*)addr = _Jv_loadDouble (&pool->data[init]);
1144       break;
1145
1146     default:
1147       throw_class_format_error ("erroneous field initializer");
1148     }
1149 }
1150
1151 inline static unsigned char*
1152 skip_one_type (unsigned char* ptr)
1153 {
1154   int ch = *ptr++;
1155
1156   while (ch == '[')
1157     { 
1158       ch = *ptr++;
1159     }
1160   
1161   if (ch == 'L')
1162     {
1163       do { ch = *ptr++; } while (ch != ';');
1164     }
1165
1166   return ptr;
1167 }
1168
1169 static ffi_type*
1170 get_ffi_type_from_signature (unsigned char* ptr)
1171 {
1172   switch (*ptr) 
1173     {
1174     case 'L':
1175     case '[':
1176       return &ffi_type_pointer;
1177       break;
1178
1179     case 'Z':
1180       // On some platforms a bool is a byte, on others an int.
1181       if (sizeof (jboolean) == sizeof (jbyte))
1182         return &ffi_type_sint8;
1183       else
1184         {
1185           JvAssert (sizeof (jbyte) == sizeof (jint));
1186           return &ffi_type_sint32;
1187         }
1188       break;
1189
1190     case 'B':
1191       return &ffi_type_sint8;
1192       break;
1193       
1194     case 'C':
1195       return &ffi_type_uint16;
1196       break;
1197           
1198     case 'S': 
1199       return &ffi_type_sint16;
1200       break;
1201           
1202     case 'I':
1203       return &ffi_type_sint32;
1204       break;
1205           
1206     case 'J':
1207       return &ffi_type_sint64;
1208       break;
1209           
1210     case 'F':
1211       return &ffi_type_float;
1212       break;
1213           
1214     case 'D':
1215       return &ffi_type_double;
1216       break;
1217
1218     case 'V':
1219       return &ffi_type_void;
1220       break;
1221     }
1222
1223   throw_internal_error ("unknown type in signature");
1224 }
1225
1226 /* this function yields the number of actual arguments, that is, if the
1227  * function is non-static, then one is added to the number of elements
1228  * found in the signature */
1229
1230 int 
1231 _Jv_count_arguments (_Jv_Utf8Const *signature,
1232                      jboolean staticp)
1233 {
1234   unsigned char *ptr = (unsigned char*) signature->chars();
1235   int arg_count = staticp ? 0 : 1;
1236
1237   /* first, count number of arguments */
1238
1239   // skip '('
1240   ptr++;
1241
1242   // count args
1243   while (*ptr != ')')
1244     {
1245       ptr = skip_one_type (ptr);
1246       arg_count += 1;
1247     }
1248
1249   return arg_count;
1250 }
1251
1252 /* This beast will build a cif, given the signature.  Memory for
1253  * the cif itself and for the argument types must be allocated by the
1254  * caller.
1255  */
1256
1257 int 
1258 _Jv_init_cif (_Jv_Utf8Const* signature,
1259               int arg_count,
1260               jboolean staticp,
1261               ffi_cif *cif,
1262               ffi_type **arg_types,
1263               ffi_type **rtype_p)
1264 {
1265   unsigned char *ptr = (unsigned char*) signature->chars();
1266
1267   int arg_index = 0;            // arg number
1268   int item_count = 0;           // stack-item count
1269
1270   // setup receiver
1271   if (!staticp)
1272     {
1273       arg_types[arg_index++] = &ffi_type_pointer;
1274       item_count += 1;
1275     }
1276
1277   // skip '('
1278   ptr++;
1279
1280   // assign arg types
1281   while (*ptr != ')')
1282     {
1283       arg_types[arg_index++] = get_ffi_type_from_signature (ptr);
1284
1285       if (*ptr == 'J' || *ptr == 'D')
1286         item_count += 2;
1287       else
1288         item_count += 1;
1289
1290       ptr = skip_one_type (ptr);
1291     }
1292
1293   // skip ')'
1294   ptr++;
1295   ffi_type *rtype = get_ffi_type_from_signature (ptr);
1296
1297   ptr = skip_one_type (ptr);
1298   if (ptr != (unsigned char*)signature->chars() + signature->len())
1299     throw_internal_error ("did not find end of signature");
1300
1301   if (ffi_prep_cif (cif, FFI_DEFAULT_ABI,
1302                     arg_count, rtype, arg_types) != FFI_OK)
1303     throw_internal_error ("ffi_prep_cif failed");
1304
1305   if (rtype_p != NULL)
1306     *rtype_p = rtype;
1307
1308   return item_count;
1309 }
1310
1311 /* we put this one here, and not in interpret.cc because it
1312  * calls the utility routines _Jv_count_arguments 
1313  * which are static to this module.  The following struct defines the
1314  * layout we use for the stubs, it's only used in the ncode method. */
1315
1316 #if FFI_NATIVE_RAW_API
1317 #   define FFI_PREP_RAW_CLOSURE ffi_prep_raw_closure_loc
1318 #   define FFI_RAW_SIZE ffi_raw_size
1319 typedef struct {
1320   ffi_raw_closure  closure;
1321   _Jv_ClosureList list;
1322   ffi_cif   cif;
1323   ffi_type *arg_types[0];
1324 } ncode_closure;
1325 typedef void (*ffi_closure_fun) (ffi_cif*,void*,INTERP_FFI_RAW_TYPE*,void*);
1326 #else
1327 #   define FFI_PREP_RAW_CLOSURE ffi_prep_java_raw_closure_loc
1328 #   define FFI_RAW_SIZE ffi_java_raw_size
1329 typedef struct {
1330   ffi_java_raw_closure  closure;
1331   _Jv_ClosureList list;
1332   ffi_cif   cif;
1333   ffi_type *arg_types[0];
1334 } ncode_closure;
1335 typedef void (*ffi_closure_fun) (ffi_cif*,void*,ffi_java_raw*,void*);
1336 #endif
1337
1338 void *
1339 _Jv_InterpMethod::ncode (jclass klass)
1340 {
1341   using namespace java::lang::reflect;
1342
1343   if (self->ncode != 0)
1344     return self->ncode;
1345
1346   jboolean staticp = (self->accflags & Modifier::STATIC) != 0;
1347   int arg_count = _Jv_count_arguments (self->signature, staticp);
1348
1349   void *code;
1350   ncode_closure *closure =
1351     (ncode_closure*)ffi_closure_alloc (sizeof (ncode_closure)
1352                                        + arg_count * sizeof (ffi_type*),
1353                                        &code);
1354   closure->list.registerClosure (klass, closure);
1355
1356   _Jv_init_cif (self->signature,
1357                 arg_count,
1358                 staticp,
1359                 &closure->cif,
1360                 &closure->arg_types[0],
1361                 NULL);
1362
1363   ffi_closure_fun fun;
1364
1365   args_raw_size = FFI_RAW_SIZE (&closure->cif);
1366
1367   JvAssert ((self->accflags & Modifier::NATIVE) == 0);
1368
1369   if ((self->accflags & Modifier::SYNCHRONIZED) != 0)
1370     {
1371       if (staticp)
1372         {
1373           if (JVMTI::enabled)
1374             fun = (ffi_closure_fun)&_Jv_InterpMethod::run_synch_class_debug;
1375           else
1376             fun = (ffi_closure_fun)&_Jv_InterpMethod::run_synch_class;
1377         }
1378       else
1379         {
1380           if (JVMTI::enabled)
1381             fun = (ffi_closure_fun)&_Jv_InterpMethod::run_synch_object_debug;
1382           else
1383             fun = (ffi_closure_fun)&_Jv_InterpMethod::run_synch_object;
1384         }
1385     }
1386   else
1387     {
1388       if (staticp)
1389         {
1390           if (JVMTI::enabled)
1391             fun = (ffi_closure_fun)&_Jv_InterpMethod::run_class_debug;
1392           else
1393             fun = (ffi_closure_fun)&_Jv_InterpMethod::run_class;
1394         }
1395       else
1396         {
1397           if (JVMTI::enabled)
1398             fun = (ffi_closure_fun)&_Jv_InterpMethod::run_normal_debug;
1399           else
1400             fun = (ffi_closure_fun)&_Jv_InterpMethod::run_normal;
1401         }
1402     }
1403
1404   FFI_PREP_RAW_CLOSURE (&closure->closure,
1405                         &closure->cif, 
1406                         fun,
1407                         (void*)this,
1408                         code);
1409
1410   self->ncode = code;
1411
1412   return self->ncode;
1413 }
1414
1415 /* Find the index of the given insn in the array of insn slots
1416    for this method. Returns -1 if not found. */
1417 jlong
1418 _Jv_InterpMethod::insn_index (pc_t pc)
1419 {
1420   jlong left = 0;
1421 #ifdef DIRECT_THREADED
1422   jlong right = number_insn_slots;
1423   pc_t insns = prepared;
1424 #else
1425   jlong right = code_length;
1426   pc_t insns = bytecode ();
1427 #endif
1428
1429   while (right >= 0)
1430     {
1431       jlong mid = (left + right) / 2;
1432       if (&insns[mid] == pc)
1433         return mid;
1434
1435       if (pc < &insns[mid])
1436         right = mid - 1;
1437       else
1438         left = mid + 1;
1439     }
1440
1441   return -1;
1442 }
1443
1444 // Method to check if an exception is caught at some location in a method
1445 // (meth).  Returns true if this method (meth) contains a catch block for the
1446 // exception (ex). False otherwise.  If there is a catch block, it sets the pc
1447 // to the location of the beginning of the catch block.
1448 jboolean
1449 _Jv_InterpMethod::check_handler (pc_t *pc, _Jv_InterpMethod *meth,
1450                                 java::lang::Throwable *ex)
1451 {
1452 #ifdef DIRECT_THREADED
1453   void *logical_pc = (void *) ((insn_slot *) (*pc) - 1);
1454 #else
1455   int logical_pc = (*pc) - 1 - meth->bytecode ();
1456 #endif
1457   _Jv_InterpException *exc = meth->exceptions ();
1458   jclass exc_class = ex->getClass ();
1459
1460   for (int i = 0; i < meth->exc_count; i++)
1461     {
1462       if (PCVAL (exc[i].start_pc) <= logical_pc
1463           && logical_pc < PCVAL (exc[i].end_pc))
1464         {
1465 #ifdef DIRECT_THREADED
1466               jclass handler = (jclass) exc[i].handler_type.p;
1467 #else
1468               jclass handler = NULL;
1469               if (exc[i].handler_type.i != 0)
1470                     handler
1471                       = (_Jv_Linker::resolve_pool_entry (meth->defining_class,
1472                                                                              ex$
1473 #endif /* DIRECT_THREADED */
1474               if (handler == NULL || handler->isAssignableFrom (exc_class))
1475                 {
1476 #ifdef DIRECT_THREADED
1477                   (*pc) = (insn_slot *) exc[i].handler_pc.p;
1478 #else
1479                   (*pc) = meth->bytecode () + exc[i].handler_pc.i;
1480 #endif /* DIRECT_THREADED */
1481                   return true;
1482                 }
1483           }
1484       }
1485   return false;
1486 }
1487
1488
1489 void
1490 _Jv_InterpMethod::get_line_table (jlong& start, jlong& end,
1491                                   jintArray& line_numbers,
1492                                   jlongArray& code_indices)
1493 {
1494 #ifdef DIRECT_THREADED
1495   /* For the DIRECT_THREADED case, if the method has not yet been
1496    * compiled, the linetable will change to insn slots instead of
1497    * bytecode PCs. It is probably easiest, in this case, to simply
1498    * compile the method and guarantee that we are using insn
1499    * slots.
1500    */
1501   _Jv_CompileMethod (this);
1502
1503   if (line_table_len > 0)
1504     {
1505       start = 0;
1506       end = number_insn_slots;
1507       line_numbers = JvNewIntArray (line_table_len);
1508       code_indices = JvNewLongArray (line_table_len);
1509
1510       jint* lines = elements (line_numbers);
1511       jlong* indices = elements (code_indices);
1512       for (int i = 0; i < line_table_len; ++i)
1513         {
1514           lines[i] = line_table[i].line;
1515           indices[i] = insn_index (line_table[i].pc);
1516         }
1517     }
1518 #else // !DIRECT_THREADED
1519   if (line_table_len > 0)
1520     {
1521       start = 0;
1522       end = code_length;
1523       line_numbers = JvNewIntArray (line_table_len);
1524       code_indices = JvNewLongArray (line_table_len);
1525
1526       jint* lines = elements (line_numbers);
1527       jlong* indices = elements (code_indices);
1528       for (int i = 0; i < line_table_len; ++i)
1529         {
1530           lines[i] = line_table[i].line;
1531           indices[i] = (jlong) line_table[i].bytecode_pc;
1532         }
1533     }
1534 #endif // !DIRECT_THREADED
1535 }
1536
1537 int 
1538 _Jv_InterpMethod::get_local_var_table (char **name, char **sig, 
1539                                        char **generic_sig, jlong *startloc,
1540                                        jint *length, jint *slot, 
1541                                        int table_slot)
1542 {
1543 #ifdef DIRECT_THREADED
1544   _Jv_CompileMethod (this);
1545 #endif
1546
1547   if (local_var_table == NULL)
1548     return -2;
1549   if (table_slot >= local_var_table_len)
1550     return -1;
1551   else
1552     {
1553       *name = local_var_table[table_slot].name;
1554       *sig = local_var_table[table_slot].descriptor;
1555       *generic_sig = local_var_table[table_slot].descriptor;
1556
1557 #ifdef DIRECT_THREADED
1558       *startloc = insn_index (local_var_table[table_slot].pc);
1559 #else
1560       *startloc = static_cast<jlong> (local_var_table[table_slot].bytecode_pc);
1561 #endif
1562       *length = static_cast<jint> (local_var_table[table_slot].length);
1563       *slot = static_cast<jint> (local_var_table[table_slot].slot);
1564     }
1565   return local_var_table_len - table_slot - 1;
1566 }
1567
1568 pc_t
1569 _Jv_InterpMethod::install_break (jlong index)
1570 {
1571   return set_insn (index, breakpoint_insn);
1572 }
1573
1574 pc_t
1575 _Jv_InterpMethod::get_insn (jlong index)
1576 {
1577   pc_t code;
1578
1579 #ifdef DIRECT_THREADED
1580   if (index >= number_insn_slots || index < 0)
1581     return NULL;
1582
1583   code = prepared;
1584 #else // !DIRECT_THREADED
1585   if (index >= code_length || index < 0)
1586     return NULL;
1587
1588   code = reinterpret_cast<pc_t> (bytecode ());
1589 #endif // !DIRECT_THREADED
1590
1591   return &code[index];
1592 }
1593
1594 pc_t
1595 _Jv_InterpMethod::set_insn (jlong index, pc_t insn)
1596 {
1597 #ifdef DIRECT_THREADED
1598   if (index >= number_insn_slots || index < 0)
1599     return NULL;
1600
1601   pc_t code = prepared;
1602   code[index].insn = insn->insn;
1603 #else // !DIRECT_THREADED
1604   if (index >= code_length || index < 0)
1605     return NULL;
1606
1607   pc_t code = reinterpret_cast<pc_t> (bytecode ());
1608   code[index] = *insn;
1609 #endif // !DIRECT_THREADED
1610
1611   return &code[index];
1612 }
1613
1614 bool
1615 _Jv_InterpMethod::breakpoint_at (jlong index)
1616 {
1617   pc_t insn = get_insn (index);
1618   if (insn != NULL)
1619     {
1620 #ifdef DIRECT_THREADED
1621       return (insn->insn == breakpoint_insn->insn);
1622 #else
1623       pc_t code = reinterpret_cast<pc_t> (bytecode ());
1624       return (code[index] == breakpoint_insn);
1625 #endif
1626     }
1627
1628   return false;
1629 }
1630
1631 void *
1632 _Jv_JNIMethod::ncode (jclass klass)
1633 {
1634   using namespace java::lang::reflect;
1635
1636   if (self->ncode != 0)
1637     return self->ncode;
1638
1639   jboolean staticp = (self->accflags & Modifier::STATIC) != 0;
1640   int arg_count = _Jv_count_arguments (self->signature, staticp);
1641
1642   void *code;
1643   ncode_closure *closure =
1644     (ncode_closure*)ffi_closure_alloc (sizeof (ncode_closure)
1645                                        + arg_count * sizeof (ffi_type*),
1646                                        &code);
1647   closure->list.registerClosure (klass, closure);
1648
1649   ffi_type *rtype;
1650   _Jv_init_cif (self->signature,
1651                 arg_count,
1652                 staticp,
1653                 &closure->cif,
1654                 &closure->arg_types[0],
1655                 &rtype);
1656
1657   ffi_closure_fun fun;
1658
1659   args_raw_size = FFI_RAW_SIZE (&closure->cif);
1660
1661   // Initialize the argument types and CIF that represent the actual
1662   // underlying JNI function.
1663   int extra_args = 1;
1664   if ((self->accflags & Modifier::STATIC))
1665     ++extra_args;
1666   jni_arg_types = (ffi_type **) _Jv_AllocBytes ((extra_args + arg_count)
1667                                                 * sizeof (ffi_type *));
1668   int offset = 0;
1669   jni_arg_types[offset++] = &ffi_type_pointer;
1670   if ((self->accflags & Modifier::STATIC))
1671     jni_arg_types[offset++] = &ffi_type_pointer;
1672   memcpy (&jni_arg_types[offset], &closure->arg_types[0],
1673           arg_count * sizeof (ffi_type *));
1674
1675   if (ffi_prep_cif (&jni_cif, _Jv_platform_ffi_abi,
1676                     extra_args + arg_count, rtype,
1677                     jni_arg_types) != FFI_OK)
1678     throw_internal_error ("ffi_prep_cif failed for JNI function");
1679
1680   JvAssert ((self->accflags & Modifier::NATIVE) != 0);
1681
1682   // FIXME: for now we assume that all native methods for
1683   // interpreted code use JNI.
1684   fun = (ffi_closure_fun) &_Jv_JNIMethod::call;
1685
1686   FFI_PREP_RAW_CLOSURE (&closure->closure,
1687                         &closure->cif, 
1688                         fun,
1689                         (void*) this,
1690                         code);
1691
1692   self->ncode = code;
1693   return self->ncode;
1694 }
1695
1696 static void
1697 throw_class_format_error (jstring msg)
1698 {
1699   jthrowable t = (msg
1700          ? new java::lang::ClassFormatError (msg)
1701          : new java::lang::ClassFormatError);
1702   REPORT_EXCEPTION (t);
1703   throw t;
1704 }
1705
1706 static void
1707 throw_class_format_error (const char *msg)
1708 {
1709   throw_class_format_error (JvNewStringLatin1 (msg));
1710 }
1711
1712 /* This function finds the method and location where the exception EXC
1713    is caught in the stack frame. On return, it sets CATCH_METHOD and
1714    CATCH_LOCATION with the method and location where the catch will
1715    occur. If the exception is not caught, these are set to 0.
1716
1717    This function should only be used with the DEBUG interpreter. */
1718 static void
1719 find_catch_location (::java::lang::Throwable *exc, jthread thread,
1720                      jmethodID *catch_method, jlong *catch_loc)
1721 {
1722   *catch_method = 0;
1723   *catch_loc = 0;
1724
1725   _Jv_InterpFrame *frame
1726     = reinterpret_cast<_Jv_InterpFrame *> (thread->interp_frame);
1727   while (frame != NULL)
1728     {
1729       pc_t pc = frame->get_pc ();
1730       _Jv_InterpMethod *imeth
1731         = reinterpret_cast<_Jv_InterpMethod *> (frame->self);
1732       if (imeth->check_handler (&pc, imeth, exc))
1733         {
1734           // This method handles the exception.
1735           *catch_method = imeth->get_method ();
1736           *catch_loc = imeth->insn_index (pc);
1737           return;
1738         }
1739
1740       frame = frame->next_interp;
1741     }
1742 }
1743
1744 /* This method handles JVMTI notifications of thrown exceptions. It
1745    calls find_catch_location to figure out where the exception is
1746    caught (if it is caught).
1747    
1748    Like find_catch_location, this should only be called with the
1749    DEBUG interpreter. Since a few exceptions occur outside the
1750    interpreter proper, it is important to not call this function
1751    without checking JVMTI_REQUESTED_EVENT(Exception) first. */
1752 void
1753 _Jv_ReportJVMTIExceptionThrow (jthrowable ex)
1754 {
1755   jthread thread = ::java::lang::Thread::currentThread ();
1756   _Jv_Frame *frame = reinterpret_cast<_Jv_Frame *> (thread->frame);
1757   jmethodID throw_meth = frame->self->get_method ();
1758   jlocation throw_loc = -1;
1759   if (frame->frame_type == frame_interpreter)
1760     {
1761       _Jv_InterpFrame * iframe
1762         = reinterpret_cast<_Jv_InterpFrame *> (frame);
1763       _Jv_InterpMethod *imeth
1764         = reinterpret_cast<_Jv_InterpMethod *> (frame->self);
1765       throw_loc = imeth->insn_index (iframe->get_pc ());
1766     }
1767
1768   jlong catch_loc;
1769   jmethodID catch_method;
1770   find_catch_location (ex, thread, &catch_method, &catch_loc);
1771   _Jv_JVMTI_PostEvent (JVMTI_EVENT_EXCEPTION, thread,
1772                        _Jv_GetCurrentJNIEnv (), throw_meth, throw_loc,
1773                        ex, catch_method, catch_loc);
1774 }
1775
1776 \f
1777
1778 void
1779 _Jv_InterpreterEngine::do_verify (jclass klass)
1780 {
1781   _Jv_InterpClass *iclass = (_Jv_InterpClass *) klass->aux_info;
1782   for (int i = 0; i < klass->method_count; i++)
1783     {
1784       using namespace java::lang::reflect;
1785       _Jv_MethodBase *imeth = iclass->interpreted_methods[i];
1786       _Jv_ushort accflags = klass->methods[i].accflags;
1787       if ((accflags & (Modifier::NATIVE | Modifier::ABSTRACT)) == 0)
1788         {
1789           _Jv_InterpMethod *im = reinterpret_cast<_Jv_InterpMethod *> (imeth);
1790           _Jv_VerifyMethod (im);
1791         }
1792     }
1793 }
1794
1795 void
1796 _Jv_InterpreterEngine::do_create_ncode (jclass klass)
1797 {
1798   _Jv_InterpClass *iclass = (_Jv_InterpClass *) klass->aux_info;
1799   for (int i = 0; i < klass->method_count; i++)
1800     {
1801       // Just skip abstract methods.  This is particularly important
1802       // because we don't resize the interpreted_methods array when
1803       // miranda methods are added to it.
1804       if ((klass->methods[i].accflags
1805            & java::lang::reflect::Modifier::ABSTRACT)
1806           != 0)
1807         continue;
1808
1809       _Jv_MethodBase *imeth = iclass->interpreted_methods[i];
1810
1811       if ((klass->methods[i].accflags & java::lang::reflect::Modifier::NATIVE)
1812           != 0)
1813         {
1814           // You might think we could use a virtual `ncode' method in
1815           // the _Jv_MethodBase and unify the native and non-native
1816           // cases.  Well, we can't, because we don't allocate these
1817           // objects using `new', and thus they don't get a vtable.
1818           _Jv_JNIMethod *jnim = reinterpret_cast<_Jv_JNIMethod *> (imeth);
1819           klass->methods[i].ncode = jnim->ncode (klass);
1820         }
1821       else if (imeth != 0)              // it could be abstract
1822         {
1823           _Jv_InterpMethod *im = reinterpret_cast<_Jv_InterpMethod *> (imeth);
1824           klass->methods[i].ncode = im->ncode (klass);
1825         }
1826     }
1827 }
1828
1829 _Jv_ClosureList **
1830 _Jv_InterpreterEngine::do_get_closure_list (jclass klass)
1831 {
1832   _Jv_InterpClass *iclass = (_Jv_InterpClass *) klass->aux_info;
1833
1834   if (!iclass->closures)
1835     iclass->closures = _Jv_ClosureListFinalizer ();
1836
1837   return iclass->closures;
1838 }
1839
1840 void
1841 _Jv_InterpreterEngine::do_allocate_static_fields (jclass klass,
1842                                                   int pointer_size,
1843                                                   int other_size)
1844 {
1845   _Jv_InterpClass *iclass = (_Jv_InterpClass *) klass->aux_info;
1846
1847   // Splitting the allocations here lets us scan reference fields and
1848   // avoid scanning non-reference fields.  How reference fields are
1849   // scanned is a bit tricky: we allocate using _Jv_AllocRawObj, which
1850   // means that this memory will be scanned conservatively (same
1851   // difference, since we know all the contents here are pointers).
1852   // Then we put pointers into this memory into the 'fields'
1853   // structure.  Most of these are interior pointers, which is ok (but
1854   // even so the pointer to the first reference field will be used and
1855   // that is not an interior pointer).  The 'fields' array is also
1856   // allocated with _Jv_AllocRawObj (see defineclass.cc), so it will
1857   // be scanned.  A pointer to this array is held by Class and thus
1858   // seen by the collector.
1859   char *reference_fields = (char *) _Jv_AllocRawObj (pointer_size);
1860   char *non_reference_fields = (char *) _Jv_AllocBytes (other_size);
1861
1862   for (int i = 0; i < klass->field_count; i++)
1863     {
1864       _Jv_Field *field = &klass->fields[i];
1865
1866       if ((field->flags & java::lang::reflect::Modifier::STATIC) == 0)
1867         continue;
1868
1869       char *base = field->isRef() ? reference_fields : non_reference_fields;
1870       field->u.addr  = base + field->u.boffset;
1871
1872       if (iclass->field_initializers[i] != 0)
1873         {
1874           _Jv_Linker::resolve_field (field, klass->loader);
1875           _Jv_InitField (0, klass, i);
1876         }
1877     }
1878
1879   // Now we don't need the field_initializers anymore, so let the
1880   // collector get rid of it.
1881   iclass->field_initializers = 0;
1882 }
1883
1884 _Jv_ResolvedMethod *
1885 _Jv_InterpreterEngine::do_resolve_method (_Jv_Method *method, jclass klass,
1886                                           jboolean staticp)
1887 {
1888   int arg_count = _Jv_count_arguments (method->signature, staticp);
1889
1890   _Jv_ResolvedMethod* result = (_Jv_ResolvedMethod*)
1891     _Jv_AllocBytes (sizeof (_Jv_ResolvedMethod)
1892                     + arg_count*sizeof (ffi_type*));
1893
1894   result->stack_item_count
1895     = _Jv_init_cif (method->signature,
1896                     arg_count,
1897                     staticp,
1898                     &result->cif,
1899                     &result->arg_types[0],
1900                     NULL);
1901
1902   result->method              = method;
1903   result->klass               = klass;
1904
1905   return result;
1906 }
1907
1908 void
1909 _Jv_InterpreterEngine::do_post_miranda_hook (jclass klass)
1910 {
1911   _Jv_InterpClass *iclass = (_Jv_InterpClass *) klass->aux_info;
1912   for (int i = 0; i < klass->method_count; i++)
1913     {
1914       // Just skip abstract methods.  This is particularly important
1915       // because we don't resize the interpreted_methods array when
1916       // miranda methods are added to it.
1917       if ((klass->methods[i].accflags
1918            & java::lang::reflect::Modifier::ABSTRACT)
1919           != 0)
1920         continue;
1921       // Miranda method additions mean that the `methods' array moves.
1922       // We cache a pointer into this array, so we have to update.
1923       iclass->interpreted_methods[i]->self = &klass->methods[i];
1924     }
1925 }
1926
1927 #ifdef DIRECT_THREADED
1928 void
1929 _Jv_CompileMethod (_Jv_InterpMethod* method)
1930 {
1931   if (method->prepared == NULL)
1932     {
1933       if (JVMTI::enabled)
1934         _Jv_InterpMethod::run_debug (NULL, NULL, method);
1935       else
1936       _Jv_InterpMethod::run (NULL, NULL, method);
1937     }
1938 }
1939 #endif // DIRECT_THREADED