* src/vm/jit/verify/typecheck.c (verify_basic_block): Use generated
[cacao.git] / src / vm / vm.c
1 /* src/vm/vm.c - VM startup and shutdown functions
2
3    Copyright (C) 1996-2005, 2006 R. Grafl, A. Krall, C. Kruegel,
4    C. Oates, R. Obermaisser, M. Platter, M. Probst, S. Ring,
5    E. Steiner, C. Thalinger, D. Thuernbeck, P. Tomsich, C. Ullrich,
6    J. Wenninger, Institut f. Computersprachen - TU Wien
7
8    This file is part of CACAO.
9
10    This program is free software; you can redistribute it and/or
11    modify it under the terms of the GNU General Public License as
12    published by the Free Software Foundation; either version 2, or (at
13    your option) any later version.
14
15    This program is distributed in the hope that it will be useful, but
16    WITHOUT ANY WARRANTY; without even the implied warranty of
17    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
18    General Public License for more details.
19
20    You should have received a copy of the GNU General Public License
21    along with this program; if not, write to the Free Software
22    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
23    02110-1301, USA.
24
25    Contact: cacao@cacaojvm.org
26
27    Authors: Christian Thalinger
28
29    Changes: Martin Platter
30
31    $Id: vm.c 4357 2006-01-22 23:33:38Z twisti $
32
33 */
34
35
36 #include "config.h"
37
38 #include <assert.h>
39 #include <errno.h>
40 #include <stdlib.h>
41
42 #if defined(WITH_JRE_LAYOUT)
43 # include <libgen.h>
44 # include <unistd.h>
45 #endif
46
47 #include "vm/types.h"
48
49 #include "mm/boehm.h"
50 #include "mm/memory.h"
51 #include "native/jni.h"
52 #include "native/native.h"
53
54 #if defined(ENABLE_THREADS)
55 # include "threads/native/threads.h"
56 #endif
57
58 #include "vm/classcache.h"
59 #include "vm/exceptions.h"
60 #include "vm/finalizer.h"
61 #include "vm/global.h"
62 #include "vm/initialize.h"
63 #include "vm/options.h"
64 #include "vm/properties.h"
65 #include "vm/signallocal.h"
66 #include "vm/stringlocal.h"
67 #include "vm/suck.h"
68 #include "vm/vm.h"
69 #include "vm/jit/jit.h"
70 #include "vm/jit/asmpart.h"
71
72 #include "vm/jit/recompile.h"
73
74 #include "vm/jit/profile/profile.h"
75 #include "vm/rt-timing.h"
76
77 #if defined(ENABLE_JVMTI)
78 #include "native/jvmti/cacaodbg.h"
79 #endif
80
81
82 /* Invocation API variables ***************************************************/
83
84 _Jv_JavaVM *_Jv_jvm;                    /* denotes a Java VM                  */
85 _Jv_JNIEnv *_Jv_env;                    /* pointer to native method interface */
86
87
88 /* global variables ***********************************************************/
89
90 s4 vms = 0;                             /* number of VMs created              */
91
92 bool vm_initializing = false;
93 bool vm_exiting = false;
94
95 char      *cacao_prefix = NULL;
96 char      *cacao_libjvm = NULL;
97 char      *classpath_libdir = NULL;
98
99 char      *mainstring = NULL;
100 classinfo *mainclass = NULL;
101
102 char *specificmethodname = NULL;
103 char *specificsignature = NULL;
104
105 bool startit = true;
106
107 #if defined(ENABLE_INTRP)
108 u1 *intrp_main_stack = NULL;
109 #endif
110
111
112 /* define heap sizes **********************************************************/
113
114 #define HEAP_MAXSIZE      128 * 1024 * 1024 /* default 128MB                  */
115 #define HEAP_STARTSIZE      2 * 1024 * 1024 /* default 2MB                    */
116 #define STACK_SIZE                64 * 1024 /* default 64kB                   */
117
118
119 /* define command line options ************************************************/
120
121 enum {
122         OPT_FOO,
123
124         /* Java options */
125
126         OPT_JAR,
127
128         OPT_D32,
129         OPT_D64,
130
131         OPT_CLASSPATH,
132         OPT_D,
133
134         OPT_VERBOSE,
135
136         OPT_VERSION,
137         OPT_SHOWVERSION,
138         OPT_FULLVERSION,
139
140         OPT_HELP,
141         OPT_X,
142
143         OPT_ESA,
144         OPT_DSA,
145
146         /* Java non-standard options */
147
148         OPT_JIT,
149         OPT_INTRP,
150
151         OPT_BOOTCLASSPATH,
152         OPT_BOOTCLASSPATH_A,
153         OPT_BOOTCLASSPATH_P,
154
155         OPT_GLIBJ,
156
157         OPT_PROF,
158         OPT_PROF_OPTION,
159
160         OPT_MS,
161         OPT_MX,
162
163         /* CACAO options */
164
165         OPT_VERBOSE1,
166         OPT_NOIEEE,
167         OPT_SOFTNULL,
168
169 #if defined(ENABLE_STATISTICS)
170         OPT_TIME,
171         OPT_STAT,
172 #endif
173
174         OPT_LOG,
175         OPT_CHECK,
176         OPT_LOAD,
177         OPT_SHOW,
178         OPT_DEBUGCOLOR,
179
180 #if !defined(NDEBUG)
181         OPT_ALL,
182         OPT_METHOD,
183         OPT_SIGNATURE,
184 #endif
185
186 #if defined(ENABLE_VERIFIER)
187         OPT_NOVERIFY,
188 #if defined(TYPECHECK_VERBOSE)
189         OPT_VERBOSETC,
190 #endif
191 #endif /* defined(ENABLE_VERIFIER) */
192         OPT_EAGER,
193
194         /* optimization options */
195
196 #if defined(ENABLE_LOOP)
197         OPT_OLOOP,
198 #endif
199         
200 #if defined(ENABLE_IFCONV)
201         OPT_IFCONV,
202 #endif
203
204 #if defined(ENABLE_LSRA) || defined(ENABLE_SSA)
205         OPT_LSRA,
206 #endif
207
208 #if defined(ENABLE_INLINING)
209         OPT_INLINING,
210 #endif
211
212 #if defined(ENABLE_INTRP)
213         /* interpreter options */
214
215         OPT_NO_DYNAMIC,
216         OPT_NO_REPLICATION,
217         OPT_NO_QUICKSUPER,
218         OPT_STATIC_SUPERS,
219         OPT_TRACE,
220 #endif
221
222         OPT_SS,
223
224 #ifdef ENABLE_JVMTI
225         OPT_DEBUG,
226         OPT_XRUNJDWP,
227         OPT_NOAGENT,
228         OPT_AGENTLIB,
229         OPT_AGENTPATH,
230 #endif
231
232         DUMMY
233 };
234
235
236 opt_struct opts[] = {
237         { "foo",               false, OPT_FOO },
238
239         /* Java options */
240
241         { "jar",               false, OPT_JAR },
242
243         { "d32",               false, OPT_D32 },
244         { "d64",               false, OPT_D64 },
245         { "client",            false, OPT_IGNORE },
246         { "server",            false, OPT_IGNORE },
247         { "jvm",               false, OPT_IGNORE },
248         { "hotspot",           false, OPT_IGNORE },
249
250         { "classpath",         true,  OPT_CLASSPATH },
251         { "cp",                true,  OPT_CLASSPATH },
252         { "D",                 true,  OPT_D },
253         { "version",           false, OPT_VERSION },
254         { "showversion",       false, OPT_SHOWVERSION },
255         { "fullversion",       false, OPT_FULLVERSION },
256         { "help",              false, OPT_HELP },
257         { "?",                 false, OPT_HELP },
258         { "X",                 false, OPT_X },
259
260         { "esa",                     false, OPT_ESA },
261         { "enablesystemassertions",  false, OPT_ESA },
262         { "dsa",                     false, OPT_DSA },
263         { "disablesystemassertions", false, OPT_DSA },
264
265         { "noasyncgc",         false, OPT_IGNORE },
266 #if defined(ENABLE_VERIFIER)
267         { "noverify",          false, OPT_NOVERIFY },
268 #endif
269         { "v",                 false, OPT_VERBOSE1 },
270         { "verbose:",          true,  OPT_VERBOSE },
271
272 #if defined(ENABLE_VERIFIER) && defined(TYPECHECK_VERBOSE)
273         { "verbosetc",         false, OPT_VERBOSETC },
274 #endif
275 #if defined(__ALPHA__)
276         { "noieee",            false, OPT_NOIEEE },
277 #endif
278         { "softnull",          false, OPT_SOFTNULL },
279 #if defined(ENABLE_STATISTICS)
280         { "time",              false, OPT_TIME },
281         { "stat",              false, OPT_STAT },
282 #endif
283         { "log",               true,  OPT_LOG },
284         { "c",                 true,  OPT_CHECK },
285         { "l",                 false, OPT_LOAD },
286         { "eager",             false, OPT_EAGER },
287
288 #if !defined(NDEBUG)
289         { "all",               false, OPT_ALL },
290         { "sig",               true,  OPT_SIGNATURE },
291 #endif
292
293 #if defined(ENABLE_LOOP)
294         { "oloop",             false, OPT_OLOOP },
295 #endif
296 #if defined(ENABLE_IFCONV)
297         { "ifconv",            false, OPT_IFCONV },
298 #endif
299 #if defined(ENABLE_LSRA) || defined(ENABLE_SSA)
300         { "lsra",              false, OPT_LSRA },
301 #endif
302
303 #if defined(ENABLE_INTRP)
304         /* interpreter options */
305
306         { "trace",             false, OPT_TRACE },
307         { "static-supers",     true,  OPT_STATIC_SUPERS },
308         { "no-dynamic",        false, OPT_NO_DYNAMIC },
309         { "no-replication",    false, OPT_NO_REPLICATION },
310         { "no-quicksuper",     false, OPT_NO_QUICKSUPER },
311 #endif
312
313         /* JVMTI Agent Command Line Options */
314 #ifdef ENABLE_JVMTI
315         { "agentlib:",         true,  OPT_AGENTLIB },
316         { "agentpath:",        true,  OPT_AGENTPATH },
317 #endif
318
319         /* Java non-standard options */
320
321         { "Xjit",              false, OPT_JIT },
322         { "Xint",              false, OPT_INTRP },
323         { "Xbootclasspath:",   true,  OPT_BOOTCLASSPATH },
324         { "Xbootclasspath/a:", true,  OPT_BOOTCLASSPATH_A },
325         { "Xbootclasspath/p:", true,  OPT_BOOTCLASSPATH_P },
326         { "Xglibj:",           true,  OPT_GLIBJ },
327
328 #ifdef ENABLE_JVMTI
329         { "Xdebug",            false, OPT_DEBUG },
330         { "Xnoagent",          false, OPT_NOAGENT },
331         { "Xrunjdwp",          true,  OPT_XRUNJDWP },
332 #endif 
333
334         { "Xms",               true,  OPT_MS },
335         { "ms",                true,  OPT_MS },
336         { "Xmx",               true,  OPT_MX },
337         { "mx",                true,  OPT_MX },
338         { "Xss",               true,  OPT_SS },
339         { "ss",                true,  OPT_SS },
340         { "Xprof:",            true,  OPT_PROF_OPTION },
341         { "Xprof",             false, OPT_PROF },
342
343         /* keep these at the end of the list */
344
345 #if defined(ENABLE_INLINING)
346         { "i",                 true,  OPT_INLINING },
347 #endif
348
349 #if !defined(NDEBUG)
350         { "m",                 true,  OPT_METHOD },
351 #endif
352
353         { "s",                 true,  OPT_SHOW },
354         { "debug-color",      false,  OPT_DEBUGCOLOR },
355
356         { NULL,                false, 0 }
357 };
358
359
360 /* usage ***********************************************************************
361
362    Prints the correct usage syntax to stdout.
363
364 *******************************************************************************/
365
366 void usage(void)
367 {
368         puts("Usage: cacao [-options] classname [arguments]");
369         puts("               (to run a class file)");
370         puts("   or  cacao [-options] -jar jarfile [arguments]");
371         puts("               (to run a standalone jar file)\n");
372
373         puts("Java options:");
374         puts("    -d32                     use 32-bit data model if available");
375         puts("    -d64                     use 64-bit data model if available");
376         puts("    -client                  compatibility (currently ignored)");
377         puts("    -server                  compatibility (currently ignored)");
378         puts("    -jvm                     compatibility (currently ignored)");
379         puts("    -hotspot                 compatibility (currently ignored)\n");
380
381         puts("    -cp <path>               specify a path to look for classes");
382         puts("    -classpath <path>        specify a path to look for classes");
383         puts("    -D<name>=<value>         add an entry to the property list");
384         puts("    -verbose[:class|gc|jni]  enable specific verbose output");
385         puts("    -version                 print product version and exit");
386         puts("    -fullversion             print jpackage-compatible product version and exit");
387         puts("    -showversion             print product version and continue");
388         puts("    -help, -?                print this help message");
389         puts("    -X                       print help on non-standard Java options");
390         puts("    -esa | -enablesystemassertions");
391         puts("                             enable system assertions");
392         puts("    -dsa | -disablesystemassertions");
393         puts("                             disable system assertions");
394         puts("");
395
396 #ifdef ENABLE_JVMTI
397         puts("    -agentlib:<agent-lib-name>=<options>  library to load containg JVMTI agent");
398         puts ("                                         for jdwp help use: -agentlib:jdwp=help");
399         puts("    -agentpath:<path-to-agent>=<options>  path to library containg JVMTI agent");
400 #endif
401
402         puts("CACAO options:");
403         puts("    -v                       write state-information");
404         puts("    -verbose[:call|exception|jit]");
405         puts("                             enable specific verbose output");
406         puts("    -debug-color             colored output for ANSI terms");
407 #ifdef TYPECHECK_VERBOSE
408         puts("    -verbosetc               write debug messages while typechecking");
409 #endif
410 #if defined(__ALPHA__)
411         puts("    -noieee                  don't use ieee compliant arithmetic");
412 #endif
413 #if defined(ENABLE_VERIFIER)
414         puts("    -noverify                don't verify classfiles");
415 #endif
416         puts("    -softnull                use software nullpointer check");
417 #if defined(ENABLE_STATISTICS)
418         puts("    -time                    measure the runtime");
419         puts("    -stat                    detailed compiler statistics");
420 #endif
421         puts("    -log logfile             specify a name for the logfile");
422         puts("    -c(heck)b(ounds)         don't check array bounds");
423         puts("            s(ync)           don't check for synchronization");
424 #if defined(ENABLE_LOOP)
425         puts("    -oloop                   optimize array accesses in loops");
426 #endif
427         puts("    -l                       don't start the class after loading");
428         puts("    -eager                   perform eager class loading and linking");
429 #if !defined(NDEBUG)
430         puts("    -all                     compile all methods, no execution");
431         puts("    -m                       compile only a specific method");
432         puts("    -sig                     specify signature for a specific method");
433 #endif
434
435         puts("    -s(how)...               show...");
436         puts("           c(onstants)       the constant pool");
437         puts("           m(ethods)         class fields and methods");
438         puts("           u(tf)             the utf - hash");
439         puts("           i(ntermediate)    intermediate representation");
440 #if defined(ENABLE_DISASSEMBLER)
441         puts("           a(ssembler)       disassembled listing");
442         puts("           e(xceptionstubs)  disassembled exception stubs (only with -sa)");
443         puts("           n(ative)          disassembled native stubs");
444 #endif
445         puts("           d(atasegment)     data segment listing");
446 #if defined(ENABLE_INLINING)
447         puts("    -i     n(line)           activate inlining");
448         puts("           v(irtual)         inline virtual methods (uses/turns rt option on)");
449         puts("           e(exception)      inline methods with exceptions");
450         puts("           p(aramopt)        optimize argument renaming");
451         puts("           o(utsiders)       inline methods of foreign classes");
452 #endif /* defined(ENABLE_INLINING) */
453 #if defined(ENABLE_IFCONV)
454         puts("    -ifconv                  use if-conversion");
455 #endif
456 #if defined(ENABLE_LSRA)
457         puts("    -lsra                    use linear scan register allocation");
458 #endif
459 #if defined(ENABLE_SSA)
460         puts("    -lsra                    use linear scan register allocation (with SSA)");
461 #endif
462
463         /* exit with error code */
464
465         exit(1);
466 }   
467
468
469 static void Xusage(void)
470 {
471 #if defined(ENABLE_JIT)
472         puts("    -Xjit                    JIT mode execution (default)");
473 #endif
474 #if defined(ENABLE_INTRP)
475         puts("    -Xint                    interpreter mode execution");
476 #endif
477         puts("    -Xbootclasspath:<zip/jar files and directories separated by :>");
478     puts("                             value is set as bootstrap class path");
479         puts("    -Xbootclasspath/a:<zip/jar files and directories separated by :>");
480         puts("                             value is appended to the bootstrap class path");
481         puts("    -Xbootclasspath/p:<zip/jar files and directories separated by :>");
482         puts("                             value is prepended to the bootstrap class path");
483         puts("    -Xglibj:<zip/jar files and directories separated by :>");
484         puts("                             value is used as Java core library, but the");
485         puts("                             hardcoded VM interface classes are prepended");
486         printf("    -Xms<size>               set the initial size of the heap (default: %dMB)\n", HEAP_STARTSIZE / 1024 / 1024);
487         printf("    -Xmx<size>               set the maximum size of the heap (default: %dMB)\n", HEAP_MAXSIZE / 1024 / 1024);
488         printf("    -Xss<size>               set the thread stack size (default: %dkB)\n", STACK_SIZE / 1024);
489         puts("    -Xprof[:bb]              collect and print profiling data");
490 #if defined(ENABLE_JVMTI)
491     /* -Xdebug option depend on gnu classpath JDWP options. options: 
492          transport=dt_socket,address=<hostname:port>,server=(y|n),suspend(y|n) */
493         puts("    -Xdebug                  enable remote debugging\n");
494         puts("    -Xrunjdwp transport=[dt_socket|...],address=<hostname:port>,server=[y|n],suspend=[y|n]\n");
495         puts("                             enable remote debugging\n");
496 #endif 
497
498         /* exit with error code */
499
500         exit(1);
501 }   
502
503
504 /* version *********************************************************************
505
506    Only prints cacao version information.
507
508 *******************************************************************************/
509
510 static void version(bool opt_exit)
511 {
512         puts("java version \""JAVA_VERSION"\"");
513         puts("CACAO version "VERSION"");
514
515         puts("Copyright (C) 1996-2005, 2006 R. Grafl, A. Krall, C. Kruegel,");
516         puts("C. Oates, R. Obermaisser, M. Platter, M. Probst, S. Ring,");
517         puts("E. Steiner, C. Thalinger, D. Thuernbeck, P. Tomsich, C. Ullrich,");
518         puts("J. Wenninger, Institut f. Computersprachen - TU Wien\n");
519
520         puts("This program is free software; you can redistribute it and/or");
521         puts("modify it under the terms of the GNU General Public License as");
522         puts("published by the Free Software Foundation; either version 2, or (at");
523         puts("your option) any later version.\n");
524
525         puts("This program is distributed in the hope that it will be useful, but");
526         puts("WITHOUT ANY WARRANTY; without even the implied warranty of");
527         puts("MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU");
528         puts("General Public License for more details.\n");
529
530         puts("Configure/Build options:\n");
531         puts("  ./configure: "VERSION_CONFIGURE_ARGS"");
532 #if defined(__VERSION__)
533         puts("  CC         : "VERSION_CC" ("__VERSION__")");
534 #else
535         puts("  CC         : "VERSION_CC"");
536 #endif
537         puts("  CFLAGS     : "VERSION_CFLAGS"\n");
538
539         puts("Default variables:\n");
540         printf("  maximum heap size              : %d\n", HEAP_MAXSIZE);
541         printf("  initial heap size              : %d\n", HEAP_STARTSIZE);
542         printf("  stack size                     : %d\n", STACK_SIZE);
543         puts("  java.boot.class.path           : "CACAO_VM_ZIP":"CLASSPATH_GLIBJ_ZIP"");
544         puts("  gnu.classpath.boot.library.path: "CLASSPATH_LIBDIR"/classpath\n");
545
546         puts("Runtime variables:\n");
547         printf("  maximum heap size              : %d\n", opt_heapmaxsize);
548         printf("  initial heap size              : %d\n", opt_heapstartsize);
549         printf("  stack size                     : %d\n", opt_stacksize);
550         printf("  java.boot.class.path           : %s\n", bootclasspath);
551         printf("  gnu.classpath.boot.library.path: %s\n", classpath_libdir);
552
553         /* exit normally, if requested */
554
555         if (opt_exit)
556                 exit(0);
557 }
558
559
560 /* fullversion *****************************************************************
561
562    Prints a Sun compatible version information (required e.g. by
563    jpackage, www.jpackage.org).
564
565 *******************************************************************************/
566
567 static void fullversion(void)
568 {
569         puts("java full version \"cacao-"JAVA_VERSION"\"");
570
571         /* exit normally */
572
573         exit(0);
574 }
575
576
577 /* forward declarations *******************************************************/
578
579 static char *vm_get_mainclass_from_jar(char *mainstring);
580 #if !defined(NDEBUG)
581 static void  vm_compile_all(void);
582 static void  vm_compile_method(void);
583 #endif
584
585
586 /* vm_create *******************************************************************
587
588    Creates a JVM.  Called by JNI_CreateJavaVM.
589
590 *******************************************************************************/
591
592 bool vm_create(JavaVMInitArgs *vm_args)
593 {
594         char *cp;
595         s4    len;
596         s4    opt;
597         s4    i, j, k;
598         bool  opt_version;
599         bool  opt_exit;
600
601 #if defined(ENABLE_JVMTI)
602         lt_dlhandle  handle;
603         char *libname, *agentarg;
604         bool jdwp,agentbypath;
605         jdwp = agentbypath = false;
606 #endif
607
608         /* check the JNI version requested */
609
610         switch (vm_args->version) {
611         case JNI_VERSION_1_1:
612                 break;
613         case JNI_VERSION_1_2:
614         case JNI_VERSION_1_4:
615                 break;
616         default:
617                 return false;
618         }
619
620         /* we only support 1 JVM instance */
621
622         if (vms > 0)
623                 return false;
624
625         if (atexit(vm_exit_handler))
626                 vm_abort("atexit failed: %s\n", strerror(errno));
627
628         if (opt_verbose)
629                 log_text("CACAO started -------------------------------------------------------");
630
631         /* set the VM starttime */
632
633         _Jv_jvm->starttime = builtin_currenttimemillis();
634
635         /* get stuff from the environment *****************************************/
636
637 #if defined(DISABLE_GC)
638         nogc_init(HEAP_MAXSIZE, HEAP_STARTSIZE);
639 #endif
640
641 #if defined(WITH_JRE_LAYOUT)
642         /* SUN also uses a buffer of 4096-bytes (strace is your friend). */
643
644         cacao_prefix = MNEW(char, 4096);
645
646         if (readlink("/proc/self/exe", cacao_prefix, 4095) == -1)
647                 vm_abort("readlink failed: %s\n", strerror(errno));
648
649         /* get the path of the current executable */
650
651         cacao_prefix = dirname(cacao_prefix);
652
653         if ((strlen(cacao_prefix) + strlen("/..") + strlen("0")) > 4096)
654                 vm_abort("libjvm name to long for buffer\n");
655
656         /* concatenate the library name */
657
658         strcat(cacao_prefix, "/..");
659
660         /* now set path to libjvm.so */
661
662         len = strlen(cacao_prefix) + strlen("/lib/libjvm") + strlen("0");
663
664         cacao_libjvm = MNEW(char, len);
665         strcpy(cacao_libjvm, cacao_prefix);
666         strcat(cacao_libjvm, "/lib/libjvm");
667
668         /* and finally set the path to GNU Classpath libraries */
669
670         len = strlen(cacao_prefix) + strlen("/lib/classpath") + strlen("0");
671
672         classpath_libdir = MNEW(char, len);
673         strcpy(classpath_libdir, cacao_prefix);
674         strcat(classpath_libdir, "/lib/classpath");
675 #else
676         cacao_prefix     = CACAO_PREFIX;
677         cacao_libjvm     = CACAO_LIBDIR"/libjvm";
678         classpath_libdir = CLASSPATH_LIBDIR"/classpath";
679 #endif
680
681         /* set the bootclasspath */
682
683         cp = getenv("BOOTCLASSPATH");
684
685         if (cp != NULL) {
686                 bootclasspath = MNEW(char, strlen(cp) + strlen("0"));
687                 strcpy(bootclasspath, cp);
688         }
689         else {
690 #if defined(WITH_JRE_LAYOUT)
691                 len =
692                         strlen(cacao_prefix) +
693                         strlen("/share/cacao/vm.zip") +
694                         strlen(":") +
695                         strlen(cacao_prefix) +
696                         strlen("/share/classpath/glibj.zip") +
697                         strlen("0");
698
699                 bootclasspath = MNEW(char, len);
700                 strcat(bootclasspath, cacao_prefix);
701                 strcat(bootclasspath, "/share/cacao/vm.zip");
702                 strcat(bootclasspath, ":");
703                 strcat(bootclasspath, cacao_prefix);
704                 strcat(bootclasspath, "/share/classpath/glibj.zip");
705 #else
706                 len = strlen(CACAO_VM_ZIP) +
707                         strlen(":") +
708                         strlen(CLASSPATH_GLIBJ_ZIP) +
709                         strlen("0");
710
711                 bootclasspath = MNEW(char, len);
712                 strcat(bootclasspath, CACAO_VM_ZIP);
713                 strcat(bootclasspath, ":");
714                 strcat(bootclasspath, CLASSPATH_GLIBJ_ZIP);
715 #endif
716         }
717
718         /* set the classpath */
719
720         cp = getenv("CLASSPATH");
721
722         if (cp != NULL) {
723                 classpath = MNEW(char, strlen(cp) + strlen("0"));
724                 strcat(classpath, cp);
725         }
726         else {
727                 classpath = MNEW(char, strlen(".") + strlen("0"));
728                 strcpy(classpath, ".");
729         }
730
731
732         /* interpret the options **************************************************/
733
734         opt_version       = false;
735         opt_exit          = false;
736
737         checknull         = false;
738         opt_noieee        = false;
739
740         opt_heapmaxsize   = HEAP_MAXSIZE;
741         opt_heapstartsize = HEAP_STARTSIZE;
742         opt_stacksize     = STACK_SIZE;
743
744
745 #if defined(ENABLE_JVMTI)
746         /* initialize JVMTI related  **********************************************/
747         jvmti = false;
748 #endif
749
750         /* initialize properties before commandline handling */
751
752         if (!properties_init())
753                 throw_cacao_exception_exit(string_java_lang_InternalError,
754                                                                    "Unable to init properties");
755
756         /* add some default properties */
757
758         properties_add("java.endorsed.dirs", ""CACAO_PREFIX"/jre/lib/endorsed");
759
760         /* iterate over all passed options */
761
762         while ((opt = options_get(opts, vm_args)) != OPT_DONE) {
763                 switch (opt) {
764                 case OPT_FOO:
765                         opt_foo = true;
766                         break;
767
768                 case OPT_IGNORE:
769                         break;
770                         
771                 case OPT_JAR:
772                         opt_jar = true;
773                         break;
774
775                 case OPT_D32:
776 #if SIZEOF_VOID_P == 8
777                         puts("Running a 32-bit JVM is not supported on this platform.");
778                         exit(1);
779 #endif
780                         break;
781
782                 case OPT_D64:
783 #if SIZEOF_VOID_P == 4
784                         puts("Running a 64-bit JVM is not supported on this platform.");
785                         exit(1);
786 #endif
787                         break;
788
789                 case OPT_CLASSPATH:
790                         /* forget old classpath and set the argument as new classpath */
791                         MFREE(classpath, char, strlen(classpath));
792
793                         classpath = MNEW(char, strlen(opt_arg) + strlen("0"));
794                         strcpy(classpath, opt_arg);
795                         break;
796
797                 case OPT_D:
798                         for (j = 0; j < strlen(opt_arg); j++) {
799                                 if (opt_arg[j] == '=') {
800                                         opt_arg[j] = '\0';
801                                         properties_add(opt_arg, opt_arg + j + 1);
802                                         goto opt_d_done;
803                                 }
804                         }
805
806                         /* if no '=' is given, just create an empty property */
807
808                         properties_add(opt_arg, "");
809
810                 opt_d_done:
811                         break;
812
813                 case OPT_BOOTCLASSPATH:
814                         /* Forget default bootclasspath and set the argument as
815                            new boot classpath. */
816
817                         MFREE(bootclasspath, char, strlen(bootclasspath));
818
819                         bootclasspath = MNEW(char, strlen(opt_arg) + strlen("0"));
820                         strcpy(bootclasspath, opt_arg);
821                         break;
822
823                 case OPT_BOOTCLASSPATH_A:
824                         /* append to end of bootclasspath */
825
826                         len = strlen(bootclasspath);
827
828                         bootclasspath = MREALLOC(bootclasspath,
829                                                                          char,
830                                                                          len,
831                                                                          len + strlen(":") +
832                                                                          strlen(opt_arg) + strlen("0"));
833
834                         strcat(bootclasspath, ":");
835                         strcat(bootclasspath, opt_arg);
836                         break;
837
838                 case OPT_BOOTCLASSPATH_P:
839                         /* prepend in front of bootclasspath */
840
841                         cp = bootclasspath;
842                         len = strlen(cp);
843
844                         bootclasspath = MNEW(char, strlen(opt_arg) + strlen(":") +
845                                                                  len + strlen("0"));
846
847                         strcpy(bootclasspath, opt_arg);
848                         strcat(bootclasspath, ":");
849                         strcat(bootclasspath, cp);
850
851                         MFREE(cp, char, len);
852                         break;
853
854                 case OPT_GLIBJ:
855                         /* use as Java core library, but prepend VM interface classes */
856
857                         MFREE(bootclasspath, char, strlen(bootclasspath));
858
859                         len = strlen(CACAO_VM_ZIP) +
860                                 strlen(":") +
861                                 strlen(opt_arg) +
862                                 strlen("0");
863
864                         bootclasspath = MNEW(char, len);
865
866                         strcpy(bootclasspath, CACAO_VM_ZIP);
867                         strcat(bootclasspath, ":");
868                         strcat(bootclasspath, opt_arg);
869                         break;
870
871 #if defined(ENABLE_JVMTI)
872                 case OPT_DEBUG:
873                         /* this option exists only for compatibility reasons */
874                         break;
875
876                 case OPT_NOAGENT:
877                         /* I don't know yet what Xnoagent should do. This is only for 
878                            compatiblity with eclipse - motse */
879                         break;
880
881                 case OPT_XRUNJDWP:
882                         agentbypath = true;
883                         jvmti       = true;
884                         jdwp        = true;
885
886                         len =
887                                 strlen(CACAO_LIBDIR) +
888                                 strlen("/libjdwp.so=") +
889                                 strlen(opt_arg) +
890                                 strlen("0");
891
892                         agentarg = MNEW(char, len);
893
894                         strcpy(agentarg, CACAO_LIBDIR);
895                         strcat(agentarg, "/libjdwp.so=");
896                         strcat(agentarg, &opt_arg[1]);
897                         break;
898
899                 case OPT_AGENTPATH:
900                         agentbypath = true;
901
902                 case OPT_AGENTLIB:
903                         jvmti = true;
904                         agentarg = opt_arg;
905                         break;
906 #endif
907                         
908                 case OPT_MX:
909                 case OPT_MS:
910                 case OPT_SS:
911                         {
912                                 char c;
913                                 c = opt_arg[strlen(opt_arg) - 1];
914
915                                 if ((c == 'k') || (c == 'K')) {
916                                         j = atoi(opt_arg) * 1024;
917
918                                 } else if ((c == 'm') || (c == 'M')) {
919                                         j = atoi(opt_arg) * 1024 * 1024;
920
921                                 } else
922                                         j = atoi(opt_arg);
923
924                                 if (opt == OPT_MX)
925                                         opt_heapmaxsize = j;
926                                 else if (opt == OPT_MS)
927                                         opt_heapstartsize = j;
928                                 else
929                                         opt_stacksize = j;
930                         }
931                         break;
932
933                 case OPT_VERBOSE1:
934                         opt_verbose = true;
935                         break;
936
937                 case OPT_VERBOSE:
938                         if (strcmp("class", opt_arg) == 0)
939                                 opt_verboseclass = true;
940
941                         else if (strcmp("gc", opt_arg) == 0)
942                                 opt_verbosegc = true;
943
944                         else if (strcmp("jni", opt_arg) == 0)
945                                 opt_verbosejni = true;
946
947                         else if (strcmp("call", opt_arg) == 0)
948                                 opt_verbosecall = true;
949
950                         else if (strcmp("jit", opt_arg) == 0) {
951                                 opt_verbose = true;
952                                 loadverbose = true;
953                                 linkverbose = true;
954                                 initverbose = true;
955                                 compileverbose = true;
956                         }
957                         else if (strcmp("exception", opt_arg) == 0)
958                                 opt_verboseexception = true;
959                         break;
960                 case OPT_DEBUGCOLOR:
961                         opt_debugcolor = true;
962                         break;
963
964 #if defined(ENABLE_VERIFIER) && defined(TYPECHECK_VERBOSE)
965                 case OPT_VERBOSETC:
966                         opt_typecheckverbose = true;
967                         break;
968 #endif
969                                 
970                 case OPT_VERSION:
971                         opt_version = true;
972                         opt_exit    = true;
973                         break;
974
975                 case OPT_FULLVERSION:
976                         fullversion();
977                         break;
978
979                 case OPT_SHOWVERSION:
980                         opt_version = true;
981                         break;
982
983                 case OPT_NOIEEE:
984                         opt_noieee = true;
985                         break;
986
987 #if defined(ENABLE_VERIFIER)
988                 case OPT_NOVERIFY:
989                         opt_verify = false;
990                         break;
991 #endif
992
993                 case OPT_SOFTNULL:
994                         checknull = true;
995                         break;
996
997 #if defined(ENABLE_STATISTICS)
998                 case OPT_TIME:
999                         opt_getcompilingtime = true;
1000                         opt_getloadingtime = true;
1001                         break;
1002                                         
1003                 case OPT_STAT:
1004                         opt_stat = true;
1005                         break;
1006 #endif
1007                                         
1008                 case OPT_LOG:
1009                         log_init(opt_arg);
1010                         break;
1011                         
1012                 case OPT_CHECK:
1013                         for (j = 0; j < strlen(opt_arg); j++) {
1014                                 switch (opt_arg[j]) {
1015                                 case 'b':
1016                                         checkbounds = false;
1017                                         break;
1018                                 case 's':
1019                                         checksync = false;
1020                                         break;
1021                                 default:
1022                                         usage();
1023                                 }
1024                         }
1025                         break;
1026                         
1027                 case OPT_LOAD:
1028                         opt_run = false;
1029                         makeinitializations = false;
1030                         break;
1031
1032                 case OPT_EAGER:
1033                         opt_eager = true;
1034                         break;
1035
1036 #if !defined(NDEBUG)
1037                 case OPT_ALL:
1038                         compileall = true;
1039                         opt_run = false;
1040                         makeinitializations = false;
1041                         break;
1042
1043                 case OPT_METHOD:
1044                         opt_run = false;
1045                         opt_method = opt_arg;
1046                         makeinitializations = false;
1047                         break;
1048
1049                 case OPT_SIGNATURE:
1050                         opt_signature = opt_arg;
1051                         break;
1052 #endif
1053
1054                 case OPT_SHOW:       /* Display options */
1055                         for (j = 0; j < strlen(opt_arg); j++) {         
1056                                 switch (opt_arg[j]) {
1057                                 case 'c':
1058                                         showconstantpool = true;
1059                                         break;
1060
1061                                 case 'u':
1062                                         showutf = true;
1063                                         break;
1064
1065                                 case 'm':
1066                                         showmethods = true;
1067                                         break;
1068
1069                                 case 'i':
1070                                         opt_showintermediate = true;
1071                                         compileverbose = true;
1072                                         break;
1073
1074 #if defined(ENABLE_DISASSEMBLER)
1075                                 case 'a':
1076                                         opt_showdisassemble = true;
1077                                         compileverbose = true;
1078                                         break;
1079
1080                                 case 'e':
1081                                         opt_showexceptionstubs = true;
1082                                         break;
1083
1084                                 case 'n':
1085                                         opt_shownativestub = true;
1086                                         break;
1087 #endif
1088
1089                                 case 'd':
1090                                         opt_showddatasegment = true;
1091                                         break;
1092
1093                                 default:
1094                                         usage();
1095                                 }
1096                         }
1097                         break;
1098                         
1099 #if defined(ENABLE_LOOP)
1100                 case OPT_OLOOP:
1101                         opt_loops = true;
1102                         break;
1103 #endif
1104
1105 #if defined(ENABLE_INLINING)
1106                 case OPT_INLINING:
1107                         for (j = 0; j < strlen(opt_arg); j++) {         
1108                                 switch (opt_arg[j]) {
1109                                 case 'n':
1110                                         /* define in options.h; Used in main.c, jit.c
1111                                            & inline.c inlining is currently
1112                                            deactivated */
1113                                         break;
1114                                 case 'v':
1115                                         inlinevirtuals = true;
1116                                         break;
1117                                 case 'e':
1118                                         inlineexceptions = true;
1119                                         break;
1120                                 case 'p':
1121                                         inlineparamopt = true;
1122                                         break;
1123                                 case 'o':
1124                                         inlineoutsiders = true;
1125                                         break;
1126                                 default:
1127                                         usage();
1128                                 }
1129                         }
1130                         break;
1131 #endif /* defined(ENABLE_INLINING) */
1132
1133 #if defined(ENABLE_IFCONV)
1134                 case OPT_IFCONV:
1135                         opt_ifconv = true;
1136                         break;
1137 #endif
1138
1139 #if defined(ENABLE_LSRA) || defined(ENABLE_SSA)
1140                 case OPT_LSRA:
1141                         opt_lsra = true;
1142                         break;
1143 #endif
1144
1145                 case OPT_HELP:
1146                         usage();
1147                         break;
1148
1149                 case OPT_X:
1150                         Xusage();
1151                         break;
1152
1153                 case OPT_ESA:
1154                         _Jv_jvm->Java_java_lang_VMClassLoader_defaultAssertionStatus = true;
1155                         break;
1156
1157                 case OPT_DSA:
1158                         _Jv_jvm->Java_java_lang_VMClassLoader_defaultAssertionStatus = false;
1159                         break;
1160
1161                 case OPT_PROF_OPTION:
1162                         /* use <= to get the last \0 too */
1163
1164                         for (j = 0, k = 0; j <= strlen(opt_arg); j++) {
1165                                 if (opt_arg[j] == ',')
1166                                         opt_arg[j] = '\0';
1167
1168                                 if (opt_arg[j] == '\0') {
1169                                         if (strcmp("bb", opt_arg + k) == 0)
1170                                                 opt_prof_bb = true;
1171
1172                                         else {
1173                                                 printf("Unknown option: -Xprof:%s\n", opt_arg + k);
1174                                                 usage();
1175                                         }
1176
1177                                         /* set k to next char */
1178
1179                                         k = j + 1;
1180                                 }
1181                         }
1182                         /* fall through */
1183
1184                 case OPT_PROF:
1185                         opt_prof = true;
1186                         break;
1187
1188                 case OPT_JIT:
1189 #if defined(ENABLE_JIT)
1190                         opt_jit = true;
1191 #else
1192                         printf("-Xjit option not enabled.\n");
1193                         exit(1);
1194 #endif
1195                         break;
1196
1197                 case OPT_INTRP:
1198 #if defined(ENABLE_INTRP)
1199                         opt_intrp = true;
1200 #else
1201                         printf("-Xint option not enabled.\n");
1202                         exit(1);
1203 #endif
1204                         break;
1205
1206 #if defined(ENABLE_INTRP)
1207                 case OPT_STATIC_SUPERS:
1208                         opt_static_supers = atoi(opt_arg);
1209                         break;
1210
1211                 case OPT_NO_DYNAMIC:
1212                         opt_no_dynamic = true;
1213                         break;
1214
1215                 case OPT_NO_REPLICATION:
1216                         opt_no_replication = true;
1217                         break;
1218
1219                 case OPT_NO_QUICKSUPER:
1220                         opt_no_quicksuper = true;
1221                         break;
1222
1223                 case OPT_TRACE:
1224                         vm_debug = true;
1225                         break;
1226 #endif
1227
1228                 default:
1229                         printf("Unknown option: %s\n",
1230                                    vm_args->options[opt_index].optionString);
1231                         usage();
1232                 }
1233         }
1234
1235
1236         /* Now we have all options handled and we can print the version
1237            information. */
1238
1239         if (opt_version)
1240                 version(opt_exit);
1241
1242
1243         /* get the main class *****************************************************/
1244
1245         if (opt_index < vm_args->nOptions) {
1246                 mainstring = vm_args->options[opt_index++].optionString;
1247
1248                 /* Put the jar file into the classpath (if any). */
1249
1250                 if (opt_jar == true) {
1251                         /* free old classpath */
1252
1253                         MFREE(classpath, char, strlen(classpath));
1254
1255                         /* put jarfile into classpath */
1256
1257                         classpath = MNEW(char, strlen(mainstring) + strlen("0"));
1258
1259                         strcpy(classpath, mainstring);
1260                 }
1261                 else {
1262                         /* replace .'s with /'s in classname */
1263
1264                         for (i = strlen(mainstring) - 1; i >= 0; i--)
1265                                 if (mainstring[i] == '.')
1266                                         mainstring[i] = '/';
1267                 }
1268         }
1269
1270 #if defined(ENABLE_JVMTI)
1271         if (jvmti) {
1272                 jvmti_set_phase(JVMTI_PHASE_ONLOAD);
1273                 jvmti_agentload(agentarg, agentbypath, &handle, &libname);
1274
1275                 if (jdwp)
1276                         MFREE(agentarg, char, strlen(agentarg));
1277
1278                 jvmti_set_phase(JVMTI_PHASE_PRIMORDIAL);
1279         }
1280
1281 #endif
1282
1283
1284         /* initialize this JVM ****************************************************/
1285
1286         vm_initializing = true;
1287
1288         /* initialize the garbage collector */
1289
1290         gc_init(opt_heapmaxsize, opt_heapstartsize);
1291
1292 #if defined(ENABLE_INTRP)
1293         /* Allocate main thread stack on the Java heap. */
1294
1295         if (opt_intrp) {
1296                 intrp_main_stack = GCMNEW(u1, opt_stacksize);
1297                 MSET(intrp_main_stack, 0, u1, opt_stacksize);
1298         }
1299 #endif
1300
1301 #if defined(ENABLE_THREADS)
1302         threads_preinit();
1303 #endif
1304
1305         /* initialize the string hashtable stuff: lock (must be done
1306            _after_ threads_preinit) */
1307
1308         if (!string_init())
1309                 throw_main_exception_exit();
1310
1311         /* initialize the utf8 hashtable stuff: lock, often used utf8
1312            strings (must be done _after_ threads_preinit) */
1313
1314         if (!utf8_init())
1315                 throw_main_exception_exit();
1316
1317         /* initialize the classcache hashtable stuff: lock, hashtable
1318            (must be done _after_ threads_preinit) */
1319
1320         if (!classcache_init())
1321                 throw_main_exception_exit();
1322
1323         /* initialize the loader with bootclasspath (must be done _after_
1324            thread_preinit) */
1325
1326         if (!suck_init())
1327                 throw_main_exception_exit();
1328
1329         suck_add_from_property("java.endorsed.dirs");
1330         suck_add(bootclasspath);
1331
1332         /* initialize the memory subsystem (must be done _after_
1333            threads_preinit) */
1334
1335         if (!memory_init())
1336                 throw_main_exception_exit();
1337
1338         /* initialize the finalizer stuff (must be done _after_
1339            threads_preinit) */
1340
1341         if (!finalizer_init())
1342                 throw_main_exception_exit();
1343
1344         /* install architecture dependent signal handler used for exceptions */
1345
1346         signal_init();
1347
1348         /* initialize the codegen subsystems */
1349
1350         codegen_init();
1351
1352         /* initializes jit compiler */
1353
1354         jit_init();
1355
1356         /* machine dependent initialization */
1357
1358 #if defined(ENABLE_JIT)
1359 # if defined(ENABLE_INTRP)
1360         if (opt_intrp)
1361                 intrp_md_init();
1362         else
1363 # endif
1364                 md_init();
1365 #else
1366         intrp_md_init();
1367 #endif
1368
1369         /* initialize the loader subsystems (must be done _after_
1370        classcache_init) */
1371
1372         if (!loader_init())
1373                 throw_main_exception_exit();
1374
1375         if (!linker_init())
1376                 throw_main_exception_exit();
1377
1378         if (!native_init())
1379                 throw_main_exception_exit();
1380
1381         if (!exceptions_init())
1382                 throw_main_exception_exit();
1383
1384         if (!builtin_init())
1385                 throw_main_exception_exit();
1386
1387         /* Initialize the JNI subsystem (must be done _before_
1388            threads_init, as threads_init can call JNI methods
1389            (e.g. NewGlobalRef). */
1390
1391         if (!jni_init())
1392                 throw_main_exception_exit();
1393
1394 #if defined(ENABLE_THREADS)
1395         if (!threads_init())
1396                 throw_main_exception_exit();
1397 #endif
1398
1399         /* That's important, otherwise we get into trouble, if the Runtime
1400            static initializer is called before (circular dependency. This
1401            is with classpath 0.09. Another important thing is, that this
1402            has to happen after initThreads!!! */
1403
1404         if (!initialize_class(class_java_lang_System))
1405                 throw_main_exception_exit();
1406
1407 #if defined(ENABLE_PROFILING)
1408         /* initialize profiling */
1409
1410         if (!profile_init())
1411                 throw_main_exception_exit();
1412 #endif
1413
1414 #if defined(ENABLE_THREADS)
1415         /* initialize recompilation */
1416
1417         if (!recompile_init())
1418                 throw_main_exception_exit();
1419                 
1420         /* finally, start the finalizer thread */
1421
1422         if (!finalizer_start_thread())
1423                 throw_main_exception_exit();
1424
1425         /* start the recompilation thread (must be done before the
1426            profiling thread) */
1427
1428         if (!recompile_start_thread())
1429                 throw_main_exception_exit();
1430
1431 # if defined(ENABLE_PROFILING)
1432         /* start the profile sampling thread */
1433
1434         if (opt_prof)
1435                 if (!profile_start_thread())
1436                         throw_main_exception_exit();
1437 # endif
1438 #endif
1439
1440 #if defined(ENABLE_JVMTI)
1441         if (jvmti) {
1442                 /* add agent library to native library hashtable */
1443                 native_hashtable_library_add(utf_new_char(libname), class_java_lang_Object->classloader, handle);
1444         }
1445 #endif
1446
1447         /* increment the number of VMs */
1448
1449         vms++;
1450
1451         /* initialization is done */
1452
1453         vm_initializing = false;
1454
1455         /* everything's ok */
1456
1457         return true;
1458 }
1459
1460
1461 /* vm_run **********************************************************************
1462
1463    Runs the main-method of the passed class.
1464
1465 *******************************************************************************/
1466
1467 void vm_run(JavaVM *vm, JavaVMInitArgs *vm_args)
1468 {
1469         utf              *mainutf;
1470         classinfo        *mainclass;
1471         methodinfo       *m;
1472         java_objectarray *oa; 
1473         s4                oalength;
1474         utf              *u;
1475         java_lang_String *s;
1476         s4                status;
1477         s4                i;
1478
1479 #if !defined(NDEBUG)
1480         if (compileall) {
1481                 vm_compile_all();
1482                 return;
1483         }
1484
1485         if (opt_method != NULL) {
1486                 vm_compile_method();
1487                 return;
1488         }
1489 #endif /* !defined(NDEBUG) */
1490
1491         /* should we run the main-method? */
1492
1493         if (mainstring == NULL)
1494                 usage();
1495
1496         /* set return value to OK */
1497
1498         status = 0;
1499
1500         if (opt_jar == true)
1501                 /* open jar file with java.util.jar.JarFile */
1502                 mainstring = vm_get_mainclass_from_jar(mainstring);
1503
1504         /* load the main class */
1505
1506         mainutf = utf_new_char(mainstring);
1507
1508         if (!(mainclass = load_class_from_sysloader(mainutf)))
1509                 throw_main_exception_exit();
1510
1511         /* error loading class, clear exceptionptr for new exception */
1512
1513         if (*exceptionptr || !mainclass) {
1514                 /*                      *exceptionptr = NULL; */
1515
1516                 /*                      *exceptionptr = */
1517                 /*                              new_exception_message(string_java_lang_NoClassDefFoundError, */
1518                 /*                                                                        mainstring); */
1519                 throw_main_exception_exit();
1520         }
1521
1522         if (!link_class(mainclass))
1523                 throw_main_exception_exit();
1524                         
1525         /* find the `main' method of the main class */
1526
1527         m = class_resolveclassmethod(mainclass,
1528                                                                  utf_new_char("main"), 
1529                                                                  utf_new_char("([Ljava/lang/String;)V"),
1530                                                                  class_java_lang_Object,
1531                                                                  false);
1532
1533         if (*exceptionptr) {
1534                 throw_main_exception_exit();
1535         }
1536
1537         /* there is no main method or it isn't static */
1538
1539         if ((m == NULL) || !(m->flags & ACC_STATIC)) {
1540                 *exceptionptr = NULL;
1541
1542                 *exceptionptr =
1543                         new_exception_message(string_java_lang_NoSuchMethodError, "main");
1544                 throw_main_exception_exit();
1545         }
1546
1547         /* build argument array */
1548
1549         oalength = vm_args->nOptions - opt_index;
1550
1551         oa = builtin_anewarray(oalength, class_java_lang_String);
1552
1553         for (i = 0; i < oalength; i++) {
1554                 u = utf_new_char(vm_args->options[opt_index + i].optionString);
1555                 s = javastring_new(u);
1556
1557                 oa->data[i] = (java_objectheader *) s;
1558         }
1559
1560 #ifdef TYPEINFO_DEBUG_TEST
1561         /* test the typeinfo system */
1562         typeinfo_test();
1563 #endif
1564         /*class_showmethods(currentThread->group->header.vftbl->class); */
1565
1566 #if defined(ENABLE_JVMTI)
1567         jvmti_set_phase(JVMTI_PHASE_LIVE);
1568 #endif
1569
1570         /* increase total started thread count */
1571
1572         _Jv_jvm->total_started_thread_count++;
1573
1574         /* start the main thread */
1575
1576         (void) vm_call_method(m, NULL, oa);
1577
1578         /* exception occurred? */
1579
1580         if (*exceptionptr) {
1581                 throw_main_exception();
1582                 status = 1;
1583         }
1584
1585         /* unload the JavaVM */
1586
1587         vm_destroy(vm);
1588
1589         /* and exit */
1590
1591         vm_exit(status);
1592 }
1593
1594
1595 /* vm_destroy ******************************************************************
1596
1597    Unloads a Java VM and reclaims its resources.
1598
1599 *******************************************************************************/
1600
1601 s4 vm_destroy(JavaVM *vm)
1602 {
1603 #if defined(ENABLE_THREADS)
1604         threads_join_all_threads();
1605 #endif
1606
1607         /* everything's ok */
1608
1609         return 0;
1610 }
1611
1612
1613 /* vm_exit *********************************************************************
1614
1615    Calls java.lang.System.exit(I)V to exit the JavaVM correctly.
1616
1617 *******************************************************************************/
1618
1619 void vm_exit(s4 status)
1620 {
1621         methodinfo *m;
1622
1623         /* signal that we are exiting */
1624
1625         vm_exiting = true;
1626
1627         assert(class_java_lang_System);
1628         assert(class_java_lang_System->state & CLASS_LOADED);
1629
1630 #if defined(ENABLE_JVMTI)
1631         if (jvmti || (dbgcom!=NULL)) {
1632                 jvmti_set_phase(JVMTI_PHASE_DEAD);
1633                 if (jvmti) jvmti_agentunload();
1634         }
1635 #endif
1636
1637         if (!link_class(class_java_lang_System))
1638                 throw_main_exception_exit();
1639
1640         /* call java.lang.System.exit(I)V */
1641
1642         m = class_resolveclassmethod(class_java_lang_System,
1643                                                                  utf_new_char("exit"),
1644                                                                  utf_int__void,
1645                                                                  class_java_lang_Object,
1646                                                                  true);
1647         
1648         if (m == NULL)
1649                 throw_main_exception_exit();
1650
1651         /* call the exit function with passed exit status */
1652
1653         (void) vm_call_method(m, NULL, status);
1654
1655         /* If we had an exception, just ignore the exception and exit with
1656            the proper code. */
1657
1658         vm_shutdown(status);
1659 }
1660
1661
1662 /* vm_shutdown *****************************************************************
1663
1664    Terminates the system immediately without freeing memory explicitly
1665    (to be used only for abnormal termination).
1666         
1667 *******************************************************************************/
1668
1669 void vm_shutdown(s4 status)
1670 {
1671         if (opt_verbose 
1672 #if defined(ENABLE_STATISTICS)
1673                 || opt_getcompilingtime || opt_stat
1674 #endif
1675            ) 
1676         {
1677                 log_text("CACAO terminated by shutdown");
1678                 dolog("Exit status: %d\n", (s4) status);
1679
1680         }
1681
1682 #if defined(ENABLE_JVMTI)
1683         /* terminate cacaodbgserver */
1684         if (dbgcom!=NULL) {
1685                 pthread_mutex_lock(&dbgcomlock);
1686                 dbgcom->running=1;
1687                 pthread_mutex_unlock(&dbgcomlock);
1688                 jvmti_cacaodbgserver_quit();
1689         }       
1690 #endif
1691
1692         exit(status);
1693 }
1694
1695
1696 /* vm_exit_handler *************************************************************
1697
1698    The exit_handler function is called upon program termination.
1699
1700    ATTENTION: Don't free system resources here! Some threads may still
1701    be running as this is called from VMRuntime.exit(). The OS does the
1702    cleanup for us.
1703
1704 *******************************************************************************/
1705
1706 void vm_exit_handler(void)
1707 {
1708 #if !defined(NDEBUG)
1709         if (showmethods)
1710                 class_showmethods(mainclass);
1711
1712         if (showconstantpool)
1713                 class_showconstantpool(mainclass);
1714
1715         if (showutf)
1716                 utf_show();
1717
1718 # if defined(ENABLE_PROFILING)
1719         if (opt_prof)
1720                 profile_printstats();
1721 # endif
1722 #endif /* !defined(NDEBUG) */
1723
1724 #if defined(ENABLE_RT_TIMING)
1725         rt_timing_print_time_stats(stderr);
1726 #endif
1727
1728 #if defined(ENABLE_CYCLES_STATS)
1729         builtin_print_cycles_stats(stderr);
1730         stacktrace_print_cycles_stats(stderr);
1731 #endif
1732
1733         if (opt_verbose 
1734 #if defined(ENABLE_STATISTICS)
1735                 || opt_getcompilingtime || opt_stat
1736 #endif
1737            ) 
1738         {
1739                 log_text("CACAO terminated");
1740
1741 #if defined(ENABLE_STATISTICS)
1742                 if (opt_stat) {
1743                         print_stats();
1744 #ifdef TYPECHECK_STATISTICS
1745                         typecheck_print_statistics(get_logfile());
1746 #endif
1747                 }
1748
1749                 mem_usagelog(1);
1750
1751                 if (opt_getcompilingtime)
1752                         print_times();
1753 #endif /* defined(ENABLE_STATISTICS) */
1754         }
1755         /* vm_print_profile(stderr);*/
1756 }
1757
1758
1759 /* vm_abort ********************************************************************
1760
1761    Prints an error message and aborts the VM.
1762
1763 *******************************************************************************/
1764
1765 void vm_abort(const char *text, ...)
1766 {
1767         va_list ap;
1768
1769         /* print the log message */
1770
1771         log_start();
1772
1773         va_start(ap, text);
1774         log_vprint(text, ap);
1775         va_end(ap);
1776
1777         log_finish();
1778
1779         /* now abort the VM */
1780
1781         abort();
1782 }
1783
1784
1785 /* vm_get_mainclass_from_jar ***************************************************
1786
1787    Gets the name of the main class from a JAR's manifest file.
1788
1789 *******************************************************************************/
1790
1791 static char *vm_get_mainclass_from_jar(char *mainstring)
1792 {
1793         classinfo         *c;
1794         java_objectheader *o;
1795         methodinfo        *m;
1796         java_lang_String  *s;
1797
1798         c = load_class_from_sysloader(utf_new_char("java/util/jar/JarFile"));
1799
1800         if (c == NULL)
1801                 throw_main_exception_exit();
1802         
1803         /* create JarFile object */
1804
1805         o = builtin_new(c);
1806
1807         if (o == NULL)
1808                 throw_main_exception_exit();
1809
1810
1811         m = class_resolveclassmethod(c,
1812                                                                  utf_init, 
1813                                                                  utf_java_lang_String__void,
1814                                                                  class_java_lang_Object,
1815                                                                  true);
1816
1817         if (m == NULL)
1818                 throw_main_exception_exit();
1819
1820         s = javastring_new_from_ascii(mainstring);
1821
1822         (void) vm_call_method(m, o, s);
1823
1824         if (*exceptionptr)
1825                 throw_main_exception_exit();
1826
1827         /* get manifest object */
1828
1829         m = class_resolveclassmethod(c,
1830                                                                  utf_new_char("getManifest"), 
1831                                                                  utf_new_char("()Ljava/util/jar/Manifest;"),
1832                                                                  class_java_lang_Object,
1833                                                                  true);
1834
1835         if (m == NULL)
1836                 throw_main_exception_exit();
1837
1838         o = vm_call_method(m, o);
1839
1840         if (o == NULL) {
1841                 fprintf(stderr, "Could not get manifest from %s (invalid or corrupt jarfile?)\n", mainstring);
1842                 vm_exit(1);
1843         }
1844
1845
1846         /* get Main Attributes */
1847
1848         m = class_resolveclassmethod(o->vftbl->class,
1849                                                                  utf_new_char("getMainAttributes"), 
1850                                                                  utf_new_char("()Ljava/util/jar/Attributes;"),
1851                                                                  class_java_lang_Object,
1852                                                                  true);
1853
1854         if (m == NULL)
1855                 throw_main_exception_exit();
1856
1857         o = vm_call_method(m, o);
1858
1859         if (o == NULL) {
1860                 fprintf(stderr, "Could not get main attributes from %s (invalid or corrupt jarfile?)\n", mainstring);
1861                 vm_exit(1);
1862         }
1863
1864
1865         /* get property Main-Class */
1866
1867         m = class_resolveclassmethod(o->vftbl->class,
1868                                                                  utf_new_char("getValue"), 
1869                                                                  utf_new_char("(Ljava/lang/String;)Ljava/lang/String;"),
1870                                                                  class_java_lang_Object,
1871                                                                  true);
1872
1873         if (m == NULL)
1874                 throw_main_exception_exit();
1875
1876         s = javastring_new_from_ascii("Main-Class");
1877
1878         o = vm_call_method(m, o, s);
1879
1880         if (o == NULL)
1881                 throw_main_exception_exit();
1882
1883         return javastring_tochar(o);
1884 }
1885
1886
1887 /* vm_compile_all **************************************************************
1888
1889    Compile all methods found in the bootclasspath.
1890
1891 *******************************************************************************/
1892
1893 #if !defined(NDEBUG)
1894 static void vm_compile_all(void)
1895 {
1896         classinfo              *c;
1897         methodinfo             *m;
1898         u4                      slot;
1899         classcache_name_entry  *nmen;
1900         classcache_class_entry *clsen;
1901         s4                      i;
1902
1903         /* create all classes found in the bootclasspath */
1904         /* XXX currently only works with zip/jar's */
1905
1906         loader_load_all_classes();
1907
1908         /* link all classes */
1909
1910         for (slot = 0; slot < hashtable_classcache.size; slot++) {
1911                 nmen = (classcache_name_entry *) hashtable_classcache.ptr[slot];
1912
1913                 for (; nmen; nmen = nmen->hashlink) {
1914                         /* iterate over all class entries */
1915
1916                         for (clsen = nmen->classes; clsen; clsen = clsen->next) {
1917                                 c = clsen->classobj;
1918
1919                                 if (c == NULL)
1920                                         continue;
1921
1922                                 if (!(c->state & CLASS_LINKED)) {
1923                                         if (!link_class(c)) {
1924                                                 fprintf(stderr, "Error linking: ");
1925                                                 utf_fprint_printable_ascii_classname(stderr, c->name);
1926                                                 fprintf(stderr, "\n");
1927
1928                                                 /* print out exception and cause */
1929
1930                                                 exceptions_print_exception(*exceptionptr);
1931
1932                                                 /* goto next class */
1933
1934                                                 continue;
1935                                         }
1936                                 }
1937
1938                                 /* compile all class methods */
1939
1940                                 for (i = 0; i < c->methodscount; i++) {
1941                                         m = &(c->methods[i]);
1942
1943                                         if (m->jcode != NULL) {
1944                                                 if (!jit_compile(m)) {
1945                                                         fprintf(stderr, "Error compiling: ");
1946                                                         utf_fprint_printable_ascii_classname(stderr, c->name);
1947                                                         fprintf(stderr, ".");
1948                                                         utf_fprint_printable_ascii(stderr, m->name);
1949                                                         utf_fprint_printable_ascii(stderr, m->descriptor);
1950                                                         fprintf(stderr, "\n");
1951
1952                                                         /* print out exception and cause */
1953
1954                                                         exceptions_print_exception(*exceptionptr);
1955                                                 }
1956                                         }
1957                                 }
1958                         }
1959                 }
1960         }
1961 }
1962 #endif /* !defined(NDEBUG) */
1963
1964
1965 /* vm_compile_method ***********************************************************
1966
1967    Compile a specific method.
1968
1969 *******************************************************************************/
1970
1971 #if !defined(NDEBUG)
1972 static void vm_compile_method(void)
1973 {
1974         methodinfo *m;
1975
1976         /* create, load and link the main class */
1977
1978         if (!(mainclass = load_class_bootstrap(utf_new_char(mainstring))))
1979                 throw_main_exception_exit();
1980
1981         if (!link_class(mainclass))
1982                 throw_main_exception_exit();
1983
1984         if (opt_signature != NULL) {
1985                 m = class_resolveclassmethod(mainclass,
1986                                                                          utf_new_char(opt_method),
1987                                                                          utf_new_char(opt_signature),
1988                                                                          mainclass,
1989                                                                          false);
1990         }
1991         else {
1992                 m = class_resolveclassmethod(mainclass,
1993                                                                          utf_new_char(opt_method),
1994                                                                          NULL,
1995                                                                          mainclass,
1996                                                                          false);
1997         }
1998
1999         if (m == NULL) {
2000                 char message[MAXLOGTEXT];
2001                 sprintf(message, "%s%s", opt_method,
2002                                 opt_signature ? opt_signature : "");
2003
2004                 *exceptionptr =
2005                         new_exception_message(string_java_lang_NoSuchMethodException,
2006                                                                   message);
2007                                                                                  
2008                 throw_main_exception_exit();
2009         }
2010                 
2011         jit_compile(m);
2012 }
2013 #endif /* !defined(NDEBUG) */
2014
2015
2016 /* vm_vmargs_from_valist *******************************************************
2017
2018    XXX
2019
2020 *******************************************************************************/
2021
2022 static void vm_vmargs_from_valist(methodinfo *m, java_objectheader *o,
2023                                                                   vm_arg *vmargs, va_list ap)
2024 {
2025         typedesc *paramtypes;
2026         s4        i;
2027
2028         paramtypes = m->parseddesc->paramtypes;
2029
2030         /* if method is non-static fill first block and skip `this' pointer */
2031
2032         i = 0;
2033
2034         if (o != NULL) {
2035                 /* the `this' pointer */
2036                 vmargs[0].type   = TYPE_ADR;
2037                 vmargs[0].data.l = (u8) (ptrint) o;
2038
2039                 paramtypes++;
2040                 i++;
2041         } 
2042
2043         for (; i < m->parseddesc->paramcount; i++, paramtypes++) {
2044                 switch (paramtypes->decltype) {
2045                 /* primitive types */
2046                 case PRIMITIVETYPE_BOOLEAN: 
2047                 case PRIMITIVETYPE_BYTE:
2048                 case PRIMITIVETYPE_CHAR:
2049                 case PRIMITIVETYPE_SHORT: 
2050                 case PRIMITIVETYPE_INT:
2051                         vmargs[i].type   = TYPE_INT;
2052                         vmargs[i].data.l = (s8) va_arg(ap, s4);
2053                         break;
2054
2055                 case PRIMITIVETYPE_LONG:
2056                         vmargs[i].type   = TYPE_LNG;
2057                         vmargs[i].data.l = (s8) va_arg(ap, s8);
2058                         break;
2059
2060                 case PRIMITIVETYPE_FLOAT:
2061                         vmargs[i].type   = TYPE_FLT;
2062 #if defined(__ALPHA__)
2063                         /* this keeps the assembler function much simpler */
2064
2065                         vmargs[i].data.d = (jdouble) va_arg(ap, jdouble);
2066 #else
2067                         vmargs[i].data.f = (jfloat) va_arg(ap, jdouble);
2068 #endif
2069                         break;
2070
2071                 case PRIMITIVETYPE_DOUBLE:
2072                         vmargs[i].type   = TYPE_DBL;
2073                         vmargs[i].data.d = (jdouble) va_arg(ap, jdouble);
2074                         break;
2075
2076                 case TYPE_ADR: 
2077                         vmargs[i].type   = TYPE_ADR;
2078                         vmargs[i].data.l = (u8) (ptrint) va_arg(ap, void*);
2079                         break;
2080                 }
2081         }
2082 }
2083
2084
2085 /* vm_vmargs_from_jvalue *******************************************************
2086
2087    XXX
2088
2089 *******************************************************************************/
2090
2091 static void vm_vmargs_from_jvalue(methodinfo *m, java_objectheader *o,
2092                                                                   vm_arg *vmargs, jvalue *args)
2093 {
2094         typedesc *paramtypes;
2095         s4        i;
2096         s4        j;
2097
2098         paramtypes = m->parseddesc->paramtypes;
2099
2100         /* if method is non-static fill first block and skip `this' pointer */
2101
2102         i = 0;
2103
2104         if (o != NULL) {
2105                 /* the `this' pointer */
2106                 vmargs[0].type   = TYPE_ADR;
2107                 vmargs[0].data.l = (u8) (ptrint) o;
2108
2109                 paramtypes++;
2110                 i++;
2111         } 
2112
2113         for (j = 0; i < m->parseddesc->paramcount; i++, j++, paramtypes++) {
2114                 switch (paramtypes->decltype) {
2115                 /* primitive types */
2116                 case PRIMITIVETYPE_BOOLEAN: 
2117                 case PRIMITIVETYPE_BYTE:
2118                 case PRIMITIVETYPE_CHAR:
2119                 case PRIMITIVETYPE_SHORT: 
2120                 case PRIMITIVETYPE_INT:
2121                         vmargs[i].type   = TYPE_INT;
2122                         vmargs[i].data.l = (s8) args[j].i;
2123                         break;
2124
2125                 case PRIMITIVETYPE_LONG:
2126                         vmargs[i].type   = TYPE_LNG;
2127                         vmargs[i].data.l = (s8) args[j].j;
2128                         break;
2129
2130                 case PRIMITIVETYPE_FLOAT:
2131                         vmargs[i].type = TYPE_FLT;
2132 #if defined(__ALPHA__)
2133                         /* this keeps the assembler function much simpler */
2134
2135                         vmargs[i].data.d = (jdouble) args[j].f;
2136 #else
2137                         vmargs[i].data.f = args[j].f;
2138 #endif
2139                         break;
2140
2141                 case PRIMITIVETYPE_DOUBLE:
2142                         vmargs[i].type   = TYPE_DBL;
2143                         vmargs[i].data.d = args[j].d;
2144                         break;
2145
2146                 case TYPE_ADR: 
2147                         vmargs[i].type   = TYPE_ADR;
2148                         vmargs[i].data.l = (u8) (ptrint) args[j].l;
2149                         break;
2150                 }
2151         }
2152 }
2153
2154
2155 /* vm_call_method **************************************************************
2156
2157    Calls a Java method with a variable number of arguments and returns
2158    an address.
2159
2160 *******************************************************************************/
2161
2162 java_objectheader *vm_call_method(methodinfo *m, java_objectheader *o, ...)
2163 {
2164         va_list            ap;
2165         java_objectheader *ro;
2166
2167         va_start(ap, o);
2168         ro = vm_call_method_valist(m, o, ap);
2169         va_end(ap);
2170
2171         return ro;
2172 }
2173
2174
2175 /* vm_call_method_valist *******************************************************
2176
2177    Calls a Java method with a variable number of arguments, passed via
2178    a va_list, and returns an address.
2179
2180 *******************************************************************************/
2181
2182 java_objectheader *vm_call_method_valist(methodinfo *m, java_objectheader *o,
2183                                                                                  va_list ap)
2184 {
2185         s4                 vmargscount;
2186         vm_arg            *vmargs;
2187         java_objectheader *ro;
2188         s4                 dumpsize;
2189
2190         /* mark start of dump memory area */
2191
2192         dumpsize = dump_size();
2193
2194         /* get number of Java method arguments */
2195
2196         vmargscount = m->parseddesc->paramcount;
2197
2198         /* allocate vm_arg array */
2199
2200         vmargs = DMNEW(vm_arg, vmargscount);
2201
2202         /* fill the vm_arg array from a va_list */
2203
2204         vm_vmargs_from_valist(m, o, vmargs, ap);
2205
2206         /* call the Java method */
2207
2208         ro = vm_call_method_vmarg(m, vmargscount, vmargs);
2209
2210         /* release dump area */
2211
2212         dump_release(dumpsize);
2213
2214         return ro;
2215 }
2216
2217
2218 /* vm_call_method_jvalue *******************************************************
2219
2220    Calls a Java method with a variable number of arguments, passed via
2221    a jvalue array, and returns an address.
2222
2223 *******************************************************************************/
2224
2225 java_objectheader *vm_call_method_jvalue(methodinfo *m, java_objectheader *o,
2226                                                                                  jvalue *args)
2227 {
2228         s4                 vmargscount;
2229         vm_arg            *vmargs;
2230         java_objectheader *ro;
2231         s4                 dumpsize;
2232
2233         /* mark start of dump memory area */
2234
2235         dumpsize = dump_size();
2236
2237         /* get number of Java method arguments */
2238
2239         vmargscount = m->parseddesc->paramcount;
2240
2241         /* allocate vm_arg array */
2242
2243         vmargs = DMNEW(vm_arg, vmargscount);
2244
2245         /* fill the vm_arg array from a va_list */
2246
2247         vm_vmargs_from_jvalue(m, o, vmargs, args);
2248
2249         /* call the Java method */
2250
2251         ro = vm_call_method_vmarg(m, vmargscount, vmargs);
2252
2253         /* release dump area */
2254
2255         dump_release(dumpsize);
2256
2257         return ro;
2258 }
2259
2260
2261 /* vm_call_method_vmarg ********************************************************
2262
2263    Calls a Java method with a variable number of arguments, passed via
2264    a vm_arg array, and returns an address.
2265
2266 *******************************************************************************/
2267
2268 java_objectheader *vm_call_method_vmarg(methodinfo *m, s4 vmargscount,
2269                                                                                 vm_arg *vmargs)
2270 {
2271         java_objectheader *o;
2272
2273 #if defined(ENABLE_JIT)
2274 # if defined(ENABLE_INTRP)
2275         if (opt_intrp)
2276                 o = intrp_asm_vm_call_method(m, vmargscount, vmargs);
2277         else
2278 # endif
2279                 o = asm_vm_call_method(m, vmargscount, vmargs);
2280 #else
2281         o = intrp_asm_vm_call_method(m, vmargscount, vmargs);
2282 #endif
2283
2284         return o;
2285 }
2286
2287
2288 /* vm_call_method_int **********************************************************
2289
2290    Calls a Java method with a variable number of arguments and returns
2291    an integer (s4).
2292
2293 *******************************************************************************/
2294
2295 s4 vm_call_method_int(methodinfo *m, java_objectheader *o, ...)
2296 {
2297         va_list ap;
2298         s4      i;
2299
2300         va_start(ap, o);
2301         i = vm_call_method_int_valist(m, o, ap);
2302         va_end(ap);
2303
2304         return i;
2305 }
2306
2307
2308 /* vm_call_method_int_valist ***************************************************
2309
2310    Calls a Java method with a variable number of arguments, passed via
2311    a va_list, and returns an integer (s4).
2312
2313 *******************************************************************************/
2314
2315 s4 vm_call_method_int_valist(methodinfo *m, java_objectheader *o, va_list ap)
2316 {
2317         s4      vmargscount;
2318         vm_arg *vmargs;
2319         s4      i;
2320         s4      dumpsize;
2321
2322         /* mark start of dump memory area */
2323
2324         dumpsize = dump_size();
2325
2326         /* get number of Java method arguments */
2327
2328         vmargscount = m->parseddesc->paramcount;
2329
2330         /* allocate vm_arg array */
2331
2332         vmargs = DMNEW(vm_arg, vmargscount);
2333
2334         /* fill the vm_arg array from a va_list */
2335
2336         vm_vmargs_from_valist(m, o, vmargs, ap);
2337
2338         /* call the Java method */
2339
2340         i = vm_call_method_int_vmarg(m, vmargscount, vmargs);
2341
2342         /* release dump area */
2343
2344         dump_release(dumpsize);
2345
2346         return i;
2347 }
2348
2349
2350 /* vm_call_method_int_jvalue ***************************************************
2351
2352    Calls a Java method with a variable number of arguments, passed via
2353    a jvalue array, and returns an integer (s4).
2354
2355 *******************************************************************************/
2356
2357 s4 vm_call_method_int_jvalue(methodinfo *m, java_objectheader *o, jvalue *args)
2358 {
2359         s4      vmargscount;
2360         vm_arg *vmargs;
2361         s4      i;
2362         s4      dumpsize;
2363
2364         /* mark start of dump memory area */
2365
2366         dumpsize = dump_size();
2367
2368         /* get number of Java method arguments */
2369
2370         vmargscount = m->parseddesc->paramcount;
2371
2372         /* allocate vm_arg array */
2373
2374         vmargs = DMNEW(vm_arg, vmargscount);
2375
2376         /* fill the vm_arg array from a va_list */
2377
2378         vm_vmargs_from_jvalue(m, o, vmargs, args);
2379
2380         /* call the Java method */
2381
2382         i = vm_call_method_int_vmarg(m, vmargscount, vmargs);
2383
2384         /* release dump area */
2385
2386         dump_release(dumpsize);
2387
2388         return i;
2389 }
2390
2391
2392 /* vm_call_method_int_vmarg ****************************************************
2393
2394    Calls a Java method with a variable number of arguments, passed via
2395    a vm_arg array, and returns an integer (s4).
2396
2397 *******************************************************************************/
2398
2399 s4 vm_call_method_int_vmarg(methodinfo *m, s4 vmargscount, vm_arg *vmargs)
2400 {
2401         s4 i;
2402
2403 #if defined(ENABLE_JIT)
2404 # if defined(ENABLE_INTRP)
2405         if (opt_intrp)
2406                 i = intrp_asm_vm_call_method_int(m, vmargscount, vmargs);
2407         else
2408 # endif
2409                 i = asm_vm_call_method_int(m, vmargscount, vmargs);
2410 #else
2411         i = intrp_asm_vm_call_method_int(m, vmargscount, vmargs);
2412 #endif
2413
2414         return i;
2415 }
2416
2417
2418 /* vm_call_method_long *********************************************************
2419
2420    Calls a Java method with a variable number of arguments and returns
2421    a long (s8).
2422
2423 *******************************************************************************/
2424
2425 s8 vm_call_method_long(methodinfo *m, java_objectheader *o, ...)
2426 {
2427         va_list ap;
2428         s8      l;
2429
2430         va_start(ap, o);
2431         l = vm_call_method_long_valist(m, o, ap);
2432         va_end(ap);
2433
2434         return l;
2435 }
2436
2437
2438 /* vm_call_method_long_valist **************************************************
2439
2440    Calls a Java method with a variable number of arguments, passed via
2441    a va_list, and returns a long (s8).
2442
2443 *******************************************************************************/
2444
2445 s8 vm_call_method_long_valist(methodinfo *m, java_objectheader *o, va_list ap)
2446 {
2447         s4      vmargscount;
2448         vm_arg *vmargs;
2449         s8      l;
2450         s4      dumpsize;
2451
2452         /* mark start of dump memory area */
2453
2454         dumpsize = dump_size();
2455
2456         /* get number of Java method arguments */
2457
2458         vmargscount = m->parseddesc->paramcount;
2459
2460         /* allocate vm_arg array */
2461
2462         vmargs = DMNEW(vm_arg, vmargscount);
2463
2464         /* fill the vm_arg array from a va_list */
2465
2466         vm_vmargs_from_valist(m, o, vmargs, ap);
2467
2468         /* call the Java method */
2469
2470         l = vm_call_method_long_vmarg(m, vmargscount, vmargs);
2471
2472         /* release dump area */
2473
2474         dump_release(dumpsize);
2475
2476         return l;
2477 }
2478
2479
2480 /* vm_call_method_long_jvalue **************************************************
2481
2482    Calls a Java method with a variable number of arguments, passed via
2483    a jvalue array, and returns a long (s8).
2484
2485 *******************************************************************************/
2486
2487 s8 vm_call_method_long_jvalue(methodinfo *m, java_objectheader *o, jvalue *args)
2488 {
2489         s4      vmargscount;
2490         vm_arg *vmargs;
2491         s8      l;
2492         s4      dumpsize;
2493
2494         /* mark start of dump memory area */
2495
2496         dumpsize = dump_size();
2497
2498         /* get number of Java method arguments */
2499
2500         vmargscount = m->parseddesc->paramcount;
2501
2502         /* allocate vm_arg array */
2503
2504         vmargs = DMNEW(vm_arg, vmargscount);
2505
2506         /* fill the vm_arg array from a va_list */
2507
2508         vm_vmargs_from_jvalue(m, o, vmargs, args);
2509
2510         /* call the Java method */
2511
2512         l = vm_call_method_long_vmarg(m, vmargscount, vmargs);
2513
2514         /* release dump area */
2515
2516         dump_release(dumpsize);
2517
2518         return l;
2519 }
2520
2521
2522 /* vm_call_method_long_vmarg ***************************************************
2523
2524    Calls a Java method with a variable number of arguments, passed via
2525    a vm_arg array, and returns a long (s8).
2526
2527 *******************************************************************************/
2528
2529 s8 vm_call_method_long_vmarg(methodinfo *m, s4 vmargscount, vm_arg *vmargs)
2530 {
2531         s8 l;
2532
2533 #if defined(ENABLE_JIT)
2534 # if defined(ENABLE_INTRP)
2535         if (opt_intrp)
2536                 l = intrp_asm_vm_call_method_long(m, vmargscount, vmargs);
2537         else
2538 # endif
2539                 l = asm_vm_call_method_long(m, vmargscount, vmargs);
2540 #else
2541         l = intrp_asm_vm_call_method_long(m, vmargscount, vmargs);
2542 #endif
2543
2544         return l;
2545 }
2546
2547
2548 /* vm_call_method_float ********************************************************
2549
2550    Calls a Java method with a variable number of arguments and returns
2551    an float.
2552
2553 *******************************************************************************/
2554
2555 float vm_call_method_float(methodinfo *m, java_objectheader *o, ...)
2556 {
2557         va_list ap;
2558         float   f;
2559
2560         va_start(ap, o);
2561         f = vm_call_method_float_valist(m, o, ap);
2562         va_end(ap);
2563
2564         return f;
2565 }
2566
2567
2568 /* vm_call_method_float_valist *************************************************
2569
2570    Calls a Java method with a variable number of arguments, passed via
2571    a va_list, and returns a float.
2572
2573 *******************************************************************************/
2574
2575 float vm_call_method_float_valist(methodinfo *m, java_objectheader *o,
2576                                                                   va_list ap)
2577 {
2578         s4      vmargscount;
2579         vm_arg *vmargs;
2580         float   f;
2581         s4      dumpsize;
2582
2583         /* mark start of dump memory area */
2584
2585         dumpsize = dump_size();
2586
2587         /* get number of Java method arguments */
2588
2589         vmargscount = m->parseddesc->paramcount;
2590
2591         /* allocate vm_arg array */
2592
2593         vmargs = DMNEW(vm_arg, vmargscount);
2594
2595         /* fill the vm_arg array from a va_list */
2596
2597         vm_vmargs_from_valist(m, o, vmargs, ap);
2598
2599         /* call the Java method */
2600
2601         f = vm_call_method_float_vmarg(m, vmargscount, vmargs);
2602
2603         /* release dump area */
2604
2605         dump_release(dumpsize);
2606
2607         return f;
2608 }
2609
2610
2611 /* vm_call_method_float_jvalue *************************************************
2612
2613    Calls a Java method with a variable number of arguments, passed via
2614    a jvalue array, and returns a float.
2615
2616 *******************************************************************************/
2617
2618 float vm_call_method_float_jvalue(methodinfo *m, java_objectheader *o,
2619                                                                   jvalue *args)
2620 {
2621         s4      vmargscount;
2622         vm_arg *vmargs;
2623         float   f;
2624         s4      dumpsize;
2625
2626         /* mark start of dump memory area */
2627
2628         dumpsize = dump_size();
2629
2630         /* get number of Java method arguments */
2631
2632         vmargscount = m->parseddesc->paramcount;
2633
2634         /* allocate vm_arg array */
2635
2636         vmargs = DMNEW(vm_arg, vmargscount);
2637
2638         /* fill the vm_arg array from a va_list */
2639
2640         vm_vmargs_from_jvalue(m, o, vmargs, args);
2641
2642         /* call the Java method */
2643
2644         f = vm_call_method_float_vmarg(m, vmargscount, vmargs);
2645
2646         /* release dump area */
2647
2648         dump_release(dumpsize);
2649
2650         return f;
2651 }
2652
2653
2654 /* vm_call_method_float_vmarg **************************************************
2655
2656    Calls a Java method with a variable number of arguments and returns
2657    an float.
2658
2659 *******************************************************************************/
2660
2661 float vm_call_method_float_vmarg(methodinfo *m, s4 vmargscount, vm_arg *vmargs)
2662 {
2663         float f;
2664
2665 #if defined(ENABLE_JIT)
2666 # if defined(ENABLE_INTRP)
2667         if (opt_intrp)
2668                 f = intrp_asm_vm_call_method_float(m, vmargscount, vmargs);
2669         else
2670 # endif
2671                 f = asm_vm_call_method_float(m, vmargscount, vmargs);
2672 #else
2673         f = intrp_asm_vm_call_method_float(m, vmargscount, vmargs);
2674 #endif
2675
2676         return f;
2677 }
2678
2679
2680 /* vm_call_method_double *******************************************************
2681
2682    Calls a Java method with a variable number of arguments and returns
2683    a double.
2684
2685 *******************************************************************************/
2686
2687 double vm_call_method_double(methodinfo *m, java_objectheader *o, ...)
2688 {
2689         va_list ap;
2690         double  d;
2691
2692         va_start(ap, o);
2693         d = vm_call_method_double_valist(m, o, ap);
2694         va_end(ap);
2695
2696         return d;
2697 }
2698
2699
2700 /* vm_call_method_double_valist ************************************************
2701
2702    Calls a Java method with a variable number of arguments, passed via
2703    a va_list, and returns a double.
2704
2705 *******************************************************************************/
2706
2707 double vm_call_method_double_valist(methodinfo *m, java_objectheader *o,
2708                                                                         va_list ap)
2709 {
2710         s4      vmargscount;
2711         vm_arg *vmargs;
2712         double  d;
2713         s4      dumpsize;
2714
2715         /* mark start of dump memory area */
2716
2717         dumpsize = dump_size();
2718
2719         /* get number of Java method arguments */
2720
2721         vmargscount = m->parseddesc->paramcount;
2722
2723         /* allocate vm_arg array */
2724
2725         vmargs = DMNEW(vm_arg, vmargscount);
2726
2727         /* fill the vm_arg array from a va_list */
2728
2729         vm_vmargs_from_valist(m, o, vmargs, ap);
2730
2731         /* call the Java method */
2732
2733         d = vm_call_method_double_vmarg(m, vmargscount, vmargs);
2734
2735         /* release dump area */
2736
2737         dump_release(dumpsize);
2738
2739         return d;
2740 }
2741
2742
2743 /* vm_call_method_double_jvalue ************************************************
2744
2745    Calls a Java method with a variable number of arguments, passed via
2746    a jvalue array, and returns a double.
2747
2748 *******************************************************************************/
2749
2750 double vm_call_method_double_jvalue(methodinfo *m, java_objectheader *o,
2751                                                                         jvalue *args)
2752 {
2753         s4      vmargscount;
2754         vm_arg *vmargs;
2755         double  d;
2756         s4      dumpsize;
2757
2758         /* mark start of dump memory area */
2759
2760         dumpsize = dump_size();
2761
2762         /* get number of Java method arguments */
2763
2764         vmargscount = m->parseddesc->paramcount;
2765
2766         /* allocate vm_arg array */
2767
2768         vmargs = DMNEW(vm_arg, vmargscount);
2769
2770         /* fill the vm_arg array from a va_list */
2771
2772         vm_vmargs_from_jvalue(m, o, vmargs, args);
2773
2774         /* call the Java method */
2775
2776         d = vm_call_method_double_vmarg(m, vmargscount, vmargs);
2777
2778         /* release dump area */
2779
2780         dump_release(dumpsize);
2781
2782         return d;
2783 }
2784
2785
2786 /* vm_call_method_double_vmarg *************************************************
2787
2788    Calls a Java method with a variable number of arguments and returns
2789    a double.
2790
2791 *******************************************************************************/
2792
2793 double vm_call_method_double_vmarg(methodinfo *m, s4 vmargscount,
2794                                                                    vm_arg *vmargs)
2795 {
2796         double d;
2797
2798 #if defined(ENABLE_JIT)
2799 # if defined(ENABLE_INTRP)
2800         if (opt_intrp)
2801                 d = intrp_asm_vm_call_method_double(m, vmargscount, vmargs);
2802         else
2803 # endif
2804                 d = asm_vm_call_method_double(m, vmargscount, vmargs);
2805 #else
2806         d = intrp_asm_vm_call_method_double(m, vmargscount, vmargs);
2807 #endif
2808
2809         return d;
2810 }
2811
2812
2813 /*
2814  * These are local overrides for various environment variables in Emacs.
2815  * Please do not remove this and leave it at the end of the file, where
2816  * Emacs will automagically detect them.
2817  * ---------------------------------------------------------------------
2818  * Local variables:
2819  * mode: c
2820  * indent-tabs-mode: t
2821  * c-basic-offset: 4
2822  * tab-width: 4
2823  * End:
2824  */